diff --git a/DEPS b/DEPS
index 0db6c8c..782585f 100644
--- a/DEPS
+++ b/DEPS
@@ -44,7 +44,7 @@
   # 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': 'bfb1b022eeae4d9d3d1ada9b0c3defcd315d5bad',
+  'v8_revision': '747d3ecdac5621e53631a155be7075aefa5aac8c',
   # 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.
@@ -60,7 +60,7 @@
   # Three lines of non-changing comments so that
   # the commit queue can handle CLs rolling SwiftShader
   # and whatever else without interference from each other.
-  'swiftshader_revision': '4d3efedb10ce60bdb7847336eba0360fdc9af9d3',
+  'swiftshader_revision': '8aa07683f555dd02e2c7cae2d3e28c53385cc504',
   # Three lines of non-changing comments so that
   # the commit queue can handle CLs rolling PDFium
   # and whatever else without interference from each other.
diff --git a/ash/highlighter/highlighter_result_view.cc b/ash/highlighter/highlighter_result_view.cc
index 13992d5f..1b822261 100644
--- a/ash/highlighter/highlighter_result_view.cc
+++ b/ash/highlighter/highlighter_result_view.cc
@@ -38,12 +38,12 @@
 const SkColor kCornerCircleColorLB = SkColorSetRGB(0x34, 0xA8, 0x53);
 const SkColor kCornerCircleColorRB = SkColorSetRGB(0xFB, 0xBC, 0x05);
 
-constexpr int kResultFadeinDelayMs = 600;
+constexpr int kResultFadeinDelayMs = 200;
 constexpr int kResultFadeinDurationMs = 400;
 constexpr int kResultFadeoutDelayMs = 500;
 constexpr int kResultFadeoutDurationMs = 200;
 
-constexpr int kResultInPlaceFadeinDelayMs = 500;
+constexpr int kResultInPlaceFadeinDelayMs = 100;
 constexpr int kResultInPlaceFadeinDurationMs = 500;
 
 constexpr float kInitialScale = 1.2;
@@ -225,11 +225,11 @@
 
   layer->SetOpacity(0);
 
-  animation_timer_.reset(
-      new base::Timer(FROM_HERE, delay,
-                      base::Bind(&HighlighterResultView::FadeIn,
-                                 base::Unretained(this), duration),
-                      false));
+  animation_timer_ = base::MakeUnique<base::Timer>(
+      FROM_HERE, delay,
+      base::Bind(&HighlighterResultView::FadeIn, base::Unretained(this),
+                 duration),
+      false);
   animation_timer_->Reset();
 }
 
@@ -248,12 +248,11 @@
     layer->SetTransform(transform);
   }
 
-  animation_timer_.reset(new base::Timer(
+  animation_timer_ = base::MakeUnique<base::Timer>(
       FROM_HERE,
-      base::TimeDelta::FromMilliseconds(kResultFadeinDurationMs +
-                                        kResultFadeoutDelayMs),
+      duration + base::TimeDelta::FromMilliseconds(kResultFadeoutDelayMs),
       base::Bind(&HighlighterResultView::FadeOut, base::Unretained(this)),
-      false));
+      false);
   animation_timer_->Reset();
 }
 
diff --git a/ash/highlighter/highlighter_view.cc b/ash/highlighter/highlighter_view.cc
index 0eb294a..a591a1f 100644
--- a/ash/highlighter/highlighter_view.cc
+++ b/ash/highlighter/highlighter_view.cc
@@ -24,7 +24,7 @@
 
 constexpr float kStrokeScale = 1.2;
 
-constexpr int kStrokeFadeoutDelayMs = 500;
+constexpr int kStrokeFadeoutDelayMs = 100;
 constexpr int kStrokeFadeoutDurationMs = 500;
 constexpr int kStrokeScaleDurationMs = 300;
 
diff --git a/ash/shelf/voice_interaction_overlay.cc b/ash/shelf/voice_interaction_overlay.cc
index 3715dc9e..669f550 100644
--- a/ash/shelf/voice_interaction_overlay.cc
+++ b/ash/shelf/voice_interaction_overlay.cc
@@ -23,8 +23,6 @@
 #include "base/memory/ptr_util.h"
 #include "base/metrics/user_metrics.h"
 #include "base/metrics/user_metrics_action.h"
-#include "base/time/time.h"
-#include "base/timer/timer.h"
 #include "chromeos/chromeos_switches.h"
 #include "ui/accessibility/ax_node_data.h"
 #include "ui/app_list/presenter/app_list.h"
@@ -37,11 +35,11 @@
 #include "ui/compositor/paint_context.h"
 #include "ui/compositor/paint_recorder.h"
 #include "ui/compositor/scoped_layer_animation_settings.h"
-#include "ui/gfx/animation/linear_animation.h"
 #include "ui/gfx/canvas.h"
 #include "ui/gfx/image/canvas_image_source.h"
 #include "ui/gfx/image/image_skia.h"
 #include "ui/gfx/image/image_skia_operations.h"
+#include "ui/gfx/paint_vector_icon.h"
 #include "ui/gfx/scoped_canvas.h"
 #include "ui/gfx/skia_paint_util.h"
 #include "ui/views/animation/flood_fill_ink_drop_ripple.h"
@@ -99,121 +97,31 @@
 // were causing visual anomalies.
 constexpr float kMinimumCircleScale = 0.001f;
 
-// These are voice interaction logo specs.
-constexpr float kMoleculeOffsetXDip[] = {-10.f, 10.f, 10.f, 19.f};
-constexpr float kMoleculeOffsetYDip[] = {-8.f, -2.f, 13.f, -9.f};
-constexpr float kMoleculeRadiusDip[] = {12.f, 6.f, 7.f, 3.f};
-constexpr float kMoleculeAmplitude = 2.f;
-constexpr SkColor kMoleculeColors[] = {
-    static_cast<SkColor>(0xFF4184F3),  // Blue
-    static_cast<SkColor>(0xFFEA4335),  // Red
-    static_cast<SkColor>(0xFFFBBC05),  // Yellow
-    static_cast<SkColor>(0xFF34A853)   // Green
-};
-constexpr int kMoleculeAnimationDurationMs = 1200;
-constexpr int kMoleculeAnimationOffset = 50;
-constexpr int kMoleculeOrder[] = {0, 2, 3, 1};
-
-}  // namespace
-
-class VoiceInteractionIcon : public ui::Layer {
+class VoiceInteractionIcon : public ui::Layer, public ui::LayerDelegate {
  public:
-  VoiceInteractionIcon() : Layer(ui::LAYER_NOT_DRAWN) {
+  VoiceInteractionIcon() {
     set_name("VoiceInteractionOverlay:ICON_LAYER");
     SetBounds(gfx::Rect(0, 0, kIconInitSizeDip, kIconInitSizeDip));
     SetFillsBoundsOpaquely(false);
     SetMasksToBounds(false);
-
-    InitMoleculeShape();
+    set_delegate(this);
   }
 
-  void StartAnimation() {
-    animation_timer_.Start(FROM_HERE,
-                           base::TimeDelta::FromMilliseconds(
-                               base::TimeTicks::kMillisecondsPerSecond /
-                               gfx::LinearAnimation::kDefaultFrameRate),
-                           this, &VoiceInteractionIcon::AnimationProgressed);
-  }
-
-  void StopAnimation() { animation_timer_.Stop(); }
-
  private:
-  enum Dot {
-    BLUE_DOT = 0,
-    RED_DOT,
-    YELLOW_DOT,
-    GREEN_DOT,
-    // The total number of shapes, not an actual shape.
-    DOT_COUNT
-  };
-
-  std::string ToLayerName(Dot dot) {
-    switch (dot) {
-      case BLUE_DOT:
-        return "BLUE_DOT";
-      case RED_DOT:
-        return "RED_DOT";
-      case YELLOW_DOT:
-        return "YELLOW_DOT";
-      case GREEN_DOT:
-        return "GREEN_DOT";
-      case DOT_COUNT:
-        NOTREACHED() << "The DOT_COUNT value should never be used.";
-        return "DOT_COUNT";
-    }
-    return "UNKNOWN";
+  // ui::LayerDelegate:
+  void OnPaintLayer(const ui::PaintContext& context) override {
+    ui::PaintRecorder recorder(context, size());
+    gfx::PaintVectorIcon(recorder.canvas(), kShelfVoiceInteractionIcon,
+                         kIconInitSizeDip, 0);
   }
 
-  void AnimationProgressed() {
-    gfx::Transform transform;
+  void OnDelegatedFrameDamage(const gfx::Rect& damage_rect_in_dip) override {}
 
-    uint64_t now = base::TimeTicks::Now().since_origin().InMilliseconds();
-    for (int i = 0; i < DOT_COUNT; ++i) {
-      float normalizedTime =
-          ((now - kMoleculeAnimationOffset * kMoleculeOrder[i]) %
-           kMoleculeAnimationDurationMs) /
-          static_cast<float>(kMoleculeAnimationDurationMs);
-
-      transform.MakeIdentity();
-      transform.Translate(0,
-                          kMoleculeAmplitude * sin(normalizedTime * 2 * M_PI));
-
-      dot_layers_[i]->SetTransform(transform);
-    }
-  }
-
-  /**
-   * Convenience method to place dots to Molecule shape used by Molecule
-   * animations.
-   */
-  void InitMoleculeShape() {
-    for (int i = 0; i < DOT_COUNT; ++i) {
-      dot_layer_delegates_[i] = base::MakeUnique<views::CircleLayerDelegate>(
-          kMoleculeColors[i], kMoleculeRadiusDip[i]);
-      dot_layers_[i] = base::MakeUnique<ui::Layer>();
-
-      dot_layers_[i]->SetBounds(gfx::Rect(
-          kIconInitSizeDip / 2 + kMoleculeOffsetXDip[i] - kMoleculeRadiusDip[i],
-          kIconInitSizeDip / 2 + kMoleculeOffsetYDip[i] - kMoleculeRadiusDip[i],
-          kMoleculeRadiusDip[i] * 2, kMoleculeRadiusDip[i] * 2));
-      dot_layers_[i]->SetFillsBoundsOpaquely(false);
-      dot_layers_[i]->set_delegate(dot_layer_delegates_[i].get());
-      dot_layers_[i]->SetVisible(true);
-      dot_layers_[i]->SetOpacity(1.0);
-      dot_layers_[i]->SetMasksToBounds(false);
-      dot_layers_[i]->set_name("DOT:" + ToLayerName(static_cast<Dot>(i)));
-
-      Add(dot_layers_[i].get());
-    }
-  }
-
-  std::unique_ptr<ui::Layer> dot_layers_[DOT_COUNT];
-  std::unique_ptr<views::CircleLayerDelegate> dot_layer_delegates_[DOT_COUNT];
-
-  base::RepeatingTimer animation_timer_;
+  void OnDeviceScaleFactorChanged(float device_scale_factor) override {}
 
   DISALLOW_COPY_AND_ASSIGN(VoiceInteractionIcon);
 };
+}  // namespace
 
 class VoiceInteractionIconBackground : public ui::Layer,
                                        public ui::LayerDelegate {
@@ -756,7 +664,6 @@
     transform.Scale(scale_factor, scale_factor);
 
     icon_layer_->SetTransform(transform);
-    icon_layer_->StartAnimation();
   }
 
   // Setup background animation.
@@ -889,7 +796,6 @@
         ui::LayerAnimator::PreemptionStrategy::ENQUEUE_NEW_ANIMATION);
 
     icon_layer_->SetOpacity(0);
-    icon_layer_->StopAnimation();
   }
 
   // Setup background animation.
diff --git a/ash/shelf/voice_interaction_overlay.h b/ash/shelf/voice_interaction_overlay.h
index f126751c..5f96fc76 100644
--- a/ash/shelf/voice_interaction_overlay.h
+++ b/ash/shelf/voice_interaction_overlay.h
@@ -21,7 +21,6 @@
 
 class AppListButton;
 class VoiceInteractionIconBackground;
-class VoiceInteractionIcon;
 
 class ASH_EXPORT VoiceInteractionOverlay : public views::View {
  public:
@@ -39,7 +38,7 @@
       const ui::CallbackLayerAnimationObserver& observer);
 
   std::unique_ptr<ui::Layer> ripple_layer_;
-  std::unique_ptr<VoiceInteractionIcon> icon_layer_;
+  std::unique_ptr<ui::Layer> icon_layer_;
   std::unique_ptr<VoiceInteractionIconBackground> background_layer_;
 
   AppListButton* host_view_;
diff --git a/base/containers/flat_map.h b/base/containers/flat_map.h
index 2972deb..72348d51 100644
--- a/base/containers/flat_map.h
+++ b/base/containers/flat_map.h
@@ -100,6 +100,8 @@
 //   Mapped&              operator[](key_type&&);
 //   pair<iterator, bool> insert(const value_type&);
 //   pair<iterator, bool> insert(value_type&&);
+//   iterator             insert(const_iterator hint, const value_type&);
+//   iterator             insert(const_iterator hint, value_type&&);
 //   void                 insert(InputIterator first, InputIterator last,
 //                               FlatContainerDupes);
 //   pair<iterator, bool> emplace(Args&&...);
diff --git a/base/containers/flat_set.h b/base/containers/flat_set.h
index 7531942..b09b5c01 100644
--- a/base/containers/flat_set.h
+++ b/base/containers/flat_set.h
@@ -86,6 +86,8 @@
 //   pair<iterator, bool> insert(key_type&&);
 //   void                 insert(InputIterator first, InputIterator last,
 //                               FlatContainerDupes);
+//   iterator             insert(const_iterator hint, const key_type&);
+//   iterator             insert(const_iterator hint, key_type&&);
 //   pair<iterator, bool> emplace(Args&&...);
 //   iterator             emplace_hint(const_iterator, Args&&...);
 //
diff --git a/base/trace_event/trace_event_argument.cc b/base/trace_event/trace_event_argument.cc
index c27a2f9e..1a5678c9 100644
--- a/base/trace_event/trace_event_argument.cc
+++ b/base/trace_event/trace_event_argument.cc
@@ -409,7 +409,7 @@
         bool value;
         CHECK(it.ReadBool(&value));
         if (cur_dict) {
-          cur_dict->SetBooleanWithoutPathExpansion(ReadKeyName(it), value);
+          cur_dict->SetKey(ReadKeyName(it), Value(value));
         } else {
           cur_list->AppendBoolean(value);
         }
diff --git a/base/values.cc b/base/values.cc
index 5d9eaa29..d7116b2 100644
--- a/base/values.cc
+++ b/base/values.cc
@@ -301,6 +301,68 @@
   return SetKey(StringPiece(key), std::move(value));
 }
 
+Value* Value::FindPath(std::initializer_list<const char*> path) {
+  return const_cast<Value*>(const_cast<const Value*>(this)->FindPath(path));
+}
+
+const Value* Value::FindPath(std::initializer_list<const char*> path) const {
+  const Value* cur = this;
+  for (const char* component : path) {
+    if (!cur->is_dict())
+      return nullptr;
+
+    auto found = cur->FindKey(component);
+    if (found == cur->DictEnd())
+      return nullptr;
+    cur = &found->second;
+  }
+  return cur;
+}
+
+Value* Value::FindPathOfType(std::initializer_list<const char*> path,
+                             Type type) {
+  return const_cast<Value*>(
+      const_cast<const Value*>(this)->FindPathOfType(path, type));
+}
+
+const Value* Value::FindPathOfType(std::initializer_list<const char*> path,
+                                   Type type) const {
+  const Value* result = FindPath(path);
+  if (!result || !result->IsType(type))
+    return nullptr;
+  return result;
+}
+
+Value* Value::SetPath(std::initializer_list<const char*> path, Value value) {
+  DCHECK_NE(path.begin(), path.end());  // Can't be empty path.
+
+  // Walk/construct intermediate dictionaries. The last element requires
+  // special handling so skip it in this loop.
+  Value* cur = this;
+  const char* const* cur_path = path.begin();
+  for (; (cur_path + 1) < path.end(); ++cur_path) {
+    if (!cur->is_dict())
+      return nullptr;
+
+    // Use lower_bound to avoid doing the search twice for missing keys.
+    const char* path_component = *cur_path;
+    auto found = cur->dict_->lower_bound(path_component);
+    if (found == cur->dict_->end() || found->first != path_component) {
+      // No key found, insert one.
+      auto inserted = cur->dict_->emplace_hint(
+          found, path_component, MakeUnique<Value>(Type::DICTIONARY));
+      cur = inserted->second.get();
+    } else {
+      cur = found->second.get();
+    }
+  }
+
+  // "cur" will now contain the last dictionary to insert or replace into.
+  if (!cur->is_dict())
+    return nullptr;
+  return &cur->SetKey(*cur_path, std::move(value))->second;
+}
+
 Value::dict_iterator Value::DictEnd() {
   CHECK(is_dict());
   return dict_iterator(dict_->end());
@@ -741,11 +803,6 @@
   return ((*dict_)[key.as_string()] = std::move(in_value)).get();
 }
 
-Value* DictionaryValue::SetBooleanWithoutPathExpansion(StringPiece path,
-                                                       bool in_value) {
-  return SetWithoutPathExpansion(path, MakeUnique<Value>(in_value));
-}
-
 Value* DictionaryValue::SetIntegerWithoutPathExpansion(StringPiece path,
                                                        int in_value) {
   return SetWithoutPathExpansion(path, MakeUnique<Value>(in_value));
diff --git a/base/values.h b/base/values.h
index fbb0647..3cd31c67 100644
--- a/base/values.h
+++ b/base/values.h
@@ -171,6 +171,40 @@
   // This overload is necessary to avoid ambiguity for const char* arguments.
   dict_iterator SetKey(const char* key, Value value);
 
+  // Searches a hierarchy of dictionary values for a given value. If a path
+  // of dictionaries exist, returns the item at that path. If any of the path
+  // components do not exist or if any but the last path components are not
+  // dictionaries, returns nullptr.
+  //
+  // The type of the leaf Value is not checked.
+  //
+  // Implementation note: This can't return an iterator because the iterator
+  // will actually be into another Value, so it can't be compared to iterators
+  // from thise one (in particular, the DictEnd() iterator).
+  //
+  // Example:
+  //   auto found = FindPath({"foo", "bar"});
+  Value* FindPath(std::initializer_list<const char*> path);
+  const Value* FindPath(std::initializer_list<const char*> path) const;
+
+  // Like FindPath but will only return the value if the leaf Value type
+  // matches the given type. Will return nullptr otherwise.
+  Value* FindPathOfType(std::initializer_list<const char*> path, Type type);
+  const Value* FindPathOfType(std::initializer_list<const char*> path,
+                              Type type) const;
+
+  // Sets the given path, expanding and creating dictionary keys as necessary.
+  //
+  // The current value must be a dictionary. If path components do not exist,
+  // they will be created. If any but the last components matches a value that
+  // is not a dictionary, the function will fail (it will not overwrite the
+  // value) and return nullptr. The last path component will be unconditionally
+  // overwritten if it exists, and created if it doesn't.
+  //
+  // Example:
+  //   value.SetPath({"foo", "bar"}, std::move(myvalue));
+  Value* SetPath(std::initializer_list<const char*> path, Value value);
+
   // |DictEnd| returns the end iterator of the underlying dictionary. It is
   // intended to be used with |FindKey| in order to determine whether a given
   // key is present in the dictionary.
@@ -306,19 +340,25 @@
 
   // Like Set(), but without special treatment of '.'.  This allows e.g. URLs to
   // be used as paths.
+  // DEPRECATED, use Value::SetKey(path, value) instead.
   Value* SetWithoutPathExpansion(StringPiece key,
                                  std::unique_ptr<Value> in_value);
 
   // Convenience forms of SetWithoutPathExpansion().
-  Value* SetBooleanWithoutPathExpansion(StringPiece path, bool in_value);
+  // DEPRECATED, use Value::SetKey(path, Value(int)) instead.
   Value* SetIntegerWithoutPathExpansion(StringPiece path, int in_value);
+  // DEPRECATED, use Value::SetKey(path, Value(double)) instead.
   Value* SetDoubleWithoutPathExpansion(StringPiece path, double in_value);
+  // DEPRECATED, use Value::SetKey(path, Value(string)) instead.
   Value* SetStringWithoutPathExpansion(StringPiece path, StringPiece in_value);
+  // DEPRECATED, use Value::SetKey(path, Value(string16)) instead.
   Value* SetStringWithoutPathExpansion(StringPiece path,
                                        const string16& in_value);
+  // DEPRECATED, use Value::SetKey(path, Value(Type::DICTIONARY)) instead.
   DictionaryValue* SetDictionaryWithoutPathExpansion(
       StringPiece path,
       std::unique_ptr<DictionaryValue> in_value);
+  // DEPRECATED, use Value::SetKey(path, Value(Type::LIST)) instead.
   ListValue* SetListWithoutPathExpansion(StringPiece path,
                                          std::unique_ptr<ListValue> in_value);
 
@@ -355,22 +395,33 @@
 
   // Like Get(), but without special treatment of '.'.  This allows e.g. URLs to
   // be used as paths.
+  // DEPRECATED, use Value::FindKey(key) instead.
   bool GetWithoutPathExpansion(StringPiece key, const Value** out_value) const;
+  // DEPRECATED, use Value::FindKey(key) instead.
   bool GetWithoutPathExpansion(StringPiece key, Value** out_value);
+  // DEPRECATED, use Value::FindKey(key) and Value::GetBool() instead.
   bool GetBooleanWithoutPathExpansion(StringPiece key, bool* out_value) const;
+  // DEPRECATED, use Value::FindKey(key) and Value::GetInt() instead.
   bool GetIntegerWithoutPathExpansion(StringPiece key, int* out_value) const;
+  // DEPRECATED, use Value::FindKey(key) and Value::GetDouble() instead.
   bool GetDoubleWithoutPathExpansion(StringPiece key, double* out_value) const;
+  // DEPRECATED, use Value::FindKey(key) and Value::GetString() instead.
   bool GetStringWithoutPathExpansion(StringPiece key,
                                      std::string* out_value) const;
+  // DEPRECATED, use Value::FindKey(key) and Value::GetString() instead.
   bool GetStringWithoutPathExpansion(StringPiece key,
                                      string16* out_value) const;
+  // DEPRECATED, use Value::FindKey(key) and Value's Dictionary API instead.
   bool GetDictionaryWithoutPathExpansion(
       StringPiece key,
       const DictionaryValue** out_value) const;
+  // DEPRECATED, use Value::FindKey(key) and Value's Dictionary API instead.
   bool GetDictionaryWithoutPathExpansion(StringPiece key,
                                          DictionaryValue** out_value);
+  // DEPRECATED, use Value::FindKey(key) and Value::GetList() instead.
   bool GetListWithoutPathExpansion(StringPiece key,
                                    const ListValue** out_value) const;
+  // DEPRECATED, use Value::FindKey(key) and Value::GetList() instead.
   bool GetListWithoutPathExpansion(StringPiece key, ListValue** out_value);
 
   // Removes the Value with the specified path from this dictionary (or one
diff --git a/base/values_unittest.cc b/base/values_unittest.cc
index 00032a5..c8f0fec5 100644
--- a/base/values_unittest.cc
+++ b/base/values_unittest.cc
@@ -597,6 +597,64 @@
   EXPECT_EQ(Value(std::move(storage)), dict);
 }
 
+TEST(ValuesTest, FindPath) {
+  // Construct a dictionary path {root}.foo.bar = 123
+  Value foo(Value::Type::DICTIONARY);
+  foo.SetKey("bar", Value(123));
+
+  Value root(Value::Type::DICTIONARY);
+  root.SetKey("foo", std::move(foo));
+
+  // No key (stupid but well-defined and takes work to prevent).
+  Value* found = root.FindPath({});
+  EXPECT_EQ(&root, found);
+
+  // Single not found key.
+  found = root.FindPath({"notfound"});
+  EXPECT_FALSE(found);
+
+  // Single found key.
+  found = root.FindPath({"foo"});
+  ASSERT_TRUE(found);
+  EXPECT_TRUE(found->is_dict());
+
+  // Double key, second not found.
+  found = root.FindPath({"foo", "notfound"});
+  EXPECT_FALSE(found);
+
+  // Double key, found.
+  found = root.FindPath({"foo", "bar"});
+  EXPECT_TRUE(found);
+  EXPECT_TRUE(found->is_int());
+  EXPECT_EQ(123, found->GetInt());
+}
+
+TEST(ValuesTest, SetPath) {
+  Value root(Value::Type::DICTIONARY);
+
+  Value* inserted = root.SetPath({"one"}, Value(123));
+  Value* found = root.FindPathOfType({"one"}, Value::Type::INTEGER);
+  ASSERT_TRUE(found);
+  EXPECT_EQ(inserted, found);
+  EXPECT_EQ(123, found->GetInt());
+
+  inserted = root.SetPath({"foo", "bar"}, Value(123));
+  found = root.FindPathOfType({"foo", "bar"}, Value::Type::INTEGER);
+  ASSERT_TRUE(found);
+  EXPECT_EQ(inserted, found);
+  EXPECT_EQ(123, found->GetInt());
+
+  // Overwrite with a different value.
+  root.SetPath({"foo", "bar"}, Value("hello"));
+  found = root.FindPathOfType({"foo", "bar"}, Value::Type::STRING);
+  ASSERT_TRUE(found);
+  EXPECT_EQ("hello", found->GetString());
+
+  // Can't change existing non-dictionary keys to dictionaries.
+  found = root.SetPath({"foo", "bar", "baz"}, Value(123));
+  EXPECT_FALSE(found);
+}
+
 TEST(ValuesTest, DictEnd) {
   Value dict(Value::Type::DICTIONARY);
   EXPECT_EQ(dict.DictItems().end(), dict.DictEnd());
@@ -826,13 +884,6 @@
 
   {
     DictionaryValue dict;
-    Value* bool_ptr = dict.SetBooleanWithoutPathExpansion("foo.bar", false);
-    EXPECT_EQ(Value::Type::BOOLEAN, bool_ptr->type());
-    EXPECT_FALSE(bool_ptr->GetBool());
-  }
-
-  {
-    DictionaryValue dict;
     Value* int_ptr = dict.SetInteger("foo.bar", 42);
     EXPECT_EQ(Value::Type::INTEGER, int_ptr->type());
     EXPECT_EQ(42, int_ptr->GetInt());
diff --git a/build/linux/sysroot_scripts/packagelist.stretch.amd64 b/build/linux/sysroot_scripts/packagelist.stretch.amd64
new file mode 100644
index 0000000..3bbb3da7
--- /dev/null
+++ b/build/linux/sysroot_scripts/packagelist.stretch.amd64
@@ -0,0 +1,223 @@
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2_1.1.3-5_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2-dev_1.1.3-5_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-0_2.22.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-dev_2.22.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-0_2.22.0-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-dev_2.22.0-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-0_2.22.0-6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-dev_2.22.0-6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/attr/libattr1_2.4.47-2+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/audit/libaudit1_2.6.7-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-client3_0.6.32-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-common3_0.6.32-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth3_5.43-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth-dev_5.43-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi0.6_5.4-7_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi-dev_5.4-7_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2_1.14.8-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2-dev_1.14.8-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-gobject2_1.14.8-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-script-interpreter2_1.14.8-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2_2.2.1-8_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2-dev_2.2.1-8_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2_2.2.1-8_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2-dev_2.2.1-8_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus-glib/libdbus-glib-1-2_0.108-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-3_1.10.18-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-dev_1.10.18-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/comerr-dev_2.1-1.43.4-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/libcomerr2_1.43.4-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf1_0.168-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf-dev_0.168-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1_2.11.0-6.7+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1-dev_2.11.0-6.7+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6_2.6.3-3.2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6-dev_2.6.3-3.2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libasan3_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libatomic1_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libcilkrts5_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc1_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc-6-dev_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgomp1_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libitm1_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/liblsan0_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libmpx2_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libquadmath0_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++6_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++-6-dev_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libtsan0_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libubsan0_6.3.0-18_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-4_3.2.6-4+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf-2-4_3.2.6-4+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-dev_3.2.6-4+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-0_2.36.5-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-dev_2.36.5-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-0_2.50.3-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-dev_2.50.3-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-3_1.3.10-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-dev_1.3.10-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-0_2.24.31-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-dev_2.24.31-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-0_3.22.11-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-dev_3.22.11-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz0b_1.4.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-dev_1.4.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-gobject0_1.4.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-icu0_1.4.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/keyutils/libkeyutils1_1.5.9-9_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/krb5-multidev_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssapi-krb5-2_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssrpc4_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libk5crypto3_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5clnt-mit11_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5srv-mit11_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkdb5-8_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-3_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-dev_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5support0_1.15-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap2_2.25-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap-dev_2.25-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm2_2.4.74-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-amdgpu1_2.4.74-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-dev_2.4.74-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-intel1_2.4.74-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-nouveau2_2.4.74-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-radeon1_2.4.74-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy0_1.3.1-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy-dev_1.3.1-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi6_3.2.1-6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi-dev_3.2.1-6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring0_3.12.0-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring-dev_3.12.0-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error0_1.26-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error-dev_1.26-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp1_1.7.4-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp-dev_1.7.4-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libn/libnss-db/libnss-db_2.2.3pre1-6+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libp11/libp11-2_0.4.3-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng16-16_1.6.28-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng-dev_1.6.28-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpthread-stubs/libpthread-stubs0-dev_0.3-4_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libs/libselinux/libselinux1_2.6-3+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libt/libtasn1-6/libtasn1-6_4.10-1.1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-6_1.6.4-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-dev_1.6.4-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb1_1.6.4-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb-dev_1.6.4-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau6_1.0.8-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau-dev_1.0.8-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1-dev_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri2-0_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri3-0_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-glx0_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-present0_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0-dev_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0-dev_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-sync1_1.12-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite1_0.4.4-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite-dev_0.4.4-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor1_1.1.14-1+b4_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor-dev_1.1.14-1+b4_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage1_1.1.4-2+b3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage-dev_1.1.4-2+b3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp6_1.1.2-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp-dev_1.1.2-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext6_1.3.3-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext-dev_1.3.3-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes3_5.0.3-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes-dev_5.0.3-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi6_1.7.9-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi-dev_1.7.9-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama1_1.1.3-1+b3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama-dev_1.1.3-1+b3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon0_0.7.1-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon-dev_0.7.1-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr2_1.5.1-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr-dev_1.5.1-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender1_0.9.10-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender-dev_0.9.10-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxshmfence/libxshmfence1_1.2-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss1_1.2.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss-dev_1.2.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt6_1.1.5-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt-dev_1.1.5-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst6_1.2.3-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst-dev_1.2.3-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxxf86vm/libxxf86vm1_1.1.4-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa-dev_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm1_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm-dev_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-dev_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-glx_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libglapi-mesa_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libwayland-egl1-mesa_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/mesa-common-dev_13.0.6-1+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4_4.12-6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4-dev_4.12-6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3_3.26.2-1.1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3-dev_3.26.2-1.1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl1.0/libssl1.0.2_1.0.2l-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl1.1_1.1.0f-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl-dev_1.1.0f-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/o/orbit2/liborbit2_2.14.19-2+b1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/p11-kit/libp11-kit0_0.23.3-2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g_1.1.8-3.6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g-dev_1.1.8-3.6_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango-1.0-0_1.40.5-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango1.0-dev_1.40.5-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangocairo-1.0-0_1.40.5-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoft2-1.0-0_1.40.5-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoxft-1.0-0_1.40.5-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pangox-compat/libpangox-1.0-0_0.0.2-5+b2_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci3_3.5.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci-dev_3.5.2-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre16-3_8.39-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre32-3_8.39-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3_8.39-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3-dev_8.39-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcrecpp0v5_8.39-3_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-0_0.34.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-dev_0.34.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse0_10.0-1+deb9u1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-dev_10.0-1+deb9u1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-mainloop-glib0_10.0-1+deb9u1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd2_0.8.6-4_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd-dev_0.8.6-4_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/speech-dispatcher_0.8.6-4_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev1_232-25+deb9u1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev-dev_232-25+deb9u1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-client0_1.12.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-cursor0_1.12.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-dev_1.12.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-server0_1.12.0-1_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland-protocols/wayland-protocols_1.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-composite/x11proto-composite-dev_0.4.2-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-core/x11proto-core-dev_7.0.31-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-damage/x11proto-damage-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-fixes/x11proto-fixes-dev_5.0-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-input/x11proto-input-dev_2.3.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-kb/x11proto-kb-dev_1.0.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-randr/x11proto-randr-dev_1.5.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-record/x11proto-record-dev_1.14.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-render/x11proto-render-dev_0.11.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-scrnsaver/x11proto-scrnsaver-dev_1.2.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xext/x11proto-xext-dev_7.3.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xinerama/x11proto-xinerama-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g_1.2.8.dfsg-5_amd64.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g-dev_1.2.8.dfsg-5_amd64.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1_2.2.0-2+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1-dev_2.2.0-2+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6_2.24-11+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6-dev_2.24-11+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls28-dev_3.5.8-5+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls30_3.5.8-5+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-dane0_3.5.8-5+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-openssl27_3.5.8-5+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutlsxx28_3.5.8-5+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20_1.7.6-2+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20-dev_1.7.6-2+deb9u1_amd64.deb
+http://security.debian.org/pool/updates/main/l/linux/linux-libc-dev_4.9.30-2+deb9u2_amd64.deb
diff --git a/build/linux/sysroot_scripts/packagelist.stretch.arm b/build/linux/sysroot_scripts/packagelist.stretch.arm
new file mode 100644
index 0000000..b57c37e
--- /dev/null
+++ b/build/linux/sysroot_scripts/packagelist.stretch.arm
@@ -0,0 +1,220 @@
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2_1.1.3-5_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2-dev_1.1.3-5_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-0_2.22.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-dev_2.22.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-0_2.22.0-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-dev_2.22.0-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-0_2.22.0-6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-dev_2.22.0-6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/attr/libattr1_2.4.47-2+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/audit/libaudit1_2.6.7-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-client3_0.6.32-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-common3_0.6.32-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth3_5.43-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth-dev_5.43-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi0.6_5.4-7_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi-dev_5.4-7_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2_1.14.8-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2-dev_1.14.8-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-gobject2_1.14.8-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-script-interpreter2_1.14.8-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2_2.2.1-8_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2-dev_2.2.1-8_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2_2.2.1-8_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2-dev_2.2.1-8_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus-glib/libdbus-glib-1-2_0.108-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-3_1.10.18-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-dev_1.10.18-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/comerr-dev_2.1-1.43.4-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/libcomerr2_1.43.4-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf1_0.168-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf-dev_0.168-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1_2.11.0-6.7+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1-dev_2.11.0-6.7+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6_2.6.3-3.2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6-dev_2.6.3-3.2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libasan3_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libatomic1_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc1_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc-6-dev_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgomp1_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++6_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++-6-dev_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libubsan0_6.3.0-18_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-4_3.2.6-4+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf-2-4_3.2.6-4+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-dev_3.2.6-4+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-0_2.36.5-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-dev_2.36.5-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-0_2.50.3-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-dev_2.50.3-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-3_1.3.10-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-dev_1.3.10-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-0_2.24.31-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-dev_2.24.31-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-0_3.22.11-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-dev_3.22.11-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz0b_1.4.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-dev_1.4.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-gobject0_1.4.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-icu0_1.4.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/keyutils/libkeyutils1_1.5.9-9_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/krb5-multidev_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssapi-krb5-2_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssrpc4_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libk5crypto3_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5clnt-mit11_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5srv-mit11_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkdb5-8_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-3_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-dev_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5support0_1.15-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap2_2.25-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap-dev_2.25-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm2_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-amdgpu1_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-dev_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-exynos1_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-freedreno1_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-nouveau2_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-omap1_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-radeon1_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-tegra0_2.4.74-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy0_1.3.1-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy-dev_1.3.1-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi6_3.2.1-6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi-dev_3.2.1-6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring0_3.12.0-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring-dev_3.12.0-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error0_1.26-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error-dev_1.26-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp1_1.7.4-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp-dev_1.7.4-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libn/libnss-db/libnss-db_2.2.3pre1-6+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libp11/libp11-2_0.4.3-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng16-16_1.6.28-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng-dev_1.6.28-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpthread-stubs/libpthread-stubs0-dev_0.3-4_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libs/libselinux/libselinux1_2.6-3+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libt/libtasn1-6/libtasn1-6_4.10-1.1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-6_1.6.4-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-dev_1.6.4-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb1_1.6.4-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb-dev_1.6.4-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau6_1.0.8-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau-dev_1.0.8-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1-dev_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri2-0_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri3-0_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-glx0_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-present0_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0-dev_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0-dev_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-sync1_1.12-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite1_0.4.4-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite-dev_0.4.4-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor1_1.1.14-1+b4_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor-dev_1.1.14-1+b4_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage1_1.1.4-2+b3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage-dev_1.1.4-2+b3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp6_1.1.2-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp-dev_1.1.2-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext6_1.3.3-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext-dev_1.3.3-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes3_5.0.3-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes-dev_5.0.3-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi6_1.7.9-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi-dev_1.7.9-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama1_1.1.3-1+b3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama-dev_1.1.3-1+b3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon0_0.7.1-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon-dev_0.7.1-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr2_1.5.1-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr-dev_1.5.1-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender1_0.9.10-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender-dev_0.9.10-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxshmfence/libxshmfence1_1.2-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss1_1.2.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss-dev_1.2.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt6_1.1.5-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt-dev_1.1.5-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst6_1.2.3-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst-dev_1.2.3-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxxf86vm/libxxf86vm1_1.1.4-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa-dev_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm1_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm-dev_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-dev_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-glx_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libglapi-mesa_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libwayland-egl1-mesa_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/mesa-common-dev_13.0.6-1+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4_4.12-6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4-dev_4.12-6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3_3.26.2-1.1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3-dev_3.26.2-1.1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl1.0/libssl1.0.2_1.0.2l-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl1.1_1.1.0f-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl-dev_1.1.0f-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/o/orbit2/liborbit2_2.14.19-2+b1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/p11-kit/libp11-kit0_0.23.3-2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g_1.1.8-3.6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g-dev_1.1.8-3.6_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango-1.0-0_1.40.5-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango1.0-dev_1.40.5-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangocairo-1.0-0_1.40.5-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoft2-1.0-0_1.40.5-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoxft-1.0-0_1.40.5-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pangox-compat/libpangox-1.0-0_0.0.2-5+b2_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci3_3.5.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci-dev_3.5.2-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre16-3_8.39-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre32-3_8.39-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3_8.39-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3-dev_8.39-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcrecpp0v5_8.39-3_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-0_0.34.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-dev_0.34.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse0_10.0-1+deb9u1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-dev_10.0-1+deb9u1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-mainloop-glib0_10.0-1+deb9u1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd2_0.8.6-4_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd-dev_0.8.6-4_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/speech-dispatcher_0.8.6-4_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev1_232-25+deb9u1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev-dev_232-25+deb9u1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-client0_1.12.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-cursor0_1.12.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-dev_1.12.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-server0_1.12.0-1_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland-protocols/wayland-protocols_1.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-composite/x11proto-composite-dev_0.4.2-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-core/x11proto-core-dev_7.0.31-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-damage/x11proto-damage-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-fixes/x11proto-fixes-dev_5.0-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-input/x11proto-input-dev_2.3.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-kb/x11proto-kb-dev_1.0.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-randr/x11proto-randr-dev_1.5.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-record/x11proto-record-dev_1.14.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-render/x11proto-render-dev_0.11.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-scrnsaver/x11proto-scrnsaver-dev_1.2.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xext/x11proto-xext-dev_7.3.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xinerama/x11proto-xinerama-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g_1.2.8.dfsg-5_armhf.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g-dev_1.2.8.dfsg-5_armhf.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1_2.2.0-2+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1-dev_2.2.0-2+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6_2.24-11+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6-dev_2.24-11+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls28-dev_3.5.8-5+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls30_3.5.8-5+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-dane0_3.5.8-5+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-openssl27_3.5.8-5+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutlsxx28_3.5.8-5+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20_1.7.6-2+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20-dev_1.7.6-2+deb9u1_armhf.deb
+http://security.debian.org/pool/updates/main/l/linux/linux-libc-dev_4.9.30-2+deb9u2_armhf.deb
diff --git a/build/linux/sysroot_scripts/packagelist.stretch.arm64 b/build/linux/sysroot_scripts/packagelist.stretch.arm64
new file mode 100644
index 0000000..2e79d83
--- /dev/null
+++ b/build/linux/sysroot_scripts/packagelist.stretch.arm64
@@ -0,0 +1,222 @@
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2_1.1.3-5_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2-dev_1.1.3-5_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-0_2.22.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-dev_2.22.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-0_2.22.0-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-dev_2.22.0-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-0_2.22.0-6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-dev_2.22.0-6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/attr/libattr1_2.4.47-2+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/audit/libaudit1_2.6.7-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-client3_0.6.32-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-common3_0.6.32-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth3_5.43-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth-dev_5.43-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi0.6_5.4-7_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi-dev_5.4-7_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2_1.14.8-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2-dev_1.14.8-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-gobject2_1.14.8-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-script-interpreter2_1.14.8-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2_2.2.1-8_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2-dev_2.2.1-8_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2_2.2.1-8_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2-dev_2.2.1-8_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus-glib/libdbus-glib-1-2_0.108-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-3_1.10.18-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-dev_1.10.18-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/comerr-dev_2.1-1.43.4-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/libcomerr2_1.43.4-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf1_0.168-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf-dev_0.168-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1_2.11.0-6.7+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1-dev_2.11.0-6.7+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6_2.6.3-3.2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6-dev_2.6.3-3.2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libasan3_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libatomic1_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc1_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc-6-dev_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgomp1_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libitm1_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++6_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++-6-dev_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libubsan0_6.3.0-18_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-4_3.2.6-4+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf-2-4_3.2.6-4+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-dev_3.2.6-4+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-0_2.36.5-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-dev_2.36.5-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-0_2.50.3-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-dev_2.50.3-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gmp/libgmp10_6.1.2+dfsg-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-3_1.3.10-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-dev_1.3.10-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-0_2.24.31-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-dev_2.24.31-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-0_3.22.11-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-dev_3.22.11-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz0b_1.4.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-dev_1.4.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-gobject0_1.4.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-icu0_1.4.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/keyutils/libkeyutils1_1.5.9-9_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/krb5-multidev_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssapi-krb5-2_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssrpc4_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libk5crypto3_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5clnt-mit11_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5srv-mit11_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkdb5-8_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-3_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-dev_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5support0_1.15-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap2_2.25-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap-dev_2.25-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdatrie/libdatrie1_0.2.10-4+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm2_2.4.74-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-amdgpu1_2.4.74-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-dev_2.4.74-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-freedreno1_2.4.74-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-nouveau2_2.4.74-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-radeon1_2.4.74-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-tegra0_2.4.74-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy0_1.3.1-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy-dev_1.3.1-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi6_3.2.1-6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi-dev_3.2.1-6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring0_3.12.0-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring-dev_3.12.0-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error0_1.26-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error-dev_1.26-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp1_1.7.4-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp-dev_1.7.4-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libn/libnss-db/libnss-db_2.2.3pre1-6+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libp11/libp11-2_0.4.3-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng16-16_1.6.28-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng-dev_1.6.28-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpthread-stubs/libpthread-stubs0-dev_0.3-4_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libs/libselinux/libselinux1_2.6-3+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libt/libtasn1-6/libtasn1-6_4.10-1.1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libt/libthai/libthai0_0.1.26-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-6_1.6.4-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-dev_1.6.4-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb1_1.6.4-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb-dev_1.6.4-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau6_1.0.8-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau-dev_1.0.8-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1-dev_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri2-0_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri3-0_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-glx0_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-present0_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0-dev_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0-dev_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-sync1_1.12-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite1_0.4.4-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite-dev_0.4.4-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor1_1.1.14-1+b4_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor-dev_1.1.14-1+b4_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage1_1.1.4-2+b3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage-dev_1.1.4-2+b3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp6_1.1.2-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp-dev_1.1.2-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext6_1.3.3-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext-dev_1.3.3-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes3_5.0.3-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes-dev_5.0.3-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi6_1.7.9-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi-dev_1.7.9-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama1_1.1.3-1+b3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama-dev_1.1.3-1+b3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon0_0.7.1-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon-dev_0.7.1-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr2_1.5.1-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr-dev_1.5.1-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender1_0.9.10-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender-dev_0.9.10-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxshmfence/libxshmfence1_1.2-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss1_1.2.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss-dev_1.2.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt6_1.1.5-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt-dev_1.1.5-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst6_1.2.3-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst-dev_1.2.3-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxxf86vm/libxxf86vm1_1.1.4-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa-dev_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm1_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm-dev_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-dev_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-glx_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libglapi-mesa_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libwayland-egl1-mesa_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/mesa-common-dev_13.0.6-1+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4_4.12-6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4-dev_4.12-6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3_3.26.2-1.1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3-dev_3.26.2-1.1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl1.0/libssl1.0.2_1.0.2l-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl1.1_1.1.0f-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl-dev_1.1.0f-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/o/orbit2/liborbit2_2.14.19-2+b1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/p11-kit/libp11-kit0_0.23.3-2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g_1.1.8-3.6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g-dev_1.1.8-3.6_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango-1.0-0_1.40.5-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango1.0-dev_1.40.5-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangocairo-1.0-0_1.40.5-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoft2-1.0-0_1.40.5-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoxft-1.0-0_1.40.5-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pangox-compat/libpangox-1.0-0_0.0.2-5+b2_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci3_3.5.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci-dev_3.5.2-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre16-3_8.39-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre32-3_8.39-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3_8.39-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3-dev_8.39-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcrecpp0v5_8.39-3_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-0_0.34.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-dev_0.34.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse0_10.0-1+deb9u1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-dev_10.0-1+deb9u1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-mainloop-glib0_10.0-1+deb9u1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd2_0.8.6-4_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd-dev_0.8.6-4_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/speech-dispatcher_0.8.6-4_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev1_232-25+deb9u1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev-dev_232-25+deb9u1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-client0_1.12.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-cursor0_1.12.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-dev_1.12.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-server0_1.12.0-1_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland-protocols/wayland-protocols_1.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-composite/x11proto-composite-dev_0.4.2-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-core/x11proto-core-dev_7.0.31-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-damage/x11proto-damage-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-fixes/x11proto-fixes-dev_5.0-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-input/x11proto-input-dev_2.3.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-kb/x11proto-kb-dev_1.0.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-randr/x11proto-randr-dev_1.5.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-record/x11proto-record-dev_1.14.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-render/x11proto-render-dev_0.11.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-scrnsaver/x11proto-scrnsaver-dev_1.2.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xext/x11proto-xext-dev_7.3.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xinerama/x11proto-xinerama-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g_1.2.8.dfsg-5_arm64.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g-dev_1.2.8.dfsg-5_arm64.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1_2.2.0-2+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1-dev_2.2.0-2+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6_2.24-11+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6-dev_2.24-11+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls28-dev_3.5.8-5+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls30_3.5.8-5+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-dane0_3.5.8-5+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-openssl27_3.5.8-5+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutlsxx28_3.5.8-5+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20_1.7.6-2+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20-dev_1.7.6-2+deb9u1_arm64.deb
+http://security.debian.org/pool/updates/main/l/linux/linux-libc-dev_4.9.30-2+deb9u2_arm64.deb
diff --git a/build/linux/sysroot_scripts/packagelist.stretch.i386 b/build/linux/sysroot_scripts/packagelist.stretch.i386
new file mode 100644
index 0000000..496f4c4c
--- /dev/null
+++ b/build/linux/sysroot_scripts/packagelist.stretch.i386
@@ -0,0 +1,221 @@
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2_1.1.3-5_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2-dev_1.1.3-5_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-0_2.22.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-dev_2.22.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-0_2.22.0-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-dev_2.22.0-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-0_2.22.0-6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-dev_2.22.0-6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/attr/libattr1_2.4.47-2+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/audit/libaudit1_2.6.7-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-client3_0.6.32-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-common3_0.6.32-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth3_5.43-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth-dev_5.43-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi0.6_5.4-7_i386.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi-dev_5.4-7_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2_1.14.8-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2-dev_1.14.8-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-gobject2_1.14.8-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-script-interpreter2_1.14.8-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2_2.2.1-8_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2-dev_2.2.1-8_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2_2.2.1-8_i386.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2-dev_2.2.1-8_i386.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus-glib/libdbus-glib-1-2_0.108-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-3_1.10.18-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-dev_1.10.18-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/comerr-dev_2.1-1.43.4-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/libcomerr2_1.43.4-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf1_0.168-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf-dev_0.168-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1_2.11.0-6.7+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1-dev_2.11.0-6.7+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6_2.6.3-3.2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6-dev_2.6.3-3.2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libasan3_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libatomic1_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libcilkrts5_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc1_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc-6-dev_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgomp1_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libitm1_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libmpx2_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libquadmath0_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++6_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++-6-dev_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libubsan0_6.3.0-18_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf-2-4_3.2.6-4+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-4_3.2.6-4+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-dev_3.2.6-4+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-0_2.36.5-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-dev_2.36.5-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-0_2.50.3-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-dev_2.50.3-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-3_1.3.10-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-dev_1.3.10-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-0_2.24.31-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-dev_2.24.31-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-0_3.22.11-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-dev_3.22.11-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz0b_1.4.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-dev_1.4.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-gobject0_1.4.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-icu0_1.4.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/keyutils/libkeyutils1_1.5.9-9_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/krb5-multidev_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssapi-krb5-2_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssrpc4_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libk5crypto3_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5clnt-mit11_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5srv-mit11_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkdb5-8_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-3_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-dev_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5support0_1.15-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap2_2.25-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap-dev_2.25-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm2_2.4.74-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-amdgpu1_2.4.74-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-dev_2.4.74-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-intel1_2.4.74-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-nouveau2_2.4.74-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-radeon1_2.4.74-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy0_1.3.1-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy-dev_1.3.1-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi6_3.2.1-6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi-dev_3.2.1-6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring0_3.12.0-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring-dev_3.12.0-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error0_1.26-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error-dev_1.26-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp1_1.7.4-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp-dev_1.7.4-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libn/libnss-db/libnss-db_2.2.3pre1-6+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libp11/libp11-2_0.4.3-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng16-16_1.6.28-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng-dev_1.6.28-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpthread-stubs/libpthread-stubs0-dev_0.3-4_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libs/libselinux/libselinux1_2.6-3+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libt/libtasn1-6/libtasn1-6_4.10-1.1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-6_1.6.4-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-dev_1.6.4-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb1_1.6.4-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb-dev_1.6.4-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau6_1.0.8-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau-dev_1.0.8-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1-dev_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri2-0_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri3-0_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-glx0_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-present0_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0-dev_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0-dev_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-sync1_1.12-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite1_0.4.4-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite-dev_0.4.4-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor1_1.1.14-1+b4_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor-dev_1.1.14-1+b4_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage1_1.1.4-2+b3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage-dev_1.1.4-2+b3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp6_1.1.2-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp-dev_1.1.2-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext6_1.3.3-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext-dev_1.3.3-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes3_5.0.3-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes-dev_5.0.3-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi6_1.7.9-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi-dev_1.7.9-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama1_1.1.3-1+b3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama-dev_1.1.3-1+b3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon0_0.7.1-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon-dev_0.7.1-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr2_1.5.1-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr-dev_1.5.1-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender1_0.9.10-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender-dev_0.9.10-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxshmfence/libxshmfence1_1.2-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss1_1.2.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss-dev_1.2.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt6_1.1.5-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt-dev_1.1.5-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst6_1.2.3-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst-dev_1.2.3-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxxf86vm/libxxf86vm1_1.1.4-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa-dev_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm1_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm-dev_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-dev_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-glx_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libglapi-mesa_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libwayland-egl1-mesa_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/mesa-common-dev_13.0.6-1+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4_4.12-6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4-dev_4.12-6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3_3.26.2-1.1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3-dev_3.26.2-1.1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl1.0/libssl1.0.2_1.0.2l-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl1.1_1.1.0f-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl-dev_1.1.0f-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/o/orbit2/liborbit2_2.14.19-2+b1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/p11-kit/libp11-kit0_0.23.3-2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g_1.1.8-3.6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g-dev_1.1.8-3.6_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango-1.0-0_1.40.5-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango1.0-dev_1.40.5-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangocairo-1.0-0_1.40.5-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoft2-1.0-0_1.40.5-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoxft-1.0-0_1.40.5-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pangox-compat/libpangox-1.0-0_0.0.2-5+b2_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci3_3.5.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci-dev_3.5.2-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre16-3_8.39-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre32-3_8.39-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3_8.39-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3-dev_8.39-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcrecpp0v5_8.39-3_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-0_0.34.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-dev_0.34.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse0_10.0-1+deb9u1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-dev_10.0-1+deb9u1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-mainloop-glib0_10.0-1+deb9u1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd2_0.8.6-4_i386.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd-dev_0.8.6-4_i386.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/speech-dispatcher_0.8.6-4_i386.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev1_232-25+deb9u1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev-dev_232-25+deb9u1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-client0_1.12.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-cursor0_1.12.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-dev_1.12.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-server0_1.12.0-1_i386.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland-protocols/wayland-protocols_1.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-composite/x11proto-composite-dev_0.4.2-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-core/x11proto-core-dev_7.0.31-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-damage/x11proto-damage-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-fixes/x11proto-fixes-dev_5.0-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-input/x11proto-input-dev_2.3.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-kb/x11proto-kb-dev_1.0.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-randr/x11proto-randr-dev_1.5.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-record/x11proto-record-dev_1.14.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-render/x11proto-render-dev_0.11.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-scrnsaver/x11proto-scrnsaver-dev_1.2.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xext/x11proto-xext-dev_7.3.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xinerama/x11proto-xinerama-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g_1.2.8.dfsg-5_i386.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g-dev_1.2.8.dfsg-5_i386.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1_2.2.0-2+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1-dev_2.2.0-2+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6_2.24-11+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6-dev_2.24-11+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls28-dev_3.5.8-5+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls30_3.5.8-5+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-dane0_3.5.8-5+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-openssl27_3.5.8-5+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutlsxx28_3.5.8-5+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20_1.7.6-2+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20-dev_1.7.6-2+deb9u1_i386.deb
+http://security.debian.org/pool/updates/main/l/linux/linux-libc-dev_4.9.30-2+deb9u2_i386.deb
diff --git a/build/linux/sysroot_scripts/packagelist.stretch.mipsel b/build/linux/sysroot_scripts/packagelist.stretch.mipsel
new file mode 100644
index 0000000..169269f1
--- /dev/null
+++ b/build/linux/sysroot_scripts/packagelist.stretch.mipsel
@@ -0,0 +1,214 @@
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2_1.1.3-5_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/alsa-lib/libasound2-dev_1.1.3-5_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-0_2.22.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/atk1.0/libatk1.0-dev_2.22.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-0_2.22.0-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-atk/libatk-bridge2.0-dev_2.22.0-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-0_2.22.0-6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/at-spi2-core/libatspi2.0-dev_2.22.0-6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/attr/libattr1_2.4.47-2+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/audit/libaudit1_2.6.7-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-client3_0.6.32-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/a/avahi/libavahi-common3_0.6.32-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth3_5.43-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/b/bluez/libbluetooth-dev_5.43-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi0.6_5.4-7_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/b/brltty/libbrlapi-dev_5.4-7_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2_1.14.8-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo2-dev_1.14.8-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-gobject2_1.14.8-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cairo/libcairo-script-interpreter2_1.14.8-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2_2.2.1-8_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcups2-dev_2.2.1-8_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2_2.2.1-8_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/c/cups/libcupsimage2-dev_2.2.1-8_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus-glib/libdbus-glib-1-2_0.108-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-3_1.10.18-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/d/dbus/libdbus-1-dev_1.10.18-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/comerr-dev_2.1-1.43.4-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/e/e2fsprogs/libcomerr2_1.43.4-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf1_0.168-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/e/elfutils/libelf-dev_0.168-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1_2.11.0-6.7+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/f/fontconfig/libfontconfig1-dev_2.11.0-6.7+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6_2.6.3-3.2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/f/freetype/libfreetype6-dev_2.6.3-3.2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libatomic1_6.3.0-18_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc1_6.3.0-18_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgcc-6-dev_6.3.0-18_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libgomp1_6.3.0-18_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++6_6.3.0-18_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gcc-6/libstdc++-6-dev_6.3.0-18_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-4_3.2.6-4+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf-2-4_3.2.6-4+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gconf/libgconf2-dev_3.2.6-4+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-0_2.36.5-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gdk-pixbuf/libgdk-pixbuf2.0-dev_2.36.5-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-0_2.50.3-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/glib2.0/libglib2.0-dev_2.50.3-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-3_1.3.10-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/graphite2/libgraphite2-dev_1.3.10-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-0_2.24.31-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+2.0/libgtk2.0-dev_2.24.31-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-0_3.22.11-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/g/gtk+3.0/libgtk-3-dev_3.22.11-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz0b_1.4.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-dev_1.4.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-gobject0_1.4.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/h/harfbuzz/libharfbuzz-icu0_1.4.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/keyutils/libkeyutils1_1.5.9-9_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/krb5-multidev_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssapi-krb5-2_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libgssrpc4_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libk5crypto3_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5clnt-mit11_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkadm5srv-mit11_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkdb5-8_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-3_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5-dev_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/k/krb5/libkrb5support0_1.15-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap2_2.25-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libc/libcap2/libcap-dev_2.25-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm2_2.4.74-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-amdgpu1_2.4.74-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-dev_2.4.74-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-nouveau2_2.4.74-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libd/libdrm/libdrm-radeon1_2.4.74-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy0_1.3.1-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libe/libepoxy/libepoxy-dev_1.3.1-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi6_3.2.1-6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libf/libffi/libffi-dev_3.2.1-6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring0_3.12.0-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgnome-keyring/libgnome-keyring-dev_3.12.0-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error0_1.26-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libg/libgpg-error/libgpg-error-dev_1.26-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp1_1.7.4-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libj/libjsoncpp/libjsoncpp-dev_1.7.4-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libn/libnss-db/libnss-db_2.2.3pre1-6+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libp11/libp11-2_0.4.3-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng16-16_1.6.28-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpng1.6/libpng-dev_1.6.28-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libp/libpthread-stubs/libpthread-stubs0-dev_0.3-4_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libs/libselinux/libselinux1_2.6-3+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libt/libtasn1-6/libtasn1-6_4.10-1.1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-6_1.6.4-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-dev_1.6.4-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb1_1.6.4-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libx11/libx11-xcb-dev_1.6.4-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau6_1.0.8-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxau/libxau-dev_1.0.8-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb1-dev_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri2-0_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-dri3-0_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-glx0_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-present0_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-render0-dev_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-shm0-dev_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcb/libxcb-sync1_1.12-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite1_0.4.4-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcomposite/libxcomposite-dev_0.4.4-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor1_1.1.14-1+b4_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxcursor/libxcursor-dev_1.1.14-1+b4_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage1_1.1.4-2+b3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdamage/libxdamage-dev_1.1.4-2+b3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp6_1.1.2-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxdmcp/libxdmcp-dev_1.1.2-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext6_1.3.3-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxext/libxext-dev_1.3.3-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes3_5.0.3-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxfixes/libxfixes-dev_5.0.3-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi6_1.7.9-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxi/libxi-dev_1.7.9-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama1_1.1.3-1+b3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxinerama/libxinerama-dev_1.1.3-1+b3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon0_0.7.1-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxkbcommon/libxkbcommon-dev_0.7.1-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr2_1.5.1-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrandr/libxrandr-dev_1.5.1-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender1_0.9.10-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxrender/libxrender-dev_0.9.10-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxshmfence/libxshmfence1_1.2-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss1_1.2.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxss/libxss-dev_1.2.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt6_1.1.5-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxt/libxt-dev_1.1.5-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst6_1.2.3-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxtst/libxtst-dev_1.2.3-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/libx/libxxf86vm/libxxf86vm1_1.1.4-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libegl1-mesa-dev_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm1_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgbm-dev_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-dev_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libgl1-mesa-glx_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libglapi-mesa_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/libwayland-egl1-mesa_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/m/mesa/mesa-common-dev_13.0.6-1+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4_4.12-6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/n/nspr/libnspr4-dev_4.12-6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3_3.26.2-1.1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/n/nss/libnss3-dev_3.26.2-1.1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl1.0/libssl1.0.2_1.0.2l-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl1.1_1.1.0f-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl-dev_1.1.0f-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/o/orbit2/liborbit2_2.14.19-2+b1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/p11-kit/libp11-kit0_0.23.3-2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g_1.1.8-3.6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pam/libpam0g-dev_1.1.8-3.6_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango-1.0-0_1.40.5-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpango1.0-dev_1.40.5-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangocairo-1.0-0_1.40.5-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoft2-1.0-0_1.40.5-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pango1.0/libpangoxft-1.0-0_1.40.5-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pangox-compat/libpangox-1.0-0_0.0.2-5+b2_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci3_3.5.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pciutils/libpci-dev_3.5.2-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre16-3_8.39-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre32-3_8.39-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3_8.39-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcre3-dev_8.39-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pcre3/libpcrecpp0v5_8.39-3_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-0_0.34.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pixman/libpixman-1-dev_0.34.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse0_10.0-1+deb9u1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-dev_10.0-1+deb9u1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/p/pulseaudio/libpulse-mainloop-glib0_10.0-1+deb9u1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd2_0.8.6-4_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/libspeechd-dev_0.8.6-4_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/s/speech-dispatcher/speech-dispatcher_0.8.6-4_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev1_232-25+deb9u1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/s/systemd/libudev-dev_232-25+deb9u1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-client0_1.12.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-cursor0_1.12.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-dev_1.12.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland/libwayland-server0_1.12.0-1_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/w/wayland-protocols/wayland-protocols_1.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-composite/x11proto-composite-dev_0.4.2-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-core/x11proto-core-dev_7.0.31-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-damage/x11proto-damage-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-fixes/x11proto-fixes-dev_5.0-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-input/x11proto-input-dev_2.3.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-kb/x11proto-kb-dev_1.0.7-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-randr/x11proto-randr-dev_1.5.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-record/x11proto-record-dev_1.14.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-render/x11proto-render-dev_0.11.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-scrnsaver/x11proto-scrnsaver-dev_1.2.2-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xext/x11proto-xext-dev_7.3.0-1_all.deb
+http://ftp.us.debian.org/debian/pool/main/x/x11proto-xinerama/x11proto-xinerama-dev_1.2.1-2_all.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g_1.2.8.dfsg-5_mipsel.deb
+http://ftp.us.debian.org/debian/pool/main/z/zlib/zlib1g-dev_1.2.8.dfsg-5_mipsel.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1_2.2.0-2+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/e/expat/libexpat1-dev_2.2.0-2+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6_2.24-11+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/g/glibc/libc6-dev_2.24-11+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls28-dev_3.5.8-5+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls30_3.5.8-5+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-dane0_3.5.8-5+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutls-openssl27_3.5.8-5+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/g/gnutls28/libgnutlsxx28_3.5.8-5+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20_1.7.6-2+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/libg/libgcrypt20/libgcrypt20-dev_1.7.6-2+deb9u1_mipsel.deb
+http://security.debian.org/pool/updates/main/l/linux/linux-libc-dev_4.9.30-2+deb9u2_mipsel.deb
diff --git a/build/linux/sysroot_scripts/sysroots.json b/build/linux/sysroot_scripts/sysroots.json
index b5d8a41..c11bd45 100644
--- a/build/linux/sysroot_scripts/sysroots.json
+++ b/build/linux/sysroot_scripts/sysroots.json
@@ -28,5 +28,35 @@
         "Sha1Sum": "67da4cf69e87719d3ca8427771c927b6af95ffba",
         "SysrootDir": "debian_jessie_mips-sysroot",
         "Tarball": "debian_jessie_mips_sysroot.tar.xz"
+    },
+    "stretch_amd64": {
+        "Revision": "7d1a17d2a858e32ce6b8a237d603019a2e3ac0b0",
+        "Sha1Sum": "4fd5bacc951f648462702952ce14063b306ce6ba",
+        "SysrootDir": "debian_stretch_amd64-sysroot",
+        "Tarball": "debian_stretch_amd64_sysroot.tar.xz"
+    },
+    "stretch_arm": {
+        "Revision": "7d1a17d2a858e32ce6b8a237d603019a2e3ac0b0",
+        "Sha1Sum": "11e30b748de602ece73687ec0bf972e662a31f3e",
+        "SysrootDir": "debian_stretch_arm-sysroot",
+        "Tarball": "debian_stretch_arm_sysroot.tar.xz"
+    },
+    "stretch_arm64": {
+        "Revision": "7d1a17d2a858e32ce6b8a237d603019a2e3ac0b0",
+        "Sha1Sum": "f863c58810c8b4e9b556ffc7fc3980f9e3ba6fc2",
+        "SysrootDir": "debian_stretch_arm64-sysroot",
+        "Tarball": "debian_stretch_arm64_sysroot.tar.xz"
+    },
+    "stretch_i386": {
+        "Revision": "7d1a17d2a858e32ce6b8a237d603019a2e3ac0b0",
+        "Sha1Sum": "32362c929300daad99c071ed80b697a618e76c79",
+        "SysrootDir": "debian_stretch_i386-sysroot",
+        "Tarball": "debian_stretch_i386_sysroot.tar.xz"
+    },
+    "stretch_mips": {
+        "Revision": "7d1a17d2a858e32ce6b8a237d603019a2e3ac0b0",
+        "Sha1Sum": "182f5c1d3347d54894ef31e273e2859d4ddc212d",
+        "SysrootDir": "debian_stretch_mips-sysroot",
+        "Tarball": "debian_stretch_mips_sysroot.tar.xz"
     }
 }
diff --git a/cc/resources/video_resource_updater.cc b/cc/resources/video_resource_updater.cc
index 1d037c66..d0787c9 100644
--- a/cc/resources/video_resource_updater.cc
+++ b/cc/resources/video_resource_updater.cc
@@ -102,21 +102,33 @@
 
 class SyncTokenClientImpl : public media::VideoFrame::SyncTokenClient {
  public:
-  explicit SyncTokenClientImpl(gpu::gles2::GLES2Interface* gl) : gl_(gl) {}
+  SyncTokenClientImpl(gpu::gles2::GLES2Interface* gl, gpu::SyncToken sync_token)
+      : gl_(gl), sync_token_(sync_token) {}
   ~SyncTokenClientImpl() override = default;
 
   void GenerateSyncToken(gpu::SyncToken* sync_token) override {
-    const uint64_t fence_sync = gl_->InsertFenceSyncCHROMIUM();
-    gl_->ShallowFlushCHROMIUM();
-    gl_->GenSyncTokenCHROMIUM(fence_sync, sync_token->GetData());
+    if (sync_token_.HasData()) {
+      *sync_token = sync_token_;
+    } else {
+      const uint64_t fence_sync = gl_->InsertFenceSyncCHROMIUM();
+      gl_->ShallowFlushCHROMIUM();
+      gl_->GenSyncTokenCHROMIUM(fence_sync, sync_token->GetData());
+    }
   }
 
   void WaitSyncToken(const gpu::SyncToken& sync_token) override {
-    gl_->WaitSyncTokenCHROMIUM(sync_token.GetConstData());
+    if (sync_token.HasData()) {
+      gl_->WaitSyncTokenCHROMIUM(sync_token.GetConstData());
+      if (sync_token_.HasData() && sync_token_ != sync_token) {
+        gl_->WaitSyncTokenCHROMIUM(sync_token_.GetConstData());
+        sync_token_.Clear();
+      }
+    }
   }
 
  private:
   gpu::gles2::GLES2Interface* gl_;
+  gpu::SyncToken sync_token_;
   DISALLOW_COPY_AND_ASSIGN(SyncTokenClientImpl);
 };
 
@@ -567,12 +579,9 @@
   // resource.
   if (lost_resource || !updater.get())
     return;
-  // First wait on the sync token returned by the browser so that the release
-  // sync token implicitly depends on it.
-  gpu::gles2::GLES2Interface* gl = updater->context_provider_->ContextGL();
-  gl->WaitSyncTokenCHROMIUM(sync_token.GetConstData());
   // The video frame will insert a wait on the previous release sync token.
-  SyncTokenClientImpl client(gl);
+  SyncTokenClientImpl client(updater->context_provider_->ContextGL(),
+                             sync_token);
   video_frame->UpdateReleaseSyncToken(&client);
 }
 
@@ -614,7 +623,8 @@
       false, false, false);
   gl->DeleteTextures(1, &src_texture_id);
 
-  SyncTokenClientImpl client(gl);
+  // Pass an empty sync token to force generation of a new sync token.
+  SyncTokenClientImpl client(gl, gpu::SyncToken());
   gpu::SyncToken sync_token = video_frame->UpdateReleaseSyncToken(&client);
 
   // Set sync token otherwise resource is assumed to be synchronized.
diff --git a/cc/resources/video_resource_updater_unittest.cc b/cc/resources/video_resource_updater_unittest.cc
index 17ec9e43..e933119f 100644
--- a/cc/resources/video_resource_updater_unittest.cc
+++ b/cc/resources/video_resource_updater_unittest.cc
@@ -174,7 +174,9 @@
     return video_frame;
   }
 
-  static void ReleaseMailboxCB(const gpu::SyncToken& sync_token) {}
+  void SetReleaseSyncToken(const gpu::SyncToken& sync_token) {
+    release_sync_token_ = sync_token;
+  }
 
   scoped_refptr<media::VideoFrame> CreateTestHardwareVideoFrame(
       unsigned target) {
@@ -184,19 +186,17 @@
     gpu::Mailbox mailbox;
     mailbox.name[0] = 51;
 
-    const gpu::SyncToken sync_token(
-        gpu::CommandBufferNamespace::GPU_IO, 0,
-        gpu::CommandBufferId::FromUnsafeValue(0x123), 7);
     gpu::MailboxHolder mailbox_holders[media::VideoFrame::kMaxPlanes] = {
-        gpu::MailboxHolder(mailbox, sync_token, target)};
+        gpu::MailboxHolder(mailbox, kMailboxSyncToken, target)};
     scoped_refptr<media::VideoFrame> video_frame =
-        media::VideoFrame::WrapNativeTextures(media::PIXEL_FORMAT_ARGB,
-                                              mailbox_holders,
-                                              base::Bind(&ReleaseMailboxCB),
-                                              size,             // coded_size
-                                              gfx::Rect(size),  // visible_rect
-                                              size,             // natural_size
-                                              base::TimeDelta());  // timestamp
+        media::VideoFrame::WrapNativeTextures(
+            media::PIXEL_FORMAT_ARGB, mailbox_holders,
+            base::Bind(&VideoResourceUpdaterTest::SetReleaseSyncToken,
+                       base::Unretained(this)),
+            size,                // coded_size
+            gfx::Rect(size),     // visible_rect
+            size,                // natural_size
+            base::TimeDelta());  // timestamp
     EXPECT_TRUE(video_frame);
     return video_frame;
   }
@@ -218,36 +218,44 @@
     const int kDimension = 10;
     gfx::Size size(kDimension, kDimension);
 
-    const gpu::SyncToken sync_token(
-        gpu::CommandBufferNamespace::GPU_IO, 0,
-        gpu::CommandBufferId::FromUnsafeValue(0x123), 7);
     const unsigned target = GL_TEXTURE_RECTANGLE_ARB;
     const int kPlanesNum = 3;
     gpu::MailboxHolder mailbox_holders[media::VideoFrame::kMaxPlanes];
     for (int i = 0; i < kPlanesNum; ++i) {
       gpu::Mailbox mailbox;
       mailbox.name[0] = 50 + 1;
-      mailbox_holders[i] = gpu::MailboxHolder(mailbox, sync_token, target);
+      mailbox_holders[i] =
+          gpu::MailboxHolder(mailbox, kMailboxSyncToken, target);
     }
     scoped_refptr<media::VideoFrame> video_frame =
-        media::VideoFrame::WrapNativeTextures(media::PIXEL_FORMAT_I420,
-                                              mailbox_holders,
-                                              base::Bind(&ReleaseMailboxCB),
-                                              size,             // coded_size
-                                              gfx::Rect(size),  // visible_rect
-                                              size,             // natural_size
-                                              base::TimeDelta());  // timestamp
+        media::VideoFrame::WrapNativeTextures(
+            media::PIXEL_FORMAT_I420, mailbox_holders,
+            base::Bind(&VideoResourceUpdaterTest::SetReleaseSyncToken,
+                       base::Unretained(this)),
+            size,                // coded_size
+            gfx::Rect(size),     // visible_rect
+            size,                // natural_size
+            base::TimeDelta());  // timestamp
     EXPECT_TRUE(video_frame);
     return video_frame;
   }
 
+  static const gpu::SyncToken kMailboxSyncToken;
+
   WebGraphicsContext3DUploadCounter* context3d_;
   scoped_refptr<TestContextProvider> context_provider_;
   std::unique_ptr<SharedBitmapManagerAllocationCounter> shared_bitmap_manager_;
   std::unique_ptr<ResourceProvider> resource_provider3d_;
   std::unique_ptr<ResourceProvider> resource_provider_software_;
+  gpu::SyncToken release_sync_token_;
 };
 
+const gpu::SyncToken VideoResourceUpdaterTest::kMailboxSyncToken =
+    gpu::SyncToken(gpu::CommandBufferNamespace::GPU_IO,
+                   0,
+                   gpu::CommandBufferId::FromUnsafeValue(0x123),
+                   7);
+
 TEST_F(VideoResourceUpdaterTest, SoftwareFrame) {
   bool use_stream_video_draw_quad = false;
   VideoResourceUpdater updater(context_provider_.get(),
@@ -566,5 +574,96 @@
   EXPECT_EQ(0, context3d_->TextureCreationCount());
 }
 
+// Passthrough the sync token returned by the compositor if we don't have an
+// existing release sync token.
+TEST_F(VideoResourceUpdaterTest, PassReleaseSyncToken) {
+  VideoResourceUpdater updater(context_provider_.get(),
+                               resource_provider3d_.get(),
+                               false /* use_stream_video_draw_quad */);
+
+  const gpu::SyncToken sync_token(gpu::CommandBufferNamespace::GPU_IO, 0,
+                                  gpu::CommandBufferId::FromUnsafeValue(0x123),
+                                  123);
+
+  {
+    scoped_refptr<media::VideoFrame> video_frame =
+        CreateTestRGBAHardwareVideoFrame();
+
+    VideoFrameExternalResources resources =
+        updater.CreateExternalResourcesFromVideoFrame(video_frame);
+
+    ASSERT_EQ(resources.release_callbacks.size(), 1u);
+    resources.release_callbacks[0].Run(sync_token, false, nullptr);
+  }
+
+  EXPECT_EQ(release_sync_token_, sync_token);
+}
+
+// Generate new sync token because video frame has an existing sync token.
+TEST_F(VideoResourceUpdaterTest, GenerateReleaseSyncToken) {
+  VideoResourceUpdater updater(context_provider_.get(),
+                               resource_provider3d_.get(),
+                               false /* use_stream_video_draw_quad */);
+
+  const gpu::SyncToken sync_token1(gpu::CommandBufferNamespace::GPU_IO, 0,
+                                   gpu::CommandBufferId::FromUnsafeValue(0x123),
+                                   123);
+
+  const gpu::SyncToken sync_token2(gpu::CommandBufferNamespace::GPU_IO, 0,
+                                   gpu::CommandBufferId::FromUnsafeValue(0x234),
+                                   234);
+
+  {
+    scoped_refptr<media::VideoFrame> video_frame =
+        CreateTestRGBAHardwareVideoFrame();
+
+    VideoFrameExternalResources resources =
+        updater.CreateExternalResourcesFromVideoFrame(video_frame);
+
+    ASSERT_EQ(resources.release_callbacks.size(), 1u);
+    resources.release_callbacks[0].Run(sync_token1, false, nullptr);
+    resources.release_callbacks[0].Run(sync_token2, false, nullptr);
+  }
+
+  EXPECT_TRUE(release_sync_token_.HasData());
+  EXPECT_NE(release_sync_token_, sync_token1);
+  EXPECT_NE(release_sync_token_, sync_token2);
+}
+
+// Pass mailbox sync token as is if no GL operations are performed before frame
+// resources are handed off to the compositor.
+TEST_F(VideoResourceUpdaterTest, PassMailboxSyncToken) {
+  VideoResourceUpdater updater(context_provider_.get(),
+                               resource_provider3d_.get(),
+                               false /* use_stream_video_draw_quad */);
+
+  scoped_refptr<media::VideoFrame> video_frame =
+      CreateTestRGBAHardwareVideoFrame();
+
+  VideoFrameExternalResources resources =
+      updater.CreateExternalResourcesFromVideoFrame(video_frame);
+
+  ASSERT_EQ(resources.mailboxes.size(), 1u);
+  EXPECT_TRUE(resources.mailboxes[0].HasSyncToken());
+  EXPECT_EQ(resources.mailboxes[0].sync_token(), kMailboxSyncToken);
+}
+
+// Generate new sync token for compositor when copying the texture.
+TEST_F(VideoResourceUpdaterTest, GenerateSyncTokenOnTextureCopy) {
+  VideoResourceUpdater updater(context_provider_.get(),
+                               resource_provider3d_.get(),
+                               false /* use_stream_video_draw_quad */);
+
+  scoped_refptr<media::VideoFrame> video_frame =
+      CreateTestStreamTextureHardwareVideoFrame(true /* needs_copy */);
+
+  VideoFrameExternalResources resources =
+      updater.CreateExternalResourcesFromVideoFrame(video_frame);
+
+  ASSERT_EQ(resources.mailboxes.size(), 1u);
+  EXPECT_TRUE(resources.mailboxes[0].HasSyncToken());
+  EXPECT_NE(resources.mailboxes[0].sync_token(), kMailboxSyncToken);
+}
+
 }  // namespace
 }  // namespace cc
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/init/ProcessInitializationHandler.java b/chrome/android/java/src/org/chromium/chrome/browser/init/ProcessInitializationHandler.java
index f6ee5fc1..38d49ab6 100644
--- a/chrome/android/java/src/org/chromium/chrome/browser/init/ProcessInitializationHandler.java
+++ b/chrome/android/java/src/org/chromium/chrome/browser/init/ProcessInitializationHandler.java
@@ -65,7 +65,6 @@
 import org.chromium.chrome.browser.profiles.ProfileManagerUtils;
 import org.chromium.chrome.browser.rlz.RevenueStats;
 import org.chromium.chrome.browser.searchwidget.SearchWidgetProvider;
-import org.chromium.chrome.browser.services.AccountsChangedReceiver;
 import org.chromium.chrome.browser.services.GoogleServicesManager;
 import org.chromium.chrome.browser.share.ShareHelper;
 import org.chromium.chrome.browser.sync.SyncController;
@@ -74,6 +73,7 @@
 import org.chromium.components.background_task_scheduler.BackgroundTaskSchedulerFactory;
 import org.chromium.components.minidump_uploader.CrashFileManager;
 import org.chromium.components.signin.AccountManagerFacade;
+import org.chromium.components.signin.AccountsChangeObserver;
 import org.chromium.content.browser.ChildProcessLauncherHelper;
 import org.chromium.content.common.ContentSwitches;
 import org.chromium.device.geolocation.LocationProviderFactory;
@@ -345,8 +345,8 @@
             @Override
             public void run() {
                 ForcedSigninProcessor.start(application, null);
-                AccountsChangedReceiver.addObserver(
-                        new AccountsChangedReceiver.AccountsChangedObserver() {
+                AccountManagerFacade.get().addObserver(
+                        new AccountsChangeObserver() {
                             @Override
                             public void onAccountsChanged() {
                                 ThreadUtils.runOnUiThread(new Runnable() {
diff --git a/chrome/app/chrome_main.cc b/chrome/app/chrome_main.cc
index eacfdb6..43bf9dc 100644
--- a/chrome/app/chrome_main.cc
+++ b/chrome/app/chrome_main.cc
@@ -103,8 +103,18 @@
 #endif  // defined(OS_LINUX) || defined(OS_MACOSX) || defined(OS_WIN)
 
 #if defined(OS_CHROMEOS) && BUILDFLAG(ENABLE_PACKAGE_MASH_SERVICES)
-  if (service_manager::ServiceManagerIsRemote())
+  if (service_manager::ServiceManagerIsRemote()) {
+    params.create_discardable_memory = false;
     params.env_mode = aura::Env::Mode::MUS;
+  }
+  // In config==mus the ui service runs in process and is shut down well before
+  // the rest of Chrome. Have Chrome create the DiscardableSharedMemoryManager
+  // to ensure the DiscardableSharedMemoryManager is destroyed later on. Doing
+  // this avoids lifetime issues when internal implementation details of
+  // DiscardableSharedMemoryManager assume DiscardableSharedMemoryManager is
+  // long lived.
+  if (command_line->GetSwitchValueASCII(switches::kMusConfig) == switches::kMus)
+    params.create_discardable_memory = true;
 #endif  // BUILDFLAG(ENABLE_PACKAGE_MASH_SERVICES)
 
   int rv = content::ContentMain(params);
diff --git a/chrome/browser/apps/drive/drive_app_mapping.cc b/chrome/browser/apps/drive/drive_app_mapping.cc
index 96a913b..d3618e5 100644
--- a/chrome/browser/apps/drive/drive_app_mapping.cc
+++ b/chrome/browser/apps/drive/drive_app_mapping.cc
@@ -31,7 +31,7 @@
 
   // Only writes non-default value.
   if (generated)
-    dict->SetBooleanWithoutPathExpansion(kKeyGenerated, true);
+    dict->SetKey(kKeyGenerated, base::Value(true));
   return dict;
 }
 
diff --git a/chrome/browser/browser_process_platform_part_chromeos.cc b/chrome/browser/browser_process_platform_part_chromeos.cc
index a79f210..37e0a13 100644
--- a/chrome/browser/browser_process_platform_part_chromeos.cc
+++ b/chrome/browser/browser_process_platform_part_chromeos.cc
@@ -38,6 +38,7 @@
 #include "chromeos/timezone/timezone_resolver.h"
 #include "components/session_manager/core/session_manager.h"
 #include "components/user_manager/user_manager.h"
+#include "content/public/browser/discardable_shared_memory_manager.h"
 #include "mash/public/interfaces/launchable.mojom.h"
 #include "services/preferences/public/interfaces/preferences.mojom.h"
 #include "services/service_manager/public/cpp/binder_registry.h"
@@ -134,10 +135,12 @@
 
 std::unique_ptr<service_manager::Service> CreateEmbeddedUIService(
     const scoped_refptr<base::SingleThreadTaskRunner>& task_runner,
-    base::WeakPtr<ui::ImageCursorsSet> image_cursors_set_weak_ptr) {
+    base::WeakPtr<ui::ImageCursorsSet> image_cursors_set_weak_ptr,
+    discardable_memory::DiscardableSharedMemoryManager* memory_manager) {
   ui::Service::InProcessConfig config;
   config.resource_runner = task_runner;
   config.image_cursors_set_weak_ptr = image_cursors_set_weak_ptr;
+  config.memory_manager = memory_manager;
   return base::MakeUnique<ui::Service>(&config);
 }
 
@@ -291,7 +294,8 @@
     service_manager::EmbeddedServiceInfo info;
     info.factory = base::Bind(&CreateEmbeddedUIService,
                               base::ThreadTaskRunnerHandle::Get(),
-                              image_cursors_set_.GetWeakPtr());
+                              image_cursors_set_.GetWeakPtr(),
+                              content::GetDiscardableSharedMemoryManager());
     info.use_own_thread = true;
     info.message_loop_type = base::MessageLoop::TYPE_UI;
     info.thread_priority = base::ThreadPriority::DISPLAY;
diff --git a/chrome/browser/chromeos/arc/intent_helper/arc_settings_service.cc b/chrome/browser/chromeos/arc/intent_helper/arc_settings_service.cc
index 8687e59a0..756df5c6 100644
--- a/chrome/browser/chromeos/arc/intent_helper/arc_settings_service.cc
+++ b/chrome/browser/chromeos/arc/intent_helper/arc_settings_service.cc
@@ -34,8 +34,6 @@
 #include "components/proxy_config/pref_proxy_config_tracker_impl.h"
 #include "components/proxy_config/proxy_config_dictionary.h"
 #include "components/proxy_config/proxy_config_pref_names.h"
-#include "device/bluetooth/bluetooth_adapter.h"
-#include "device/bluetooth/bluetooth_adapter_factory.h"
 #include "net/proxy/proxy_config.h"
 
 using ::chromeos::CrosSettings;
@@ -99,7 +97,6 @@
 // about and sends the new values to Android to keep the state in sync.
 class ArcSettingsServiceImpl
     : public chromeos::system::TimezoneSettings::Observer,
-      public device::BluetoothAdapter::Observer,
       public ArcSessionManager::Observer,
       public chromeos::NetworkStateHandlerObserver {
  public:
@@ -114,10 +111,6 @@
   // TimezoneSettings::Observer:
   void TimezoneChanged(const icu::TimeZone& timezone) override;
 
-  // BluetoothAdapter::Observer:
-  void AdapterPoweredChanged(device::BluetoothAdapter* adapter,
-                             bool powered) override;
-
   // ArcSessionManager::Observer:
   void OnArcInitialStart() override;
 
@@ -164,9 +157,6 @@
   void SyncTimeZoneByGeolocation() const;
   void SyncUse24HourClock() const;
 
-  void OnBluetoothAdapterInitialized(
-      scoped_refptr<device::BluetoothAdapter> adapter);
-
   // Registers to listen to a particular perf.
   void AddPrefToObserve(const std::string& pref_name);
 
@@ -198,9 +188,6 @@
   std::unique_ptr<chromeos::CrosSettings::ObserverSubscription>
       reporting_consent_subscription_;
 
-  scoped_refptr<device::BluetoothAdapter> bluetooth_adapter_;
-
-  // WeakPtrFactory to use for callback for getting the bluetooth adapter.
   base::WeakPtrFactory<ArcSettingsServiceImpl> weak_factory_;
 
   DISALLOW_COPY_AND_ASSIGN(ArcSettingsServiceImpl);
@@ -224,9 +211,6 @@
   ArcSessionManager* arc_session_manager = ArcSessionManager::Get();
   if (arc_session_manager)
     arc_session_manager->RemoveObserver(this);
-
-  if (bluetooth_adapter_)
-    bluetooth_adapter_->RemoveObserver(this);
 }
 
 void ArcSettingsServiceImpl::OnPrefChanged(const std::string& pref_name) const {
@@ -274,15 +258,6 @@
   SyncTimeZone();
 }
 
-void ArcSettingsServiceImpl::AdapterPoweredChanged(
-    device::BluetoothAdapter* adapter,
-    bool powered) {
-  base::DictionaryValue extras;
-  extras.SetBoolean("enable", powered);
-  SendSettingsBroadcast("org.chromium.arc.intent_helper.SET_BLUETOOTH_STATE",
-                        extras);
-}
-
 void ArcSettingsServiceImpl::OnArcInitialStart() {
   SyncInitialSettings();
 }
@@ -328,12 +303,6 @@
 
   TimezoneSettings::GetInstance()->AddObserver(this);
 
-  if (device::BluetoothAdapterFactory::IsBluetoothSupported()) {
-    device::BluetoothAdapterFactory::GetAdapter(
-        base::Bind(&ArcSettingsServiceImpl::OnBluetoothAdapterInitialized,
-                   weak_factory_.GetWeakPtr()));
-  }
-
   chromeos::NetworkHandler::Get()->network_state_handler()->AddObserver(
       this, FROM_HERE);
 }
@@ -569,15 +538,6 @@
                         extras);
 }
 
-void ArcSettingsServiceImpl::OnBluetoothAdapterInitialized(
-    scoped_refptr<device::BluetoothAdapter> adapter) {
-  DCHECK(adapter);
-  bluetooth_adapter_ = adapter;
-  bluetooth_adapter_->AddObserver(this);
-
-  AdapterPoweredChanged(adapter.get(), adapter->IsPowered());
-}
-
 void ArcSettingsServiceImpl::AddPrefToObserve(const std::string& pref_name) {
   registrar_.Add(pref_name, base::Bind(&ArcSettingsServiceImpl::OnPrefChanged,
                                        base::Unretained(this)));
diff --git a/chrome/browser/chromeos/arc/voice_interaction/arc_voice_interaction_arc_home_service.cc b/chrome/browser/chromeos/arc/voice_interaction/arc_voice_interaction_arc_home_service.cc
index 8e263ba..9b10280 100644
--- a/chrome/browser/chromeos/arc/voice_interaction/arc_voice_interaction_arc_home_service.cc
+++ b/chrome/browser/chromeos/arc/voice_interaction/arc_voice_interaction_arc_home_service.cc
@@ -31,6 +31,7 @@
 #include "content/public/browser/web_contents.h"
 #include "ui/accessibility/platform/ax_snapshot_node_android_platform.h"
 #include "ui/aura/window.h"
+#include "ui/compositor/dip_util.h"
 #include "ui/snapshot/snapshot.h"
 #include "ui/wm/public/activation_client.h"
 #include "url/gurl.h"
@@ -173,10 +174,11 @@
     return;
   }
 
-  web_contents->RequestAXTreeSnapshot(
-      base::Bind(&RequestVoiceInteractionStructureCallback, callback,
-                 browser->window()->GetBounds(),
-                 web_contents->GetLastCommittedURL().spec()));
+  web_contents->RequestAXTreeSnapshot(base::Bind(
+      &RequestVoiceInteractionStructureCallback, callback,
+      ui::ConvertRectToPixel(browser->window()->GetNativeWindow()->layer(),
+                             browser->window()->GetBounds()),
+      web_contents->GetLastCommittedURL().spec()));
 }
 
 void ArcVoiceInteractionArcHomeService::OnVoiceInteractionOobeSetupComplete() {
diff --git a/chrome/browser/chromeos/file_system_provider/registry.cc b/chrome/browser/chromeos/file_system_provider/registry.cc
index 70cced13..39f315d 100644
--- a/chrome/browser/chromeos/file_system_provider/registry.cc
+++ b/chrome/browser/chromeos/file_system_provider/registry.cc
@@ -56,10 +56,10 @@
                                              file_system_info.file_system_id());
   file_system->SetStringWithoutPathExpansion(kPrefKeyDisplayName,
                                              file_system_info.display_name());
-  file_system->SetBooleanWithoutPathExpansion(kPrefKeyWritable,
-                                              file_system_info.writable());
-  file_system->SetBooleanWithoutPathExpansion(
-      kPrefKeySupportsNotifyTag, file_system_info.supports_notify_tag());
+  file_system->SetKey(kPrefKeyWritable,
+                      base::Value(file_system_info.writable()));
+  file_system->SetKey(kPrefKeySupportsNotifyTag,
+                      base::Value(file_system_info.supports_notify_tag()));
   file_system->SetIntegerWithoutPathExpansion(
       kPrefKeyOpenedFilesLimit, file_system_info.opened_files_limit());
 
@@ -69,8 +69,7 @@
     auto watcher = base::MakeUnique<base::DictionaryValue>();
     watcher->SetStringWithoutPathExpansion(kPrefKeyWatcherEntryPath,
                                            it.second.entry_path.value());
-    watcher->SetBooleanWithoutPathExpansion(kPrefKeyWatcherRecursive,
-                                            it.second.recursive);
+    watcher->SetKey(kPrefKeyWatcherRecursive, base::Value(it.second.recursive));
     watcher->SetStringWithoutPathExpansion(kPrefKeyWatcherLastTag,
                                            it.second.last_tag);
     auto persistent_origins_value = base::MakeUnique<base::ListValue>();
diff --git a/chrome/browser/chromeos/file_system_provider/registry_unittest.cc b/chrome/browser/chromeos/file_system_provider/registry_unittest.cc
index 01f7cd4..6a73417e 100644
--- a/chrome/browser/chromeos/file_system_provider/registry_unittest.cc
+++ b/chrome/browser/chromeos/file_system_provider/registry_unittest.cc
@@ -61,9 +61,9 @@
   file_system->SetStringWithoutPathExpansion(kPrefKeyFileSystemId,
                                              kFileSystemId);
   file_system->SetStringWithoutPathExpansion(kPrefKeyDisplayName, kDisplayName);
-  file_system->SetBooleanWithoutPathExpansion(kPrefKeyWritable, writable);
-  file_system->SetBooleanWithoutPathExpansion(kPrefKeySupportsNotifyTag,
-                                              supports_notify_tag);
+  file_system->SetKey(kPrefKeyWritable, base::Value(writable));
+  file_system->SetKey(kPrefKeySupportsNotifyTag,
+                      base::Value(supports_notify_tag));
   file_system->SetIntegerWithoutPathExpansion(kPrefKeyOpenedFilesLimit,
                                               opened_files_limit);
 
@@ -71,8 +71,8 @@
   auto watcher_value = base::MakeUnique<base::DictionaryValue>();
   watcher_value->SetStringWithoutPathExpansion(kPrefKeyWatcherEntryPath,
                                                watcher.entry_path.value());
-  watcher_value->SetBooleanWithoutPathExpansion(kPrefKeyWatcherRecursive,
-                                                watcher.recursive);
+  watcher_value->SetKey(kPrefKeyWatcherRecursive,
+                        base::Value(watcher.recursive));
   watcher_value->SetStringWithoutPathExpansion(kPrefKeyWatcherLastTag,
                                                watcher.last_tag);
   auto persistent_origins_value = base::MakeUnique<base::ListValue>();
diff --git a/chrome/browser/chromeos/login/users/supervised_user_manager_impl.cc b/chrome/browser/chromeos/login/users/supervised_user_manager_impl.cc
index e745b54..49ca31a 100644
--- a/chrome/browser/chromeos/login/users/supervised_user_manager_impl.cc
+++ b/chrome/browser/chromeos/login/users/supervised_user_manager_impl.cc
@@ -278,9 +278,9 @@
 
   bool flag;
   if (GetUserBooleanValue(user_id, kSupervisedUserNeedPasswordUpdate, &flag))
-    result->SetBooleanWithoutPathExpansion(kRequirePasswordUpdate, flag);
+    result->SetKey(kRequirePasswordUpdate, base::Value(flag));
   if (GetUserBooleanValue(user_id, kSupervisedUserIncompleteKey, &flag))
-    result->SetBooleanWithoutPathExpansion(kHasIncompleteKey, flag);
+    result->SetKey(kHasIncompleteKey, base::Value(flag));
 
   std::string salt;
   if (GetUserStringValue(user_id, kSupervisedUserPasswordSalt, &salt))
@@ -359,7 +359,7 @@
                                                     const bool value) {
   PrefService* local_state = g_browser_process->local_state();
   DictionaryPrefUpdate update(local_state, key);
-  update->SetBooleanWithoutPathExpansion(user_id, value);
+  update->SetKey(user_id, base::Value(value));
 }
 
 const user_manager::User* SupervisedUserManagerImpl::FindByDisplayName(
diff --git a/chrome/browser/chromeos/options/vpn_config_view.cc b/chrome/browser/chromeos/options/vpn_config_view.cc
index ab4d066..7506513 100644
--- a/chrome/browser/chromeos/options/vpn_config_view.cc
+++ b/chrome/browser/chromeos/options/vpn_config_view.cc
@@ -378,8 +378,7 @@
     bool only_policy_autoconnect =
         onc::PolicyAllowsOnlyPolicyNetworksToAutoconnect(!shared);
     if (only_policy_autoconnect) {
-      properties.SetBooleanWithoutPathExpansion(shill::kAutoConnectProperty,
-                                                false);
+      properties.SetKey(shill::kAutoConnectProperty, base::Value(false));
     }
 
     NetworkConnect::Get()->CreateConfigurationAndConnect(&properties, shared);
@@ -906,8 +905,8 @@
       NOTREACHED();
       break;
   }
-  properties->SetBooleanWithoutPathExpansion(
-      shill::kSaveCredentialsProperty, GetSaveCredentials());
+  properties->SetKey(shill::kSaveCredentialsProperty,
+                     base::Value(GetSaveCredentials()));
 }
 
 void VPNConfigView::Refresh() {
diff --git a/chrome/browser/chromeos/options/wifi_config_view.cc b/chrome/browser/chromeos/options/wifi_config_view.cc
index ae8b76a..8638cff 100644
--- a/chrome/browser/chromeos/options/wifi_config_view.cc
+++ b/chrome/browser/chromeos/options/wifi_config_view.cc
@@ -679,8 +679,7 @@
   bool only_policy_autoconnect =
       onc::PolicyAllowsOnlyPolicyNetworksToAutoconnect(!share_network);
   if (only_policy_autoconnect) {
-    properties.SetBooleanWithoutPathExpansion(shill::kAutoConnectProperty,
-                                              false);
+    properties.SetKey(shill::kAutoConnectProperty, base::Value(false));
   }
 
   if (service_path_.empty()) {
@@ -691,8 +690,8 @@
     shill_property_util::SetSSID(GetSsid(), &properties);
     properties.SetStringWithoutPathExpansion(
         shill::kModeProperty, shill::kModeManaged);
-    properties.SetBooleanWithoutPathExpansion(
-        shill::kSaveCredentialsProperty, GetSaveCredentials());
+    properties.SetKey(shill::kSaveCredentialsProperty,
+                      base::Value(GetSaveCredentials()));
     std::string security_class = shill::kSecurityNone;
     if (!eap_method_combobox_) {
       switch (security_combobox_->selected_index()) {
@@ -730,8 +729,8 @@
     }
     if (eap_method_combobox_) {
       SetEapProperties(&properties, true /* configured */);
-      properties.SetBooleanWithoutPathExpansion(
-          shill::kSaveCredentialsProperty, GetSaveCredentials());
+      properties.SetKey(shill::kSaveCredentialsProperty,
+                        base::Value(GetSaveCredentials()));
     } else {
       const std::string passphrase = GetPassphrase();
       if (!passphrase.empty()) {
@@ -891,8 +890,8 @@
 
   SetEapClientCertProperties(properties);
 
-  properties->SetBooleanWithoutPathExpansion(
-      shill::kEapUseSystemCasProperty, GetEapUseSystemCas());
+  properties->SetKey(shill::kEapUseSystemCasProperty,
+                     base::Value(GetEapUseSystemCas()));
   if (!configured || passphrase_textfield_->changed()) {
     properties->SetStringWithoutPathExpansion(
         shill::kEapPasswordProperty, GetPassphrase());
diff --git a/chrome/browser/chromeos/options/wimax_config_view.cc b/chrome/browser/chromeos/options/wimax_config_view.cc
index ec0cf562..b049a02f 100644
--- a/chrome/browser/chromeos/options/wimax_config_view.cc
+++ b/chrome/browser/chromeos/options/wimax_config_view.cc
@@ -155,8 +155,8 @@
       shill::kEapIdentityProperty, GetEapIdentity());
   properties.SetStringWithoutPathExpansion(
       shill::kEapPasswordProperty, GetEapPassphrase());
-  properties.SetBooleanWithoutPathExpansion(
-      shill::kSaveCredentialsProperty, GetSaveCredentials());
+  properties.SetKey(shill::kSaveCredentialsProperty,
+                    base::Value(GetSaveCredentials()));
 
   const bool share_default = true;
   bool share_network = GetShareNetwork(share_default);
@@ -164,8 +164,7 @@
   bool only_policy_autoconnect =
       onc::PolicyAllowsOnlyPolicyNetworksToAutoconnect(!share_network);
   if (only_policy_autoconnect) {
-    properties.SetBooleanWithoutPathExpansion(shill::kAutoConnectProperty,
-                                              false);
+    properties.SetKey(shill::kAutoConnectProperty, base::Value(false));
   }
 
   NetworkConnect::Get()->ConfigureNetworkIdAndConnect(wimax->guid(), properties,
diff --git a/chrome/browser/chromeos/platform_keys/key_permissions.cc b/chrome/browser/chromeos/platform_keys/key_permissions.cc
index 4957a74d..5e37002 100644
--- a/chrome/browser/chromeos/platform_keys/key_permissions.cc
+++ b/chrome/browser/chromeos/platform_keys/key_permissions.cc
@@ -283,12 +283,11 @@
     new_entry->SetStringWithoutPathExpansion(kStateStoreSPKI, entry.spki_b64);
     // Omit writing default values, namely |false|.
     if (entry.sign_once) {
-      new_entry->SetBooleanWithoutPathExpansion(kStateStoreSignOnce,
-                                                entry.sign_once);
+      new_entry->SetKey(kStateStoreSignOnce, base::Value(entry.sign_once));
     }
     if (entry.sign_unlimited) {
-      new_entry->SetBooleanWithoutPathExpansion(kStateStoreSignUnlimited,
-                                                entry.sign_unlimited);
+      new_entry->SetKey(kStateStoreSignUnlimited,
+                        base::Value(entry.sign_unlimited));
     }
     new_state->Append(std::move(new_entry));
   }
diff --git a/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.cc b/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.cc
index ec59bcf..205b231 100644
--- a/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.cc
+++ b/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.cc
@@ -15,6 +15,7 @@
 #include "base/bind.h"
 #include "base/bind_helpers.h"
 #include "base/macros.h"
+#include "base/task_scheduler/post_task.h"
 #include "base/time/time.h"
 #include "chrome/browser/extensions/api/braille_display_private/brlapi_connection.h"
 #include "chrome/browser/extensions/api/braille_display_private/brlapi_keycode_map.h"
@@ -166,34 +167,41 @@
   if (!libbrlapi_loader_.loaded()) {
     return;
   }
+
+  if (!sequenced_task_runner_) {
+    sequenced_task_runner_ = base::CreateSequencedTaskRunnerWithTraits(
+        {base::MayBlock(), base::TaskPriority::USER_VISIBLE});
+  }
+
   // Only try to connect after we've started to watch the
   // socket directory.  This is necessary to avoid a race condition
   // and because we don't retry to connect after errors that will
   // persist until there's a change to the socket directory (i.e.
   // ENOENT).
-  BrowserThread::PostTaskAndReply(
-      BrowserThread::FILE, FROM_HERE,
-      base::BindOnce(&BrailleControllerImpl::StartWatchingSocketDirOnFileThread,
+  sequenced_task_runner_->PostTaskAndReply(
+      FROM_HERE,
+      base::BindOnce(&BrailleControllerImpl::StartWatchingSocketDirOnTaskThread,
                      base::Unretained(this)),
       base::BindOnce(&BrailleControllerImpl::TryToConnect,
                      base::Unretained(this)));
   ResetRetryConnectHorizon();
 }
 
-void BrailleControllerImpl::StartWatchingSocketDirOnFileThread() {
-  DCHECK_CURRENTLY_ON(BrowserThread::FILE);
+void BrailleControllerImpl::StartWatchingSocketDirOnTaskThread() {
+  base::ThreadRestrictions::AssertIOAllowed();
   base::FilePath brlapi_dir(BRLAPI_SOCKETPATH);
   if (!file_path_watcher_.Watch(
-          brlapi_dir, false, base::Bind(
-              &BrailleControllerImpl::OnSocketDirChangedOnFileThread,
-              base::Unretained(this)))) {
+          brlapi_dir, false,
+          base::Bind(&BrailleControllerImpl::OnSocketDirChangedOnTaskThread,
+                     base::Unretained(this)))) {
     LOG(WARNING) << "Couldn't watch brlapi directory " << BRLAPI_SOCKETPATH;
   }
 }
 
-void BrailleControllerImpl::OnSocketDirChangedOnFileThread(
-    const base::FilePath& path, bool error) {
-  DCHECK_CURRENTLY_ON(BrowserThread::FILE);
+void BrailleControllerImpl::OnSocketDirChangedOnTaskThread(
+    const base::FilePath& path,
+    bool error) {
+  base::ThreadRestrictions::AssertIOAllowed();
   if (error) {
     LOG(ERROR) << "Error watching brlapi directory: " << path.value();
     return;
diff --git a/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.h b/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.h
index 63962e8..82fe471 100644
--- a/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.h
+++ b/chrome/browser/extensions/api/braille_display_private/braille_controller_brlapi.h
@@ -55,8 +55,8 @@
   // Tries to connect and starts watching for new brlapi servers.
   // No-op if already called.
   void StartConnecting();
-  void StartWatchingSocketDirOnFileThread();
-  void OnSocketDirChangedOnFileThread(const base::FilePath& path, bool error);
+  void StartWatchingSocketDirOnTaskThread();
+  void OnSocketDirChangedOnTaskThread(const base::FilePath& path, bool error);
   void OnSocketDirChangedOnIOThread();
   void TryToConnect();
   void ResetRetryConnectHorizon();
@@ -75,11 +75,12 @@
   bool started_connecting_;
   bool connect_scheduled_;
   base::Time retry_connect_horizon_;
+  scoped_refptr<base::SequencedTaskRunner> sequenced_task_runner_;
 
   // Manipulated on the UI thread.
   base::ObserverList<BrailleObserver> observers_;
 
-  // Manipulated on the FILE thread.
+  // Manipulated by the SequencedTaskRunner.
   base::FilePathWatcher file_path_watcher_;
 
   friend struct base::DefaultSingletonTraits<BrailleControllerImpl>;
diff --git a/chrome/browser/extensions/api/media_galleries/media_galleries_api.cc b/chrome/browser/extensions/api/media_galleries/media_galleries_api.cc
index 6a6a648..7aa039b0 100644
--- a/chrome/browser/extensions/api/media_galleries/media_galleries_api.cc
+++ b/chrome/browser/extensions/api/media_galleries/media_galleries_api.cc
@@ -182,12 +182,11 @@
       file_system_dict_value->SetStringWithoutPathExpansion(
           kDeviceIdKey, filesystems[i].transient_device_id);
     }
-    file_system_dict_value->SetBooleanWithoutPathExpansion(
-        kIsRemovableKey, filesystems[i].removable);
-    file_system_dict_value->SetBooleanWithoutPathExpansion(
-        kIsMediaDeviceKey, filesystems[i].media_device);
-    file_system_dict_value->SetBooleanWithoutPathExpansion(
-        kIsAvailableKey, true);
+    file_system_dict_value->SetKey(kIsRemovableKey,
+                                   base::Value(filesystems[i].removable));
+    file_system_dict_value->SetKey(kIsMediaDeviceKey,
+                                   base::Value(filesystems[i].media_device));
+    file_system_dict_value->SetKey(kIsAvailableKey, base::Value(true));
 
     list->Append(std::move(file_system_dict_value));
 
diff --git a/chrome/browser/extensions/api/networking_private/networking_private_chromeos_apitest.cc b/chrome/browser/extensions/api/networking_private/networking_private_chromeos_apitest.cc
index 918c0f4b..b86fb43e 100644
--- a/chrome/browser/extensions/api/networking_private/networking_private_chromeos_apitest.cc
+++ b/chrome/browser/extensions/api/networking_private/networking_private_chromeos_apitest.cc
@@ -880,12 +880,13 @@
 
 IN_PROC_BROWSER_TEST_F(NetworkingPrivateChromeOSApiTest, GetGlobalPolicy) {
   base::DictionaryValue global_config;
-  global_config.SetBooleanWithoutPathExpansion(
+  global_config.SetKey(
       ::onc::global_network_config::kAllowOnlyPolicyNetworksToAutoconnect,
-      true);
-  global_config.SetBooleanWithoutPathExpansion(
-      ::onc::global_network_config::kAllowOnlyPolicyNetworksToConnect, false);
-  global_config.SetBooleanWithoutPathExpansion("SomeNewGlobalPolicy", false);
+      base::Value(true));
+  global_config.SetKey(
+      ::onc::global_network_config::kAllowOnlyPolicyNetworksToConnect,
+      base::Value(false));
+  global_config.SetKey("SomeNewGlobalPolicy", base::Value(false));
   chromeos::NetworkHandler::Get()
       ->managed_network_configuration_handler()
       ->SetPolicy(::onc::ONC_SOURCE_DEVICE_POLICY,
diff --git a/chrome/browser/extensions/api/notifications/notifications_api.cc b/chrome/browser/extensions/api/notifications/notifications_api.cc
index 7936059..da49e6a0 100644
--- a/chrome/browser/extensions/api/notifications/notifications_api.cc
+++ b/chrome/browser/extensions/api/notifications/notifications_api.cc
@@ -650,8 +650,8 @@
 
   for (std::set<std::string>::iterator iter = notification_ids.begin();
        iter != notification_ids.end(); iter++) {
-    result->SetBooleanWithoutPathExpansion(
-        StripScopeFromIdentifier(extension_->id(), *iter), true);
+    result->SetKey(StripScopeFromIdentifier(extension_->id(), *iter),
+                   base::Value(true));
   }
 
   SetResult(std::move(result));
diff --git a/chrome/browser/extensions/api/platform_keys/platform_keys_apitest_nss.cc b/chrome/browser/extensions/api/platform_keys/platform_keys_apitest_nss.cc
index 5364c96..7f8e774 100644
--- a/chrome/browser/extensions/api/platform_keys/platform_keys_apitest_nss.cc
+++ b/chrome/browser/extensions/api/platform_keys/platform_keys_apitest_nss.cc
@@ -195,8 +195,7 @@
     {
       std::unique_ptr<base::DictionaryValue> cert1_key_permission(
           new base::DictionaryValue);
-      cert1_key_permission->SetBooleanWithoutPathExpansion(
-          "allowCorporateKeyUsage", true);
+      cert1_key_permission->SetKey("allowCorporateKeyUsage", base::Value(true));
       key_permissions_policy.SetWithoutPathExpansion(
           extension_->id(), std::move(cert1_key_permission));
     }
diff --git a/chrome/browser/extensions/api/virtual_keyboard_private/OWNERS b/chrome/browser/extensions/api/virtual_keyboard_private/OWNERS
index 5af418a..4198610 100644
--- a/chrome/browser/extensions/api/virtual_keyboard_private/OWNERS
+++ b/chrome/browser/extensions/api/virtual_keyboard_private/OWNERS
@@ -1,4 +1,3 @@
-bshe@chromium.org
-kevers@chromium.org
+file://ui/keyboard/OWNERS
 
 # COMPONENT: UI>Input>VirtualKeyboard
diff --git a/chrome/browser/extensions/api/virtual_keyboard_private/chrome_virtual_keyboard_delegate.cc b/chrome/browser/extensions/api/virtual_keyboard_private/chrome_virtual_keyboard_delegate.cc
index 3392f30..6da975d 100644
--- a/chrome/browser/extensions/api/virtual_keyboard_private/chrome_virtual_keyboard_delegate.cc
+++ b/chrome/browser/extensions/api/virtual_keyboard_private/chrome_virtual_keyboard_delegate.cc
@@ -42,18 +42,6 @@
   return feature + (enabled ? "-enabled" : "-disabled");
 }
 
-keyboard::KeyboardMode getKeyboardModeEnum(keyboard_api::KeyboardMode mode) {
-  switch (mode) {
-    case keyboard_api::KEYBOARD_MODE_NONE:
-      return keyboard::NONE;
-    case keyboard_api::KEYBOARD_MODE_FULL_WIDTH:
-      return keyboard::FULL_WIDTH;
-    case keyboard_api::KEYBOARD_MODE_FLOATING:
-      return keyboard::FLOATING;
-  }
-  return keyboard::NONE;
-}
-
 keyboard::KeyboardState getKeyboardStateEnum(
     keyboard_api::KeyboardState state) {
   switch (state) {
@@ -165,15 +153,9 @@
 }
 
 bool ChromeVirtualKeyboardDelegate::SetVirtualKeyboardMode(int mode_enum) {
-  keyboard::KeyboardMode keyboard_mode =
-      getKeyboardModeEnum(static_cast<keyboard_api::KeyboardMode>(mode_enum));
-  keyboard::KeyboardController* controller =
-      keyboard::KeyboardController::GetInstance();
-  if (!controller)
-    return false;
-
-  controller->SetKeyboardMode(keyboard_mode);
-  return true;
+  // TODO(blakeo): remove this. The virtual keyboard's implementation of mode
+  // was removed, and so this should be removed from the JS API side as well.
+  return false;
 }
 
 bool ChromeVirtualKeyboardDelegate::SetRequestedKeyboardState(int state_enum) {
diff --git a/chrome/browser/media/router/discovery/discovery_network_monitor.cc b/chrome/browser/media/router/discovery/discovery_network_monitor.cc
index da57b342..cdaf3be6 100644
--- a/chrome/browser/media/router/discovery/discovery_network_monitor.cc
+++ b/chrome/browser/media/router/discovery/discovery_network_monitor.cc
@@ -52,13 +52,12 @@
   return g_discovery_monitor.Pointer();
 }
 
-void DiscoveryNetworkMonitor::RebindNetworkChangeObserverForTest() {
-  net::NetworkChangeNotifier::AddNetworkChangeObserver(this);
-}
-
-void DiscoveryNetworkMonitor::SetNetworkInfoFunctionForTest(
-    NetworkInfoFunction strategy) {
-  network_info_function_ = strategy;
+// static
+std::unique_ptr<DiscoveryNetworkMonitor>
+DiscoveryNetworkMonitor::CreateInstanceForTest(NetworkInfoFunction strategy) {
+  auto* discovery_network_monitor = new DiscoveryNetworkMonitor();
+  discovery_network_monitor->SetNetworkInfoFunctionForTest(std::move(strategy));
+  return std::unique_ptr<DiscoveryNetworkMonitor>(discovery_network_monitor);
 }
 
 void DiscoveryNetworkMonitor::AddObserver(Observer* const observer) {
@@ -100,6 +99,11 @@
   net::NetworkChangeNotifier::RemoveNetworkChangeObserver(this);
 }
 
+void DiscoveryNetworkMonitor::SetNetworkInfoFunctionForTest(
+    NetworkInfoFunction strategy) {
+  network_info_function_ = strategy;
+}
+
 void DiscoveryNetworkMonitor::OnNetworkChanged(
     net::NetworkChangeNotifier::ConnectionType) {
   task_runner_->PostTask(
diff --git a/chrome/browser/media/router/discovery/discovery_network_monitor.h b/chrome/browser/media/router/discovery/discovery_network_monitor.h
index 9a80084..5e93d9c 100644
--- a/chrome/browser/media/router/discovery/discovery_network_monitor.h
+++ b/chrome/browser/media/router/discovery/discovery_network_monitor.h
@@ -50,8 +50,8 @@
 
   static DiscoveryNetworkMonitor* GetInstance();
 
-  void RebindNetworkChangeObserverForTest();
-  void SetNetworkInfoFunctionForTest(NetworkInfoFunction);
+  static std::unique_ptr<DiscoveryNetworkMonitor> CreateInstanceForTest(
+      NetworkInfoFunction strategy);
 
   void AddObserver(Observer* const observer);
   void RemoveObserver(Observer* const observer);
@@ -67,12 +67,14 @@
   void GetNetworkId(NetworkIdCallback callback);
 
  private:
-  friend class DiscoveryNetworkMonitorTest;
+  friend struct std::default_delete<DiscoveryNetworkMonitor>;
   friend struct base::LazyInstanceTraitsBase<DiscoveryNetworkMonitor>;
 
   DiscoveryNetworkMonitor();
   ~DiscoveryNetworkMonitor() override;
 
+  void SetNetworkInfoFunctionForTest(NetworkInfoFunction strategy);
+
   // net::NetworkChangeNotifier::NetworkChangeObserver
   void OnNetworkChanged(
       net::NetworkChangeNotifier::ConnectionType type) override;
diff --git a/chrome/browser/media/router/discovery/discovery_network_monitor_unittest.cc b/chrome/browser/media/router/discovery/discovery_network_monitor_unittest.cc
index 5bed890..7570e46 100644
--- a/chrome/browser/media/router/discovery/discovery_network_monitor_unittest.cc
+++ b/chrome/browser/media/router/discovery/discovery_network_monitor_unittest.cc
@@ -6,18 +6,13 @@
 
 #include <memory>
 
-#include "base/run_loop.h"
 #include "base/task_scheduler/task_scheduler.h"
-#include "content/public/browser/browser_thread.h"
-#include "content/public/test/test_browser_thread_bundle.h"
-#include "content/public/test/test_utils.h"
+#include "base/test/scoped_task_environment.h"
 #include "testing/gmock/include/gmock/gmock.h"
 #include "testing/gtest/include/gtest/gtest.h"
 
 namespace {
 
-using content::BrowserThread;
-
 using testing::Invoke;
 using testing::_;
 
@@ -30,19 +25,13 @@
 
 class DiscoveryNetworkMonitorTest : public testing::Test {
  protected:
-  void SetUp() override {
-    fake_network_info.clear();
-    discovery_network_monitor->SetNetworkInfoFunctionForTest(
-        &FakeGetNetworkInfo);
-  }
-
-  void TearDown() override { delete discovery_network_monitor; }
+  void SetUp() override { fake_network_info.clear(); }
 
   static std::vector<DiscoveryNetworkInfo> FakeGetNetworkInfo() {
     return fake_network_info;
   }
 
-  content::TestBrowserThreadBundle test_browser_thread_bundle;
+  base::test::ScopedTaskEnvironment scoped_task_environment;
   MockDiscoveryObserver mock_observer;
 
   std::vector<DiscoveryNetworkInfo> fake_ethernet_info{
@@ -55,10 +44,8 @@
       base::WrapUnique(net::NetworkChangeNotifier::CreateMock());
 
   static std::vector<DiscoveryNetworkInfo> fake_network_info;
-  // A raw pointer is used here with the delete in TearDown to avoid making the
-  // destructor public.
-  DiscoveryNetworkMonitor* discovery_network_monitor =
-      new DiscoveryNetworkMonitor();
+  std::unique_ptr<DiscoveryNetworkMonitor> discovery_network_monitor =
+      DiscoveryNetworkMonitor::CreateInstanceForTest(&FakeGetNetworkInfo);
 };
 
 // static
@@ -79,7 +66,7 @@
 
   net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests(
       net::NetworkChangeNotifier::CONNECTION_ETHERNET);
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 
   std::string ethernet_network_id = current_network_id;
 
@@ -89,7 +76,7 @@
 
   net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests(
       net::NetworkChangeNotifier::CONNECTION_NONE);
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 
   fake_network_info = fake_wifi_info;
   EXPECT_CALL(mock_observer, OnNetworksChanged(_))
@@ -97,7 +84,7 @@
 
   net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests(
       net::NetworkChangeNotifier::CONNECTION_WIFI);
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 
   std::string wifi_network_id = current_network_id;
   fake_network_info = fake_ethernet_info;
@@ -106,7 +93,7 @@
 
   net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests(
       net::NetworkChangeNotifier::CONNECTION_ETHERNET);
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 
   EXPECT_EQ(ethernet_network_id, current_network_id);
   EXPECT_NE(ethernet_network_id, wifi_network_id);
@@ -122,14 +109,14 @@
 
   net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests(
       net::NetworkChangeNotifier::CONNECTION_ETHERNET);
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 
   discovery_network_monitor->RemoveObserver(&mock_observer);
   fake_network_info.clear();
 
   net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests(
       net::NetworkChangeNotifier::CONNECTION_NONE);
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 }
 
 TEST_F(DiscoveryNetworkMonitorTest, RefreshIndependentOfChangeObserver) {
@@ -145,7 +132,7 @@
   };
 
   discovery_network_monitor->Refresh(base::BindOnce(force_refresh_callback));
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 }
 
 TEST_F(DiscoveryNetworkMonitorTest, GetNetworkIdWithoutRefresh) {
@@ -155,7 +142,7 @@
     EXPECT_EQ(DiscoveryNetworkMonitor::kNetworkIdDisconnected, network_id);
   };
   discovery_network_monitor->GetNetworkId(base::BindOnce(check_network_id));
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 }
 
 TEST_F(DiscoveryNetworkMonitorTest, GetNetworkIdWithRefresh) {
@@ -172,7 +159,7 @@
   };
   discovery_network_monitor->Refresh(
       base::BindOnce(capture_network_id, &current_network_id));
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 
   auto check_network_id = [](const std::string& refresh_network_id,
                              const std::string& network_id) {
@@ -180,7 +167,7 @@
   };
   discovery_network_monitor->GetNetworkId(
       base::BindOnce(check_network_id, base::ConstRef(current_network_id)));
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 }
 
 TEST_F(DiscoveryNetworkMonitorTest, GetNetworkIdWithObserver) {
@@ -191,7 +178,7 @@
 
   net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests(
       net::NetworkChangeNotifier::CONNECTION_ETHERNET);
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 
   std::string current_network_id;
   auto check_network_id = [](const std::string& network_id) {
@@ -201,5 +188,5 @@
               network_id);
   };
   discovery_network_monitor->GetNetworkId(base::BindOnce(check_network_id));
-  content::RunAllBlockingPoolTasksUntilIdle();
+  scoped_task_environment.RunUntilIdle();
 }
diff --git a/chrome/browser/media/webrtc/media_stream_device_permission_context.cc b/chrome/browser/media/webrtc/media_stream_device_permission_context.cc
index 0450d8b..477fa62 100644
--- a/chrome/browser/media/webrtc/media_stream_device_permission_context.cc
+++ b/chrome/browser/media/webrtc/media_stream_device_permission_context.cc
@@ -101,6 +101,5 @@
 }
 
 bool MediaStreamDevicePermissionContext::IsRestrictedToSecureOrigins() const {
-  return base::FeatureList::IsEnabled(
-      features::kRequireSecureOriginsForPepperMediaRequests);
+  return true;
 }
diff --git a/chrome/browser/media/webrtc/media_stream_device_permission_context_unittest.cc b/chrome/browser/media/webrtc/media_stream_device_permission_context_unittest.cc
index 5c8682c..7dbaaf09 100644
--- a/chrome/browser/media/webrtc/media_stream_device_permission_context_unittest.cc
+++ b/chrome/browser/media/webrtc/media_stream_device_permission_context_unittest.cc
@@ -67,24 +67,6 @@
                                       secure_url.GetOrigin(),
                                       content_settings_type, std::string()));
 
-    {
-      // TODO(raymes): Remove this when crbug.com/526324 is fixed.
-      base::test::ScopedFeatureList scoped_feature_list;
-      scoped_feature_list.InitAndDisableFeature(
-          features::kRequireSecureOriginsForPepperMediaRequests);
-      EXPECT_EQ(CONTENT_SETTING_ASK,
-                permission_context
-                    .GetPermissionStatus(nullptr /* render_frame_host */,
-                                         insecure_url, insecure_url)
-                    .content_setting);
-
-      EXPECT_EQ(CONTENT_SETTING_ASK,
-                permission_context
-                    .GetPermissionStatus(nullptr /* render_frame_host */,
-                                         insecure_url, secure_url)
-                    .content_setting);
-    }
-
     EXPECT_EQ(CONTENT_SETTING_BLOCK,
               permission_context
                   .GetPermissionStatus(nullptr /* render_frame_host */,
@@ -110,18 +92,6 @@
                                       content_settings_type,
                                       std::string()));
 
-    {
-      // TODO(raymes): Remove this when crbug.com/526324 is fixed.
-      base::test::ScopedFeatureList scoped_feature_list;
-      scoped_feature_list.InitAndDisableFeature(
-          features::kRequireSecureOriginsForPepperMediaRequests);
-      EXPECT_EQ(CONTENT_SETTING_ASK,
-                permission_context
-                    .GetPermissionStatus(nullptr /* render_frame_host */,
-                                         secure_url, secure_url)
-                    .content_setting);
-    }
-
     EXPECT_EQ(CONTENT_SETTING_ASK,
               permission_context
                   .GetPermissionStatus(nullptr /* render_frame_host */,
diff --git a/chrome/browser/media/webrtc/media_stream_devices_controller.cc b/chrome/browser/media/webrtc/media_stream_devices_controller.cc
index fa81065..11bd8a4 100644
--- a/chrome/browser/media/webrtc/media_stream_devices_controller.cc
+++ b/chrome/browser/media/webrtc/media_stream_devices_controller.cc
@@ -4,7 +4,6 @@
 
 #include "chrome/browser/media/webrtc/media_stream_devices_controller.h"
 
-#include <map>
 #include <utility>
 
 #include "base/callback_helpers.h"
@@ -34,7 +33,6 @@
 #include "components/prefs/scoped_user_pref_update.h"
 #include "components/url_formatter/elide_url.h"
 #include "content/public/browser/browser_thread.h"
-#include "content/public/browser/navigation_handle.h"
 #include "content/public/browser/render_frame_host.h"
 #include "content/public/browser/render_process_host.h"
 #include "content/public/browser/render_widget_host_view.h"
@@ -102,62 +100,6 @@
   }
 }
 
-// This helper class helps to measure the number of media stream requests that
-// occur. It ensures that only one request will be recorded per navigation, per
-// frame. TODO(raymes): Remove this when https://crbug.com/526324 is fixed.
-class MediaPermissionRequestLogger : content::WebContentsObserver {
-  // Map of <render process id, render frame id> ->
-  // MediaPermissionRequestLogger.
-  using RequestMap = std::map<std::pair<int, int>,
-                              std::unique_ptr<MediaPermissionRequestLogger>>;
-
- public:
-  static void LogRequest(content::WebContents* contents,
-                         int render_process_id,
-                         int render_frame_id,
-                         bool is_secure) {
-    RequestMap::key_type key =
-        std::make_pair(render_process_id, render_frame_id);
-    if (!base::ContainsKey(GetRequestMap(), key)) {
-      UMA_HISTOGRAM_BOOLEAN("Pepper.SecureOrigin.MediaStreamRequest",
-                            is_secure);
-      GetRequestMap()[key] =
-          base::WrapUnique(new MediaPermissionRequestLogger(contents, key));
-    }
-  }
-
- private:
-  MediaPermissionRequestLogger(content::WebContents* contents,
-                               RequestMap::key_type key)
-      : WebContentsObserver(contents), key_(key) {}
-
-  void PageChanged(content::RenderFrameHost* render_frame_host) {
-    if (std::make_pair(render_frame_host->GetProcess()->GetID(),
-                       render_frame_host->GetRoutingID()) == key_) {
-      GetRequestMap().erase(key_);
-    }
-  }
-
-  static RequestMap& GetRequestMap() {
-    CR_DEFINE_STATIC_LOCAL(RequestMap, request_map, ());
-    return request_map;
-  }
-
-  // content::WebContentsObserver overrides
-  void DidFinishNavigation(
-      content::NavigationHandle* navigation_handle) override {
-    if (navigation_handle->HasCommitted())
-      PageChanged(navigation_handle->GetRenderFrameHost());
-  }
-
-  void RenderFrameDeleted(
-      content::RenderFrameHost* render_frame_host) override {
-    PageChanged(render_frame_host);
-  }
-
-  RequestMap::key_type key_;
-};
-
 bool HasAvailableDevices(ContentSettingsType content_type,
                          const std::string& device_id) {
   const content::MediaStreamDevices* devices = nullptr;
@@ -455,12 +397,6 @@
   }
   content::WebContents* web_contents =
       content::WebContents::FromRenderFrameHost(rfh);
-  if (request.request_type == content::MEDIA_OPEN_DEVICE_PEPPER_ONLY) {
-    MediaPermissionRequestLogger::LogRequest(
-        web_contents, request.render_process_id, request.render_frame_id,
-        content::IsOriginSecure(request.security_origin));
-  }
-
   std::unique_ptr<MediaStreamDevicesController> controller(
       new MediaStreamDevicesController(web_contents, request, callback));
 
diff --git a/chrome/browser/media/webrtc/media_stream_devices_controller_browsertest.cc b/chrome/browser/media/webrtc/media_stream_devices_controller_browsertest.cc
index 0828ef3..ae32f7f 100644
--- a/chrome/browser/media/webrtc/media_stream_devices_controller_browsertest.cc
+++ b/chrome/browser/media/webrtc/media_stream_devices_controller_browsertest.cc
@@ -845,41 +845,12 @@
   ASSERT_TRUE(CheckDevicesListContains(content::MEDIA_DEVICE_VIDEO_CAPTURE));
 }
 
-// For Pepper request from insecure origin, even if it's ALLOW, it won't be
-// changed to ASK.
 IN_PROC_BROWSER_TEST_P(MediaStreamDevicesControllerTest,
                        PepperRequestInsecure) {
   InitWithUrl(GURL("http://www.example.com"));
 
   SetPromptResponseType(PermissionRequestManager::ACCEPT_ALL);
 
-  {
-    // Test that with the kRequireSecureOriginsForPepperMediaRequests flag
-    // disabled that permission will be denied. TODO(raymes): Remove this when
-    // crbug.com/526324 is fixed.
-    base::test::ScopedFeatureList scoped_feature_list;
-    if (GetParam() == TestType::TEST_WITH_GROUPED_MEDIA_REQUESTS) {
-      scoped_feature_list.InitWithFeatures(
-          {features::kUsePermissionManagerForMediaRequests},
-          {features::kRequireSecureOriginsForPepperMediaRequests});
-    } else {
-      scoped_feature_list.InitWithFeatures(
-          {}, {features::kUsePermissionManagerForMediaRequests,
-               features::kRequireSecureOriginsForPepperMediaRequests});
-    }
-    RequestPermissions(
-        GetWebContents(),
-        CreateRequestWithType(example_audio_id(), std::string(),
-                              content::MEDIA_OPEN_DEVICE_PEPPER_ONLY),
-        base::Bind(&MediaStreamDevicesControllerTest::OnMediaStreamResponse,
-                   base::Unretained(this)));
-    ASSERT_EQ(2u, TotalPromptRequestCount());
-
-    ASSERT_EQ(content::MEDIA_DEVICE_OK, media_stream_result());
-    ASSERT_TRUE(CheckDevicesListContains(content::MEDIA_DEVICE_AUDIO_CAPTURE));
-    ASSERT_FALSE(CheckDevicesListContains(content::MEDIA_DEVICE_VIDEO_CAPTURE));
-  }
-
   ResetPromptCounters();
   RequestPermissions(
       GetWebContents(),
diff --git a/chrome/browser/resources/chromeos/login/oobe_welcome.html b/chrome/browser/resources/chromeos/login/oobe_welcome.html
index 834a00936..57a045a3 100644
--- a/chrome/browser/resources/chromeos/login/oobe_welcome.html
+++ b/chrome/browser/resources/chromeos/login/oobe_welcome.html
@@ -84,7 +84,7 @@
     <link rel="stylesheet" href="oobe_dialog_parameters.css">
     <link rel="stylesheet" href="oobe_flex_layout.css">
     <oobe-welcome-dialog id="welcomeScreen" role="dialog"
-        i18n-values="aria-label:networkScreenGreeting"
+        aria-label="[[i18nDynamic(locale, 'networkScreenGreeting')]]"
         current-language="[[currentLanguage]]"
         on-language-button-clicked="onWelcomeSelectLanguageButtonClicked_"
         on-accessibility-button-clicked="onWelcomeAccessibilityButtonClicked_"
@@ -96,7 +96,7 @@
         debugging-link-visible="[[debuggingLinkVisible]]">
     </oobe-welcome-dialog>
     <oobe-dialog id="languageScreen" role="dialog" hidden has-buttons
-        i18n-values="aria-label:languageSectionTitle">
+        aria-label="[[i18nDynamic(locale, 'languageSectionTitle')]]">
       <hd-iron-icon class="oobe-icon"
           icon1x="oobe-welcome-32:language" icon2x="oobe-welcome-64:language">
       </hd-iron-icon>
@@ -113,9 +113,9 @@
               [[i18nDynamic(locale, 'languageDropdownTitle')]]
             </div>
             <oobe-i18n-dropdown id="languageSelect" items="[[languages]]"
-                on-select-item="onLanguageSelected_"
-                class="focus-on-show"
-                i18n-values="label-for-aria:languageDropdownLabel">
+                on-select-item="onLanguageSelected_" class="focus-on-show"
+                label-for-aria=
+                    "[[i18nDynamic(locale, 'languageDropdownLabel')]]">
             </oobe-i18n-dropdown>
           </div>
           <div id="keyboardDropdownContainer"
@@ -127,7 +127,8 @@
             </div>
             <oobe-i18n-dropdown id="keyboardSelect" items="[[keyboards]]"
                 on-select-item="onKeyboardSelected_"
-                i18n-values="label-for-aria:keyboardDropdownLabel">
+                label-for-aria=
+                    "[[i18nDynamic(locale, 'keyboardDropdownLabel')]]">
             </oobe-i18n-dropdown>
           </div>
         </template>
@@ -139,7 +140,7 @@
       </div>
     </oobe-dialog>
     <oobe-dialog id="accessibilityScreen" role="dialog" hidden has-buttons
-        i18n-values="aria-label:accessibilitySectionTitle">
+        aria-label="[[i18nDynamic(locale, 'accessibilitySectionTitle')]]">
       <hd-iron-icon class="oobe-icon"
           icon1x="oobe-welcome-32:accessibility"
           icon2x="oobe-welcome-64:accessibility">
@@ -156,7 +157,7 @@
         <oobe-a11y-option checked="[[a11yStatus.spokenFeedbackEnabled]]"
             on-change="onA11yOptionChanged_"
             chrome-message="enableSpokenFeedback"
-            i18n-values="label-for-aria:spokenFeedbackOption"
+            label-for-aria="[[i18nDynamic(locale, 'spokenFeedbackOption')]]"
             class="focus-on-show">
           <span class="title">
             [[i18nDynamic(locale, 'spokenFeedbackOption')]]
@@ -169,9 +170,8 @@
           </span>
         </oobe-a11y-option>
         <oobe-a11y-option checked="[[a11yStatus.largeCursorEnabled]]"
-            on-change="onA11yOptionChanged_"
-            chrome-message="enableLargeCursor"
-            i18n-values="label-for-aria:largeCursorOption">
+            on-change="onA11yOptionChanged_" chrome-message="enableLargeCursor"
+            label-for-aria="[[i18nDynamic(locale, 'largeCursorOption')]]">
           <span class="title">
             [[i18nDynamic(locale, 'largeCursorOption')]]
           </span>
@@ -183,9 +183,8 @@
           </span>
         </oobe-a11y-option>
         <oobe-a11y-option checked="[[a11yStatus.highContrastEnabled]]"
-            on-change="onA11yOptionChanged_"
-            chrome-message="enableHighContrast"
-            i18n-values="label-for-aria:highContrastOption">
+            on-change="onA11yOptionChanged_" chrome-message="enableHighContrast"
+            label-for-aria="[[i18nDynamic(locale, 'highContrastOption')]]">
           <span class="title">
             [[i18nDynamic(locale, 'highContrastOption')]]
           </span>
@@ -199,7 +198,7 @@
         <oobe-a11y-option checked="[[a11yStatus.screenMagnifierEnabled]]"
             on-change="onA11yOptionChanged_"
             chrome-message="enableScreenMagnifier"
-            i18n-values="label-for-aria:screenMagnifierOption">
+            label-for-aria="[[i18nDynamic(locale, 'screenMagnifierOption')]]">
           <span class="title">
             [[i18nDynamic(locale, 'screenMagnifierOption')]]
           </span>
@@ -213,7 +212,7 @@
         <oobe-a11y-option checked="[[a11yStatus.virtualKeyboardEnabled]]"
             on-change="onA11yOptionChanged_"
             chrome-message="enableVirtualKeyboard"
-            i18n-values="label-for-aria:virtualKeyboardOption">
+            label-for-aria="[[i18nDynamic(locale, 'virtualKeyboardOption')]]">
           <span class="title">
             [[i18nDynamic(locale, 'virtualKeyboardOption')]]
           </span>
@@ -232,7 +231,7 @@
       </div>
     </oobe-dialog>
     <oobe-dialog id="timezoneScreen" role="dialog" hidden has-buttons
-        i18n-values="aria-label:timezoneSectionTitle">
+        aria-label="[[i18nDynamic(locale, 'timezoneSectionTitle')]]">
       <hd-iron-icon class="oobe-icon"
           icon1x="oobe-welcome-32:timezone" icon2x="oobe-welcome-64:timezone">
       </hd-iron-icon>
@@ -248,7 +247,7 @@
           </div>
           <oobe-i18n-dropdown id="timezoneSelect" items="[[timezones]]"
               on-select-item="onTimezoneSelected_"
-              i18n-values="label-for-aria:timezoneDropdownLabel"
+              label-for-aria="[i18nDynamic(locale, 'timezoneDropdownLabel')]]"
               class="focus-on-show">
           </oobe-i18n-dropdown>
         </div>
@@ -260,7 +259,7 @@
       </div>
     </oobe-dialog>
     <oobe-dialog id="oobeAdvancedOptionsScreen" role="dialog" hidden has-buttons
-        i18n-values="aria-label:advancedOptionsSectionTitle">
+        aria-label="[[i18nDynamic(locale, 'advancedOptionsSectionTitle')]]">
       <div id="oobeBoxIcon" class="oobe-icon"></div>
       <div class="header">
         <h1 class="title">
@@ -303,7 +302,7 @@
       </div>
     </oobe-dialog>
     <oobe-dialog id="networkSelectionScreen" role="dialog" hidden has-buttons
-        i18n-values="aria-label:networkSectionTitle"
+        aria-label="[[i18nDynamic(locale, 'networkSectionTitle')]]"
         on-show-dialog="onNetworkSelectionScreenShown_">
       <hd-iron-icon class="oobe-icon"
           icon1x="oobe-welcome-32:wifi" icon2x="oobe-welcome-64:wifi">
diff --git a/chrome/browser/resources/chromeos/login/oobe_welcome.js b/chrome/browser/resources/chromeos/login/oobe_welcome.js
index fa124350..7500d0c 100644
--- a/chrome/browser/resources/chromeos/login/oobe_welcome.js
+++ b/chrome/browser/resources/chromeos/login/oobe_welcome.js
@@ -134,6 +134,7 @@
       proxySettingsMenuName: loadTimeData.getString('proxySettingsMenuName'),
     };
 
+    this.$.welcomeScreen.i18nUpdateLocale();
     this.i18nUpdateLocale();
   },
 
diff --git a/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.html b/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.html
index 980ee6ec..f06e30b 100644
--- a/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.html
+++ b/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.html
@@ -3,6 +3,7 @@
      found in the LICENSE file. -->
 
 <link rel="import" href="chrome://resources/polymer/v1_0/paper-styles/color.html">
+<link rel="import" href="chrome://resources/html/i18n_behavior.html">
 
 <!--
   OOBE Welcome screen
@@ -15,13 +16,14 @@
     <div class="layout horizontal flex">
       <div class="vertical-margin"></div>
       <div class="welcome-content flex layout vertical center">
-        <h1 id="title" i18n-content="networkScreenGreeting"></h1>
+        <h1 id="title">[[i18nDynamic(locale, 'networkScreenGreeting')]]</h1>
         <img id="welcomeIllustration"
             srcset="images/welcome_illustration_1x.png 1x,
                     images/welcome_illustration_2x.png 2x">
         <div hidden="[[!debuggingLinkVisible]]">
-          <a href="#" i18n-content="debuggingFeaturesLink"
-              on-tap="onDebuggingLinkClicked_"></a>
+          <a href="#" on-tap="onDebuggingLinkClicked_">
+            [[i18nDynamic(locale, 'debuggingFeaturesLink')]]
+          </a>
         </div>
         <div class="flex"></div>
         <div id="buttons" class="layout horizontal center">
@@ -37,19 +39,19 @@
               icon1x="oobe-welcome-32:accessibility"
               icon2x="oobe-welcome-64:accessibility"
               on-tap="onAccessibilityClicked_">
-            <div i18n-content="accessibilityLink"></div>
+            <div>[[i18nDynamic(locale, 'accessibilityLink')]]</div>
           </oobe-welcome-secondary-button>
           <oobe-welcome-secondary-button id="timezoneSettingsButton"
               icon1x="oobe-welcome-32:timezone"
               icon2x="oobe-welcome-64:timezone"
               on-tap="onTimezoneClicked_"
               hidden="[[!timezoneButtonVisible]]">
-            <div i18n-content="timezoneButtonText"></div>
+            <div>[[i18nDynamic(locale, 'timezoneButtonText')]]</div>
           </oobe-welcome-secondary-button>
           <div class="flex"></div>
           <oobe-text-button id="welcomeNextButton"
               inverse on-tap="onNextClicked_">
-            <div i18n-content="welcomeNextButtonText"></div>
+            <div>[[i18nDynamic(locale, 'welcomeNextButtonText')]]</div>
           </oobe-text-button>
         </div>
         <div id="bottom-margin"></div>
diff --git a/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.js b/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.js
index 2a641e3..ced59e5 100644
--- a/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.js
+++ b/chrome/browser/resources/chromeos/login/oobe_welcome_dialog.js
@@ -59,6 +59,9 @@
 
   Polymer({
     is: 'oobe-welcome-dialog',
+
+    behaviors: [I18nBehavior],
+
     properties: {
       /**
        * Currently selected system language (display name).
diff --git a/chrome/browser/resources/md_extensions/detail_view.html b/chrome/browser/resources/md_extensions/detail_view.html
index c94089a..63cf959 100644
--- a/chrome/browser/resources/md_extensions/detail_view.html
+++ b/chrome/browser/resources/md_extensions/detail_view.html
@@ -20,13 +20,14 @@
     <style include=
         "iron-flex cr-hidden-style cr-icons action-link paper-toggle-style">
       :host {
-        display: flex;
-        justify-content: center;
+        display: block;
+        height: 100%;
+        overflow: auto;
       }
 
       #main {
         background-color: white;
-        height: 100%;
+        margin: auto;
         width: 640px;
       }
 
diff --git a/chrome/browser/resources/md_user_manager/control_bar.js b/chrome/browser/resources/md_user_manager/control_bar.js
index 5e22faf..b58e5815 100644
--- a/chrome/browser/resources/md_user_manager/control_bar.js
+++ b/chrome/browser/resources/md_user_manager/control_bar.js
@@ -52,14 +52,14 @@
    * @private
    */
   onLaunchGuestTap_: function(event) {
-    this.browserProxy_.areAllProfilesLocked().then(function(allProfilesLocked) {
+    this.browserProxy_.areAllProfilesLocked().then(allProfilesLocked => {
       if (!allProfilesLocked || this.isForceSigninEnabled_) {
         this.browserProxy_.launchGuestUser();
       } else {
         document.querySelector('error-dialog')
             .show(this.i18n('browseAsGuestAllProfilesLockedError'));
       }
-    }.bind(this));
+    });
   },
 
   /**
@@ -68,7 +68,7 @@
    * @private
    */
   onAddUserTap_: function(event) {
-    this.browserProxy_.areAllProfilesLocked().then(function(allProfilesLocked) {
+    this.browserProxy_.areAllProfilesLocked().then(allProfilesLocked => {
       if (!allProfilesLocked || this.isForceSigninEnabled_) {
         // Event is caught by user-manager-pages.
         this.fire('change-page', {page: 'create-user-page'});
@@ -76,6 +76,6 @@
         document.querySelector('error-dialog')
             .show(this.i18n('addProfileAllProfilesLockedError'));
       }
-    }.bind(this));
+    });
   }
 });
diff --git a/chrome/browser/resources/md_user_manager/create_profile.js b/chrome/browser/resources/md_user_manager/create_profile.js
index 59deaa4..05b9f68b 100644
--- a/chrome/browser/resources/md_user_manager/create_profile.js
+++ b/chrome/browser/resources/md_user_manager/create_profile.js
@@ -154,9 +154,9 @@
         'create-profile-warning', this.handleMessage_.bind(this));
     this.addWebUIListener(
         'create-profile-error', this.handleMessage_.bind(this));
-    this.addWebUIListener('profile-icons-received', function(icons) {
+    this.addWebUIListener('profile-icons-received', icons => {
       this.availableIcons_ = icons;
-    }.bind(this));
+    });
     this.addWebUIListener(
         'profile-defaults-received', this.handleProfileDefaults_.bind(this));
     this.addWebUIListener(
diff --git a/chrome/browser/resources/settings/people_page/easy_unlock_turn_off_dialog.html b/chrome/browser/resources/settings/people_page/easy_unlock_turn_off_dialog.html
index a393ad2..b4acc33 100644
--- a/chrome/browser/resources/settings/people_page/easy_unlock_turn_off_dialog.html
+++ b/chrome/browser/resources/settings/people_page/easy_unlock_turn_off_dialog.html
@@ -17,7 +17,7 @@
       <div slot="body">
         [[getDescriptionText_(status_)]]
       </div>
-      <div slot="button-container">
+      <div slot="button-container"
           hidden="[[isButtonBarHidden_(status_)]]">
         <paper-spinner active="[[isSpinnerActive_(status_)]]">
         </paper-spinner>
diff --git a/chrome/browser/resources/settings/settings_page/settings_section.js b/chrome/browser/resources/settings/settings_page/settings_section.js
index 9ee94f57..acf75000 100644
--- a/chrome/browser/resources/settings/settings_page/settings_section.js
+++ b/chrome/browser/resources/settings/settings_page/settings_section.js
@@ -97,6 +97,14 @@
   },
 
   /**
+   * Calling this method fires the 'settings-section-expanded event'.
+   */
+  setExpanded_: function() {
+    this.classList.add('expanded');
+    this.fire('settings-section-expanded');
+  },
+
+  /**
    * @return {boolean} True if the section is currently rendered and not
    *     already expanded or transitioning.
    */
@@ -113,7 +121,7 @@
     this.$.card.top = containerTop + 'px';
     this.$.card.height = 'calc(100% - ' + containerTop + 'px)';
 
-    this.classList.add('expanded');
+    this.setExpanded_();
   },
 
   /**
@@ -146,17 +154,13 @@
 
     var animation =
         this.animateCard_('fixed', startTop, endTop, startHeight, endHeight);
-    animation.finished
-        .then(
-            () => {
-              this.classList.add('expanded');
-            },
-            function() {})
-        .then(() => {
-          // Unset these changes whether the animation finished or canceled.
-          this.classList.remove('expanding');
-          this.style.height = '';
-        });
+    // The empty onRejected function prevents the promise from skipping forward
+    // to the next then() with a rejection callback.
+    animation.finished.then(this.setExpanded_.bind(this), () => {}).then(() => {
+      // Unset these changes whether the animation finished or canceled.
+      this.classList.remove('expanding');
+      this.style.height = '';
+    });
     return animation;
   },
 
diff --git a/chrome/browser/supervised_user/legacy/supervised_user_shared_settings_service.cc b/chrome/browser/supervised_user/legacy/supervised_user_shared_settings_service.cc
index d537b4d..9db94e8 100644
--- a/chrome/browser/supervised_user/legacy/supervised_user_shared_settings_service.cc
+++ b/chrome/browser/supervised_user/legacy/supervised_user_shared_settings_service.cc
@@ -115,7 +115,7 @@
         key, base::MakeUnique<base::DictionaryValue>());
   }
   dict->SetWithoutPathExpansion(kValue, base::MakeUnique<base::Value>(value));
-  dict->SetBooleanWithoutPathExpansion(kAcknowledged, acknowledged);
+  dict->SetKey(kAcknowledged, base::Value(acknowledged));
 
   if (!sync_processor_)
     return;
@@ -236,8 +236,8 @@
     // Every setting we get from the server should have the acknowledged flag
     // set.
     DCHECK(supervised_user_shared_setting.acknowledged());
-    dict->SetBooleanWithoutPathExpansion(
-        kAcknowledged, supervised_user_shared_setting.acknowledged());
+    dict->SetKey(kAcknowledged,
+                 base::Value(supervised_user_shared_setting.acknowledged()));
     callbacks_.Notify(su_id, key);
 
     if (pref_seen_keys.find(su_id) == pref_seen_keys.end())
@@ -348,8 +348,9 @@
         std::unique_ptr<Value> value =
             base::JSONReader::Read(supervised_user_shared_setting.value());
         dict->SetWithoutPathExpansion(kValue, std::move(value));
-        dict->SetBooleanWithoutPathExpansion(
-            kAcknowledged, supervised_user_shared_setting.acknowledged());
+        dict->SetKey(
+            kAcknowledged,
+            base::Value(supervised_user_shared_setting.acknowledged()));
         break;
       }
       case SyncChange::ACTION_DELETE: {
diff --git a/chrome/browser/supervised_user/supervised_user_browsertest.cc b/chrome/browser/supervised_user/supervised_user_browsertest.cc
index 6af9d87..4bbd701 100644
--- a/chrome/browser/supervised_user/supervised_user_browsertest.cc
+++ b/chrome/browser/supervised_user/supervised_user_browsertest.cc
@@ -343,7 +343,7 @@
 
   // Set the host as allowed.
   std::unique_ptr<base::DictionaryValue> dict(new base::DictionaryValue);
-  dict->SetBooleanWithoutPathExpansion(allowed_url.host(), true);
+  dict->SetKey(allowed_url.host(), base::Value(true));
   SupervisedUserSettingsService* supervised_user_settings_service =
       SupervisedUserSettingsServiceFactory::GetForProfile(
           browser()->profile());
@@ -406,7 +406,7 @@
 
   // Set the host as blocked and wait for the interstitial to appear.
   auto dict = base::MakeUnique<base::DictionaryValue>();
-  dict->SetBooleanWithoutPathExpansion(test_url.host(), false);
+  dict->SetKey(test_url.host(), base::Value(false));
   SupervisedUserSettingsService* supervised_user_settings_service =
       SupervisedUserSettingsServiceFactory::GetForProfile(
           browser()->profile());
@@ -449,7 +449,7 @@
 
   // Set the host as blocked and wait for the interstitial to appear.
   auto dict = base::MakeUnique<base::DictionaryValue>();
-  dict->SetBooleanWithoutPathExpansion(test_url.host(), false);
+  dict->SetKey(test_url.host(), base::Value(false));
   SupervisedUserSettingsService* supervised_user_settings_service =
       SupervisedUserSettingsServiceFactory::GetForProfile(browser()->profile());
   auto message_loop_runner = base::MakeRefCounted<content::MessageLoopRunner>();
@@ -486,7 +486,7 @@
 
   // Set the host as blocked and wait for the interstitial to appear.
   auto dict = base::MakeUnique<base::DictionaryValue>();
-  dict->SetBooleanWithoutPathExpansion(test_url.host(), false);
+  dict->SetKey(test_url.host(), base::Value(false));
   SupervisedUserSettingsService* supervised_user_settings_service =
       SupervisedUserSettingsServiceFactory::GetForProfile(
           browser()->profile());
@@ -504,7 +504,7 @@
   ASSERT_TRUE(ShownPageIsInterstitial(web_contents));
 
   dict = base::MakeUnique<base::DictionaryValue>();
-  dict->SetBooleanWithoutPathExpansion(test_url.host(), true);
+  dict->SetKey(test_url.host(), base::Value(true));
   supervised_user_settings_service->SetLocalSetting(
       supervised_users::kContentPackManualBehaviorHosts, std::move(dict));
   ASSERT_EQ(SupervisedUserURLFilter::ALLOW,
@@ -530,7 +530,7 @@
 
   // Set the host as allowed.
   std::unique_ptr<base::DictionaryValue> dict(new base::DictionaryValue);
-  dict->SetBooleanWithoutPathExpansion(test_url.host(), true);
+  dict->SetKey(test_url.host(), base::Value(true));
   SupervisedUserSettingsService* supervised_user_settings_service =
       SupervisedUserSettingsServiceFactory::GetForProfile(
           browser()->profile());
diff --git a/chrome/browser/supervised_user/supervised_user_navigation_throttle_browsertest.cc b/chrome/browser/supervised_user/supervised_user_navigation_throttle_browsertest.cc
index 179b75a6..2bb533f 100644
--- a/chrome/browser/supervised_user/supervised_user_navigation_throttle_browsertest.cc
+++ b/chrome/browser/supervised_user/supervised_user_navigation_throttle_browsertest.cc
@@ -51,7 +51,7 @@
     SupervisedUserSettingsService* settings_service =
         SupervisedUserSettingsServiceFactory::GetForProfile(profile);
     auto dict = base::MakeUnique<base::DictionaryValue>();
-    dict->SetBooleanWithoutPathExpansion(host, false);
+    dict->SetKey(host, base::Value(false));
     settings_service->SetLocalSetting(
         supervised_users::kContentPackManualBehaviorHosts, std::move(dict));
   }
diff --git a/chrome/browser/ui/app_list/arc/arc_app_list_prefs.cc b/chrome/browser/ui/app_list/arc/arc_app_list_prefs.cc
index 767b277..ec46dad 100644
--- a/chrome/browser/ui/app_list/arc/arc_app_list_prefs.cc
+++ b/chrome/browser/ui/app_list/arc/arc_app_list_prefs.cc
@@ -97,7 +97,7 @@
     DictionaryPrefUpdate update(prefs_,
                                 prefs::kArcSetNotificationsEnabledDeferred);
     base::DictionaryValue* const dict = update.Get();
-    dict->SetBooleanWithoutPathExpansion(app_id, enabled);
+    dict->SetKey(app_id, base::Value(enabled));
   }
 
   bool Get(const std::string& app_id, bool* enabled) {
diff --git a/chrome/browser/ui/app_list/arc/arc_app_utils.cc b/chrome/browser/ui/app_list/arc/arc_app_utils.cc
index 8c52664..b3c89682 100644
--- a/chrome/browser/ui/app_list/arc/arc_app_utils.cc
+++ b/chrome/browser/ui/app_list/arc/arc_app_utils.cc
@@ -77,6 +77,12 @@
 constexpr char kIntentPrefix[] = "#Intent";
 constexpr char kLaunchFlags[] = "launchFlags";
 
+constexpr char kAndroidClockAppId[] = "ddmmnabaeomoacfpfjgghfpocfolhjlg";
+
+constexpr char const* kAppIdsHiddenInLauncher[] = {
+    kAndroidClockAppId, kSettingsAppId,
+};
+
 // Find a proper size and position for a given rectangle on the screen.
 // TODO(skuhne): This needs more consideration, but it is lacking
 // WindowPositioner functionality since we do not have an Aura::Window yet.
@@ -246,7 +252,11 @@
 const char kInitialStartParam[] = "S.org.chromium.arc.start_type=initialStart";
 
 bool ShouldShowInLauncher(const std::string& app_id) {
-  return app_id != kSettingsAppId;
+  for (auto* const id : kAppIdsHiddenInLauncher) {
+    if (id == app_id)
+      return false;
+  }
+  return true;
 }
 
 bool LaunchAndroidSettingsApp(content::BrowserContext* context,
diff --git a/chrome/browser/ui/app_list/search/search_controller_factory.cc b/chrome/browser/ui/app_list/search/search_controller_factory.cc
index 30740cd..6ae06f8 100644
--- a/chrome/browser/ui/app_list/search/search_controller_factory.cc
+++ b/chrome/browser/ui/app_list/search/search_controller_factory.cc
@@ -89,12 +89,13 @@
       base::MakeUnique<AppSearchProvider>(
           profile, list_controller, base::MakeUnique<base::DefaultClock>(),
           model->top_level_item_list()));
-  controller->AddProvider(
-      omnibox_group_id,
-      base::MakeUnique<OmniboxProvider>(profile, list_controller));
-  controller->AddProvider(
-      webstore_group_id,
-      base::MakeUnique<WebstoreProvider>(profile, list_controller));
+  controller->AddProvider(omnibox_group_id, base::MakeUnique<OmniboxProvider>(
+                                                profile, list_controller));
+  if (!features::IsPlayStoreAppSearchEnabled()) {
+    controller->AddProvider(
+        webstore_group_id,
+        base::MakeUnique<WebstoreProvider>(profile, list_controller));
+  }
   if (features::IsAnswerCardEnabled()) {
     controller->AddProvider(
         answer_card_group_id,
diff --git a/chrome/browser/ui/ash/ash_init.cc b/chrome/browser/ui/ash/ash_init.cc
index 58beeeb1..8786dc4 100644
--- a/chrome/browser/ui/ash/ash_init.cc
+++ b/chrome/browser/ui/ash/ash_init.cc
@@ -71,9 +71,13 @@
   // its own callback to detect when the connection to mus is lost and that is
   // what shuts everything down.
   window_manager->SetLostConnectionCallback(base::BindOnce(&base::DoNothing));
+  // When Ash runs in the same services as chrome content creates the
+  // DiscardableSharedMemoryManager.
+  const bool create_discardable_memory = false;
   std::unique_ptr<aura::WindowTreeClient> window_tree_client =
-      base::MakeUnique<aura::WindowTreeClient>(connector, window_manager.get(),
-                                               window_manager.get());
+      base::MakeUnique<aura::WindowTreeClient>(
+          connector, window_manager.get(), window_manager.get(), nullptr,
+          nullptr, create_discardable_memory);
   const bool automatically_create_display_roots = false;
   window_tree_client->ConnectAsWindowManager(
       automatically_create_display_roots);
diff --git a/chrome/browser/ui/ash/keyboard_controller_browsertest.cc b/chrome/browser/ui/ash/keyboard_controller_browsertest.cc
index 964e183..6ca85e0 100644
--- a/chrome/browser/ui/ash/keyboard_controller_browsertest.cc
+++ b/chrome/browser/ui/ash/keyboard_controller_browsertest.cc
@@ -114,33 +114,6 @@
   EXPECT_FALSE(IsKeyboardVisible());
 }
 
-// Test for crbug.com/489366. In FLOATING mode, switch to a new IME in a
-// different extension should exit FLOATING mode and position the new IME in
-// FULL_WIDTH mode.
-IN_PROC_BROWSER_TEST_F(VirtualKeyboardWebContentTest,
-                       IMEInDifferentExtensionNotCentered) {
-  gfx::Rect test_bounds(0, 0, 0, kKeyboardHeightForTest);
-  FocusEditableNodeAndShowKeyboard(test_bounds);
-  keyboard::KeyboardController* controller =
-      keyboard::KeyboardController::GetInstance();
-  const gfx::Rect& screen_bounds = ash::Shell::GetPrimaryRootWindow()->bounds();
-  gfx::Rect keyboard_bounds = controller->GetContainerWindow()->bounds();
-  EXPECT_EQ(kKeyboardHeightForTest, keyboard_bounds.height());
-  EXPECT_EQ(screen_bounds.height(),
-            keyboard_bounds.height() + keyboard_bounds.y());
-  controller->SetKeyboardMode(keyboard::FLOATING);
-  // Move keyboard to a random place.
-  ui()->GetContentsWindow()->SetBounds(gfx::Rect(50, 50, 50, 50));
-  EXPECT_EQ(gfx::Rect(50, 50, 50, 50),
-            controller->GetContainerWindow()->bounds());
-
-  MockEnableIMEInDifferentExtension("chrome-extension://domain-1", test_bounds);
-  keyboard_bounds = controller->GetContainerWindow()->bounds();
-  EXPECT_EQ(kKeyboardHeightForTest, keyboard_bounds.height());
-  EXPECT_EQ(screen_bounds.height(),
-            keyboard_bounds.height() + keyboard_bounds.y());
-}
-
 class VirtualKeyboardAppWindowTest : public extensions::PlatformAppBrowserTest {
  public:
   VirtualKeyboardAppWindowTest() {}
diff --git a/chrome/browser/ui/ash/palette_delegate_chromeos.cc b/chrome/browser/ui/ash/palette_delegate_chromeos.cc
index 5ebe4f4..0ef322db 100644
--- a/chrome/browser/ui/ash/palette_delegate_chromeos.cc
+++ b/chrome/browser/ui/ash/palette_delegate_chromeos.cc
@@ -28,6 +28,8 @@
 
 namespace chromeos {
 
+constexpr int kMetalayerSelectionDelayMs = 600;
+
 class VoiceInteractionSelectionObserver
     : public ash::HighlighterSelectionObserver {
  public:
@@ -37,6 +39,18 @@
 
  private:
   void HandleSelection(const gfx::Rect& rect) override {
+    // Delay the actual voice interaction service invocation for better
+    // visual synchronization with the metalayer animation.
+    delay_timer_ = base::MakeUnique<base::Timer>(
+        FROM_HERE,
+        base::TimeDelta::FromMilliseconds(kMetalayerSelectionDelayMs),
+        base::Bind(&VoiceInteractionSelectionObserver::ReportSelection,
+                   base::Unretained(this), rect),
+        false /* not repeating */);
+    delay_timer_->Reset();
+  }
+
+  void ReportSelection(const gfx::Rect& rect) {
     auto* framework =
         arc::ArcVoiceInteractionFrameworkService::GetForBrowserContext(
             profile_);
@@ -47,6 +61,8 @@
 
   Profile* const profile_;  // Owned by ProfileManager.
 
+  std::unique_ptr<base::Timer> delay_timer_;
+
   DISALLOW_COPY_AND_ASSIGN(VoiceInteractionSelectionObserver);
 };
 
diff --git a/chrome/browser/ui/webui/chromeos/login/network_screen_handler.cc b/chrome/browser/ui/webui/chromeos/login/network_screen_handler.cc
index 749ec57..0cdd481 100644
--- a/chrome/browser/ui/webui/chromeos/login/network_screen_handler.cc
+++ b/chrome/browser/ui/webui/chromeos/login/network_screen_handler.cc
@@ -28,6 +28,7 @@
 #include "chrome/browser/chromeos/system/timezone_util.h"
 #include "chrome/browser/ui/webui/chromeos/login/l10n_util.h"
 #include "chrome/browser/ui/webui/chromeos/login/oobe_ui.h"
+#include "chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.h"
 #include "chrome/common/pref_names.h"
 #include "chrome/grit/generated_resources.h"
 #include "chromeos/chromeos_switches.h"
@@ -204,6 +205,7 @@
 
   builder->Add("timezoneDropdownTitle", IDS_TIMEZONE_DROPDOWN_TITLE);
   builder->Add("timezoneButtonText", IDS_TIMEZONE_BUTTON_TEXT);
+  network_element::AddLocalizedValuesToBuilder(builder);
 }
 
 void NetworkScreenHandler::GetAdditionalParameters(
diff --git a/chrome/browser/ui/webui/chromeos/login/oobe_ui.cc b/chrome/browser/ui/webui/chromeos/login/oobe_ui.cc
index b811e7a9..c0a4755e 100644
--- a/chrome/browser/ui/webui/chromeos/login/oobe_ui.cc
+++ b/chrome/browser/ui/webui/chromeos/login/oobe_ui.cc
@@ -62,7 +62,6 @@
 #include "chrome/browser/ui/webui/chromeos/login/voice_interaction_value_prop_screen_handler.h"
 #include "chrome/browser/ui/webui/chromeos/login/wait_for_container_ready_screen_handler.h"
 #include "chrome/browser/ui/webui/chromeos/login/wrong_hwid_screen_handler.h"
-#include "chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.h"
 #include "chrome/browser/ui/webui/chromeos/user_image_source.h"
 #include "chrome/browser/ui/webui/test_files_request_filter.h"
 #include "chrome/browser/ui/webui/theme_source.h"
@@ -358,7 +357,6 @@
   content::WebUIDataSource* html_source =
       CreateOobeUIDataSource(localized_strings, display_type_);
   content::WebUIDataSource::Add(profile, html_source);
-  network_element::AddLocalizedStrings(html_source);
 
   // Set up the chrome://userimage/ source.
   UserImageSource* user_image_source = new UserImageSource();
diff --git a/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.cc b/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.cc
index b589e1f9..ef5eb81 100644
--- a/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.cc
+++ b/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.cc
@@ -6,31 +6,42 @@
 
 #include "build/build_config.h"
 #include "chrome/grit/generated_resources.h"
+#include "components/login/localized_values_builder.h"
 #include "content/public/browser/web_ui_data_source.h"
 
 namespace chromeos {
 namespace network_element {
 
+namespace {
+
+struct {
+  const char* name;
+  int id;
+} const localized_strings[] = {
+    {"OncTypeCellular", IDS_NETWORK_TYPE_MOBILE_DATA},
+    {"OncTypeEthernet", IDS_NETWORK_TYPE_ETHERNET},
+    {"OncTypeTether", IDS_NETWORK_TYPE_MOBILE_DATA},
+    {"OncTypeVPN", IDS_NETWORK_TYPE_VPN},
+    {"OncTypeWiFi", IDS_NETWORK_TYPE_WIFI},
+    {"OncTypeWiMAX", IDS_NETWORK_TYPE_WIMAX},
+    {"networkListItemConnected", IDS_STATUSBAR_NETWORK_DEVICE_CONNECTED},
+    {"networkListItemConnecting", IDS_STATUSBAR_NETWORK_DEVICE_CONNECTING},
+    {"networkListItemConnectingTo", IDS_NETWORK_LIST_CONNECTING_TO},
+    {"networkListItemNotConnected", IDS_NETWORK_LIST_NOT_CONNECTED},
+    {"vpnNameTemplate", IDS_NETWORK_LIST_THIRD_PARTY_VPN_NAME_TEMPLATE},
+};
+}  //  namespace
+
 void AddLocalizedStrings(content::WebUIDataSource* html_source) {
-  struct {
-    const char* name;
-    int id;
-  } localized_strings[] = {
-      {"OncTypeCellular", IDS_NETWORK_TYPE_MOBILE_DATA},
-      {"OncTypeEthernet", IDS_NETWORK_TYPE_ETHERNET},
-      {"OncTypeTether", IDS_NETWORK_TYPE_MOBILE_DATA},
-      {"OncTypeVPN", IDS_NETWORK_TYPE_VPN},
-      {"OncTypeWiFi", IDS_NETWORK_TYPE_WIFI},
-      {"OncTypeWiMAX", IDS_NETWORK_TYPE_WIMAX},
-      {"networkListItemConnected", IDS_STATUSBAR_NETWORK_DEVICE_CONNECTED},
-      {"networkListItemConnecting", IDS_STATUSBAR_NETWORK_DEVICE_CONNECTING},
-      {"networkListItemConnectingTo", IDS_NETWORK_LIST_CONNECTING_TO},
-      {"networkListItemNotConnected", IDS_NETWORK_LIST_NOT_CONNECTED},
-      {"vpnNameTemplate", IDS_NETWORK_LIST_THIRD_PARTY_VPN_NAME_TEMPLATE},
-  };
   for (const auto& entry : localized_strings)
     html_source->AddLocalizedString(entry.name, entry.id);
 }
 
+void AddLocalizedValuesToBuilder(::login::LocalizedValuesBuilder* builder) {
+  for (const auto& entry : localized_strings)
+    builder->Add(entry.name, entry.id);
+}
+
 }  // namespace network_element
+
 }  // namespace chromeos
diff --git a/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.h b/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.h
index e47f871a..a16ead5 100644
--- a/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.h
+++ b/chrome/browser/ui/webui/chromeos/network_element_localized_strings_provider.h
@@ -5,6 +5,10 @@
 #ifndef CHROME_BROWSER_UI_WEBUI_CHROMEOS_NETWORK_ELEMENT_LOCALIZED_STRINGS_PROVIDER_H_
 #define CHROME_BROWSER_UI_WEBUI_CHROMEOS_NETWORK_ELEMENT_LOCALIZED_STRINGS_PROVIDER_H_
 
+namespace login {
+class LocalizedValuesBuilder;
+}
+
 namespace content {
 class WebUIDataSource;
 }
@@ -16,6 +20,9 @@
 // correspond to ids in ui/webui/resources/cr_elements/chromeos/network/.
 void AddLocalizedStrings(content::WebUIDataSource* html_source);
 
+// Same as AddLocalizedStrings but for a LocalizedValuesBuilder.
+void AddLocalizedValuesToBuilder(::login::LocalizedValuesBuilder* builder);
+
 }  // namespace network_element
 }  // namespace chromeos
 
diff --git a/chrome/browser/ui/webui/policy_ui_handler.cc b/chrome/browser/ui/webui/policy_ui_handler.cc
index 8f3a4dc..42f02b4 100644
--- a/chrome/browser/ui/webui/policy_ui_handler.cc
+++ b/chrome/browser/ui/webui/policy_ui_handler.cc
@@ -632,7 +632,7 @@
 
 void PolicyUIHandler::AddPolicyName(const std::string& name,
                                     base::DictionaryValue* names) const {
-  names->SetBooleanWithoutPathExpansion(name, true);
+  names->SetKey(name, base::Value(true));
 }
 
 void PolicyUIHandler::SendPolicyNames() const {
diff --git a/chrome/installer/zucchini/BUILD.gn b/chrome/installer/zucchini/BUILD.gn
index 775eaad..8fe9cfa 100644
--- a/chrome/installer/zucchini/BUILD.gn
+++ b/chrome/installer/zucchini/BUILD.gn
@@ -17,6 +17,8 @@
     "crc32.h",
     "disassembler.cc",
     "disassembler.h",
+    "disassembler_no_op.cc",
+    "disassembler_no_op.h",
     "image_utils.h",
     "io_utils.cc",
     "io_utils.h",
diff --git a/chrome/installer/zucchini/disassembler_no_op.cc b/chrome/installer/zucchini/disassembler_no_op.cc
new file mode 100644
index 0000000..f6178da3
--- /dev/null
+++ b/chrome/installer/zucchini/disassembler_no_op.cc
@@ -0,0 +1,36 @@
+// Copyright 2017 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.
+
+#include "chrome/installer/zucchini/disassembler_no_op.h"
+
+namespace zucchini {
+
+std::unique_ptr<DisassemblerNoOp> DisassemblerNoOp::Make(
+    ConstBufferView image) {
+  std::unique_ptr<DisassemblerNoOp> disasm(new DisassemblerNoOp());
+  if (!disasm->Parse(image))
+    return nullptr;
+  return disasm;
+}
+
+DisassemblerNoOp::DisassemblerNoOp() = default;
+DisassemblerNoOp::~DisassemblerNoOp() = default;
+
+ExecutableType DisassemblerNoOp::GetExeType() const {
+  return kExeTypeNoOp;
+}
+
+std::string DisassemblerNoOp::GetExeTypeString() const {
+  return "(Unknown)";
+}
+
+std::vector<ReferenceGroup> DisassemblerNoOp::GetReferenceGroups() const {
+  return std::vector<ReferenceGroup>();
+}
+
+bool DisassemblerNoOp::Parse(ConstBufferView image) {
+  return true;
+}
+
+}  // namespace zucchini
diff --git a/chrome/installer/zucchini/disassembler_no_op.h b/chrome/installer/zucchini/disassembler_no_op.h
new file mode 100644
index 0000000..13ff32b
--- /dev/null
+++ b/chrome/installer/zucchini/disassembler_no_op.h
@@ -0,0 +1,42 @@
+// Copyright 2017 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 CHROME_INSTALLER_ZUCCHINI_DISASSEMBLER_NO_OP_H_
+#define CHROME_INSTALLER_ZUCCHINI_DISASSEMBLER_NO_OP_H_
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include "base/macros.h"
+#include "chrome/installer/zucchini/buffer_view.h"
+#include "chrome/installer/zucchini/disassembler.h"
+#include "chrome/installer/zucchini/image_utils.h"
+
+namespace zucchini {
+
+// This disassembler works on any file and does not look for reference.
+class DisassemblerNoOp : public Disassembler {
+ public:
+  static std::unique_ptr<DisassemblerNoOp> Make(ConstBufferView image);
+
+  ~DisassemblerNoOp() override;
+
+  // Disassembler:
+  ExecutableType GetExeType() const override;
+  std::string GetExeTypeString() const override;
+  std::vector<ReferenceGroup> GetReferenceGroups() const override;
+
+ protected:
+  DisassemblerNoOp();
+
+ private:
+  bool Parse(ConstBufferView image) override;
+
+  DISALLOW_COPY_AND_ASSIGN(DisassemblerNoOp);
+};
+
+}  // namespace zucchini
+
+#endif  // CHROME_INSTALLER_ZUCCHINI_DISASSEMBLER_NO_OP_H_
diff --git a/chrome/profiling/json_exporter_unittest.cc b/chrome/profiling/json_exporter_unittest.cc
index eca5a6e..5edeaca7 100644
--- a/chrome/profiling/json_exporter_unittest.cc
+++ b/chrome/profiling/json_exporter_unittest.cc
@@ -33,21 +33,6 @@
   return nullptr;
 }
 
-const base::Value* ResolveValuePath(const base::Value& input,
-                                    std::initializer_list<const char*> path) {
-  const base::Value* cur = &input;
-  for (const char* component : path) {
-    if (!cur->is_dict())
-      return nullptr;
-
-    auto found = cur->FindKey(component);
-    if (found == cur->DictEnd())
-      return nullptr;
-    cur = &found->second;
-  }
-  return cur;
-}
-
 }  // namespace
 
 TEST(ProfilingJsonExporter, Simple) {
@@ -84,13 +69,13 @@
   ASSERT_TRUE(periodic_interval) << "Array contains no periodic_interval";
 
   const base::Value* heaps_v2 =
-      ResolveValuePath(*periodic_interval, {"args", "dumps", "heaps_v2"});
+      periodic_interval->GetPath({"args", "dumps", "heaps_v2"});
   ASSERT_TRUE(heaps_v2);
 
   // Counts should be a list of two items, a 1 and a 2 (in either order). The
   // two matching 16-byte allocations should be coalesced to produce the 2.
   const base::Value* counts =
-      ResolveValuePath(*heaps_v2, {"allocators", "malloc", "counts"});
+      heaps_v2->GetPath({"allocators", "malloc", "counts"});
   ASSERT_TRUE(counts);
   EXPECT_EQ(2u, counts->GetList().size());
   EXPECT_TRUE((counts->GetList()[0].GetInt() == 1 &&
diff --git a/chrome/test/base/mash_browser_tests_main.cc b/chrome/test/base/mash_browser_tests_main.cc
index 023ca48b..6b5073e 100644
--- a/chrome/test/base/mash_browser_tests_main.cc
+++ b/chrome/test/base/mash_browser_tests_main.cc
@@ -99,6 +99,8 @@
   int RunTestSuite(int argc, char** argv) override {
     test_suite_.reset(new MashTestSuite(argc, argv));
     content::GetContentMainParams()->env_mode = aura::Env::Mode::MUS;
+    content::GetContentMainParams()->create_discardable_memory =
+        (config_ == MojoTestConnector::Config::MUS);
     const int result = test_suite_->Run();
     test_suite_.reset();
     return result;
diff --git a/chrome/test/data/webui/BUILD.gn b/chrome/test/data/webui/BUILD.gn
index 1de35e3..c400955 100644
--- a/chrome/test/data/webui/BUILD.gn
+++ b/chrome/test/data/webui/BUILD.gn
@@ -43,6 +43,7 @@
     "../../../browser/ui/webui/identity_internals_ui_browsertest.js",
     "../../../browser/ui/webui/sync_internals_browsertest.js",
     "../chromeos/oobe_webui_browsertest.js",
+    "//third_party/axe-core/axe.js",
     "about_invalidations_browsertest.js",
     "accessibility_audit_browsertest.js",
     "assertions.js",
@@ -76,6 +77,7 @@
     "ntp4.js",
     "polymer_browser_test_base.js",
     "sandboxstatus_browsertest.js",
+    "settings/accessibility_browsertest.js",
     "settings/advanced_page_browsertest.js",
     "settings/animation_browsertest.js",
     "settings/basic_page_browsertest.js",
diff --git a/chrome/test/data/webui/settings/accessibility_browsertest.js b/chrome/test/data/webui/settings/accessibility_browsertest.js
new file mode 100644
index 0000000..7753144
--- /dev/null
+++ b/chrome/test/data/webui/settings/accessibility_browsertest.js
@@ -0,0 +1,95 @@
+// Copyright 2017 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.
+
+/** @fileoverview Runs the Polymer Accessibility Settings tests. */
+
+// Disable in debug and memory sanitizer modes because of timeouts.
+GEN('#if defined(NDEBUG)');
+
+/** @const {string} Path to root from chrome/test/data/webui/settings/. */
+var ROOT_PATH = '../../../../../';
+
+// Polymer BrowserTest fixture and aXe-core accessibility audit.
+GEN_INCLUDE([
+  ROOT_PATH + 'chrome/test/data/webui/polymer_browser_test_base.js',
+  ROOT_PATH + 'third_party/axe-core/axe.js',
+]);
+
+/**
+ * @typedef {{
+ *   rules: {
+ *     'color_contrast': ({ enabled: boolean} | undefined),
+ *     'aria_valid_attr': ({ enabled: boolean} | undefined),
+ *   }
+ * }}
+ * @see https://github.com/dequelabs/axe-core/blob/develop/doc/API.md#options-parameter
+ */
+function AccessibilityAuditConfig() {}
+
+/**
+ * Test fixture for Accessibility of Chrome Settings.
+ * @constructor
+ * @extends {PolymerTest}
+ */
+function SettingsAccessibilityTest() {}
+
+/**
+ * Run aXe-core accessibility audit, print console-friendly representation
+ * of violations to console, and fail the test if there are audit failures.
+ * @param {AccessibilityAuditConfig} options Dictionary disabling specific
+ *    audit rules.
+ * @return {Promise} A promise resolved if the accessibility audit completes
+ *    with no issues, or rejected if the audit finds any accessibility issues.
+ */
+SettingsAccessibilityTest.runAudit = function(options) {
+  // Ignore iron-iconset-svg elements that have duplicate ids and result in
+  // false postives from the audit.
+  var context = {exclude: ['iron-iconset-svg']};
+  options = options || {};
+
+  return new Promise(function(resolve, reject) {
+    axe.run(context, options, function(err, results) {
+      if (err)
+        reject(err);
+
+      var violationCount = results.violations.length;
+      if (violationCount) {
+        // Pretty print out the violations detected by the audit.
+        console.log(JSON.stringify(results.violations, null, 4));
+        reject('Found ' + violationCount + ' accessibility violations.');
+      } else {
+        resolve();
+      }
+    });
+  });
+};
+
+SettingsAccessibilityTest.prototype = {
+  __proto__: PolymerTest.prototype,
+
+  /** @override */
+  browsePreload: 'chrome://md-settings/',
+
+  // Include files that define the mocha tests.
+  extraLibraries: PolymerTest.getLibraries(ROOT_PATH).concat([
+    'ensure_lazy_loaded.js', 'passwords_and_autofill_fake_data.js',
+    'passwords_a11y_test.js'
+  ]),
+
+  // TODO(hcarmona): Remove once ADT is not longer in the testing infrastructure
+  runAccessibilityChecks: false,
+
+  setUp: function() {
+    PolymerTest.prototype.setUp.call(this);
+    settings.ensureLazyLoaded();
+  },
+};
+
+// TODO(quacht): Enable in separate CL.
+// Test disabled since it doesn't work on all platforms.
+// TEST_F('SettingsAccessibilityTest', 'All', function() {
+//   mocha.run();
+// });
+
+GEN('#endif  // defined(NDEBUG)');
\ No newline at end of file
diff --git a/chrome/test/data/webui/settings/passwords_a11y_test.js b/chrome/test/data/webui/settings/passwords_a11y_test.js
new file mode 100644
index 0000000..f6359ec
--- /dev/null
+++ b/chrome/test/data/webui/settings/passwords_a11y_test.js
@@ -0,0 +1,80 @@
+// Copyright 2017 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.
+
+/** @fileoverview Suite of accessibility tests for the passwords page. */
+
+suite('SettingsPasswordsAccessibility', function() {
+  var passwordsSection = null;
+  var passwordManager = null;
+
+  /** @type {AccessibilityAuditConfig} **/
+  // TODO(quacht): Enable these rules when the audit filter is implemented, and
+  // we can filter out specific audit violations.
+  var auditOptions = {
+    'rules': {
+      // Enable 'color-contrast' when failure is resolved.
+      // http://crbug.com/748608
+      'color-contrast': {enabled: false},
+      // http://crbug.com/748632
+      'aria-valid-attr': {enabled: false}
+    }
+  };
+
+  setup(function() {
+    return new Promise(function(resolve) {
+      // Reset to a blank page.
+      PolymerTest.clearBody();
+
+      // Set the URL to be that of specific route to load upon injecting
+      // settings-ui. Simply calling settings.navigateTo(route) prevents
+      // use of mock APIs for fake data.
+      window.history.pushState(
+          'object or string', 'Test', settings.routes.MANAGE_PASSWORDS.path);
+
+      PasswordManagerImpl.instance_ = new TestPasswordManager();
+      passwordManager = PasswordManagerImpl.instance_;
+
+      var settingsUi = document.createElement('settings-ui');
+
+      // The settings section will expand to load the MANAGE_PASSWORDS route
+      // (based on the URL set above) once the settings-ui element is attached
+      settingsUi.addEventListener('settings-section-expanded', function() {
+        // Passwords section should be loaded before setup is complete.
+        passwordsSection = settingsUi.$$('settings-main')
+                               .$$('settings-basic-page')
+                               .$$('settings-passwords-and-forms-page')
+                               .$$('passwords-section');
+
+        assertTrue(!!passwordsSection);
+
+        assertEquals(passwordManager, passwordsSection.passwordManager_);
+
+        resolve();
+      });
+
+      document.body.appendChild(settingsUi);
+    });
+  });
+
+  test('Accessible with 0 passwords', function() {
+    assertEquals(0, passwordsSection.savedPasswords.length);
+    return SettingsAccessibilityTest.runAudit(auditOptions);
+  });
+
+  test('Accessible with 100 passwords', function() {
+    var fakePasswords = [];
+    for (var i = 0; i < 100; i++) {
+      fakePasswords.push(FakeDataMaker.passwordEntry());
+    }
+
+    // Set list of passwords.
+    passwordManager.lastCallback.addSavedPasswordListChangedListener(
+        fakePasswords);
+    Polymer.dom.flush();
+
+    assertEquals(100, passwordsSection.savedPasswords.length);
+
+    return SettingsAccessibilityTest.runAudit(auditOptions);
+  });
+});
\ No newline at end of file
diff --git a/chromecast/browser/cast_browser_main_parts.cc b/chromecast/browser/cast_browser_main_parts.cc
index d5ad0a2..617934a 100644
--- a/chromecast/browser/cast_browser_main_parts.cc
+++ b/chromecast/browser/cast_browser_main_parts.cc
@@ -262,6 +262,8 @@
     {switches::kEnableNetworkInformationDownlinkMax, ""},
     // TODO(halliwell): Remove after fixing b/35422666.
     {switches::kEnableUseZoomForDSF, "false"},
+    // TODO(halliwell): Revert after fix for b/63101386.
+    {cc::switches::kDisallowNonExactResourceReuse, ""},
 };
 
 void AddDefaultCommandLineSwitches(base::CommandLine* command_line) {
diff --git a/chromecast/media/cma/backend/android/audio_decoder_android.cc b/chromecast/media/cma/backend/android/audio_decoder_android.cc
index 98c2a5a..33f03afe 100644
--- a/chromecast/media/cma/backend/android/audio_decoder_android.cc
+++ b/chromecast/media/cma/backend/android/audio_decoder_android.cc
@@ -70,7 +70,7 @@
       rate_shifter_output_(
           ::media::AudioBus::Create(kNumChannels, kDefaultFramesPerBuffer)),
       current_pts_(kInvalidTimestamp),
-      sink_(AudioSinkAndroid::kSinkTypeJavaBased),
+      sink_(AudioSinkManager::GetDefaultSinkType()),
       pending_output_frames_(kNoPendingOutput),
       volume_multiplier_(1.0f),
       pool_(new ::media::AudioBufferMemoryPool()),
diff --git a/chromecast/media/cma/backend/android/audio_sink_android.cc b/chromecast/media/cma/backend/android/audio_sink_android.cc
index 8094ff9..703d8e42 100644
--- a/chromecast/media/cma/backend/android/audio_sink_android.cc
+++ b/chromecast/media/cma/backend/android/audio_sink_android.cc
@@ -24,6 +24,22 @@
   }
 }
 
+// static
+bool AudioSinkAndroid::GetSessionIds(SinkType sink_type,
+                                     int* media_id,
+                                     int* non_media_id) {
+  switch (sink_type) {
+    case AudioSinkAndroid::kSinkTypeNativeBased:
+      // TODO(ckuiper): implement a sink using native code.
+      NOTREACHED() << "Native-based audio sink is not implemented yet!";
+      break;
+    case AudioSinkAndroid::kSinkTypeJavaBased:
+      return AudioSinkAndroidAudioTrackImpl::GetSessionIds(media_id,
+                                                           non_media_id);
+  }
+  return false;
+}
+
 ManagedAudioSink::ManagedAudioSink(SinkType sink_type)
     : sink_type_(sink_type), sink_(nullptr) {}
 
diff --git a/chromecast/media/cma/backend/android/audio_sink_android.h b/chromecast/media/cma/backend/android/audio_sink_android.h
index fa1d834..fba4d3d 100644
--- a/chromecast/media/cma/backend/android/audio_sink_android.h
+++ b/chromecast/media/cma/backend/android/audio_sink_android.h
@@ -57,6 +57,13 @@
     virtual ~Delegate() {}
   };
 
+  // Gets the Android audio session ids used for media and non-media tracks.
+  // Set a return value pointer to null if that id is not needed.
+  // Returns true if the ids populated are valid.
+  static bool GetSessionIds(SinkType sink_type,
+                            int* media_id,
+                            int* non_media_id);
+
   AudioSinkAndroid() {}
   virtual ~AudioSinkAndroid() {}
 
diff --git a/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.cc b/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.cc
index 83cb01d..0b8c1a61 100644
--- a/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.cc
+++ b/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.cc
@@ -44,6 +44,25 @@
 namespace chromecast {
 namespace media {
 
+// static
+bool AudioSinkAndroidAudioTrackImpl::GetSessionIds(int* media_id,
+                                                   int* non_media_id) {
+  bool is_valid = true;
+  if (media_id) {
+    *media_id = Java_AudioSinkAudioTrackImpl_getSessionIdMedia(
+        base::android::AttachCurrentThread());
+    if (*media_id == -1)
+      is_valid = false;
+  }
+  if (non_media_id) {
+    *non_media_id = Java_AudioSinkAudioTrackImpl_getSessionIdNonMedia(
+        base::android::AttachCurrentThread());
+    if (*non_media_id == -1)
+      is_valid = false;
+  }
+  return is_valid;
+}
+
 AudioSinkAndroidAudioTrackImpl::AudioSinkAndroidAudioTrackImpl(
     AudioSinkAndroid::Delegate* delegate,
     int input_samples_per_second,
diff --git a/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.h b/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.h
index e969658b..005e3f5 100644
--- a/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.h
+++ b/chromecast/media/cma/backend/android/audio_sink_android_audiotrack_impl.h
@@ -43,6 +43,11 @@
 
   static bool RegisterJni(JNIEnv* env);
 
+  // Gets the Android audio session ids used for media and non-media tracks.
+  // Set a return value pointer to null if that id is not needed.
+  // Returns true if the ids populated are valid.
+  static bool GetSessionIds(int* media_id, int* non_media_id);
+
   // Called from Java so that we can cache the addresses of the Java-managed
   // byte_buffers.
   void CacheDirectBufferAddress(
diff --git a/chromecast/media/cma/backend/android/audio_sink_manager.cc b/chromecast/media/cma/backend/android/audio_sink_manager.cc
index b1461b3..67f3c93 100644
--- a/chromecast/media/cma/backend/android/audio_sink_manager.cc
+++ b/chromecast/media/cma/backend/android/audio_sink_manager.cc
@@ -42,6 +42,17 @@
   return g_sink_manager_instance.Pointer();
 }
 
+// static
+AudioSinkAndroid::SinkType AudioSinkManager::GetDefaultSinkType() {
+  return AudioSinkAndroid::kSinkTypeJavaBased;
+}
+
+// static
+bool AudioSinkManager::GetSessionIds(int* media_id, int* non_media_id) {
+  return AudioSinkAndroid::GetSessionIds(GetDefaultSinkType(), media_id,
+                                         non_media_id);
+}
+
 AudioSinkManager::AudioSinkManager() {}
 AudioSinkManager::~AudioSinkManager() {}
 
diff --git a/chromecast/media/cma/backend/android/audio_sink_manager.h b/chromecast/media/cma/backend/android/audio_sink_manager.h
index 6372f82..123486e5 100644
--- a/chromecast/media/cma/backend/android/audio_sink_manager.h
+++ b/chromecast/media/cma/backend/android/audio_sink_manager.h
@@ -21,6 +21,12 @@
 class AudioSinkManager {
  public:
   static AudioSinkManager* Get();
+  static AudioSinkAndroid::SinkType GetDefaultSinkType();
+
+  // Gets the Android audio session ids used for media and non-media tracks.
+  // Set a return value pointer to null if that id is not needed.
+  // Returns true if the ids populated are valid.
+  static bool GetSessionIds(int* media_id, int* non_media_id);
 
   // Adds the given sink instance to the vector.
   void Add(AudioSinkAndroid* sink);
diff --git a/chromecast/media/cma/backend/android/java/src/org/chromium/chromecast/cma/backend/android/AudioSinkAudioTrackImpl.java b/chromecast/media/cma/backend/android/java/src/org/chromium/chromecast/cma/backend/android/AudioSinkAudioTrackImpl.java
index 9b69a9c..8af04241 100644
--- a/chromecast/media/cma/backend/android/java/src/org/chromium/chromecast/cma/backend/android/AudioSinkAudioTrackImpl.java
+++ b/chromecast/media/cma/backend/android/java/src/org/chromium/chromecast/cma/backend/android/AudioSinkAudioTrackImpl.java
@@ -5,6 +5,8 @@
 package org.chromium.chromecast.cma.backend.android;
 
 import android.annotation.TargetApi;
+import android.content.Context;
+import android.media.AudioAttributes;
 import android.media.AudioFormat;
 import android.media.AudioManager;
 import android.media.AudioTimestamp;
@@ -13,6 +15,7 @@
 import android.os.SystemClock;
 import android.util.SparseIntArray;
 
+import org.chromium.base.ContextUtils;
 import org.chromium.base.Log;
 import org.chromium.base.annotations.CalledByNative;
 import org.chromium.base.annotations.JNINamespace;
@@ -48,11 +51,22 @@
     private static final int DEBUG_LEVEL = 0;
 
     // Mapping from Android's stream_type to Cast's AudioContentType (used for callback).
-    private static final SparseIntArray CAST_TYPE_TO_ANDROID_TYPE_MAP = new SparseIntArray(3) {
+    private static final SparseIntArray CAST_TYPE_TO_ANDROID_USAGE_TYPE_MAP = new SparseIntArray(
+            3) {
         {
-            append(AudioContentType.MEDIA, AudioManager.STREAM_MUSIC);
-            append(AudioContentType.ALARM, AudioManager.STREAM_ALARM);
-            append(AudioContentType.COMMUNICATION, AudioManager.STREAM_SYSTEM);
+            append(AudioContentType.MEDIA, AudioAttributes.USAGE_MEDIA);
+            append(AudioContentType.ALARM, AudioAttributes.USAGE_ALARM);
+            append(AudioContentType.COMMUNICATION, AudioAttributes.USAGE_ASSISTANCE_SONIFICATION);
+        }
+    };
+
+    private static final SparseIntArray CAST_TYPE_TO_ANDROID_CONTENT_TYPE_MAP = new SparseIntArray(
+            3) {
+        {
+            append(AudioContentType.MEDIA, AudioAttributes.CONTENT_TYPE_MUSIC);
+            // Note: ALARM uses the same as COMMUNICATON.
+            append(AudioContentType.ALARM, AudioAttributes.CONTENT_TYPE_SONIFICATION);
+            append(AudioContentType.COMMUNICATION, AudioAttributes.CONTENT_TYPE_SONIFICATION);
         }
     };
 
@@ -68,6 +82,11 @@
     private static final long TIMESTAMP_UPDATE_PERIOD = 3 * SEC_IN_NSEC;
     private static final long UNDERRUN_LOG_THROTTLE_PERIOD = SEC_IN_NSEC;
 
+    private static AudioManager sAudioManager = null;
+
+    private static int sSessionIdMedia = AudioManager.ERROR;
+    private static int sSessionIdNonMedia = AudioManager.ERROR;
+
     private final long mNativeAudioSinkAudioTrackImpl;
 
     private boolean mIsInitialized;
@@ -101,6 +120,40 @@
     private ByteBuffer mRenderingDelayBuffer; // RenderingDelay return value
                                               // (java->native)
 
+    private static AudioManager getAudioManager() {
+        if (sAudioManager == null) {
+            sAudioManager = (AudioManager) ContextUtils.getApplicationContext().getSystemService(
+                    Context.AUDIO_SERVICE);
+        }
+        return sAudioManager;
+    }
+
+    @CalledByNative
+    public static int getSessionIdMedia() {
+        if (sSessionIdMedia == AudioManager.ERROR) {
+            sSessionIdMedia = getAudioManager().generateAudioSessionId();
+            if (sSessionIdMedia == AudioManager.ERROR) {
+                Log.e(TAG, "Cannot generate session-id for media tracks!");
+            } else {
+                Log.i(TAG, "Session-id for media tracks is " + sSessionIdMedia);
+            }
+        }
+        return sSessionIdMedia;
+    }
+
+    @CalledByNative
+    public static int getSessionIdNonMedia() {
+        if (sSessionIdNonMedia == AudioManager.ERROR) {
+            sSessionIdNonMedia = getAudioManager().generateAudioSessionId();
+            if (sSessionIdNonMedia == AudioManager.ERROR) {
+                Log.e(TAG, "Cannot generate session-id for non-media tracks!");
+            } else {
+                Log.i(TAG, "Session-id for non-media tracks is " + sSessionIdNonMedia);
+            }
+        }
+        return sSessionIdNonMedia;
+    }
+
     /** Construction */
     @CalledByNative
     private static AudioSinkAudioTrackImpl createAudioSinkAudioTrackImpl(
@@ -149,11 +202,32 @@
         // similar.
         int bufferSizeInBytes =
                 5 * AudioTrack.getMinBufferSize(mSampleRateInHz, CHANNEL_CONFIG, AUDIO_FORMAT);
-        int streamType = CAST_TYPE_TO_ANDROID_TYPE_MAP.get(castContentType);
+
+        int usageType = CAST_TYPE_TO_ANDROID_USAGE_TYPE_MAP.get(castContentType);
+        int contentType = CAST_TYPE_TO_ANDROID_CONTENT_TYPE_MAP.get(castContentType);
+        int sessionId = (usageType == AudioAttributes.USAGE_MEDIA) ? getSessionIdMedia()
+                                                                   : getSessionIdNonMedia();
         Log.i(TAG,
-                "Init: create an AudioTrack of size=" + bufferSizeInBytes + " type=" + streamType);
-        mAudioTrack = new AudioTrack(streamType, mSampleRateInHz, CHANNEL_CONFIG, AUDIO_FORMAT,
-                bufferSizeInBytes, AUDIO_MODE);
+                "Init: create an AudioTrack of size=" + bufferSizeInBytes
+                        + " usageType=" + usageType + " contentType=" + contentType
+                        + " with session-id=" + sessionId);
+
+        AudioTrack.Builder builder = new AudioTrack.Builder();
+        builder.setBufferSizeInBytes(bufferSizeInBytes)
+                .setTransferMode(AUDIO_MODE)
+                .setAudioAttributes(new AudioAttributes.Builder()
+                                            .setUsage(usageType)
+                                            .setContentType(contentType)
+                                            .build())
+                .setAudioFormat(new AudioFormat.Builder()
+                                        .setEncoding(AUDIO_FORMAT)
+                                        .setSampleRate(mSampleRateInHz)
+                                        .setChannelMask(CHANNEL_CONFIG)
+                                        .build());
+        if (sessionId != AudioManager.ERROR) builder.setSessionId(sessionId);
+
+        mAudioTrack = builder.build();
+
         mRefPointTStamp = new AudioTimestamp();
 
         // Allocated shared buffers.
diff --git a/chromeos/components/tether/wifi_hotspot_connector.cc b/chromeos/components/tether/wifi_hotspot_connector.cc
index 34740d2d..3fd0a84b 100644
--- a/chromeos/components/tether/wifi_hotspot_connector.cc
+++ b/chromeos/components/tether/wifi_hotspot_connector.cc
@@ -197,11 +197,10 @@
   shill_property_util::SetSSID(ssid, &properties);
   properties.SetStringWithoutPathExpansion(shill::kGuidProperty,
                                            wifi_network_guid_);
-  properties.SetBooleanWithoutPathExpansion(shill::kAutoConnectProperty, false);
+  properties.SetKey(shill::kAutoConnectProperty, base::Value(false));
   properties.SetStringWithoutPathExpansion(shill::kTypeProperty,
                                            shill::kTypeWifi);
-  properties.SetBooleanWithoutPathExpansion(shill::kSaveCredentialsProperty,
-                                            true);
+  properties.SetKey(shill::kSaveCredentialsProperty, base::Value(true));
 
   if (password.empty()) {
     properties.SetStringWithoutPathExpansion(shill::kSecurityClassProperty,
diff --git a/chromeos/dbus/fake_shill_device_client.cc b/chromeos/dbus/fake_shill_device_client.cc
index 0cb8164..a371aa6 100644
--- a/chromeos/dbus/fake_shill_device_client.cc
+++ b/chromeos/dbus/fake_shill_device_client.cc
@@ -398,8 +398,8 @@
   properties->SetStringWithoutPathExpansion(
       shill::kDBusServiceProperty, modemmanager::kModemManager1ServiceName);
   if (type == shill::kTypeCellular) {
-    properties->SetBooleanWithoutPathExpansion(
-        shill::kCellularAllowRoamingProperty, false);
+    properties->SetKey(shill::kCellularAllowRoamingProperty,
+                       base::Value(false));
   }
 }
 
@@ -504,8 +504,8 @@
                                               status.type);
   simlock_dict->SetIntegerWithoutPathExpansion(
       shill::kSIMLockRetriesLeftProperty, status.retries_left);
-  simlock_dict->SetBooleanWithoutPathExpansion(shill::kSIMLockEnabledProperty,
-                                               status.lock_enabled);
+  simlock_dict->SetKey(shill::kSIMLockEnabledProperty,
+                       base::Value(status.lock_enabled));
   NotifyObserversPropertyChanged(dbus::ObjectPath(device_path),
                                  shill::kSIMLockStatusProperty);
 }
diff --git a/chromeos/dbus/fake_shill_service_client.cc b/chromeos/dbus/fake_shill_service_client.cc
index 363b1c7a..dc7dc7a8 100644
--- a/chromeos/dbus/fake_shill_service_client.cc
+++ b/chromeos/dbus/fake_shill_service_client.cc
@@ -374,7 +374,7 @@
                                             device_path);
   properties->SetStringWithoutPathExpansion(shill::kTypeProperty, type);
   properties->SetStringWithoutPathExpansion(shill::kStateProperty, state);
-  properties->SetBooleanWithoutPathExpansion(shill::kVisibleProperty, visible);
+  properties->SetKey(shill::kVisibleProperty, base::Value(visible));
   if (type == shill::kTypeWifi) {
     properties->SetStringWithoutPathExpansion(shill::kSecurityClassProperty,
                                               shill::kSecurityNone);
diff --git a/chromeos/dbus/shill_device_client_unittest.cc b/chromeos/dbus/shill_device_client_unittest.cc
index fe717bd4..641bb2be 100644
--- a/chromeos/dbus/shill_device_client_unittest.cc
+++ b/chromeos/dbus/shill_device_client_unittest.cc
@@ -126,8 +126,7 @@
 
   // Set expectations.
   base::DictionaryValue value;
-  value.SetBooleanWithoutPathExpansion(shill::kCellularAllowRoamingProperty,
-                                       kValue);
+  value.SetKey(shill::kCellularAllowRoamingProperty, base::Value(kValue));
   PrepareForMethodCall(shill::kGetPropertiesFunction,
                        base::Bind(&ExpectNoArgument),
                        response.get());
diff --git a/chromeos/dbus/shill_manager_client_unittest.cc b/chromeos/dbus/shill_manager_client_unittest.cc
index 7a1ea81..cd58338 100644
--- a/chromeos/dbus/shill_manager_client_unittest.cc
+++ b/chromeos/dbus/shill_manager_client_unittest.cc
@@ -139,7 +139,7 @@
 
   // Create the expected value.
   base::DictionaryValue value;
-  value.SetBooleanWithoutPathExpansion(shill::kOfflineModeProperty, true);
+  value.SetKey(shill::kOfflineModeProperty, base::Value(true));
   // Set expectations.
   PrepareForMethodCall(shill::kGetPropertiesFunction,
                        base::Bind(&ExpectNoArgument),
diff --git a/chromeos/dbus/shill_profile_client_unittest.cc b/chromeos/dbus/shill_profile_client_unittest.cc
index eb17a9a4..6f63b57 100644
--- a/chromeos/dbus/shill_profile_client_unittest.cc
+++ b/chromeos/dbus/shill_profile_client_unittest.cc
@@ -167,7 +167,7 @@
 
   // Create the expected value.
   base::DictionaryValue value;
-  value.SetBooleanWithoutPathExpansion(shill::kOfflineModeProperty, true);
+  value.SetKey(shill::kOfflineModeProperty, base::Value(true));
   // Set expectations.
   PrepareForMethodCall(shill::kDeleteEntryFunction,
                        base::Bind(&ExpectStringArgument, kExampleEntryPath),
diff --git a/chromeos/geolocation/simple_geolocation_request.cc b/chromeos/geolocation/simple_geolocation_request.cc
index ab15034..fcda985 100644
--- a/chromeos/geolocation/simple_geolocation_request.cc
+++ b/chromeos/geolocation/simple_geolocation_request.cc
@@ -389,7 +389,7 @@
     return std::string(kSimpleGeolocationRequestBody);
 
   std::unique_ptr<base::DictionaryValue> request(new base::DictionaryValue);
-  request->SetBooleanWithoutPathExpansion(kConsiderIp, true);
+  request->SetKey(kConsiderIp, base::Value(true));
 
   if (wifi_data_) {
     auto wifi_access_points = base::MakeUnique<base::ListValue>();
diff --git a/chromeos/network/auto_connect_handler_unittest.cc b/chromeos/network/auto_connect_handler_unittest.cc
index 078a9b3..46d3a4c 100644
--- a/chromeos/network/auto_connect_handler_unittest.cc
+++ b/chromeos/network/auto_connect_handler_unittest.cc
@@ -308,9 +308,9 @@
   // Applying the policy which restricts autoconnect should disconnect from the
   // shared, unmanaged network.
   base::DictionaryValue global_config;
-  global_config.SetBooleanWithoutPathExpansion(
+  global_config.SetKey(
       ::onc::global_network_config::kAllowOnlyPolicyNetworksToAutoconnect,
-      true);
+      base::Value(true));
 
   SetupPolicy(std::string(),            // no network configs
               base::DictionaryValue(),  // no global config
@@ -398,9 +398,9 @@
   EXPECT_EQ(shill::kStateIdle, GetServiceState("wifi1"));
 
   base::DictionaryValue global_config;
-  global_config.SetBooleanWithoutPathExpansion(
+  global_config.SetKey(
       ::onc::global_network_config::kAllowOnlyPolicyNetworksToAutoconnect,
-      true);
+      base::Value(true));
 
   // Applying the policy which restricts autoconnect should disconnect from the
   // shared, unmanaged network.
@@ -430,8 +430,9 @@
   EXPECT_EQ(shill::kStateIdle, GetServiceState("wifi1"));
 
   base::DictionaryValue global_config;
-  global_config.SetBooleanWithoutPathExpansion(
-      ::onc::global_network_config::kAllowOnlyPolicyNetworksToConnect, true);
+  global_config.SetKey(
+      ::onc::global_network_config::kAllowOnlyPolicyNetworksToConnect,
+      base::Value(true));
 
   // Applying the policy which restricts autoconnect should disconnect from the
   // shared, unmanaged network.
diff --git a/chromeos/network/network_connection_handler_impl_unittest.cc b/chromeos/network/network_connection_handler_impl_unittest.cc
index 0131ceee..1a8550b 100644
--- a/chromeos/network/network_connection_handler_impl_unittest.cc
+++ b/chromeos/network/network_connection_handler_impl_unittest.cc
@@ -360,8 +360,9 @@
        NetworkConnectionHandlerConnectProhibited) {
   EXPECT_FALSE(ConfigureService(kConfigConnectable).empty());
   base::DictionaryValue global_config;
-  global_config.SetBooleanWithoutPathExpansion(
-      ::onc::global_network_config::kAllowOnlyPolicyNetworksToConnect, true);
+  global_config.SetKey(
+      ::onc::global_network_config::kAllowOnlyPolicyNetworksToConnect,
+      base::Value(true));
   SetupPolicy("[]", global_config, false /* load as device policy */);
   LoginToRegularUser();
   Connect(kWifi0);
diff --git a/chromeos/network/network_state.cc b/chromeos/network/network_state.cc
index c6c7369..809fbd8 100644
--- a/chromeos/network/network_state.cc
+++ b/chromeos/network/network_state.cc
@@ -271,8 +271,8 @@
     dictionary->SetIntegerWithoutPathExpansion(kTetherBatteryPercentage,
                                                battery_percentage());
     dictionary->SetStringWithoutPathExpansion(kTetherCarrier, carrier());
-    dictionary->SetBooleanWithoutPathExpansion(kTetherHasConnectedToHost,
-                                               tether_has_connected_to_host());
+    dictionary->SetKey(kTetherHasConnectedToHost,
+                       base::Value(tether_has_connected_to_host()));
     dictionary->SetIntegerWithoutPathExpansion(kTetherSignalStrength,
                                                signal_strength());
 
@@ -286,8 +286,7 @@
     return;
 
   if (visible()) {
-    dictionary->SetBooleanWithoutPathExpansion(shill::kConnectableProperty,
-                                               connectable());
+    dictionary->SetKey(shill::kConnectableProperty, base::Value(connectable()));
     dictionary->SetIntegerWithoutPathExpansion(shill::kSignalStrengthProperty,
                                                signal_strength());
   }
@@ -309,8 +308,8 @@
                                               activation_state());
     dictionary->SetStringWithoutPathExpansion(shill::kRoamingStateProperty,
                                               roaming());
-    dictionary->SetBooleanWithoutPathExpansion(shill::kOutOfCreditsProperty,
-                                               cellular_out_of_credits());
+    dictionary->SetKey(shill::kOutOfCreditsProperty,
+                       base::Value(cellular_out_of_credits()));
   }
 }
 
diff --git a/chromeos/network/network_util.cc b/chromeos/network/network_util.cc
index 7ba8ecf..4ed4ec9 100644
--- a/chromeos/network/network_util.cc
+++ b/chromeos/network/network_util.cc
@@ -176,9 +176,8 @@
     if (device) {
       std::unique_ptr<base::DictionaryValue> device_dict(
           new base::DictionaryValue);
-      device_dict->SetBooleanWithoutPathExpansion(
-          shill::kProviderRequiresRoamingProperty,
-          device->provider_requires_roaming());
+      device_dict->SetKey(shill::kProviderRequiresRoamingProperty,
+                          base::Value(device->provider_requires_roaming()));
       shill_dictionary->SetWithoutPathExpansion(shill::kDeviceProperty,
                                                 std::move(device_dict));
     }
diff --git a/chromeos/network/onc/onc_merger.cc b/chromeos/network/onc/onc_merger.cc
index f6ad5e8..6069541 100644
--- a/chromeos/network/onc/onc_merger.cc
+++ b/chromeos/network/onc/onc_merger.cc
@@ -57,7 +57,7 @@
        it != recommended_value->end(); ++it) {
     std::string entry;
     if (it->GetAsString(&entry))
-      result->SetBooleanWithoutPathExpansion(entry, true);
+      result->SetKey(entry, base::Value(true));
   }
 }
 
@@ -451,12 +451,12 @@
           base::MakeUnique<base::Value>(*values.shared_setting));
     }
     if (HasUserPolicy() && values.user_editable) {
-      augmented_value->SetBooleanWithoutPathExpansion(
-          ::onc::kAugmentationUserEditable, true);
+      augmented_value->SetKey(::onc::kAugmentationUserEditable,
+                              base::Value(true));
     }
     if (HasDevicePolicy() && values.device_editable) {
-      augmented_value->SetBooleanWithoutPathExpansion(
-          ::onc::kAugmentationDeviceEditable, true);
+      augmented_value->SetKey(::onc::kAugmentationDeviceEditable,
+                              base::Value(true));
     }
     if (augmented_value->empty())
       augmented_value.reset();
diff --git a/chromeos/network/onc/onc_translator_onc_to_shill.cc b/chromeos/network/onc/onc_translator_onc_to_shill.cc
index cc3714d..05df1ce1 100644
--- a/chromeos/network/onc/onc_translator_onc_to_shill.cc
+++ b/chromeos/network/onc/onc_translator_onc_to_shill.cc
@@ -237,8 +237,8 @@
   bool allow_gateway_arp_polling;
   if (onc_object_->GetBooleanWithoutPathExpansion(
           ::onc::wifi::kAllowGatewayARPPolling, &allow_gateway_arp_polling)) {
-    shill_dictionary_->SetBooleanWithoutPathExpansion(
-        shill::kLinkMonitorDisableProperty, !allow_gateway_arp_polling);
+    shill_dictionary_->SetKey(shill::kLinkMonitorDisableProperty,
+                              base::Value(!allow_gateway_arp_polling));
   }
 
   CopyFieldsAccordingToSignature();
diff --git a/chromeos/network/onc/onc_translator_shill_to_onc.cc b/chromeos/network/onc/onc_translator_shill_to_onc.cc
index a6f77bc..f9962b1 100644
--- a/chromeos/network/onc/onc_translator_shill_to_onc.cc
+++ b/chromeos/network/onc/onc_translator_shill_to_onc.cc
@@ -357,8 +357,8 @@
   bool link_monitor_disable;
   if (shill_dictionary_->GetBooleanWithoutPathExpansion(
           shill::kLinkMonitorDisableProperty, &link_monitor_disable)) {
-    onc_object_->SetBooleanWithoutPathExpansion(
-        ::onc::wifi::kAllowGatewayARPPolling, !link_monitor_disable);
+    onc_object_->SetKey(::onc::wifi::kAllowGatewayARPPolling,
+                        base::Value(!link_monitor_disable));
   }
 
   CopyPropertiesAccordingToSignature();
@@ -490,8 +490,8 @@
         ::onc::network_config::kConnectionState, onc_state);
     // Only set 'RestrictedConnectivity' if captive portal state is true.
     if (NetworkState::NetworkStateIsCaptivePortal(*shill_dictionary_)) {
-      onc_object_->SetBooleanWithoutPathExpansion(
-          ::onc::network_config::kRestrictedConnectivity, true);
+      onc_object_->SetKey(::onc::network_config::kRestrictedConnectivity,
+                          base::Value(true));
     }
   }
 
diff --git a/chromeos/network/policy_util.cc b/chromeos/network/policy_util.cc
index 491f0a3..c38557a 100644
--- a/chromeos/network/policy_util.cc
+++ b/chromeos/network/policy_util.cc
@@ -215,7 +215,7 @@
   else
     NOTREACHED();
 
-  auto_connect_dictionary->SetBooleanWithoutPathExpansion(policy_source, false);
+  auto_connect_dictionary->SetKey(policy_source, base::Value(false));
   auto_connect_dictionary->SetStringWithoutPathExpansion(
       ::onc::kAugmentationEffectiveSetting, policy_source);
 }
@@ -296,8 +296,8 @@
 
   // If autoconnect is not explicitly set yet, it might automatically be enabled
   // by Shill. To prevent that, disable it explicitly.
-  shill_properties_to_update->SetBooleanWithoutPathExpansion(
-      shill::kAutoConnectProperty, false);
+  shill_properties_to_update->SetKey(shill::kAutoConnectProperty,
+                                     base::Value(false));
 }
 
 std::unique_ptr<base::DictionaryValue> CreateShillConfiguration(
@@ -363,8 +363,8 @@
   if (network_policy && IsAutoConnectEnabledInPolicy(*network_policy)) {
     VLOG(1) << "Enable ManagedCredentials for managed network with GUID "
             << guid;
-    shill_dictionary->SetBooleanWithoutPathExpansion(
-        shill::kManagedCredentialsProperty, true);
+    shill_dictionary->SetKey(shill::kManagedCredentialsProperty,
+                             base::Value(true));
   }
 
   if (!network_policy && global_policy) {
diff --git a/components/arc/bluetooth/arc_bluetooth_bridge.cc b/components/arc/bluetooth/arc_bluetooth_bridge.cc
index 5da2da0..e58f78ac 100644
--- a/components/arc/bluetooth/arc_bluetooth_bridge.cc
+++ b/components/arc/bluetooth/arc_bluetooth_bridge.cc
@@ -14,6 +14,7 @@
 #include <utility>
 
 #include "base/bind.h"
+#include "base/json/json_writer.h"
 #include "base/logging.h"
 #include "base/memory/ptr_util.h"
 #include "base/memory/singleton.h"
@@ -87,6 +88,22 @@
 // From https://www.bluetooth.com/specifications/assigned-numbers/baseband
 // The Class of Device for generic computer.
 constexpr uint32_t kBluetoothComputerClass = 0x100;
+// Timeout for Android to complete a disabling op to adapter.
+// In the case where an enabling op happens immediately after a disabling op,
+// Android takes the following enabling op as a no-op and waits 3~4 seconds for
+// the previous disabling op to finish, so the enabling op will never be
+// fulfilled by Android, and the disabling op will later routed back to Chrome
+// while Chrome's adapter is enabled. This results in the wrong power state
+// which should be enabled. Since the signaling from Android to Chrome for
+// Bluetooth is via Bluetooth HAL layer which run on the same process as
+// Bluetooth Service in Java space, so the signaling to Chrome about the
+// to-be-happen sleep cannot be done. This timeout tries to ensure the validity
+// and the order of toggles on power state sent to Android.
+// If Android takes more than 5 seconds to complete the intent initiated by
+// Chrome, Chrome will take EnableAdapter/DisableAdapter calls as a request from
+// Android to toggle the power state. The power state will be synced on both
+// Chrome and Android, but as a result, Bluetooth will be off.
+constexpr base::TimeDelta kPowerIntentTimeout = base::TimeDelta::FromSeconds(5);
 
 using GattStatusCallback =
     base::Callback<void(arc::mojom::BluetoothGattStatus)>;
@@ -281,8 +298,12 @@
 
 ArcBluetoothBridge::ArcBluetoothBridge(content::BrowserContext* context,
                                        ArcBridgeService* bridge_service)
-    : arc_bridge_service_(bridge_service), binding_(this), weak_factory_(this) {
+    : arc_bridge_service_(bridge_service),
+      binding_(this),
+      intent_helper_observer_(this),
+      weak_factory_(this) {
   arc_bridge_service_->bluetooth()->AddObserver(this);
+  arc_bridge_service_->intent_helper()->AddObserver(&intent_helper_observer_);
 
   if (BluetoothAdapterFactory::IsBluetoothSupported()) {
     VLOG(1) << "Registering bluetooth adapter.";
@@ -299,11 +320,14 @@
   if (bluetooth_adapter_)
     bluetooth_adapter_->RemoveObserver(this);
 
+  arc_bridge_service_->intent_helper()->RemoveObserver(
+      &intent_helper_observer_);
   arc_bridge_service_->bluetooth()->RemoveObserver(this);
 }
 
 void ArcBluetoothBridge::OnAdapterInitialized(
     scoped_refptr<BluetoothAdapter> adapter) {
+  DCHECK(adapter);
   DCHECK_CALLED_ON_VALID_THREAD(thread_checker_);
 
   // We can downcast here because we are always running on Chrome OS, and
@@ -311,13 +335,8 @@
   bluetooth_adapter_ =
       static_cast<bluez::BluetoothAdapterBlueZ*>(adapter.get());
 
-  // The ARC instance was ready before the Bluetooth adapter, hence we didn't
-  // register ourselves as an observer with it then. Since our adapter is
-  // ready, we should register it now.
-  if (!bluetooth_adapter_->HasObserver(this) &&
-      arc_bridge_service_->bluetooth()->has_instance()) {
+  if (!bluetooth_adapter_->HasObserver(this))
     bluetooth_adapter_->AddObserver(this);
-  }
 }
 
 void ArcBluetoothBridge::OnInstanceReady() {
@@ -329,16 +348,11 @@
   binding_.Bind(mojo::MakeRequest(&host_proxy));
   bluetooth_instance->Init(std::move(host_proxy));
 
-  // The Bluetooth adapter was ready before the ARC instance, hence we didn't
-  // register ourselves as an observer with it then. Since our instance is
-  // ready, we should register it now.
-  if (bluetooth_adapter_ && !bluetooth_adapter_->HasObserver(this))
-    bluetooth_adapter_->AddObserver(this);
+  is_bluetooth_instance_up_ = true;
 }
 
 void ArcBluetoothBridge::OnInstanceClosed() {
-  if (bluetooth_adapter_)
-    bluetooth_adapter_->RemoveObserver(this);
+  is_bluetooth_instance_up_ = false;
 }
 
 void ArcBluetoothBridge::SendDevice(const BluetoothDevice* device) const {
@@ -382,13 +396,29 @@
   OnGattConnectStateChanged(std::move(addr), true);
 }
 
+void ArcBluetoothBridge::AdapterPoweredChanged(BluetoothAdapter* adapter,
+                                               bool powered) {
+  AdapterPowerState power_change =
+      powered ? AdapterPowerState::TURN_ON : AdapterPowerState::TURN_OFF;
+  if (IsPowerChangeInitiatedByRemote(power_change))
+    DequeueRemotePowerChange(power_change);
+  else
+    EnqueueLocalPowerChange(power_change);
+}
+
 void ArcBluetoothBridge::DeviceAdded(BluetoothAdapter* adapter,
                                      BluetoothDevice* device) {
+  if (!IsInstanceUp())
+    return;
+
   SendDevice(device);
 }
 
 void ArcBluetoothBridge::DeviceChanged(BluetoothAdapter* adapter,
                                        BluetoothDevice* device) {
+  if (!IsInstanceUp())
+    return;
+
   SendDevice(device);
 
   if (!(device->GetType() & device::BLUETOOTH_TRANSPORT_LE))
@@ -414,6 +444,9 @@
 void ArcBluetoothBridge::DeviceAddressChanged(BluetoothAdapter* adapter,
                                               BluetoothDevice* device,
                                               const std::string& old_address) {
+  if (!IsInstanceUp())
+    return;
+
   if (old_address == device->GetAddress())
     return;
 
@@ -443,6 +476,9 @@
 void ArcBluetoothBridge::DevicePairedChanged(BluetoothAdapter* adapter,
                                              BluetoothDevice* device,
                                              bool new_paired_status) {
+  if (!IsInstanceUp())
+    return;
+
   DCHECK(adapter);
   DCHECK(device);
 
@@ -463,6 +499,9 @@
 
 void ArcBluetoothBridge::DeviceRemoved(BluetoothAdapter* adapter,
                                        BluetoothDevice* device) {
+  if (!IsInstanceUp())
+    return;
+
   DCHECK(adapter);
   DCHECK(device);
 
@@ -482,6 +521,8 @@
 void ArcBluetoothBridge::GattServiceAdded(BluetoothAdapter* adapter,
                                           BluetoothDevice* device,
                                           BluetoothRemoteGattService* service) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
@@ -489,11 +530,16 @@
     BluetoothAdapter* adapter,
     BluetoothDevice* device,
     BluetoothRemoteGattService* service) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
 void ArcBluetoothBridge::GattServicesDiscovered(BluetoothAdapter* adapter,
                                                 BluetoothDevice* device) {
+  if (!IsInstanceUp())
+    return;
+
   auto* btle_instance = ARC_GET_INSTANCE_FOR_METHOD(
       arc_bridge_service_->bluetooth(), OnSearchComplete);
   if (!btle_instance)
@@ -509,36 +555,48 @@
 void ArcBluetoothBridge::GattDiscoveryCompleteForService(
     BluetoothAdapter* adapter,
     BluetoothRemoteGattService* service) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
 void ArcBluetoothBridge::GattServiceChanged(
     BluetoothAdapter* adapter,
     BluetoothRemoteGattService* service) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
 void ArcBluetoothBridge::GattCharacteristicAdded(
     BluetoothAdapter* adapter,
     BluetoothRemoteGattCharacteristic* characteristic) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
 void ArcBluetoothBridge::GattCharacteristicRemoved(
     BluetoothAdapter* adapter,
     BluetoothRemoteGattCharacteristic* characteristic) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
 void ArcBluetoothBridge::GattDescriptorAdded(
     BluetoothAdapter* adapter,
     BluetoothRemoteGattDescriptor* descriptor) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
 void ArcBluetoothBridge::GattDescriptorRemoved(
     BluetoothAdapter* adapter,
     BluetoothRemoteGattDescriptor* descriptor) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
@@ -546,6 +604,9 @@
     BluetoothAdapter* adapter,
     BluetoothRemoteGattCharacteristic* characteristic,
     const std::vector<uint8_t>& value) {
+  if (!IsInstanceUp())
+    return;
+
   auto* btle_instance = ARC_GET_INSTANCE_FOR_METHOD(
       arc_bridge_service_->bluetooth(), OnGattNotify);
   if (!btle_instance)
@@ -574,6 +635,8 @@
     BluetoothAdapter* adapter,
     BluetoothRemoteGattDescriptor* descriptor,
     const std::vector<uint8_t>& value) {
+  if (!IsInstanceUp())
+    return;
   // Placeholder for GATT client functionality
 }
 
@@ -676,13 +739,13 @@
 
 void ArcBluetoothBridge::EnableAdapter(const EnableAdapterCallback& callback) {
   DCHECK(bluetooth_adapter_);
-  if (!bluetooth_adapter_->IsPowered()) {
-    bluetooth_adapter_->SetPowered(
-        true, base::Bind(&ArcBluetoothBridge::OnPoweredOn,
-                         weak_factory_.GetWeakPtr(), callback),
-        base::Bind(&ArcBluetoothBridge::OnPoweredError,
-                   weak_factory_.GetWeakPtr(), callback));
-    return;
+  if (IsPowerChangeInitiatedByLocal(AdapterPowerState::TURN_ON)) {
+    DequeueLocalPowerChange(AdapterPowerState::TURN_ON);
+  } else {
+    if (!bluetooth_adapter_->IsPowered()) {
+      EnqueueRemotePowerChange(AdapterPowerState::TURN_ON, callback);
+      return;
+    }
   }
 
   OnPoweredOn(callback);
@@ -691,11 +754,16 @@
 void ArcBluetoothBridge::DisableAdapter(
     const DisableAdapterCallback& callback) {
   DCHECK(bluetooth_adapter_);
-  bluetooth_adapter_->SetPowered(
-      false, base::Bind(&ArcBluetoothBridge::OnPoweredOff,
-                        weak_factory_.GetWeakPtr(), callback),
-      base::Bind(&ArcBluetoothBridge::OnPoweredError,
-                 weak_factory_.GetWeakPtr(), callback));
+  if (IsPowerChangeInitiatedByLocal(AdapterPowerState::TURN_OFF)) {
+    DequeueLocalPowerChange(AdapterPowerState::TURN_OFF);
+  } else {
+    if (bluetooth_adapter_->IsPowered()) {
+      EnqueueRemotePowerChange(AdapterPowerState::TURN_OFF, callback);
+      return;
+    }
+  }
+
+  OnPoweredOff(callback);
 }
 
 void ArcBluetoothBridge::GetAdapterProperty(mojom::BluetoothPropertyType type) {
@@ -1320,6 +1388,25 @@
                                  desc_id->uuid);
 }
 
+void ArcBluetoothBridge::SendBluetoothPoweredStateBroadcast(
+    AdapterPowerState powered) const {
+  auto* intent_instance = ARC_GET_INSTANCE_FOR_METHOD(
+      arc_bridge_service_->intent_helper(), SendBroadcast);
+  if (!intent_instance)
+    return;
+
+  base::DictionaryValue extras;
+  extras.SetBoolean("enable", powered == AdapterPowerState::TURN_ON);
+  std::string extras_json;
+  bool write_success = base::JSONWriter::Write(extras, &extras_json);
+  DCHECK(write_success);
+
+  intent_instance->SendBroadcast(
+      "org.chromium.arc.intent_helper.SET_BLUETOOTH_STATE",
+      "org.chromium.arc.intent_helper",
+      "org.chromium.arc.intent_helper.SettingsReceiver", extras_json);
+}
+
 void ArcBluetoothBridge::ReadGattCharacteristic(
     mojom::BluetoothAddressPtr remote_addr,
     mojom::BluetoothGattServiceIDPtr service_id,
@@ -1878,6 +1965,97 @@
                                          std::move(addr), bond_state);
 }
 
+ArcBluetoothBridge::IntentHelperObserver::IntentHelperObserver(
+    ArcBluetoothBridge* bluetooth_bridge)
+    : bluetooth_bridge_(bluetooth_bridge) {}
+
+ArcBluetoothBridge::IntentHelperObserver::~IntentHelperObserver() = default;
+
+void ArcBluetoothBridge::IntentHelperObserver::OnInstanceReady() {
+  bluetooth_bridge_->SendInitialPowerChange();
+}
+
+bool ArcBluetoothBridge::IsPowerChangeInitiatedByRemote(
+    ArcBluetoothBridge::AdapterPowerState powered) const {
+  return !remote_power_changes_.empty() &&
+         remote_power_changes_.front() == powered;
+}
+
+bool ArcBluetoothBridge::IsPowerChangeInitiatedByLocal(
+    ArcBluetoothBridge::AdapterPowerState powered) const {
+  return !local_power_changes_.empty() &&
+         local_power_changes_.front() == powered;
+}
+
+void ArcBluetoothBridge::SendInitialPowerChange() {
+  if (!bluetooth_adapter_ || !bluetooth_adapter_->IsPowered()) {
+    // The default power state of Bluetooth on Android is off, so there is no
+    // need to send an intent to turn off Bluetooth if the initial power state
+    // is off.
+    return;
+  }
+  EnqueueLocalPowerChange(AdapterPowerState::TURN_ON);
+}
+
+void ArcBluetoothBridge::EnqueueLocalPowerChange(
+    ArcBluetoothBridge::AdapterPowerState powered) {
+  local_power_changes_.push(powered);
+
+  if (power_intent_timer_.IsRunning())
+    return;
+
+  SendBluetoothPoweredStateBroadcast(local_power_changes_.front());
+  power_intent_timer_.Start(
+      FROM_HERE, kPowerIntentTimeout,
+      base::Bind(&ArcBluetoothBridge::DequeueLocalPowerChange,
+                 weak_factory_.GetWeakPtr(), powered));
+}
+
+void ArcBluetoothBridge::DequeueLocalPowerChange(
+    ArcBluetoothBridge::AdapterPowerState powered) {
+  power_intent_timer_.Stop();
+
+  if (!IsPowerChangeInitiatedByLocal(powered))
+    return;
+
+  AdapterPowerState current_change = local_power_changes_.front();
+  AdapterPowerState last_change = local_power_changes_.back();
+
+  // Compress the queue for power intent to reduce the amount of intents being
+  // sent to Android so that the powered state will be synced between Android
+  // and Chrome even if the state is toggled repeatedly on Chrome.
+  std::queue<AdapterPowerState> empty_queue;
+  std::swap(local_power_changes_, empty_queue);
+
+  if (last_change == current_change)
+    return;
+
+  local_power_changes_.push(last_change);
+
+  SendBluetoothPoweredStateBroadcast(last_change);
+  power_intent_timer_.Start(
+      FROM_HERE, kPowerIntentTimeout,
+      base::Bind(&ArcBluetoothBridge::DequeueLocalPowerChange,
+                 weak_factory_.GetWeakPtr(), last_change));
+}
+
+void ArcBluetoothBridge::EnqueueRemotePowerChange(
+    ArcBluetoothBridge::AdapterPowerState powered,
+    const EnableAdapterCallback& callback) {
+  remote_power_changes_.push(powered);
+  bluetooth_adapter_->SetPowered(
+      powered == AdapterPowerState::TURN_ON,
+      base::Bind(&ArcBluetoothBridge::OnPoweredOff, weak_factory_.GetWeakPtr(),
+                 callback),
+      base::Bind(&ArcBluetoothBridge::OnPoweredError,
+                 weak_factory_.GetWeakPtr(), callback));
+}
+
+void ArcBluetoothBridge::DequeueRemotePowerChange(
+    ArcBluetoothBridge::AdapterPowerState powered) {
+  remote_power_changes_.pop();
+}
+
 std::vector<mojom::BluetoothPropertyPtr>
 ArcBluetoothBridge::GetDeviceProperties(mojom::BluetoothPropertyType type,
                                         const BluetoothDevice* device) const {
diff --git a/components/arc/bluetooth/arc_bluetooth_bridge.h b/components/arc/bluetooth/arc_bluetooth_bridge.h
index 68936c0..f4d6e2b 100644
--- a/components/arc/bluetooth/arc_bluetooth_bridge.h
+++ b/components/arc/bluetooth/arc_bluetooth_bridge.h
@@ -9,6 +9,7 @@
 
 #include <map>
 #include <memory>
+#include <queue>
 #include <string>
 #include <unordered_map>
 #include <unordered_set>
@@ -17,6 +18,7 @@
 #include "base/callback.h"
 #include "base/timer/timer.h"
 #include "components/arc/common/bluetooth.mojom.h"
+#include "components/arc/common/intent_helper.mojom.h"
 #include "components/arc/instance_holder.h"
 #include "components/keyed_service/core/keyed_service.h"
 #include "device/bluetooth/bluetooth_adapter.h"
@@ -62,7 +64,10 @@
 
   void OnAdapterInitialized(scoped_refptr<device::BluetoothAdapter> adapter);
 
-  // Overridden from device::BluetoothAdadpter::Observer
+  // Overridden from device::BluetoothAdapter::Observer
+  void AdapterPoweredChanged(device::BluetoothAdapter* adapter,
+                             bool powered) override;
+
   void DeviceAdded(device::BluetoothAdapter* adapter,
                    device::BluetoothDevice* device) override;
 
@@ -341,6 +346,49 @@
       std::unique_ptr<device::BluetoothGattNotifySession> notify_session);
 
  private:
+  // IntentHelperObserver listens to the OnInstanceReady call on the intent
+  // helper which indicated the IntentHelperService has been brought up and the
+  // initial powered state of Bluetooth adapter can be sent to Android.
+  class IntentHelperObserver
+      : public InstanceHolder<mojom::IntentHelperInstance>::Observer {
+   public:
+    explicit IntentHelperObserver(ArcBluetoothBridge* bluetooth_bridge);
+    ~IntentHelperObserver() override;
+
+   private:
+    // InstanceHolder<mojom::IntentHelperInstance>::Observer overrides
+    void OnInstanceReady() override;
+
+    // ArcBluetoothBridge owns IntentHelperObserver, and ArcBluetoothBridge will
+    // always outlive it.
+    ArcBluetoothBridge* const bluetooth_bridge_;
+
+    DISALLOW_COPY_AND_ASSIGN(IntentHelperObserver);
+  };
+
+  // Power state change on Bluetooth adapter.
+  enum class AdapterPowerState { TURN_OFF, TURN_ON };
+
+  bool IsInstanceUp() const { return is_bluetooth_instance_up_; }
+
+  // Indicates if a power change is initiated by Chrome / Android.
+  bool IsPowerChangeInitiatedByRemote(
+      ArcBluetoothBridge::AdapterPowerState powered) const;
+  bool IsPowerChangeInitiatedByLocal(
+      ArcBluetoothBridge::AdapterPowerState powered) const;
+
+  // Called by IntentHelperObserver to send the initial power state.
+  void SendInitialPowerChange();
+
+  // Manages the powered change intents sent to Android.
+  void EnqueueLocalPowerChange(AdapterPowerState powered);
+  void DequeueLocalPowerChange(AdapterPowerState powered);
+
+  // Manages the powered change requests received from Android.
+  void EnqueueRemotePowerChange(AdapterPowerState powered,
+                                const EnableAdapterCallback& callback);
+  void DequeueRemotePowerChange(AdapterPowerState powered);
+
   std::vector<mojom::BluetoothPropertyPtr> GetDeviceProperties(
       mojom::BluetoothPropertyType type,
       const device::BluetoothDevice* device) const;
@@ -362,6 +410,9 @@
       mojom::BluetoothGattIDPtr char_id,
       mojom::BluetoothGattIDPtr desc_id) const;
 
+  // Send the power status change to Android via an intent.
+  void SendBluetoothPoweredStateBroadcast(AdapterPowerState powered) const;
+
   // Propagates the list of paired device to Android.
   void SendCachedPairedDevices() const;
 
@@ -471,6 +522,19 @@
   // Timer to turn adapter discoverable off.
   base::OneShotTimer discoverable_off_timer_;
 
+  // This indicates whether the remote Bluetooth ARC instance is ready to
+  // receive events.
+  bool is_bluetooth_instance_up_;
+
+  // Observer to listen the start-up of Intent Helper.
+  IntentHelperObserver intent_helper_observer_;
+  // Queue to track the powered state changes initiated by Android.
+  std::queue<AdapterPowerState> remote_power_changes_;
+  // Queue to track the powered state changes initiated by Chrome.
+  std::queue<AdapterPowerState> local_power_changes_;
+  // Timer to track the completion of power-changed intent sent to Android.
+  base::OneShotTimer power_intent_timer_;
+
   // Holds advertising data registered by the instance.
   //
   // When a handle is reserved, an entry is placed into the advertisements_
diff --git a/components/arc/net/arc_net_host_impl.cc b/components/arc/net/arc_net_host_impl.cc
index 54e2e32..9336911 100644
--- a/components/arc/net/arc_net_host_impl.cc
+++ b/components/arc/net/arc_net_host_impl.cc
@@ -504,8 +504,7 @@
                                             onc::network_config::kWiFi);
   wifi_dict->SetStringWithoutPathExpansion(onc::wifi::kHexSSID,
                                            cfg->hexssid.value());
-  wifi_dict->SetBooleanWithoutPathExpansion(onc::wifi::kAutoConnect,
-                                            details->autoconnect);
+  wifi_dict->SetKey(onc::wifi::kAutoConnect, base::Value(details->autoconnect));
   if (cfg->security.empty()) {
     wifi_dict->SetStringWithoutPathExpansion(onc::wifi::kSecurity,
                                              onc::wifi::kSecurityNone);
diff --git a/components/metrics/metrics_log.cc b/components/metrics/metrics_log.cc
index 7fc04fc..e6215d799 100644
--- a/components/metrics/metrics_log.cc
+++ b/components/metrics/metrics_log.cc
@@ -27,7 +27,6 @@
 #include "components/metrics/metrics_pref_names.h"
 #include "components/metrics/metrics_provider.h"
 #include "components/metrics/metrics_service_client.h"
-#include "components/metrics/persistent_system_profile.h"
 #include "components/metrics/proto/histogram_event.pb.h"
 #include "components/metrics/proto/system_profile.pb.h"
 #include "components/metrics/proto/user_action_event.pb.h"
@@ -88,13 +87,11 @@
 MetricsLog::MetricsLog(const std::string& client_id,
                        int session_id,
                        LogType log_type,
-                       MetricsServiceClient* client,
-                       PrefService* local_state)
+                       MetricsServiceClient* client)
     : closed_(false),
       log_type_(log_type),
       client_(client),
-      creation_time_(base::TimeTicks::Now()),
-      local_state_(local_state) {
+      creation_time_(base::TimeTicks::Now()) {
   if (IsTestingID(client_id))
     uma_proto_.set_client_id(0);
   else
@@ -109,10 +106,6 @@
 
   SystemProfileProto* system_profile = uma_proto()->mutable_system_profile();
   RecordCoreSystemProfile(client_, system_profile);
-  if (log_type_ == ONGOING_LOG) {
-    GlobalPersistentSystemProfile::GetInstance()->SetSystemProfile(
-        *system_profile, /*complete=*/false);
-  }
 }
 
 MetricsLog::~MetricsLog() {
@@ -217,9 +210,6 @@
   // uma log upload, just as we send histogram data.
   WriteRealtimeStabilityAttributes(incremental_uptime, uptime);
 
-  if (local_state_->GetBoolean(prefs::kMetricsResetIds))
-    UMA_HISTOGRAM_BOOLEAN("UMA.IsClonedInstall", true);
-
   delegating_provider->ProvideCurrentSessionData(uma_proto());
 }
 
@@ -269,7 +259,7 @@
     stability->set_uptime_sec(uptime_sec);
 }
 
-std::string MetricsLog::RecordEnvironment(
+const SystemProfileProto& MetricsLog::RecordEnvironment(
     DelegatingProvider* delegating_provider,
     int64_t install_date,
     int64_t metrics_reporting_enabled_date) {
@@ -300,16 +290,7 @@
 
   delegating_provider->ProvideSystemProfileMetrics(system_profile);
 
-  EnvironmentRecorder recorder(local_state_);
-  std::string serialized_proto =
-      recorder.SerializeAndRecordEnvironmentToPrefs(*system_profile);
-
-  if (log_type_ == ONGOING_LOG) {
-    GlobalPersistentSystemProfile::GetInstance()->SetSystemProfile(
-        serialized_proto, /*complete=*/true);
-  }
-
-  return serialized_proto;
+  return *system_profile;
 }
 
 bool MetricsLog::LoadIndependentMetrics(MetricsProvider* metrics_provider) {
@@ -321,12 +302,13 @@
                                                      &snapshot_manager);
 }
 
-bool MetricsLog::LoadSavedEnvironmentFromPrefs(std::string* app_version) {
+bool MetricsLog::LoadSavedEnvironmentFromPrefs(PrefService* local_state,
+                                               std::string* app_version) {
   DCHECK(app_version);
   app_version->clear();
 
   SystemProfileProto* system_profile = uma_proto()->mutable_system_profile();
-  EnvironmentRecorder recorder(local_state_);
+  EnvironmentRecorder recorder(local_state);
   bool success = recorder.LoadEnvironmentFromPrefs(system_profile);
   if (success)
     *app_version = system_profile->app_version();
diff --git a/components/metrics/metrics_log.h b/components/metrics/metrics_log.h
index d113e06..af30a57 100644
--- a/components/metrics/metrics_log.h
+++ b/components/metrics/metrics_log.h
@@ -55,8 +55,7 @@
   MetricsLog(const std::string& client_id,
              int session_id,
              LogType log_type,
-             MetricsServiceClient* client,
-             PrefService* local_state);
+             MetricsServiceClient* client);
   virtual ~MetricsLog();
 
   // Registers local state prefs used by this class.
@@ -91,14 +90,12 @@
   // TODO(rkaplow): I think this can be a little refactored as it currently
   // records a pretty arbitrary set of things.
   // Records the current operating environment, including metrics provided by
-  // the specified |delegating_provider|.  Takes the list of synthetic
-  // trial IDs as a parameter. A synthetic trial is one that is set up
-  // dynamically by code in Chrome. For example, a pref may be mapped to a
-  // synthetic trial such that the group is determined by the pref value. The
-  // current environment is returned serialized as a string.
-  std::string RecordEnvironment(DelegatingProvider* delegating_provider,
-                                int64_t install_date,
-                                int64_t metrics_reporting_enabled_date);
+  // the specified |delegating_provider|. The current environment is
+  // returned as a SystemProfileProto.
+  const SystemProfileProto& RecordEnvironment(
+      DelegatingProvider* delegating_provider,
+      int64_t install_date,
+      int64_t metrics_reporting_enabled_date);
 
   // Loads a saved system profile and the associated metrics into the log.
   // Returns true on success. Keep calling it with fresh logs until it returns
@@ -109,7 +106,8 @@
   // call from prefs. On success, returns true and |app_version| contains the
   // recovered version. Otherwise (if there was no saved environment in prefs
   // or it could not be decoded), returns false and |app_version| is empty.
-  bool LoadSavedEnvironmentFromPrefs(std::string* app_version);
+  bool LoadSavedEnvironmentFromPrefs(PrefService* local_state,
+                                     std::string* app_version);
 
   // Record data from providers about the previous session into the log.
   void RecordPreviousSessionData(DelegatingProvider* delegating_provider);
@@ -181,8 +179,6 @@
   // The time when the current log was created.
   const base::TimeTicks creation_time_;
 
-  PrefService* local_state_;
-
   DISALLOW_COPY_AND_ASSIGN(MetricsLog);
 };
 
diff --git a/components/metrics/metrics_log_manager_unittest.cc b/components/metrics/metrics_log_manager_unittest.cc
index 3dafa34..4857a99 100644
--- a/components/metrics/metrics_log_manager_unittest.cc
+++ b/components/metrics/metrics_log_manager_unittest.cc
@@ -35,7 +35,7 @@
   MetricsLogStore* log_store() { return &log_store_; }
 
   MetricsLog* CreateLog(MetricsLog::LogType log_type) {
-    return new MetricsLog("id", 0, log_type, &client_, &pref_service_);
+    return new MetricsLog("id", 0, log_type, &client_);
   }
 
  private:
diff --git a/components/metrics/metrics_log_store_unittest.cc b/components/metrics/metrics_log_store_unittest.cc
index 5c35274..50b78c7 100644
--- a/components/metrics/metrics_log_store_unittest.cc
+++ b/components/metrics/metrics_log_store_unittest.cc
@@ -21,7 +21,7 @@
   ~MetricsLogStoreTest() override {}
 
   MetricsLog* CreateLog(MetricsLog::LogType log_type) {
-    return new MetricsLog("id", 0, log_type, &client_, &pref_service_);
+    return new MetricsLog("id", 0, log_type, &client_);
   }
 
   // Returns the stored number of logs of the given type.
diff --git a/components/metrics/metrics_log_unittest.cc b/components/metrics/metrics_log_unittest.cc
index 58160a0e7..3a91d46 100644
--- a/components/metrics/metrics_log_unittest.cc
+++ b/components/metrics/metrics_log_unittest.cc
@@ -55,8 +55,7 @@
                  LogType log_type,
                  MetricsServiceClient* client,
                  TestingPrefServiceSimple* prefs)
-      : MetricsLog(client_id, session_id, log_type, client, prefs),
-        prefs_(prefs) {
+      : MetricsLog(client_id, session_id, log_type, client), prefs_(prefs) {
     InitPrefs();
   }
 
@@ -130,10 +129,10 @@
   TestMetricsServiceClient client;
   TestingPrefServiceSimple prefs;
 
-  MetricsLog log1("id", 0, MetricsLog::ONGOING_LOG, &client, &prefs);
+  MetricsLog log1("id", 0, MetricsLog::ONGOING_LOG, &client);
   EXPECT_EQ(MetricsLog::ONGOING_LOG, log1.log_type());
 
-  MetricsLog log2("id", 0, MetricsLog::INITIAL_STABILITY_LOG, &client, &prefs);
+  MetricsLog log2("id", 0, MetricsLog::INITIAL_STABILITY_LOG, &client);
   EXPECT_EQ(MetricsLog::INITIAL_STABILITY_LOG, log2.log_type());
 }
 
@@ -142,7 +141,7 @@
   client.set_version_string("bogus version");
   TestingPrefServiceSimple prefs;
   MetricsLog log("totally bogus client ID", 137, MetricsLog::ONGOING_LOG,
-                 &client, &prefs);
+                 &client);
   log.CloseLog();
 
   std::string encoded;
@@ -257,14 +256,17 @@
       kClientId, kSessionId, MetricsLog::ONGOING_LOG, &client, &prefs_);
 
   DelegatingProvider delegating_provider;
-  log.RecordEnvironment(&delegating_provider, kInstallDate, kEnabledDate);
+  const SystemProfileProto& system_profile =
+      log.RecordEnvironment(&delegating_provider, kInstallDate, kEnabledDate);
+  EnvironmentRecorder writer(&prefs_);
+  writer.SerializeAndRecordEnvironmentToPrefs(system_profile);
   // Check that the system profile on the log has the correct values set.
   CheckSystemProfile(log.system_profile());
 
   // Check that the system profile has also been written to prefs.
   SystemProfileProto decoded_system_profile;
-  EnvironmentRecorder recorder(&prefs_);
-  EXPECT_TRUE(recorder.LoadEnvironmentFromPrefs(&decoded_system_profile));
+  EnvironmentRecorder reader(&prefs_);
+  EXPECT_TRUE(reader.LoadEnvironmentFromPrefs(&decoded_system_profile));
   CheckSystemProfile(decoded_system_profile);
 }
 
diff --git a/components/metrics/metrics_service.cc b/components/metrics/metrics_service.cc
index 5a93e5b..a3aa510 100644
--- a/components/metrics/metrics_service.cc
+++ b/components/metrics/metrics_service.cc
@@ -154,6 +154,7 @@
 #include "components/metrics/metrics_rotation_scheduler.h"
 #include "components/metrics/metrics_service_client.h"
 #include "components/metrics/metrics_state_manager.h"
+#include "components/metrics/persistent_system_profile.h"
 #include "components/metrics/stability_metrics_provider.h"
 #include "components/metrics/url_constants.h"
 #include "components/prefs/pref_registry_simple.h"
@@ -236,6 +237,8 @@
   RegisterMetricsProvider(
       base::MakeUnique<StabilityMetricsProvider>(local_state_));
 
+  RegisterMetricsProvider(state_manager_->GetProvider());
+
   RegisterMetricsProvider(base::MakeUnique<variations::FieldTrialsProvider>(
       &synthetic_trial_registry_, base::StringPiece()));
 }
@@ -316,6 +319,12 @@
 
   state_manager_->ForceClientIdCreation();
   client_->SetMetricsClientId(state_manager_->client_id());
+
+  SystemProfileProto system_profile;
+  MetricsLog::RecordCoreSystemProfile(client_, &system_profile);
+  GlobalPersistentSystemProfile::GetInstance()->SetSystemProfile(
+      system_profile, /*complete=*/false);
+
   if (!log_manager_.current_log())
     OpenNewLog();
 
@@ -733,7 +742,7 @@
   // log describes stats from the _previous_ session.
   std::string system_profile_app_version;
   if (!initial_stability_log->LoadSavedEnvironmentFromPrefs(
-          &system_profile_app_version)) {
+          local_state_, &system_profile_app_version)) {
     return false;
   }
   if (system_profile_app_version != prefs_previous_version)
@@ -812,15 +821,29 @@
 std::unique_ptr<MetricsLog> MetricsService::CreateLog(
     MetricsLog::LogType log_type) {
   return base::MakeUnique<MetricsLog>(state_manager_->client_id(), session_id_,
-                                      log_type, client_, local_state_);
+                                      log_type, client_);
+}
+
+std::string MetricsService::RecordCurrentEnvironmentHelper(
+    MetricsLog* log,
+    PrefService* local_state,
+    DelegatingProvider* delegating_provider,
+    int64_t install_date,
+    int64_t enable_date) {
+  const SystemProfileProto& system_profile =
+      log->RecordEnvironment(delegating_provider, install_date, enable_date);
+  EnvironmentRecorder recorder(local_state);
+  return recorder.SerializeAndRecordEnvironmentToPrefs(system_profile);
 }
 
 void MetricsService::RecordCurrentEnvironment(MetricsLog* log) {
   DCHECK(client_);
-  std::string serialized_environment =
-      log->RecordEnvironment(&delegating_provider_, GetInstallDate(),
-                             GetMetricsReportingEnabledDate());
-  client_->OnEnvironmentUpdate(&serialized_environment);
+  std::string serialized_proto = RecordCurrentEnvironmentHelper(
+      log, local_state_, &delegating_provider_, GetInstallDate(),
+      GetMetricsReportingEnabledDate());
+  GlobalPersistentSystemProfile::GetInstance()->SetSystemProfile(
+      serialized_proto, /*complete=*/true);
+  client_->OnEnvironmentUpdate(&serialized_proto);
 }
 
 void MetricsService::RecordCurrentHistograms() {
diff --git a/components/metrics/metrics_service.h b/components/metrics/metrics_service.h
index cbb53e15..2dfe686 100644
--- a/components/metrics/metrics_service.h
+++ b/components/metrics/metrics_service.h
@@ -183,6 +183,16 @@
     return reporting_service_.metrics_log_store();
   }
 
+  // Records the current environment (system profile) in |log|, and persists
+  // the results in prefs.
+  // Exposed for testing.
+  static std::string RecordCurrentEnvironmentHelper(
+      MetricsLog* log,
+      PrefService* local_state,
+      DelegatingProvider* delegating_provider,
+      int64_t install_date,
+      int64_t enable_date);
+
  private:
   // The MetricsService has a lifecycle that is stored as a state.
   // See metrics_service.cc for description of this lifecycle.
@@ -284,7 +294,9 @@
   // Creates a new MetricsLog instance with the given |log_type|.
   std::unique_ptr<MetricsLog> CreateLog(MetricsLog::LogType log_type);
 
-  // Records the current environment (system profile) in |log|.
+  // Records the current environment (system profile) in |log|, and persists
+  // the results in prefs and GlobalPersistentSystemProfile.
+  // Exposed for testing.
   void RecordCurrentEnvironment(MetricsLog* log);
 
   // Record complete list of histograms into the current log.
diff --git a/components/metrics/metrics_service_unittest.cc b/components/metrics/metrics_service_unittest.cc
index 30d64a7d..bcf85090 100644
--- a/components/metrics/metrics_service_unittest.cc
+++ b/components/metrics/metrics_service_unittest.cc
@@ -56,6 +56,7 @@
 
   using MetricsService::log_manager;
   using MetricsService::log_store;
+  using MetricsService::RecordCurrentEnvironmentHelper;
 
  private:
   DISALLOW_COPY_AND_ASSIGN(TestMetricsService);
@@ -65,13 +66,8 @@
  public:
   TestMetricsLog(const std::string& client_id,
                  int session_id,
-                 MetricsServiceClient* client,
-                 PrefService* local_state)
-      : MetricsLog(client_id,
-                   session_id,
-                   MetricsLog::ONGOING_LOG,
-                   client,
-                   local_state) {}
+                 MetricsServiceClient* client)
+      : MetricsLog(client_id, session_id, MetricsLog::ONGOING_LOG, client) {}
 
   ~TestMetricsLog() override {}
 
@@ -190,9 +186,10 @@
   // Save an existing system profile to prefs, to correspond to what would be
   // saved from a previous session.
   TestMetricsServiceClient client;
-  TestMetricsLog log("client", 1, &client, GetLocalState());
+  TestMetricsLog log("client", 1, &client);
   DelegatingProvider delegating_provider;
-  log.RecordEnvironment(&delegating_provider, 0, 0);
+  TestMetricsService::RecordCurrentEnvironmentHelper(
+      &log, GetLocalState(), &delegating_provider, 0, 0);
 
   // Record stability build time and version from previous session, so that
   // stability metrics (including exited cleanly flag) won't be cleared.
@@ -261,9 +258,10 @@
   // Save an existing system profile to prefs, to correspond to what would be
   // saved from a previous session.
   TestMetricsServiceClient client;
-  TestMetricsLog log("client", 1, &client, GetLocalState());
+  TestMetricsLog log("client", 1, &client);
   DelegatingProvider delegating_provider;
-  log.RecordEnvironment(&delegating_provider, 0, 0);
+  TestMetricsService::RecordCurrentEnvironmentHelper(
+      &log, GetLocalState(), &delegating_provider, 0, 0);
 
   // Record stability build time and version from previous session, so that
   // stability metrics (including exited cleanly flag) won't be cleared.
diff --git a/components/metrics/metrics_state_manager.cc b/components/metrics/metrics_state_manager.cc
index 45c2c48..2e93a8e 100644
--- a/components/metrics/metrics_state_manager.cc
+++ b/components/metrics/metrics_state_manager.cc
@@ -20,6 +20,7 @@
 #include "components/metrics/enabled_state_provider.h"
 #include "components/metrics/machine_id_provider.h"
 #include "components/metrics/metrics_pref_names.h"
+#include "components/metrics/metrics_provider.h"
 #include "components/metrics/metrics_switches.h"
 #include "components/prefs/pref_registry_simple.h"
 #include "components/prefs/pref_service.h"
@@ -50,6 +51,22 @@
                               low_entropy_source_value);
 }
 
+class MetricsStateMetricsProvider : public MetricsProvider {
+ public:
+  MetricsStateMetricsProvider(PrefService* local_state)
+      : local_state_(local_state) {}
+
+  // MetricsProvider:
+  void ProvideCurrentSessionData(
+      ChromeUserMetricsExtension* uma_proto) override {
+    if (local_state_->GetBoolean(prefs::kMetricsResetIds))
+      UMA_HISTOGRAM_BOOLEAN("UMA.IsClonedInstall", true);
+  }
+
+ private:
+  PrefService* local_state_;
+};
+
 }  // namespace
 
 // static
@@ -81,6 +98,10 @@
   instance_exists_ = false;
 }
 
+std::unique_ptr<MetricsProvider> MetricsStateManager::GetProvider() {
+  return base::MakeUnique<MetricsStateMetricsProvider>(local_state_);
+}
+
 bool MetricsStateManager::IsMetricsReportingEnabled() {
   return enabled_state_provider_->IsReportingEnabled();
 }
diff --git a/components/metrics/metrics_state_manager.h b/components/metrics/metrics_state_manager.h
index fbb0f595..2eb84369 100644
--- a/components/metrics/metrics_state_manager.h
+++ b/components/metrics/metrics_state_manager.h
@@ -23,6 +23,7 @@
 
 class ClonedInstallDetector;
 class EnabledStateProvider;
+class MetricsProvider;
 
 // Responsible for managing MetricsService state prefs, specifically the UMA
 // client id and low entropy source. Code outside the metrics directory should
@@ -41,6 +42,8 @@
 
   virtual ~MetricsStateManager();
 
+  std::unique_ptr<MetricsProvider> GetProvider();
+
   // Returns true if the user has consented to sending metric reports, and there
   // is no other reason to disable reporting. One such reason is client
   // sampling, and this client isn't in the sample.
diff --git a/components/proximity_auth/proximity_auth_local_state_pref_manager_unittest.cc b/components/proximity_auth/proximity_auth_local_state_pref_manager_unittest.cc
index c5be80a..d8257d1d5 100644
--- a/components/proximity_auth/proximity_auth_local_state_pref_manager_unittest.cc
+++ b/components/proximity_auth/proximity_auth_local_state_pref_manager_unittest.cc
@@ -58,11 +58,11 @@
     user1_prefs->SetIntegerWithoutPathExpansion(
         proximity_auth::prefs::kEasyUnlockProximityThreshold,
         kProximityThreshold1);
-    user1_prefs->SetBooleanWithoutPathExpansion(
+    user1_prefs->SetKey(
         proximity_auth::prefs::kProximityAuthIsChromeOSLoginEnabled,
-        kIsChromeOSLoginEnabled1);
-    user1_prefs->SetBooleanWithoutPathExpansion(
-        proximity_auth::prefs::kEasyUnlockAllowed, kIsEasyUnlockAllowed1);
+        base::Value(kIsChromeOSLoginEnabled1));
+    user1_prefs->SetKey(proximity_auth::prefs::kEasyUnlockAllowed,
+                        base::Value(kIsEasyUnlockAllowed1));
     DictionaryPrefUpdate update1(&local_state_,
                                  prefs::kEasyUnlockLocalStateUserPrefs);
     update1->SetWithoutPathExpansion(user1_.GetUserEmail(),
@@ -73,11 +73,11 @@
     user2_prefs->SetIntegerWithoutPathExpansion(
         proximity_auth::prefs::kEasyUnlockProximityThreshold,
         kProximityThreshold2);
-    user2_prefs->SetBooleanWithoutPathExpansion(
+    user2_prefs->SetKey(
         proximity_auth::prefs::kProximityAuthIsChromeOSLoginEnabled,
-        kIsChromeOSLoginEnabled2);
-    user2_prefs->SetBooleanWithoutPathExpansion(
-        proximity_auth::prefs::kEasyUnlockAllowed, kIsEasyUnlockAllowed2);
+        base::Value(kIsChromeOSLoginEnabled2));
+    user2_prefs->SetKey(proximity_auth::prefs::kEasyUnlockAllowed,
+                        base::Value(kIsEasyUnlockAllowed2));
 
     DictionaryPrefUpdate update2(&local_state_,
                                  prefs::kEasyUnlockLocalStateUserPrefs);
diff --git a/components/proximity_auth/proximity_auth_profile_pref_manager.cc b/components/proximity_auth/proximity_auth_profile_pref_manager.cc
index 691c7e6..dc9eb12 100644
--- a/components/proximity_auth/proximity_auth_profile_pref_manager.cc
+++ b/components/proximity_auth/proximity_auth_profile_pref_manager.cc
@@ -79,12 +79,12 @@
   std::unique_ptr<base::DictionaryValue> user_prefs_dict(
       new base::DictionaryValue());
 
-  user_prefs_dict->SetBooleanWithoutPathExpansion(prefs::kEasyUnlockAllowed,
-                                                  IsEasyUnlockAllowed());
+  user_prefs_dict->SetKey(prefs::kEasyUnlockAllowed,
+                          base::Value(IsEasyUnlockAllowed()));
   user_prefs_dict->SetIntegerWithoutPathExpansion(
       prefs::kEasyUnlockProximityThreshold, GetProximityThreshold());
-  user_prefs_dict->SetBooleanWithoutPathExpansion(
-      prefs::kProximityAuthIsChromeOSLoginEnabled, IsChromeOSLoginEnabled());
+  user_prefs_dict->SetKey(prefs::kProximityAuthIsChromeOSLoginEnabled,
+                          base::Value(IsChromeOSLoginEnabled()));
 
   DictionaryPrefUpdate update(local_state_,
                               prefs::kEasyUnlockLocalStateUserPrefs);
diff --git a/components/signin/ios/browser/account_consistency_service.mm b/components/signin/ios/browser/account_consistency_service.mm
index a56cc1b..30fcf3f 100644
--- a/components/signin/ios/browser/account_consistency_service.mm
+++ b/components/signin/ios/browser/account_consistency_service.mm
@@ -373,7 +373,7 @@
       case ADD_CHROME_CONNECTED_COOKIE:
         // Add request.domain to prefs, use |true| as a dummy value (that is
         // never used), as the dictionary is used as a set.
-        update->SetBooleanWithoutPathExpansion(request.domain, true);
+        update->SetKey(request.domain, base::Value(true));
         break;
       case REMOVE_CHROME_CONNECTED_COOKIE:
         // Remove request.domain from prefs.
diff --git a/components/user_manager/user_manager_base.cc b/components/user_manager/user_manager_base.cc
index dddc4e56..92e81fbf 100644
--- a/components/user_manager/user_manager_base.cc
+++ b/components/user_manager/user_manager_base.cc
@@ -396,8 +396,8 @@
   {
     DictionaryPrefUpdate force_online_update(GetLocalState(),
                                              kUserForceOnlineSignin);
-    force_online_update->SetBooleanWithoutPathExpansion(
-        account_id.GetUserEmail(), force_online_signin);
+    force_online_update->SetKey(account_id.GetUserEmail(),
+                                base::Value(force_online_signin));
   }
   GetLocalState()->CommitPendingWrite();
 }
diff --git a/components/variations/client_filterable_state.cc b/components/variations/client_filterable_state.cc
index 0e36db82..6fda4f4 100644
--- a/components/variations/client_filterable_state.cc
+++ b/components/variations/client_filterable_state.cc
@@ -20,6 +20,8 @@
   return Study::PLATFORM_CHROMEOS;
 #elif defined(OS_ANDROID)
   return Study::PLATFORM_ANDROID;
+#elif defined(OS_FUCHSIA)
+  return Study::PLATFORM_FUCHSIA;
 #elif defined(OS_LINUX) || defined(OS_BSD) || defined(OS_SOLARIS)
   // Default BSD and SOLARIS to Linux to not break those builds, although these
   // platforms are not officially supported by Chrome.
diff --git a/components/variations/proto/study.proto b/components/variations/proto/study.proto
index b7a0bb69b..2ed59b7 100644
--- a/components/variations/proto/study.proto
+++ b/components/variations/proto/study.proto
@@ -189,6 +189,7 @@
     PLATFORM_ANDROID         = 4;
     PLATFORM_IOS             = 5;
     PLATFORM_ANDROID_WEBVIEW = 6;
+    PLATFORM_FUCHSIA         = 7;
   }
 
   // Possible form factors Chrome is running on.
diff --git a/components/variations/study_filtering_unittest.cc b/components/variations/study_filtering_unittest.cc
index c9728e4..acf097a 100644
--- a/components/variations/study_filtering_unittest.cc
+++ b/components/variations/study_filtering_unittest.cc
@@ -215,8 +215,7 @@
       Study::PLATFORM_WINDOWS,         Study::PLATFORM_MAC,
       Study::PLATFORM_LINUX,           Study::PLATFORM_CHROMEOS,
       Study::PLATFORM_ANDROID,         Study::PLATFORM_IOS,
-      Study::PLATFORM_ANDROID_WEBVIEW,
-  };
+      Study::PLATFORM_ANDROID_WEBVIEW, Study::PLATFORM_FUCHSIA};
   ASSERT_EQ(Study::Platform_ARRAYSIZE, static_cast<int>(arraysize(platforms)));
   bool platform_added[arraysize(platforms)] = { 0 };
 
diff --git a/components/viz/client/BUILD.gn b/components/viz/client/BUILD.gn
index fb3ff53ca..625ab212 100644
--- a/components/viz/client/BUILD.gn
+++ b/components/viz/client/BUILD.gn
@@ -10,6 +10,7 @@
     "client_layer_tree_frame_sink.h",
     "client_shared_bitmap_manager.cc",
     "client_shared_bitmap_manager.h",
+    "hit_test_data_provider.h",
     "local_surface_id_provider.cc",
     "local_surface_id_provider.h",
   ]
@@ -21,5 +22,6 @@
     "//components/viz/common",
     "//mojo/public/cpp/bindings",
     "//services/viz/public/interfaces/compositing",
+    "//services/viz/public/interfaces/hit_test",
   ]
 }
diff --git a/components/viz/client/DEPS b/components/viz/client/DEPS
index 2c27406..5e958cd 100644
--- a/components/viz/client/DEPS
+++ b/components/viz/client/DEPS
@@ -7,5 +7,6 @@
   "+mojo/public/cpp/bindings",
   "+mojo/public/cpp/system",
   "+services/viz/public/interfaces/compositing",
+  "+services/viz/public/interfaces/hit_test",
   "+ui/gfx/geometry",
 ]
diff --git a/components/viz/client/client_layer_tree_frame_sink.cc b/components/viz/client/client_layer_tree_frame_sink.cc
index 76524c0..06982cc 100644
--- a/components/viz/client/client_layer_tree_frame_sink.cc
+++ b/components/viz/client/client_layer_tree_frame_sink.cc
@@ -8,6 +8,7 @@
 #include "base/memory/ptr_util.h"
 #include "cc/output/compositor_frame.h"
 #include "cc/output/layer_tree_frame_sink_client.h"
+#include "components/viz/client/hit_test_data_provider.h"
 #include "components/viz/client/local_surface_id_provider.h"
 #include "components/viz/common/frame_sinks/begin_frame_args.h"
 #include "components/viz/common/resources/shared_bitmap_manager.h"
@@ -22,12 +23,14 @@
     std::unique_ptr<SyntheticBeginFrameSource> synthetic_begin_frame_source,
     mojom::CompositorFrameSinkPtrInfo compositor_frame_sink_info,
     mojom::CompositorFrameSinkClientRequest client_request,
+    std::unique_ptr<HitTestDataProvider> hit_test_data_provider,
     std::unique_ptr<LocalSurfaceIdProvider> local_surface_id_provider,
     bool enable_surface_synchronization)
     : cc::LayerTreeFrameSink(std::move(context_provider),
                              std::move(worker_context_provider),
                              gpu_memory_buffer_manager,
                              shared_bitmap_manager),
+      hit_test_data_provider_(std::move(hit_test_data_provider)),
       local_surface_id_provider_(std::move(local_surface_id_provider)),
       synthetic_begin_frame_source_(std::move(synthetic_begin_frame_source)),
       compositor_frame_sink_info_(std::move(compositor_frame_sink_info)),
@@ -43,9 +46,11 @@
     std::unique_ptr<SyntheticBeginFrameSource> synthetic_begin_frame_source,
     mojom::CompositorFrameSinkPtrInfo compositor_frame_sink_info,
     mojom::CompositorFrameSinkClientRequest client_request,
+    std::unique_ptr<HitTestDataProvider> hit_test_data_provider,
     std::unique_ptr<LocalSurfaceIdProvider> local_surface_id_provider,
     bool enable_surface_synchronization)
     : cc::LayerTreeFrameSink(std::move(vulkan_context_provider)),
+      hit_test_data_provider_(std::move(hit_test_data_provider)),
       local_surface_id_provider_(std::move(local_surface_id_provider)),
       synthetic_begin_frame_source_(std::move(synthetic_begin_frame_source)),
       compositor_frame_sink_info_(std::move(compositor_frame_sink_info)),
@@ -116,6 +121,8 @@
         local_surface_id_provider_->GetLocalSurfaceIdForFrame(frame);
   }
 
+  // TODO(gklassen): Use hit_test_data_provider_->GetHitTestData() to obtain
+  // hit-test data and send to |compositor_frame_sink_|.
   compositor_frame_sink_->SubmitCompositorFrame(local_surface_id_,
                                                 std::move(frame));
 }
diff --git a/components/viz/client/client_layer_tree_frame_sink.h b/components/viz/client/client_layer_tree_frame_sink.h
index 1bade0ba..3242f437 100644
--- a/components/viz/client/client_layer_tree_frame_sink.h
+++ b/components/viz/client/client_layer_tree_frame_sink.h
@@ -17,6 +17,7 @@
 
 namespace viz {
 
+class HitTestDataProvider;
 class LocalSurfaceIdProvider;
 class SharedBitmapManager;
 
@@ -32,6 +33,7 @@
       std::unique_ptr<SyntheticBeginFrameSource> synthetic_begin_frame_source,
       mojom::CompositorFrameSinkPtrInfo compositor_frame_sink_info,
       mojom::CompositorFrameSinkClientRequest client_request,
+      std::unique_ptr<HitTestDataProvider> hit_test_data_provider,
       std::unique_ptr<LocalSurfaceIdProvider> local_surface_id_provider,
       bool enable_surface_synchronization);
 
@@ -40,12 +42,16 @@
       std::unique_ptr<SyntheticBeginFrameSource> synthetic_begin_frame_source,
       mojom::CompositorFrameSinkPtrInfo compositor_frame_sink_info,
       mojom::CompositorFrameSinkClientRequest client_request,
+      std::unique_ptr<HitTestDataProvider> hit_test_data_provider,
       std::unique_ptr<LocalSurfaceIdProvider> local_surface_id_provider,
       bool enable_surface_synchronization);
 
   ~ClientLayerTreeFrameSink() override;
 
   base::WeakPtr<ClientLayerTreeFrameSink> GetWeakPtr();
+  const HitTestDataProvider* hit_test_data_provider() const {
+    return hit_test_data_provider_.get();
+  }
 
   // cc::LayerTreeFrameSink implementation.
   bool BindToClient(cc::LayerTreeFrameSinkClient* client) override;
@@ -71,6 +77,7 @@
 
   bool begin_frames_paused_ = false;
   LocalSurfaceId local_surface_id_;
+  std::unique_ptr<HitTestDataProvider> hit_test_data_provider_;
   std::unique_ptr<LocalSurfaceIdProvider> local_surface_id_provider_;
   std::unique_ptr<ExternalBeginFrameSource> begin_frame_source_;
   std::unique_ptr<SyntheticBeginFrameSource> synthetic_begin_frame_source_;
diff --git a/components/viz/client/hit_test_data_provider.h b/components/viz/client/hit_test_data_provider.h
new file mode 100644
index 0000000..83dff17
--- /dev/null
+++ b/components/viz/client/hit_test_data_provider.h
@@ -0,0 +1,30 @@
+// Copyright 2017 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 COMPONENTS_VIZ_CLIENT_HIT_TEST_DATA_PROVIDER_H_
+#define COMPONENTS_VIZ_CLIENT_HIT_TEST_DATA_PROVIDER_H_
+
+#include <memory>
+#include <vector>
+
+#include "base/macros.h"
+#include "services/viz/public/interfaces/hit_test/hit_test_region_list.mojom.h"
+
+namespace viz {
+
+class HitTestDataProvider {
+ public:
+  HitTestDataProvider() = default;
+  virtual ~HitTestDataProvider() = default;
+
+  // Returns an array of hit-test regions.
+  virtual mojom::HitTestRegionListPtr GetHitTestData() const = 0;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(HitTestDataProvider);
+};
+
+}  // namespace viz
+
+#endif  // COMPONENTS_VIZ_CLIENT_HIT_TEST_DATA_PROVIDER_H_
diff --git a/content/app/content_main_runner.cc b/content/app/content_main_runner.cc
index 9c8e3f49..454b382 100644
--- a/content/app/content_main_runner.cc
+++ b/content/app/content_main_runner.cc
@@ -445,6 +445,8 @@
   int Initialize(const ContentMainParams& params) override {
     ui_task_ = params.ui_task;
 
+    create_discardable_memory_ = params.create_discardable_memory;
+
 #if defined(USE_AURA)
     env_mode_ = params.env_mode;
 #endif
@@ -683,6 +685,7 @@
 #if defined(USE_AURA)
     main_params.env_mode = env_mode_;
 #endif
+    main_params.create_discardable_memory = create_discardable_memory_;
 
     return RunNamedProcessTypeMain(process_type, main_params, delegate_);
   }
@@ -741,6 +744,8 @@
   aura::Env::Mode env_mode_ = aura::Env::Mode::LOCAL;
 #endif
 
+  bool create_discardable_memory_ = true;
+
   DISALLOW_COPY_AND_ASSIGN(ContentMainRunnerImpl);
 };
 
diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn
index c5e533a..ab2964c 100644
--- a/content/browser/BUILD.gn
+++ b/content/browser/BUILD.gn
@@ -594,6 +594,7 @@
     "devtools/shared_worker_devtools_manager.h",
     "devtools/worker_devtools_agent_host.cc",
     "devtools/worker_devtools_agent_host.h",
+    "discardable_shared_memory_manager.cc",
     "dom_storage/dom_storage_area.cc",
     "dom_storage/dom_storage_area.h",
     "dom_storage/dom_storage_context_impl.cc",
diff --git a/content/browser/browser_main_loop.cc b/content/browser/browser_main_loop.cc
index b1ea8a0..cdfd981 100644
--- a/content/browser/browser_main_loop.cc
+++ b/content/browser/browser_main_loop.cc
@@ -686,9 +686,7 @@
         BrowserThread::GetTaskRunnerForThread(BrowserThread::UI));
   }
 
-  // Only use discardable_memory::DiscardableSharedMemoryManager when Chrome is
-  // not running in mus+ash.
-  if (!service_manager::ServiceManagerIsRemote()) {
+  if (parameters_.create_discardable_memory) {
     discardable_shared_memory_manager_ =
         base::MakeUnique<discardable_memory::DiscardableSharedMemoryManager>();
     // TODO(boliu): kSingleProcess check is a temporary workaround for
diff --git a/content/browser/discardable_shared_memory_manager.cc b/content/browser/discardable_shared_memory_manager.cc
new file mode 100644
index 0000000..54c05e9
--- /dev/null
+++ b/content/browser/discardable_shared_memory_manager.cc
@@ -0,0 +1,17 @@
+// Copyright 2017 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.
+
+#include "content/public/browser/discardable_shared_memory_manager.h"
+
+#include "content/browser/browser_main_loop.h"
+
+namespace content {
+
+discardable_memory::DiscardableSharedMemoryManager*
+GetDiscardableSharedMemoryManager() {
+  return content::BrowserMainLoop::GetInstance()
+      ->discardable_shared_memory_manager();
+}
+
+}  // namespace content
diff --git a/content/browser/gpu/browser_gpu_memory_buffer_manager.cc b/content/browser/gpu/browser_gpu_memory_buffer_manager.cc
index bd0afaa..98e4f9c 100644
--- a/content/browser/gpu/browser_gpu_memory_buffer_manager.cc
+++ b/content/browser/gpu/browser_gpu_memory_buffer_manager.cc
@@ -356,6 +356,11 @@
   }
 
   GpuProcessHost* host = GpuProcessHost::Get();
+  if (!host) {
+    DLOG(ERROR) << "Cannot allocate GpuMemoryBuffer with no GpuProcessHost.";
+    callback.Run(gfx::GpuMemoryBufferHandle());
+    return;
+  }
   // Note: Unretained is safe as IO thread is stopped before manager is
   // destroyed.
   host->CreateGpuMemoryBuffer(
diff --git a/content/browser/media/capture/desktop_capture_device.cc b/content/browser/media/capture/desktop_capture_device.cc
index 6cd40bb..740b8dc 100644
--- a/content/browser/media/capture/desktop_capture_device.cc
+++ b/content/browser/media/capture/desktop_capture_device.cc
@@ -267,11 +267,14 @@
   }
   // Align to 2x2 pixel boundaries, as required by OnIncomingCapturedData() so
   // it can convert the frame to I420 format.
-  const webrtc::DesktopSize output_size(
+  webrtc::DesktopSize output_size(
       resolution_chooser_->capture_size().width() & ~1,
       resolution_chooser_->capture_size().height() & ~1);
-  if (output_size.is_empty())
-    return;
+  if (output_size.is_empty()) {
+    // Even RESOLUTION_POLICY_ANY_WITHIN_LIMIT is used, a non-empty size should
+    // be guaranteed.
+    output_size.set(2, 2);
+  }
 
   size_t output_bytes = output_size.width() * output_size.height() *
       webrtc::DesktopFrame::kBytesPerPixel;
diff --git a/content/public/app/content_main.h b/content/public/app/content_main.h
index 6305501..3ae55883 100644
--- a/content/public/app/content_main.h
+++ b/content/public/app/content_main.h
@@ -57,6 +57,9 @@
   aura::Env::Mode env_mode = aura::Env::Mode::LOCAL;
 #endif
 
+  // If true a DiscardableSharedMemoryManager is created.
+  bool create_discardable_memory = true;
+
 #if defined(OS_MACOSX)
   // The outermost autorelease pool to pass to main entry points.
   base::mac::ScopedNSAutoreleasePool* autorelease_pool = nullptr;
diff --git a/content/public/browser/BUILD.gn b/content/public/browser/BUILD.gn
index d6faf35..331d44b 100644
--- a/content/public/browser/BUILD.gn
+++ b/content/public/browser/BUILD.gn
@@ -99,6 +99,7 @@
     "devtools_manager_delegate.cc",
     "devtools_manager_delegate.h",
     "devtools_socket_factory.h",
+    "discardable_shared_memory_manager.h",
     "dom_storage_context.h",
     "download_danger_type.h",
     "download_interrupt_reason_values.h",
diff --git a/content/public/browser/discardable_shared_memory_manager.h b/content/public/browser/discardable_shared_memory_manager.h
new file mode 100644
index 0000000..feb6b45
--- /dev/null
+++ b/content/public/browser/discardable_shared_memory_manager.h
@@ -0,0 +1,21 @@
+// Copyright 2017 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 CONTENT_PUBLIC_BROWSER_DISCARDABLE_SHARED_MEMORY_MANAGER_H_
+#define CONTENT_PUBLIC_BROWSER_DISCARDABLE_SHARED_MEMORY_MANAGER_H_
+
+#include "content/common/content_export.h"
+
+namespace discardable_memory {
+class DiscardableSharedMemoryManager;
+}
+
+namespace content {
+
+CONTENT_EXPORT discardable_memory::DiscardableSharedMemoryManager*
+GetDiscardableSharedMemoryManager();
+
+}  // namespace content
+
+#endif  // CONTENT_PUBLIC_BROWSER_DISCARDABLE_SHARED_MEMORY_MANAGER_H_
diff --git a/content/public/common/content_features.cc b/content/public/common/content_features.cc
index 18c0a30..44009e6 100644
--- a/content/public/common/content_features.cc
+++ b/content/public/common/content_features.cc
@@ -238,12 +238,6 @@
 const base::Feature kReportRendererPeakMemoryStats{
     "ReportRendererPeakMemoryStats", base::FEATURE_DISABLED_BY_DEFAULT};
 
-// Require camera/mic requests from pepper plugins to be made from secure
-// origins.
-const base::Feature kRequireSecureOriginsForPepperMediaRequests{
-    "RequireSecureOriginsForPepperMediaRequests",
-    base::FEATURE_ENABLED_BY_DEFAULT};
-
 // Loading Dispatcher v0 support with ResourceLoadScheduler (crbug.com/729954).
 const base::Feature kResourceLoadScheduler{"ResourceLoadScheduler",
                                            base::FEATURE_DISABLED_BY_DEFAULT};
diff --git a/content/public/common/content_features.h b/content/public/common/content_features.h
index 5c1277ed..dc9d971 100644
--- a/content/public/common/content_features.h
+++ b/content/public/common/content_features.h
@@ -64,8 +64,6 @@
 CONTENT_EXPORT extern const base::Feature kRafAlignedTouchInputEvents;
 CONTENT_EXPORT extern const base::Feature kRenderingPipelineThrottling;
 CONTENT_EXPORT extern const base::Feature kReportRendererPeakMemoryStats;
-CONTENT_EXPORT extern const base::Feature
-    kRequireSecureOriginsForPepperMediaRequests;
 CONTENT_EXPORT extern const base::Feature kResourceLoadScheduler;
 CONTENT_EXPORT extern const base::Feature kScrollAnchoring;
 CONTENT_EXPORT extern const base::Feature kServiceWorkerNavigationPreload;
diff --git a/content/public/common/main_function_params.h b/content/public/common/main_function_params.h
index dac29913..9a99f18 100644
--- a/content/public/common/main_function_params.h
+++ b/content/public/common/main_function_params.h
@@ -58,6 +58,9 @@
   aura::Env::Mode env_mode = aura::Env::Mode::LOCAL;
 #endif
 
+  // Whether DiscardableSharedMemoryManager should be created.
+  bool create_discardable_memory = true;
+
   // Used by InProcessBrowserTest. If non-null BrowserMain schedules this
   // task to run on the MessageLoop and BrowserInit is not invoked.
   base::Closure* ui_task;
diff --git a/content/renderer/mus/renderer_window_tree_client.cc b/content/renderer/mus/renderer_window_tree_client.cc
index f07a5466..408c281 100644
--- a/content/renderer/mus/renderer_window_tree_client.cc
+++ b/content/renderer/mus/renderer_window_tree_client.cc
@@ -10,6 +10,7 @@
 #include "base/lazy_instance.h"
 #include "cc/base/switches.h"
 #include "components/viz/client/client_layer_tree_frame_sink.h"
+#include "components/viz/client/hit_test_data_provider.h"
 #include "components/viz/client/local_surface_id_provider.h"
 
 namespace content {
@@ -88,7 +89,7 @@
       std::move(context_provider), nullptr /* worker_context_provider */,
       gpu_memory_buffer_manager, nullptr /* shared_bitmap_manager */,
       nullptr /* synthetic_begin_frame_source */, std::move(sink_info),
-      std::move(client_request),
+      std::move(client_request), nullptr /* hit_test_data_provider_ */,
       base::MakeUnique<viz::DefaultLocalSurfaceIdProvider>(),
       enable_surface_synchronization);
   tree_->AttachCompositorFrameSink(root_window_id_, std::move(sink_request),
diff --git a/content/renderer/pepper/pepper_media_device_manager.cc b/content/renderer/pepper/pepper_media_device_manager.cc
index 7908178..6163a882 100644
--- a/content/renderer/pepper/pepper_media_device_manager.cc
+++ b/content/renderer/pepper/pepper_media_device_manager.cc
@@ -143,9 +143,7 @@
 
   RendererPpapiHostImpl* host =
       RendererPpapiHostImpl::GetForPPInstance(pp_instance);
-  if (base::FeatureList::IsEnabled(
-          features::kRequireSecureOriginsForPepperMediaRequests) &&
-      !host->IsSecureContext(pp_instance)) {
+  if (!host->IsSecureContext(pp_instance)) {
     RenderFrame* render_frame = host->GetRenderFrameForInstance(pp_instance);
     if (render_frame) {
       render_frame->AddMessageToConsole(CONSOLE_MESSAGE_LEVEL_WARNING,
diff --git a/content/renderer/render_thread_impl.cc b/content/renderer/render_thread_impl.cc
index 58ac590..0c23197 100644
--- a/content/renderer/render_thread_impl.cc
+++ b/content/renderer/render_thread_impl.cc
@@ -55,6 +55,7 @@
 #include "components/metrics/single_sample_metrics.h"
 #include "components/viz/client/client_layer_tree_frame_sink.h"
 #include "components/viz/client/client_shared_bitmap_manager.h"
+#include "components/viz/client/hit_test_data_provider.h"
 #include "components/viz/client/local_surface_id_provider.h"
 #include "components/viz/common/quads/copy_output_request.h"
 #include "components/viz/common/resources/buffer_to_texture_target_map.h"
@@ -1972,7 +1973,7 @@
       callback.Run(base::MakeUnique<viz::ClientLayerTreeFrameSink>(
           std::move(vulkan_context_provider),
           std::move(synthetic_begin_frame_source), std::move(sink_info),
-          std::move(client_request),
+          std::move(client_request), nullptr /* hit_test_data_provider */,
           base::MakeUnique<RendererLocalSurfaceIdProvider>(),
           false /* enable_surface_synchroninzation */));
       return;
@@ -2002,7 +2003,7 @@
     callback.Run(base::MakeUnique<viz::ClientLayerTreeFrameSink>(
         nullptr, nullptr, nullptr, shared_bitmap_manager(),
         std::move(synthetic_begin_frame_source), std::move(sink_info),
-        std::move(client_request),
+        std::move(client_request), nullptr /* hit_test_data_provider */,
         base::MakeUnique<RendererLocalSurfaceIdProvider>(),
         false /* enable_surface_synchroninzation */));
     return;
@@ -2077,7 +2078,7 @@
       std::move(context_provider), std::move(worker_context_provider),
       GetGpuMemoryBufferManager(), nullptr,
       std::move(synthetic_begin_frame_source), std::move(sink_info),
-      std::move(client_request),
+      std::move(client_request), nullptr /* hit_test_data_provider */,
       base::MakeUnique<RendererLocalSurfaceIdProvider>(),
       false /* enable_surface_synchroninzation */));
 }
diff --git a/dbus/values_util_unittest.cc b/dbus/values_util_unittest.cc
index a4854dc..25b516f 100644
--- a/dbus/values_util_unittest.cc
+++ b/dbus/values_util_unittest.cc
@@ -339,7 +339,7 @@
 
   // Create the expected value.
   base::DictionaryValue dictionary_value;
-  dictionary_value.SetBooleanWithoutPathExpansion(kKey1, kBoolValue);
+  dictionary_value.SetKey(kKey1, base::Value(kBoolValue));
   dictionary_value.SetIntegerWithoutPathExpansion(kKey2, kInt32Value);
   dictionary_value.SetDoubleWithoutPathExpansion(kKey3, kDoubleValue);
 
diff --git a/extensions/browser/api/execute_code_function.cc b/extensions/browser/api/execute_code_function.cc
index bf04871e..0c9efcb 100644
--- a/extensions/browser/api/execute_code_function.cc
+++ b/extensions/browser/api/execute_code_function.cc
@@ -237,7 +237,7 @@
                        resource_.relative_path().AsUTF8Unsafe(),
                        true /* We assume this call always succeeds */));
   } else {
-    FileReader::OptionalFileThreadTaskCallback get_file_and_l10n_callback =
+    FileReader::OptionalFileSequenceTask get_file_and_l10n_callback =
         base::Bind(&ExecuteCodeFunction::GetFileURLAndMaybeLocalizeInBackground,
                    this, extension_id, extension_path, extension_default_locale,
                    might_require_localization);
diff --git a/extensions/browser/api/networking_private/networking_private_chromeos.cc b/extensions/browser/api/networking_private/networking_private_chromeos.cc
index 4611127..30de935 100644
--- a/extensions/browser/api/networking_private/networking_private_chromeos.cc
+++ b/extensions/browser/api/networking_private/networking_private_chromeos.cc
@@ -266,7 +266,7 @@
   }
   dict->SetWithoutPathExpansion(::onc::kAugmentationActiveSetting,
                                 std::move(value));
-  dict->SetBooleanWithoutPathExpansion(::onc::kAugmentationUserEditable, false);
+  dict->SetKey(::onc::kAugmentationUserEditable, base::Value(false));
 }
 
 std::string GetProxySettingsType(const UIProxyConfig::Mode& mode) {
diff --git a/extensions/browser/file_reader.cc b/extensions/browser/file_reader.cc
index 3efc7d51a..d00d410 100644
--- a/extensions/browser/file_reader.cc
+++ b/extensions/browser/file_reader.cc
@@ -8,37 +8,36 @@
 #include "base/callback_helpers.h"
 #include "base/files/file_util.h"
 #include "base/threading/thread_task_runner_handle.h"
-#include "content/public/browser/browser_thread.h"
-
-using content::BrowserThread;
+#include "extensions/browser/extension_file_task_runner.h"
 
 FileReader::FileReader(
     const extensions::ExtensionResource& resource,
-    const OptionalFileThreadTaskCallback& optional_file_thread_task_callback,
+    const OptionalFileSequenceTask& optional_file_sequence_task,
     const DoneCallback& done_callback)
     : resource_(resource),
-      optional_file_thread_task_callback_(optional_file_thread_task_callback),
+      optional_file_sequence_task_(optional_file_sequence_task),
       done_callback_(done_callback),
       origin_task_runner_(base::ThreadTaskRunnerHandle::Get()) {}
 
 void FileReader::Start() {
-  BrowserThread::PostTask(
-      BrowserThread::FILE, FROM_HERE,
-      base::Bind(&FileReader::ReadFileOnBackgroundThread, this));
+  extensions::GetExtensionFileTaskRunner()->PostTask(
+      FROM_HERE, base::Bind(&FileReader::ReadFileOnFileSequence, this));
 }
 
 FileReader::~FileReader() {}
 
-void FileReader::ReadFileOnBackgroundThread() {
+void FileReader::ReadFileOnFileSequence() {
+  DCHECK(
+      extensions::GetExtensionFileTaskRunner()->RunsTasksInCurrentSequence());
+
   std::unique_ptr<std::string> data(new std::string());
   bool success = base::ReadFileToString(resource_.GetFilePath(), data.get());
 
-  if (!optional_file_thread_task_callback_.is_null()) {
+  if (!optional_file_sequence_task_.is_null()) {
     if (success) {
-      base::ResetAndReturn(&optional_file_thread_task_callback_)
-          .Run(data.get());
+      base::ResetAndReturn(&optional_file_sequence_task_).Run(data.get());
     } else {
-      optional_file_thread_task_callback_.Reset();
+      optional_file_sequence_task_.Reset();
     }
   }
 
diff --git a/extensions/browser/file_reader.h b/extensions/browser/file_reader.h
index a9f88688..15dc1be 100644
--- a/extensions/browser/file_reader.h
+++ b/extensions/browser/file_reader.h
@@ -13,37 +13,40 @@
 #include "extensions/common/extension_resource.h"
 
 // This file defines an interface for reading a file asynchronously on a
-// background thread.
+// background sequence.
 // Consider abstracting out a FilePathProvider (ExtensionResource) and moving
 // back to chrome/browser/net if other subsystems want to use it.
 class FileReader : public base::RefCountedThreadSafe<FileReader> {
  public:
+  // TODO(devlin): Use base::OnceCallback here.
   // Reports success or failure and the data of the file upon success.
   using DoneCallback = base::Callback<void(bool, std::unique_ptr<std::string>)>;
   // Lets the caller accomplish tasks on the file data, after the file content
   // has been read.
   // If the file reading doesn't succeed, this will be ignored.
-  using OptionalFileThreadTaskCallback = base::Callback<void(std::string*)>;
+  using OptionalFileSequenceTask = base::Callback<void(std::string*)>;
 
   FileReader(const extensions::ExtensionResource& resource,
-             const OptionalFileThreadTaskCallback& file_thread_task_callback,
+             const OptionalFileSequenceTask& file_sequence_task,
              const DoneCallback& done_callback);
 
-  // Called to start reading the file on a background thread.  Upon completion,
+  // Called to start reading the file on a background sequence. Upon completion,
   // the callback will be notified of the results.
   void Start();
 
  private:
   friend class base::RefCountedThreadSafe<FileReader>;
 
-  virtual ~FileReader();
+  ~FileReader();
 
-  void ReadFileOnBackgroundThread();
+  void ReadFileOnFileSequence();
 
   extensions::ExtensionResource resource_;
-  OptionalFileThreadTaskCallback optional_file_thread_task_callback_;
+  OptionalFileSequenceTask optional_file_sequence_task_;
   DoneCallback done_callback_;
   const scoped_refptr<base::SingleThreadTaskRunner> origin_task_runner_;
+
+  DISALLOW_COPY_AND_ASSIGN(FileReader);
 };
 
 #endif  // EXTENSIONS_BROWSER_FILE_READER_H_
diff --git a/extensions/browser/file_reader_unittest.cc b/extensions/browser/file_reader_unittest.cc
index 1e65242..dcee191f 100644
--- a/extensions/browser/file_reader_unittest.cc
+++ b/extensions/browser/file_reader_unittest.cc
@@ -2,41 +2,44 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
+#include "extensions/browser/file_reader.h"
+
 #include "base/bind.h"
 #include "base/bind_helpers.h"
 #include "base/files/file_path.h"
 #include "base/files/file_util.h"
-#include "base/message_loop/message_loop.h"
 #include "base/path_service.h"
 #include "base/run_loop.h"
+#include "base/test/scoped_task_environment.h"
 #include "components/crx_file/id_util.h"
-#include "content/public/test/test_browser_thread.h"
-#include "extensions/browser/file_reader.h"
 #include "extensions/common/extension_paths.h"
 #include "extensions/common/extension_resource.h"
 #include "testing/gtest/include/gtest/gtest.h"
 
-using content::BrowserThread;
-
 namespace extensions {
 
 class FileReaderTest : public testing::Test {
  public:
-  FileReaderTest() : file_thread_(BrowserThread::FILE) {
-    file_thread_.Start();
-  }
+  FileReaderTest() {}
+
  private:
-  base::MessageLoop message_loop_;
-  content::TestBrowserThread file_thread_;
+  base::test::ScopedTaskEnvironment task_environment_;
+
+  DISALLOW_COPY_AND_ASSIGN(FileReaderTest);
 };
 
 class Receiver {
  public:
-  Receiver() : succeeded_(false) {
-  }
+  Receiver(const ExtensionResource& resource)
+      : succeeded_(false),
+        file_reader_(new FileReader(
+            resource,
+            FileReader::OptionalFileSequenceTask(),
+            base::Bind(&Receiver::DidReadFile, base::Unretained(this)))) {}
 
-  FileReader::DoneCallback NewCallback() {
-    return base::Bind(&Receiver::DidReadFile, base::Unretained(this));
+  void Run() {
+    file_reader_->Start();
+    run_loop_.Run();
   }
 
   bool succeeded() const { return succeeded_; }
@@ -46,11 +49,15 @@
   void DidReadFile(bool success, std::unique_ptr<std::string> data) {
     succeeded_ = success;
     data_ = std::move(data);
-    base::RunLoop::QuitCurrentWhenIdleDeprecated();
+    run_loop_.QuitWhenIdle();
   }
 
   bool succeeded_;
   std::unique_ptr<std::string> data_;
+  scoped_refptr<FileReader> file_reader_;
+  base::RunLoop run_loop_;
+
+  DISALLOW_COPY_AND_ASSIGN(Receiver);
 };
 
 void RunBasicTest(const char* filename) {
@@ -64,14 +71,8 @@
   std::string file_contents;
   ASSERT_TRUE(base::ReadFileToString(path, &file_contents));
 
-  Receiver receiver;
-
-  scoped_refptr<FileReader> file_reader(
-      new FileReader(resource, FileReader::OptionalFileThreadTaskCallback(),
-                     receiver.NewCallback()));
-  file_reader->Start();
-
-  base::RunLoop().Run();
+  Receiver receiver(resource);
+  receiver.Run();
 
   EXPECT_TRUE(receiver.succeeded());
   EXPECT_EQ(file_contents, receiver.data());
@@ -93,14 +94,8 @@
       FILE_PATH_LITERAL("file_that_does_not_exist")));
   path = path.AppendASCII("file_that_does_not_exist");
 
-  Receiver receiver;
-
-  scoped_refptr<FileReader> file_reader(
-      new FileReader(resource, FileReader::OptionalFileThreadTaskCallback(),
-                     receiver.NewCallback()));
-  file_reader->Start();
-
-  base::RunLoop().Run();
+  Receiver receiver(resource);
+  receiver.Run();
 
   EXPECT_FALSE(receiver.succeeded());
 }
diff --git a/extensions/browser/updater/extension_downloader.cc b/extensions/browser/updater/extension_downloader.cc
index 056721b..8541e7eb 100644
--- a/extensions/browser/updater/extension_downloader.cc
+++ b/extensions/browser/updater/extension_downloader.cc
@@ -22,9 +22,9 @@
 #include "base/time/time.h"
 #include "base/version.h"
 #include "components/update_client/update_query_params.h"
-#include "content/public/browser/browser_thread.h"
 #include "content/public/browser/notification_details.h"
 #include "content/public/browser/notification_service.h"
+#include "extensions/browser/extension_file_task_runner.h"
 #include "extensions/browser/extensions_browser_client.h"
 #include "extensions/browser/notification_types.h"
 #include "extensions/browser/updater/extension_cache.h"
@@ -46,7 +46,6 @@
 
 using base::Time;
 using base::TimeDelta;
-using content::BrowserThread;
 using update_client::UpdateQueryParams;
 
 namespace extensions {
@@ -858,7 +857,7 @@
   // processed in memory, so it is fetched into a string.
   if (fetch->id != kBlacklistAppID) {
     extension_fetcher_->SaveResponseToTemporaryFile(
-        BrowserThread::GetTaskRunnerForThread(BrowserThread::FILE));
+        GetExtensionFileTaskRunner());
   }
 
   if (fetch->credentials == ExtensionFetch::CREDENTIALS_OAUTH2_TOKEN &&
diff --git a/gpu/config/gpu_driver_bug_list.json b/gpu/config/gpu_driver_bug_list.json
index 939c41b0..89a64a8 100644
--- a/gpu/config/gpu_driver_bug_list.json
+++ b/gpu/config/gpu_driver_bug_list.json
@@ -1,6 +1,6 @@
 {
   "name": "gpu driver bug list",
-  "version": "10.22",
+  "version": "10.23",
   "entries": [
     {
       "id": 1,
@@ -2443,6 +2443,7 @@
       "vendor_id": "0x8086",
       "device_id": ["0x0412", "0x0d26", "0x0a2e", "0x0a26", "0x0d22", "0x161e",
                     "0x1626", "0x162b", "0x1622"],
+      "multi_gpu_category": "any",
       "features": [
         "avoid_stencil_buffers"
       ]
diff --git a/gpu/config/gpu_info_collector_fuchsia.cc b/gpu/config/gpu_info_collector_fuchsia.cc
index 7e9a8c7a..b349a252 100644
--- a/gpu/config/gpu_info_collector_fuchsia.cc
+++ b/gpu/config/gpu_info_collector_fuchsia.cc
@@ -18,4 +18,8 @@
   return kCollectInfoNonFatalFailure;
 }
 
+CollectInfoResult CollectContextGraphicsInfo(GPUInfo* gpu_info) {
+  return CollectBasicGraphicsInfo(gpu_info);
+}
+
 }  // namespace gpu
diff --git a/gpu/ipc/service/BUILD.gn b/gpu/ipc/service/BUILD.gn
index 22c3748b..983715b6 100644
--- a/gpu/ipc/service/BUILD.gn
+++ b/gpu/ipc/service/BUILD.gn
@@ -126,6 +126,9 @@
   if (use_ozone) {
     deps += [ "//ui/ozone" ]
   }
+  if (is_fuchsia) {
+    sources += [ "image_transport_surface_fuchsia.cc" ]
+  }
 }
 
 source_set("test_support") {
diff --git a/gpu/ipc/service/gpu_vsync_provider_win.cc b/gpu/ipc/service/gpu_vsync_provider_win.cc
index c2d8c8a..47cf27f 100644
--- a/gpu/ipc/service/gpu_vsync_provider_win.cc
+++ b/gpu/ipc/service/gpu_vsync_provider_win.cc
@@ -153,7 +153,7 @@
 GpuVSyncWorker::GpuVSyncWorker(
     const gfx::VSyncProvider::UpdateVSyncCallback& callback,
     SurfaceHandle surface_handle)
-    : base::Thread(base::StringPrintf("VSync-%d", surface_handle)),
+    : base::Thread(base::StringPrintf("VSync-%p", surface_handle)),
       callback_(callback),
       surface_handle_(surface_handle) {
   HMODULE gdi32 = GetModuleHandle(L"gdi32");
@@ -558,8 +558,12 @@
 
   // Start the thread.
   base::Thread::Options options;
-  // TODO(stanisc): might consider even higher priority - REALTIME_AUDIO.
-  options.priority = base::ThreadPriority::DISPLAY;
+  // Realtime priority is needed to ensure the minimal possible wakeup latency
+  // and to ensure that the thread isn't pre-empted when it handles the v-blank
+  // wake-up.  The thread sleeps most of the time and does a tiny amount of
+  // actual work on each cycle. So the increased priority is mostly for the best
+  // possible latency.
+  options.priority = base::ThreadPriority::REALTIME_AUDIO;
   vsync_worker_->StartWithOptions(options);
 }
 
diff --git a/gpu/ipc/service/image_transport_surface_fuchsia.cc b/gpu/ipc/service/image_transport_surface_fuchsia.cc
new file mode 100644
index 0000000..65d3013c
--- /dev/null
+++ b/gpu/ipc/service/image_transport_surface_fuchsia.cc
@@ -0,0 +1,22 @@
+// Copyright 2017 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.
+
+#include "gpu/ipc/service/image_transport_surface.h"
+
+#include "base/logging.h"
+#include "ui/gl/gl_surface_stub.h"
+
+namespace gpu {
+
+// static
+scoped_refptr<gl::GLSurface> ImageTransportSurface::CreateNativeSurface(
+    base::WeakPtr<ImageTransportSurfaceDelegate> delegate,
+    SurfaceHandle surface_handle,
+    gl::GLSurfaceFormat format) {
+  DCHECK(gl::GetGLImplementation() == gl::kGLImplementationMockGL ||
+         gl::GetGLImplementation() == gl::kGLImplementationStubGL);
+  return new gl::GLSurfaceStub;
+}
+
+}  // namespace gpu
diff --git a/ios/chrome/app/main_controller.mm b/ios/chrome/app/main_controller.mm
index 821bb10..ead40d6 100644
--- a/ios/chrome/app/main_controller.mm
+++ b/ios/chrome/app/main_controller.mm
@@ -1361,6 +1361,15 @@
   }
 }
 
+- (void)showHistory {
+  _historyPanelViewController = [HistoryPanelViewController
+      controllerToPresentForBrowserState:_mainBrowserState
+                                  loader:self.currentBVC];
+  [self.currentBVC presentViewController:_historyPanelViewController
+                                animated:YES
+                              completion:nil];
+}
+
 #pragma mark - chromeExecuteCommand
 
 - (IBAction)chromeExecuteCommand:(id)sender {
@@ -1398,9 +1407,6 @@
     case IDC_SHOW_SAVE_PASSWORDS_SETTINGS:
       [self showSavePasswordsSettings];
       break;
-    case IDC_SHOW_HISTORY:
-      [self showHistory];
-      break;
     case IDC_TOGGLE_TAB_SWITCHER: {
       DCHECK(!_tabSwitcherIsActive);
       if (!_isProcessingVoiceSearchCommand) {
@@ -2061,15 +2067,6 @@
                 viewController:self.mainViewController];
 }
 
-- (void)showHistory {
-  _historyPanelViewController = [HistoryPanelViewController
-      controllerToPresentForBrowserState:_mainBrowserState
-                                  loader:self.currentBVC];
-  [self.currentBVC presentViewController:_historyPanelViewController
-                                animated:YES
-                              completion:nil];
-}
-
 - (void)dismissSigninInteractionController {
   // The sign-in interaction controller is destroyed as a result of calling
   // |cancelAndDismiss|. Destroying it here may lead to a missing call of the
diff --git a/ios/chrome/browser/about_flags.mm b/ios/chrome/browser/about_flags.mm
index ebe19a2..d8ab5687 100644
--- a/ios/chrome/browser/about_flags.mm
+++ b/ios/chrome/browser/about_flags.mm
@@ -128,16 +128,6 @@
   if ([defaults boolForKey:@"TabStripAutoScrollNewTabsDisabled"])
     command_line->AppendSwitch(switches::kDisableTabStripAutoScrollNewTabs);
 
-  // Populate command line flag for the SnapshotLRUCache experiment from the
-  // configuration plist.
-  NSString* enableLRUSnapshotCache =
-      [defaults stringForKey:@"SnapshotLRUCache"];
-  if ([enableLRUSnapshotCache isEqualToString:@"Enabled"]) {
-    command_line->AppendSwitch(switches::kEnableLRUSnapshotCache);
-  } else if ([enableLRUSnapshotCache isEqualToString:@"Disabled"]) {
-    command_line->AppendSwitch(switches::kDisableLRUSnapshotCache);
-  }
-
   // Populate command line flags from PasswordGenerationEnabled.
   NSString* enablePasswordGenerationValue =
       [defaults stringForKey:@"PasswordGenerationEnabled"];
@@ -178,15 +168,6 @@
     command_line->AppendSwitch(switches::kDisableOfflineAutoReload);
   }
 
-  // Populate command line flags from EnableFastWebScrollViewInsets.
-  NSString* enableFastWebScrollViewInsets =
-      [defaults stringForKey:@"EnableFastWebScrollViewInsets"];
-  if ([enableFastWebScrollViewInsets isEqualToString:@"Enabled"]) {
-    command_line->AppendSwitch(switches::kEnableIOSFastWebScrollViewInsets);
-  } else if ([enableFastWebScrollViewInsets isEqualToString:@"Disabled"]) {
-    command_line->AppendSwitch(switches::kDisableIOSFastWebScrollViewInsets);
-  }
-
   // Populate command line flags from ReaderModeEnabled.
   if ([defaults boolForKey:@"ReaderModeEnabled"]) {
     command_line->AppendSwitch(switches::kEnableReaderModeToolbarIcon);
diff --git a/ios/chrome/browser/chrome_switches.cc b/ios/chrome/browser/chrome_switches.cc
index 4d196a63..f29a42d 100644
--- a/ios/chrome/browser/chrome_switches.cc
+++ b/ios/chrome/browser/chrome_switches.cc
@@ -15,10 +15,6 @@
 // Disables Contextual Search.
 const char kDisableContextualSearch[] = "disable-contextual-search";
 
-// Disables a workaround for fast inset updates for UIWebView.scrollView.
-const char kDisableIOSFastWebScrollViewInsets[] =
-    "disable-fast-web-scroll-view-insets";
-
 // Lists separated by commas the name of features to disable.
 // See base::FeatureList::InitializeFromCommandLine for details.
 const char kDisableIOSFeatures[] = "disable-features";
@@ -31,9 +27,6 @@
 const char kDisableIOSPasswordSuggestions[] =
     "disable-ios-password-suggestions";
 
-// Disable the snapshots lru cache.
-const char kDisableLRUSnapshotCache[] = "disable-lru-snapshot-cache";
-
 // Disable auto-reload of error pages if offline.
 const char kDisableOfflineAutoReload[] = "disable-offline-auto-reload";
 
@@ -60,10 +53,6 @@
 // Enables Contextual Search.
 const char kEnableContextualSearch[] = "enable-contextual-search";
 
-// Enables a workaround for fast inset updates for UIWebView.scrollView.
-const char kEnableIOSFastWebScrollViewInsets[] =
-    "enable-fast-web-scroll-view-insets";
-
 // Lists separated by commas the name of features to disable.
 // See base::FeatureList::InitializeFromCommandLine for details.
 const char kEnableIOSFeatures[] = "enable-features";
@@ -76,9 +65,6 @@
 // Enable password generation for iOS.
 const char kEnableIOSPasswordGeneration[] = "enable-ios-password-generation";
 
-// Enables the snapshot lru cache.
-const char kEnableLRUSnapshotCache[] = "enable-lru-snapshot-cache";
-
 // Enable auto-reload of error pages if offline.
 const char kEnableOfflineAutoReload[] = "enable-offline-auto-reload";
 
diff --git a/ios/chrome/browser/chrome_switches.h b/ios/chrome/browser/chrome_switches.h
index 28c5600..f199f46 100644
--- a/ios/chrome/browser/chrome_switches.h
+++ b/ios/chrome/browser/chrome_switches.h
@@ -10,11 +10,9 @@
 namespace switches {
 
 extern const char kDisableContextualSearch[];
-extern const char kDisableIOSFastWebScrollViewInsets[];
 extern const char kDisableIOSFeatures[];
 extern const char kDisableIOSPasswordGeneration[];
 extern const char kDisableIOSPasswordSuggestions[];
-extern const char kDisableLRUSnapshotCache[];
 extern const char kDisableNTPFavicons[];
 extern const char kDisableOfflineAutoReload[];
 extern const char kDisableTabStripAutoScrollNewTabs[];
@@ -25,11 +23,9 @@
 extern const char kDisableThirdPartyKeyboardWorkaround[];
 
 extern const char kEnableContextualSearch[];
-extern const char kEnableIOSFastWebScrollViewInsets[];
 extern const char kEnableIOSFeatures[];
 extern const char kEnableIOSHandoffToOtherDevices[];
 extern const char kEnableIOSPasswordGeneration[];
-extern const char kEnableLRUSnapshotCache[];
 extern const char kEnableNTPFavicons[];
 extern const char kEnableOfflineAutoReload[];
 extern const char kEnableReaderModeToolbarIcon[];
diff --git a/ios/chrome/browser/experimental_flags.mm b/ios/chrome/browser/experimental_flags.mm
index 58a761b..d9c91ff0 100644
--- a/ios/chrome/browser/experimental_flags.mm
+++ b/ios/chrome/browser/experimental_flags.mm
@@ -107,19 +107,8 @@
 }
 
 bool IsLRUSnapshotCacheEnabled() {
-  // Check if the experimental flag is forced on or off.
-  base::CommandLine* command_line = base::CommandLine::ForCurrentProcess();
-  if (command_line->HasSwitch(switches::kEnableLRUSnapshotCache)) {
-    return true;
-  } else if (command_line->HasSwitch(switches::kDisableLRUSnapshotCache)) {
-    return false;
-  }
-
-  // Check if the finch experiment is turned on.
-  std::string group_name =
-      base::FieldTrialList::FindFullName("IOSLRUSnapshotCache");
-  return base::StartsWith(group_name, "Enabled",
-                          base::CompareCase::INSENSITIVE_ASCII);
+  // TODO(crbug.com/751553): Remove this flag and its associated code.
+  return NO;
 }
 
 bool IsMDMIntegrationEnabled() {
diff --git a/ios/chrome/browser/resources/Settings.bundle/Experimental.plist b/ios/chrome/browser/resources/Settings.bundle/Experimental.plist
index 0125c83..e579a27 100644
--- a/ios/chrome/browser/resources/Settings.bundle/Experimental.plist
+++ b/ios/chrome/browser/resources/Settings.bundle/Experimental.plist
@@ -6,28 +6,6 @@
 	<array>
 		<dict>
 			<key>Type</key>
-			<string>PSMultiValueSpecifier</string>
-			<key>Title</key>
-			<string>Enable SnapshotLRUCache</string>
-			<key>Key</key>
-			<string>SnapshotLRUCache</string>
-			<key>DefaultValue</key>
-			<string></string>
-			<key>Values</key>
-			<array>
-				<string></string>
-				<string>Enabled</string>
-				<string>Disabled</string>
-			</array>
-			<key>Titles</key>
-			<array>
-				<string>Default</string>
-				<string>Enabled</string>
-				<string>Disabled</string>
-			</array>
-		</dict>
-		<dict>
-			<key>Type</key>
 			<string>PSGroupSpecifier</string>
 			<key>Title</key>
 			<string>iPad Tab Strip</string>
@@ -98,28 +76,6 @@
 		</dict>
 		<dict>
 			<key>Type</key>
-			<string>PSMultiValueSpecifier</string>
-			<key>Title</key>
-			<string>Enable Fast Web Scroll Insets</string>
-			<key>Key</key>
-			<string>EnableFastWebScrollViewInsets</string>
-			<key>DefaultValue</key>
-			<string></string>
-			<key>Values</key>
-			<array>
-				<string></string>
-				<string>Enabled</string>
-				<string>Disabled</string>
-			</array>
-			<key>Titles</key>
-			<array>
-				<string>Default</string>
-				<string>Enabled</string>
-				<string>Disabled</string>
-			</array>
-		</dict>
-		<dict>
-			<key>Type</key>
 			<string>PSToggleSwitchSpecifier</string>
 			<key>Title</key>
 			<string>Fake Cloud Policy Type</string>
diff --git a/ios/chrome/browser/ui/browser_view_controller.mm b/ios/chrome/browser/ui/browser_view_controller.mm
index ea24c59c..0279a644 100644
--- a/ios/chrome/browser/ui/browser_view_controller.mm
+++ b/ios/chrome/browser/ui/browser_view_controller.mm
@@ -4184,7 +4184,8 @@
       } else {
         UIViewController* controller = [RecentTabsPanelViewController
             controllerToPresentForBrowserState:_browserState
-                                        loader:self];
+                                        loader:self
+                                    dispatcher:self.dispatcher];
         controller.modalPresentationStyle = UIModalPresentationFormSheet;
         controller.modalPresentationCapturesStatusBarAppearance = YES;
         [self presentViewController:controller animated:YES completion:nil];
diff --git a/ios/chrome/browser/ui/commands/application_commands.h b/ios/chrome/browser/ui/commands/application_commands.h
index f0bfd72a..5f8c795 100644
--- a/ios/chrome/browser/ui/commands/application_commands.h
+++ b/ios/chrome/browser/ui/commands/application_commands.h
@@ -39,6 +39,9 @@
 // Starts a voice search on the current BVC.
 - (void)startVoiceSearch:(StartVoiceSearchCommand*)command;
 
+// Shows the History UI.
+- (void)showHistory;
+
 @end
 
 #endif  // IOS_CHROME_BROWSER_UI_COMMANDS_APPLICATION_COMMANDS_H_
diff --git a/ios/chrome/browser/ui/commands/ios_command_ids.h b/ios/chrome/browser/ui/commands/ios_command_ids.h
index d53a63f..52690363 100644
--- a/ios/chrome/browser/ui/commands/ios_command_ids.h
+++ b/ios/chrome/browser/ui/commands/ios_command_ids.h
@@ -17,7 +17,6 @@
 #define IDC_FIND                                       37000
 #define IDC_FIND_NEXT                                  37001
 #define IDC_FIND_PREVIOUS                              37002
-#define IDC_SHOW_HISTORY                               40010
 #define IDC_SHOW_BOOKMARK_MANAGER                      40011
 #define IDC_HELP_PAGE_VIA_MENU                         40020
 #define IDC_TOGGLE_TAB_SWITCHER                        40901
diff --git a/ios/chrome/browser/ui/key_commands_provider.mm b/ios/chrome/browser/ui/key_commands_provider.mm
index c907932..20a78fc 100644
--- a/ios/chrome/browser/ui/key_commands_provider.mm
+++ b/ios/chrome/browser/ui/key_commands_provider.mm
@@ -189,7 +189,7 @@
                                      title:l10n_util::GetNSStringWithFixup(
                                                IDS_HISTORY_SHOW_HISTORY)
                                     action:^{
-                                      execute(IDC_SHOW_HISTORY);
+                                      [weakDispatcher showHistory];
                                     }],
       [UIKeyCommand
           cr_keyCommandWithInput:@"."
diff --git a/ios/chrome/browser/ui/ntp/new_tab_page_controller.mm b/ios/chrome/browser/ui/ntp/new_tab_page_controller.mm
index 814babf..7a52b7c 100644
--- a/ios/chrome/browser/ui/ntp/new_tab_page_controller.mm
+++ b/ios/chrome/browser/ui/ntp/new_tab_page_controller.mm
@@ -605,7 +605,8 @@
     if (!_openTabsController)
       _openTabsController =
           [[RecentTabsPanelController alloc] initWithLoader:_loader
-                                               browserState:_browserState];
+                                               browserState:_browserState
+                                                 dispatcher:self.dispatcher];
     // TODO(crbug.com/708319): Also set panelController for opentabs here.
     view = [_openTabsController view];
     [_openTabsController setDelegate:self];
diff --git a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.h b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.h
index aa4a580..ce91b0b6 100644
--- a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.h
+++ b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.h
@@ -13,6 +13,7 @@
 class ChromeBrowserState;
 }
 
+@protocol ApplicationCommands;
 @class RecentTabsTableViewController;
 @protocol UrlLoader;
 
@@ -27,7 +28,8 @@
 
 // Public initializer.
 - (instancetype)initWithLoader:(id<UrlLoader>)loader
-                  browserState:(ios::ChromeBrowserState*)browserState;
+                  browserState:(ios::ChromeBrowserState*)browserState
+                    dispatcher:(id<ApplicationCommands>)dispatcher;
 
 // Private initializer, exposed for testing.
 - (instancetype)initWithController:(RecentTabsTableViewController*)controller
diff --git a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.mm b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.mm
index f3f0682..0b6d67f4 100644
--- a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.mm
+++ b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_controller.mm
@@ -57,10 +57,12 @@
 @synthesize delegate = _delegate;
 
 - (instancetype)initWithLoader:(id<UrlLoader>)loader
-                  browserState:(ios::ChromeBrowserState*)browserState {
+                  browserState:(ios::ChromeBrowserState*)browserState
+                    dispatcher:(id<ApplicationCommands>)dispatcher {
   return [self initWithController:[[RecentTabsTableViewController alloc]
                                       initWithBrowserState:browserState
-                                                    loader:loader]
+                                                    loader:loader
+                                                dispatcher:dispatcher]
                      browserState:browserState];
 }
 
diff --git a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.h b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.h
index a9dc268..a487051d3 100644
--- a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.h
+++ b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.h
@@ -12,21 +12,24 @@
 }
 
 @protocol UrlLoader;
+@protocol ApplicationCommands;
 
 // UIViewController wrapper for RecentTabsPanelController for modal display.
 @interface RecentTabsPanelViewController : UIViewController
 
 - (instancetype)initWithLoader:(id<UrlLoader>)loader
                   browserState:(ios::ChromeBrowserState*)browserState
+                    dispatcher:(id<ApplicationCommands>)dispatcher
     NS_DESIGNATED_INITIALIZER;
 
 - (instancetype)initWithNibName:(NSString*)nibNameOrNil
                          bundle:(NSBundle*)nibBundleOrNil NS_UNAVAILABLE;
 - (instancetype)initWithCoder:(NSCoder*)aDecoder NS_UNAVAILABLE;
 
-+ (UIViewController*)controllerToPresentForBrowserState:
-                         (ios::ChromeBrowserState*)browserState
-                                                 loader:(id<UrlLoader>)loader;
++ (UIViewController*)
+controllerToPresentForBrowserState:(ios::ChromeBrowserState*)browserState
+                            loader:(id<UrlLoader>)loader
+                        dispatcher:(id<ApplicationCommands>)dispatcher;
 
 @end
 
diff --git a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.mm b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.mm
index 4bf078f..7784111 100644
--- a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.mm
+++ b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_panel_view_controller.mm
@@ -34,13 +34,15 @@
   PanelBarView* _panelBarView;
 }
 
-+ (UIViewController*)controllerToPresentForBrowserState:
-                         (ios::ChromeBrowserState*)browserState
-                                                 loader:(id<UrlLoader>)loader {
++ (UIViewController*)
+controllerToPresentForBrowserState:(ios::ChromeBrowserState*)browserState
+                            loader:(id<UrlLoader>)loader
+                        dispatcher:(id<ApplicationCommands>)dispatcher {
   UIViewController* controller = [[RecentTabsWrapperViewController alloc] init];
   RecentTabsPanelViewController* rtpvc =
       [[RecentTabsPanelViewController alloc] initWithLoader:loader
-                                               browserState:browserState];
+                                               browserState:browserState
+                                                 dispatcher:dispatcher];
   [controller addChildViewController:rtpvc];
 
   PanelBarView* panelBarView = [[PanelBarView alloc] init];
@@ -80,12 +82,14 @@
 }
 
 - (instancetype)initWithLoader:(id<UrlLoader>)loader
-                  browserState:(ios::ChromeBrowserState*)browserState {
+                  browserState:(ios::ChromeBrowserState*)browserState
+                    dispatcher:(id<ApplicationCommands>)dispatcher {
   self = [super initWithNibName:nil bundle:nil];
   if (self) {
     _recentTabsController =
         [[RecentTabsPanelController alloc] initWithLoader:loader
-                                             browserState:browserState];
+                                             browserState:browserState
+                                               dispatcher:dispatcher];
     if ([self respondsToSelector:@selector(edgesForExtendedLayout)])
       self.edgesForExtendedLayout = UIRectEdgeNone;
   }
diff --git a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.h b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.h
index a29da1c7..9ac48c54 100644
--- a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.h
+++ b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.h
@@ -18,6 +18,8 @@
 class ChromeBrowserState;
 }
 
+@protocol ApplicationCommands;
+
 @protocol RecentTabsTableViewControllerDelegate<NSObject>
 // Tells the delegate when the table view content scrolled or changed size.
 - (void)recentTabsTableViewContentMoved:(UITableView*)tableView;
@@ -49,7 +51,8 @@
 // |browserState|
 // and |loader| must not be nil.
 - (instancetype)initWithBrowserState:(ios::ChromeBrowserState*)browserState
-                              loader:(id<UrlLoader>)loader;
+                              loader:(id<UrlLoader>)loader
+                          dispatcher:(id<ApplicationCommands>)dispatcher;
 
 // Refreshes the table view to match the current sync state.
 - (void)refreshUserState:(SessionsSyncUserState)state;
diff --git a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.mm b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.mm
index 42ae5cd..5906a830 100644
--- a/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.mm
+++ b/ios/chrome/browser/ui/ntp/recent_tabs/recent_tabs_table_view_controller.mm
@@ -24,6 +24,7 @@
 #import "ios/chrome/browser/ui/authentication/signin_promo_view_consumer.h"
 #import "ios/chrome/browser/ui/authentication/signin_promo_view_mediator.h"
 #import "ios/chrome/browser/ui/commands/UIKit+ChromeExecuteCommand.h"
+#include "ios/chrome/browser/ui/commands/application_commands.h"
 #import "ios/chrome/browser/ui/commands/generic_chrome_command.h"
 #include "ios/chrome/browser/ui/commands/ios_command_ids.h"
 #import "ios/chrome/browser/ui/context_menu/context_menu_coordinator.h"
@@ -156,11 +157,16 @@
 - (void)removeSessionAtIndexPath:(NSIndexPath*)indexPath;
 // Handles long presses on the UITableView, possibly opening context menus.
 - (void)handleLongPress:(UILongPressGestureRecognizer*)longPressGesture;
+
+// The dispatcher used by this ViewController.
+@property(nonatomic, readonly, weak) id<ApplicationCommands> dispatcher;
+
 @end
 
 @implementation RecentTabsTableViewController
 
 @synthesize delegate = delegate_;
+@synthesize dispatcher = _dispatcher;
 
 - (instancetype)init {
   NOTREACHED();
@@ -168,7 +174,8 @@
 }
 
 - (instancetype)initWithBrowserState:(ios::ChromeBrowserState*)browserState
-                              loader:(id<UrlLoader>)loader {
+                              loader:(id<UrlLoader>)loader
+                          dispatcher:(id<ApplicationCommands>)dispatcher {
   self = [super initWithStyle:UITableViewStylePlain];
   if (self) {
     DCHECK(browserState);
@@ -177,6 +184,7 @@
     _loader = loader;
     _sessionState = SessionsSyncUserState::USER_SIGNED_OUT;
     _syncedSessions.reset(new synced_sessions::SyncedSessions());
+    _dispatcher = dispatcher;
   }
   return self;
 }
@@ -412,12 +420,9 @@
 }
 
 - (void)showFullHistory {
-  UIViewController* rootViewController =
-      self.tableView.window.rootViewController;
+  __weak RecentTabsTableViewController* weakSelf = self;
   ProceduralBlock openHistory = ^{
-    GenericChromeCommand* openHistory =
-        [[GenericChromeCommand alloc] initWithTag:IDC_SHOW_HISTORY];
-    [rootViewController chromeExecuteCommand:openHistory];
+    [weakSelf.dispatcher showHistory];
   };
   // Dismiss modal, if shown, and open history.
   if (IsIPadIdiom()) {
diff --git a/ios/chrome/browser/ui/tools_menu/tools_menu_constants.h b/ios/chrome/browser/ui/tools_menu/tools_menu_constants.h
index 389721f..1543526 100644
--- a/ios/chrome/browser/ui/tools_menu/tools_menu_constants.h
+++ b/ios/chrome/browser/ui/tools_menu/tools_menu_constants.h
@@ -52,6 +52,7 @@
   TOOLS_NEW_INCOGNITO_TAB_ITEM = -9,
   TOOLS_READING_LIST = -10,
   TOOLS_READER_MODE = -11,
+  TOOLS_SHOW_HISTORY = -12,
 };
 
 #endif  // IOS_CHROME_BROWSER_UI_TOOLS_MENU_TOOLS_MENU_CONSTANTS_H_
diff --git a/ios/chrome/browser/ui/tools_menu/tools_menu_model.mm b/ios/chrome/browser/ui/tools_menu/tools_menu_model.mm
index 7c4bc08..bb7c7573 100644
--- a/ios/chrome/browser/ui/tools_menu/tools_menu_model.mm
+++ b/ios/chrome/browser/ui/tools_menu/tools_menu_model.mm
@@ -61,7 +61,8 @@
     IDC_SHOW_OTHER_DEVICES, nullptr,      ToolbarTypeWebAll,
     kVisibleNotIncognitoOnly,             nil },
   { IDS_HISTORY_SHOW_HISTORY,             kToolsMenuHistoryId,
-    IDC_SHOW_HISTORY, nullptr,            ToolbarTypeWebAll,
+    TOOLS_SHOW_HISTORY,
+    @selector(showHistory),               ToolbarTypeWebAll,
     0,                                    nil },
   { IDS_IOS_OPTIONS_REPORT_AN_ISSUE,      kToolsMenuReportAnIssueId,
     IDC_REPORT_AN_ISSUE, nullptr,         ToolbarTypeAll,
diff --git a/ios/chrome/browser/ui/tools_menu/tools_popup_controller.mm b/ios/chrome/browser/ui/tools_menu/tools_popup_controller.mm
index 4bdd072..1829904 100644
--- a/ios/chrome/browser/ui/tools_menu/tools_popup_controller.mm
+++ b/ios/chrome/browser/ui/tools_menu/tools_popup_controller.mm
@@ -209,7 +209,7 @@
     case IDC_SHOW_BOOKMARK_MANAGER:
       base::RecordAction(UserMetricsAction("MobileMenuAllBookmarks"));
       break;
-    case IDC_SHOW_HISTORY:
+    case TOOLS_SHOW_HISTORY:
       base::RecordAction(UserMetricsAction("MobileMenuHistory"));
       break;
     case IDC_SHOW_OTHER_DEVICES:
diff --git a/ios/chrome/today_extension/today_metrics_logger.h b/ios/chrome/today_extension/today_metrics_logger.h
index 7d93f55e..c4d62fdf 100644
--- a/ios/chrome/today_extension/today_metrics_logger.h
+++ b/ios/chrome/today_extension/today_metrics_logger.h
@@ -15,7 +15,6 @@
 namespace base {
 
 class SequencedWorkerPool;
-class SequencedTaskRunner;
 
 }  // namespace base
 
@@ -26,10 +25,6 @@
 
 }  // namespace
 
-class ValueMapPrefStore;
-class PrefRegistrySimple;
-class PrefService;
-
 // Utility class to create metrics log that can be pushed to Chrome. The
 // extension creates and fills the logs with UserAction. The upload is done by
 // the Chrome application.
@@ -56,10 +51,6 @@
   bool CreateNewLog();
 
   base::MessageLoop message_loop_;
-  scoped_refptr<PrefRegistrySimple> pref_registry_;
-  std::unique_ptr<PrefService> pref_service_;
-  scoped_refptr<ValueMapPrefStore> value_map_prefs_;
-  scoped_refptr<base::SequencedTaskRunner> sequenced_task_runner_;
   std::unique_ptr<TodayMetricsLog> log_;
   scoped_refptr<base::SequencedWorkerPool> thread_pool_;
   std::unique_ptr<TodayMetricsServiceClient> metrics_service_client_;
diff --git a/ios/chrome/today_extension/today_metrics_logger.mm b/ios/chrome/today_extension/today_metrics_logger.mm
index 6d02986c..55b210c 100644
--- a/ios/chrome/today_extension/today_metrics_logger.mm
+++ b/ios/chrome/today_extension/today_metrics_logger.mm
@@ -84,8 +84,7 @@
   TodayMetricsLog(const std::string& client_id,
                   int session_id,
                   LogType log_type,
-                  TodayMetricsServiceClient* client,
-                  PrefService* local_state);
+                  TodayMetricsServiceClient* client);
 
   // Fills |encoded_log| with the serialized protobuf representation of the
   // record. Can be called even on open log.
@@ -158,13 +157,8 @@
 TodayMetricsLog::TodayMetricsLog(const std::string& client_id,
                                  int session_id,
                                  LogType log_type,
-                                 TodayMetricsServiceClient* client,
-                                 PrefService* local_state)
-    : metrics::MetricsLog(client_id,
-                          session_id,
-                          log_type,
-                          client,
-                          local_state) {}
+                                 TodayMetricsServiceClient* client)
+    : metrics::MetricsLog(client_id, session_id, log_type, client) {}
 
 void TodayMetricsLog::GetOpenEncodedLog(std::string* encoded_log) const {
   uma_proto()->SerializeToString(encoded_log);
@@ -239,8 +233,7 @@
       session_id, app_group::APP_GROUP_TODAY_EXTENSION);
   log_.reset(new TodayMetricsLog(base::SysNSStringToUTF8(client_id), session_id,
                                  metrics::MetricsLog::ONGOING_LOG,
-                                 metrics_service_client_.get(),
-                                 pref_service_.get()));
+                                 metrics_service_client_.get()));
 
   metrics::DelegatingProvider delegating_provider;
   log_->RecordEnvironment(&delegating_provider, [install_date longLongValue],
@@ -250,25 +243,12 @@
 }
 
 TodayMetricsLogger::TodayMetricsLogger()
-    : pref_registry_(new PrefRegistrySimple()),
-      thread_pool_(
+    : thread_pool_(
           new base::SequencedWorkerPool(2,
                                         "LoggerPool",
                                         base::TaskPriority::BACKGROUND)),
       metrics_service_client_(new TodayMetricsServiceClient()),
       histogram_snapshot_manager_(this) {
-  metrics::MetricsLog::RegisterPrefs(pref_registry_.get());
-
-  NSString* url = [[NSSearchPathForDirectoriesInDomains(
-      NSLibraryDirectory, NSUserDomainMask, YES) objectAtIndex:0]
-      stringByAppendingPathComponent:@"Application Support/localstate"];
-  base::FilePath path(base::SysNSStringToUTF8(url));
-  sequenced_task_runner_ =
-      JsonPrefStore::GetTaskRunnerForFile(path, thread_pool_.get());
-  PrefServiceFactory factory;
-  factory.set_extension_prefs(value_map_prefs_.get());
-  factory.SetUserPrefsFile(path, sequenced_task_runner_.get());
-  pref_service_ = factory.Create(pref_registry_.get());
   base::StatisticsRecorder::Initialize();
 }
 
diff --git a/ios/clean/chrome/browser/ui/recent_tabs/recent_tabs_coordinator.mm b/ios/clean/chrome/browser/ui/recent_tabs/recent_tabs_coordinator.mm
index 539bee2..12ca148 100644
--- a/ios/clean/chrome/browser/ui/recent_tabs/recent_tabs_coordinator.mm
+++ b/ios/clean/chrome/browser/ui/recent_tabs/recent_tabs_coordinator.mm
@@ -28,13 +28,15 @@
   if (!IsIPadIdiom()) {
     self.viewController = [RecentTabsPanelViewController
         controllerToPresentForBrowserState:self.browser->browser_state()
-                                    loader:nil];
+                                    loader:nil
+                                dispatcher:nil];
     self.viewController.modalPresentationStyle = UIModalPresentationFormSheet;
     self.viewController.modalPresentationCapturesStatusBarAppearance = YES;
   } else {
     self.wrapperController = [[RecentTabsPanelController alloc]
         initWithLoader:nil
-          browserState:self.browser->browser_state()];
+          browserState:self.browser->browser_state()
+            dispatcher:nil];
     self.viewController = [self.wrapperController viewController];
   }
   [super start];
diff --git a/media/base/video_frame_metadata.cc b/media/base/video_frame_metadata.cc
index 5b65cd2f..b8bc5ed 100644
--- a/media/base/video_frame_metadata.cc
+++ b/media/base/video_frame_metadata.cc
@@ -31,7 +31,7 @@
 }
 
 void VideoFrameMetadata::SetBoolean(Key key, bool value) {
-  dictionary_.SetBooleanWithoutPathExpansion(ToInternalKey(key), value);
+  dictionary_.SetKey(ToInternalKey(key), base::Value(value));
 }
 
 void VideoFrameMetadata::SetInteger(Key key, int value) {
diff --git a/net/http/http_auth_handler_ntlm_portable_unittest.cc b/net/http/http_auth_handler_ntlm_portable_unittest.cc
index 9d77ec4a..a379c717 100644
--- a/net/http/http_auth_handler_ntlm_portable_unittest.cc
+++ b/net/http/http_auth_handler_ntlm_portable_unittest.cc
@@ -48,13 +48,20 @@
         &auth_handler_);
   }
 
-  std::string CreateNtlmAuthHeader(base::StringPiece message) {
+  std::string CreateNtlmAuthHeader(ntlm::Buffer message) {
     std::string output;
-    base::Base64Encode(message, &output);
+    base::Base64Encode(
+        base::StringPiece(reinterpret_cast<const char*>(message.data()),
+                          message.size()),
+        &output);
 
     return "NTLM " + output;
   }
 
+  std::string CreateNtlmAuthHeader(const uint8_t* buffer, size_t length) {
+    return CreateNtlmAuthHeader(ntlm::Buffer(buffer, length));
+  }
+
   HttpAuth::AuthorizationResult HandleAnotherChallenge(
       const std::string& challenge) {
     HttpAuthChallengeTokenizer tokenizer(challenge.begin(), challenge.end());
@@ -202,9 +209,8 @@
   ASSERT_EQ(OK, CreateHandler());
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(CreateNtlmAuthHeader(base::StringPiece(
-                reinterpret_cast<const char*>(ntlm::test::kMinChallengeMessage),
-                ntlm::kChallengeHeaderLen))));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(
+                ntlm::test::kMinChallengeMessage, ntlm::kChallengeHeaderLen)));
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 }
 
@@ -212,13 +218,12 @@
   ASSERT_EQ(OK, CreateHandler());
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 
-  char raw[31];
+  uint8_t raw[31];
   memcpy(raw, ntlm::test::kMinChallengeMessage, 31);
 
   // Fail because the minimum size valid message is 32 bytes.
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(
-                CreateNtlmAuthHeader(base::StringPiece(raw, sizeof(raw)))));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(raw, arraysize(raw))));
   ASSERT_EQ(ERR_UNEXPECTED, GetGenerateAuthTokenResult());
 }
 
@@ -226,7 +231,7 @@
   ASSERT_EQ(OK, CreateHandler());
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 
-  char raw[32];
+  uint8_t raw[32];
   memcpy(raw, ntlm::test::kMinChallengeMessage, 32);
   // Modify the default valid message to overwrite the last byte of the
   // signature.
@@ -234,8 +239,7 @@
 
   // Fail because the first 8 bytes don't match "NTLMSSP\0"
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(
-                CreateNtlmAuthHeader(base::StringPiece(raw, sizeof(raw)))));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(raw, arraysize(raw))));
   ASSERT_EQ(ERR_UNEXPECTED, GetGenerateAuthTokenResult());
 }
 
@@ -243,7 +247,7 @@
   ASSERT_EQ(OK, CreateHandler());
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 
-  char raw[32];
+  uint8_t raw[32];
   memcpy(raw, ntlm::test::kMinChallengeMessage, 32);
   // Modify the message type so it is not 0x00000002
   raw[8] = 0x03;
@@ -251,7 +255,7 @@
   // Fail because the message type should be MessageType::kChallenge
   // (0x00000002)
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(CreateNtlmAuthHeader(raw)));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(raw, arraysize(raw))));
   ASSERT_EQ(ERR_UNEXPECTED, GetGenerateAuthTokenResult());
 }
 
@@ -264,14 +268,13 @@
   // expected response from a compliant server when no target name is sent.
   // In reality the offset should always be ignored if the length is zero.
   // Also implementations often just write zeros.
-  char raw[32];
+  uint8_t raw[32];
   memcpy(raw, ntlm::test::kMinChallengeMessage, 32);
   // Modify the default valid message to overwrite the offset to zero.
   raw[16] = 0x00;
 
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(
-                CreateNtlmAuthHeader(base::StringPiece(raw, sizeof(raw)))));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(raw, arraysize(raw))));
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 }
 
@@ -280,7 +283,7 @@
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 
   // One extra byte is provided for target name.
-  char raw[33];
+  uint8_t raw[33];
   memcpy(raw, ntlm::test::kMinChallengeMessage, 32);
   // Modify the default valid message to indicate 1 byte is present in the
   // target name payload.
@@ -290,8 +293,7 @@
   raw[32] = 'Z';
 
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(
-                CreateNtlmAuthHeader(base::StringPiece(raw, sizeof(raw)))));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(raw, arraysize(raw))));
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 }
 
@@ -299,7 +301,7 @@
   ASSERT_EQ(OK, CreateHandler());
   ASSERT_EQ(OK, GetGenerateAuthTokenResult());
 
-  char raw[32];
+  uint8_t raw[32];
   memcpy(raw, ntlm::test::kMinChallengeMessage, 32);
   // Modify the default valid message to claim that the target name field is 1
   // byte long overrunning the end of the message message.
@@ -310,8 +312,7 @@
   // the message buffer because the offset is past the end of the message.
   // Verify it gets rejected.
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(
-                CreateNtlmAuthHeader(base::StringPiece(raw, sizeof(raw)))));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(raw, arraysize(raw))));
   ASSERT_EQ(ERR_UNEXPECTED, GetGenerateAuthTokenResult());
 }
 
@@ -321,7 +322,7 @@
 
   // Message has 1 extra byte of space after the header for the target name.
   // One extra byte is provided for target name.
-  char raw[33];
+  uint8_t raw[33];
   memcpy(raw, ntlm::test::kMinChallengeMessage, 32);
   // Modify the default valid message to indicate 2 bytes are present in the
   // target name payload (however there is only space for 1).
@@ -334,8 +335,7 @@
   // the message buffer because the length is longer than available space.
   // Verify it gets rejected.
   ASSERT_EQ(HttpAuth::AUTHORIZATION_RESULT_ACCEPT,
-            HandleAnotherChallenge(
-                CreateNtlmAuthHeader(base::StringPiece(raw, sizeof(raw)))));
+            HandleAnotherChallenge(CreateNtlmAuthHeader(raw, arraysize(raw))));
   ASSERT_EQ(ERR_UNEXPECTED, GetGenerateAuthTokenResult());
 }
 
diff --git a/net/ntlm/ntlm_buffer_reader.cc b/net/ntlm/ntlm_buffer_reader.cc
index 95ae2e6..ebebc50 100644
--- a/net/ntlm/ntlm_buffer_reader.cc
+++ b/net/ntlm/ntlm_buffer_reader.cc
@@ -11,14 +11,17 @@
 namespace net {
 namespace ntlm {
 
-NtlmBufferReader::NtlmBufferReader(base::StringPiece buffer)
+NtlmBufferReader::NtlmBufferReader(const Buffer& buffer)
     : buffer_(buffer), cursor_(0) {
   DCHECK(buffer.data());
 }
 
+NtlmBufferReader::NtlmBufferReader(base::StringPiece str)
+    : NtlmBufferReader(reinterpret_cast<const uint8_t*>(str.data()),
+                       str.size()) {}
+
 NtlmBufferReader::NtlmBufferReader(const uint8_t* ptr, size_t len)
-    : NtlmBufferReader(
-          base::StringPiece(reinterpret_cast<const char*>(ptr), len)) {}
+    : NtlmBufferReader(Buffer(ptr, len)) {}
 
 NtlmBufferReader::~NtlmBufferReader() {}
 
diff --git a/net/ntlm/ntlm_buffer_reader.h b/net/ntlm/ntlm_buffer_reader.h
index d31429f..dd72b9b 100644
--- a/net/ntlm/ntlm_buffer_reader.h
+++ b/net/ntlm/ntlm_buffer_reader.h
@@ -46,6 +46,7 @@
 // [2] http://davenport.sourceforge.net/ntlm.html
 class NET_EXPORT_PRIVATE NtlmBufferReader {
  public:
+  explicit NtlmBufferReader(const Buffer& buffer);
   explicit NtlmBufferReader(base::StringPiece buffer);
 
   // This class does not take ownership of |ptr|, so the caller must ensure
@@ -165,9 +166,7 @@
   void AdvanceCursor(size_t count) { SetCursor(GetCursor() + count); }
 
   // Returns a constant pointer to the start of the buffer.
-  const uint8_t* GetBufferPtr() const {
-    return reinterpret_cast<const uint8_t*>(buffer_.data());
-  }
+  const uint8_t* GetBufferPtr() const { return buffer_.data(); }
 
   // Returns a pointer to the underlying buffer at the current cursor
   // position.
@@ -179,7 +178,7 @@
     return *(GetBufferAtCursor());
   }
 
-  const base::StringPiece buffer_;
+  const Buffer buffer_;
   size_t cursor_;
 
   DISALLOW_COPY_AND_ASSIGN(NtlmBufferReader);
diff --git a/net/ntlm/ntlm_buffer_writer.cc b/net/ntlm/ntlm_buffer_writer.cc
index 0b5e3aa..746b453 100644
--- a/net/ntlm/ntlm_buffer_writer.cc
+++ b/net/ntlm/ntlm_buffer_writer.cc
@@ -10,13 +10,13 @@
 #include "base/strings/utf_string_conversions.h"
 #include "build/build_config.h"
 
+template class std::basic_string<uint8_t>;
+
 namespace net {
 namespace ntlm {
 
 NtlmBufferWriter::NtlmBufferWriter(size_t buffer_len)
-    : buffer_len_(buffer_len), cursor_(0) {
-  buffer_.reset(new uint8_t[buffer_len]());
-}
+    : buffer_(buffer_len, 0), cursor_(0) {}
 
 NtlmBufferWriter::~NtlmBufferWriter() {}
 
diff --git a/net/ntlm/ntlm_buffer_writer.h b/net/ntlm/ntlm_buffer_writer.h
index 067885d..ecda8cd8 100644
--- a/net/ntlm/ntlm_buffer_writer.h
+++ b/net/ntlm/ntlm_buffer_writer.h
@@ -46,15 +46,11 @@
   explicit NtlmBufferWriter(size_t buffer_len);
   ~NtlmBufferWriter();
 
-  size_t GetLength() const { return buffer_len_; }
+  size_t GetLength() const { return buffer_.size(); }
   size_t GetCursor() const { return cursor_; }
   bool IsEndOfBuffer() const { return cursor_ >= GetLength(); }
-
-  // Gets a base::StringPiece view over the entire buffer.
-  base::StringPiece GetBuffer() const {
-    return base::StringPiece(reinterpret_cast<const char*>(buffer_.get()),
-                             buffer_len_);
-  }
+  const Buffer& GetBuffer() const { return buffer_; }
+  Buffer Pass() const { return std::move(buffer_); }
 
   // Returns true if there are |len| more bytes between the current cursor
   // position and the end of the buffer.
@@ -159,13 +155,16 @@
   void AdvanceCursor(size_t count) { SetCursor(GetCursor() + count); }
 
   // Returns a pointer to the start of the buffer.
-  uint8_t* GetBufferPtr() const { return buffer_.get(); }
+  const uint8_t* GetBufferPtr() const { return &buffer_[0]; }
+  uint8_t* GetBufferPtr() { return &buffer_[0]; }
 
   // Returns pointer into the buffer at the current cursor location.
-  uint8_t* GetBufferPtrAtCursor() const { return buffer_.get() + GetCursor(); }
+  const uint8_t* GetBufferPtrAtCursor() const {
+    return GetBufferPtr() + GetCursor();
+  }
+  uint8_t* GetBufferPtrAtCursor() { return GetBufferPtr() + GetCursor(); }
 
-  std::unique_ptr<uint8_t[]> buffer_;
-  size_t buffer_len_;
+  Buffer buffer_;
   size_t cursor_;
 
   DISALLOW_COPY_AND_ASSIGN(NtlmBufferWriter);
diff --git a/net/ntlm/ntlm_buffer_writer_unittest.cc b/net/ntlm/ntlm_buffer_writer_unittest.cc
index 3616b9f..c05a1728 100644
--- a/net/ntlm/ntlm_buffer_writer_unittest.cc
+++ b/net/ntlm/ntlm_buffer_writer_unittest.cc
@@ -13,16 +13,15 @@
 
 namespace {
 
-// Helper method to hide all the ugly casting.
+// Helper method to get a raw pointer to the buffer.
 const uint8_t* GetBufferPtr(const NtlmBufferWriter& writer) {
-  return reinterpret_cast<const uint8_t*>(writer.GetBuffer().data());
+  return writer.GetBuffer().data();
 }
 
 // Helper method to get a byte at a specific index in the buffer.
 uint8_t GetByteFromBuffer(const NtlmBufferWriter& writer, size_t index) {
-  base::StringPiece piece(writer.GetBuffer());
-  EXPECT_TRUE(index < piece.length());
-  return static_cast<uint8_t>(piece.data()[index]);
+  EXPECT_TRUE(index < writer.GetLength());
+  return writer.GetBuffer()[index];
 }
 
 }  // namespace
diff --git a/net/ntlm/ntlm_constants.h b/net/ntlm/ntlm_constants.h
index 8dc6bb3c..53f69a6 100644
--- a/net/ntlm/ntlm_constants.h
+++ b/net/ntlm/ntlm_constants.h
@@ -7,6 +7,7 @@
 
 #include <stddef.h>
 #include <stdint.h>
+#include <string>
 #include <type_traits>
 
 #include "base/macros.h"
@@ -15,6 +16,8 @@
 namespace net {
 namespace ntlm {
 
+using Buffer = std::basic_string<uint8_t>;
+
 // A security buffer is a structure within an NTLM message that indicates
 // the offset from the beginning of the message and the length of a payload
 // that occurs later in the message. Within the raw message there is also
diff --git a/remoting/client/display/gl_renderer.cc b/remoting/client/display/gl_renderer.cc
index 2913ff3..ba52b37 100644
--- a/remoting/client/display/gl_renderer.cc
+++ b/remoting/client/display/gl_renderer.cc
@@ -106,6 +106,9 @@
 void GlRenderer::OnSurfaceCreated(std::unique_ptr<Canvas> canvas) {
   DCHECK(thread_checker_.CalledOnValidThread());
   canvas_ = std::move(canvas);
+  if (view_width_ > 0 && view_height_ > 0) {
+    canvas_->SetViewSize(view_width_, view_height_);
+  }
   for (auto& drawable : drawables_) {
     drawable->SetCanvas(canvas_->GetWeakPtr());
   }
@@ -113,10 +116,13 @@
 
 void GlRenderer::OnSurfaceChanged(int view_width, int view_height) {
   DCHECK(thread_checker_.CalledOnValidThread());
+  view_width_ = view_width;
+  view_height_ = view_height;
+
   if (!canvas_) {
-    LOG(WARNING) << "Trying to set the view size when the canvas is not ready.";
     return;
   }
+
   canvas_->SetViewSize(view_width, view_height);
   RequestRender();
 }
diff --git a/remoting/client/display/gl_renderer.h b/remoting/client/display/gl_renderer.h
index 46632187..3d14fc1 100644
--- a/remoting/client/display/gl_renderer.h
+++ b/remoting/client/display/gl_renderer.h
@@ -127,6 +127,10 @@
   int canvas_width_ = 0;
   int canvas_height_ = 0;
 
+  // Used to store the view size before the canvas is created.
+  int view_width_ = 0;
+  int view_height_ = 0;
+
   std::unique_ptr<Canvas> canvas_;
 
   GlCursor cursor_;
diff --git a/remoting/ios/app/host_view_controller.mm b/remoting/ios/app/host_view_controller.mm
index a1ca14f..3fb4a366 100644
--- a/remoting/ios/app/host_view_controller.mm
+++ b/remoting/ios/app/host_view_controller.mm
@@ -51,6 +51,8 @@
   // When set to true, ClientKeyboard will immediately resign first responder
   // after it becomes first responder.
   BOOL _blocksKeyboard;
+  NSLayoutConstraint* _keyboardHeightConstraint;
+  EAGLView* _hostView;
 }
 @end
 
@@ -79,15 +81,21 @@
 
 #pragma mark - UIViewController
 
-- (void)loadView {
-  EAGLView* glView = [[EAGLView alloc] initWithFrame:CGRectZero];
-  glView.displayTaskRunner =
-      remoting::ChromotingClientRuntime::GetInstance()->display_task_runner();
-  self.view = glView;
-}
-
 - (void)viewDidLoad {
   [super viewDidLoad];
+  _hostView = [[EAGLView alloc] initWithFrame:CGRectZero];
+  _hostView.displayTaskRunner =
+      remoting::ChromotingClientRuntime::GetInstance()->display_task_runner();
+  _hostView.translatesAutoresizingMaskIntoConstraints = NO;
+  [self.view addSubview:_hostView];
+
+  [NSLayoutConstraint activateConstraints:@[
+    [_hostView.topAnchor constraintEqualToAnchor:self.view.topAnchor],
+    [_hostView.leadingAnchor constraintEqualToAnchor:self.view.leadingAnchor],
+    [_hostView.trailingAnchor constraintEqualToAnchor:self.view.trailingAnchor],
+  ]];
+  [self setKeyboardSize:CGSizeZero needsLayout:NO];
+
   _floatingButton =
       [MDCFloatingButton floatingButtonWithShape:MDCFloatingButtonShapeMini];
   // Note(nicholss): Setting title to " " because the FAB requires the title
@@ -107,13 +115,13 @@
                                    primaryImage:RemotingTheme.menuIcon
                                     activeImage:RemotingTheme.closeIcon];
   [_floatingButton addSubview:_actionImageView];
-  [self.view addSubview:_floatingButton];
+  [_hostView addSubview:_floatingButton];
 
   [self applyInputMode];
 
   _clientKeyboard = [[ClientKeyboard alloc] init];
   _clientKeyboard.delegate = self;
-  [self.view addSubview:_clientKeyboard];
+  [_hostView addSubview:_clientKeyboard];
 
   NSDictionary* views = @{@"fab" : _floatingButton};
   NSDictionary* metrics = @{ @"inset" : @(kFabInset) };
@@ -142,7 +150,7 @@
   [super viewDidUnload];
   // TODO(nicholss): There needs to be a hook to tell the client we are done.
 
-  [(EAGLView*)self.view stop];
+  [_hostView stop];
   _clientGestures = nil;
   _client = nil;
 }
@@ -154,16 +162,11 @@
 - (void)viewDidAppear:(BOOL)animated {
   [super viewDidAppear:animated];
   if (!_surfaceCreated) {
-    [_client.displayHandler onSurfaceCreated:(EAGLView*)self.view];
+    [_client.displayHandler onSurfaceCreated:_hostView];
     _surfaceCreated = YES;
   }
-  // viewDidLayoutSubviews may be called before viewDidAppear, in which case
-  // the surface is not ready to handle the transformation matrix.
-  // Call onSurfaceChanged here to cover that case.
-  [_client surfaceChanged:self.view.frame];
-  [self resizeHostToFitIfNeeded];
 
-  [PhysicalKeyboardDetector detectOnView:self.view
+  [PhysicalKeyboardDetector detectOnView:_hostView
                                 callback:^(BOOL hasPhysicalKeyboard) {
                                   if (hasPhysicalKeyboard) {
                                     _clientKeyboard.hasPhysicalKeyboard =
@@ -182,7 +185,7 @@
 
   if (!_clientGestures) {
     _clientGestures =
-        [[ClientGestures alloc] initWithView:self.view client:_client];
+        [[ClientGestures alloc] initWithView:_hostView client:_client];
     _clientGestures.delegate = self;
   }
   [[NSNotificationCenter defaultCenter]
@@ -210,12 +213,8 @@
 - (void)viewDidLayoutSubviews {
   [super viewDidLayoutSubviews];
 
-  if (self.view.window != nil) {
-    // If the context is not set yet, the view size will be set in
-    // viewDidAppear.
-    [_client surfaceChanged:self.view.bounds];
-    [self resizeHostToFitIfNeeded];
-  }
+  [_client surfaceChanged:_hostView.bounds];
+  [self resizeHostToFitIfNeeded];
 
   [self updateFABConstraintsAnimated:NO];
 }
@@ -250,26 +249,11 @@
       [[[notification userInfo] objectForKey:UIKeyboardFrameEndUserInfoKey]
           CGRectValue]
           .size;
-  if (_keyboardSize.height != keyboardSize.height) {
-    CGFloat deltaHeight = keyboardSize.height - _keyboardSize.height;
-    [UIView animateWithDuration:kKeyboardAnimationTime
-                     animations:^{
-                       CGRect f = self.view.frame;
-                       f.size.height -= deltaHeight;
-                       self.view.frame = f;
-                     }];
-    _keyboardSize = keyboardSize;
-  }
+  [self setKeyboardSize:keyboardSize needsLayout:YES];
 }
 
 - (void)keyboardWillHide:(NSNotification*)notification {
-  [UIView animateWithDuration:kKeyboardAnimationTime
-                   animations:^{
-                     CGRect f = self.view.frame;
-                     f.size.height += _keyboardSize.height;
-                     self.view.frame = f;
-                   }];
-  _keyboardSize = CGSizeZero;
+  [self setKeyboardSize:CGSizeZero needsLayout:YES];
 }
 
 #pragma mark - ClientKeyboardDelegate
@@ -364,8 +348,8 @@
 
   if (_settings.shouldResizeHostToFit && !isPhonePortrait &&
       ![self isKeyboardActive]) {
-    [_client setHostResolution:self.view.frame.size
-                         scale:self.view.contentScaleFactor];
+    [_client setHostResolution:_hostView.frame.size
+                         scale:_hostView.contentScaleFactor];
   }
 }
 
@@ -467,17 +451,12 @@
         restoresKeyboard:NO
                  handler:settingsHandler];
 
-  void (^moveFABHandler)(UIAlertAction*) = ^(UIAlertAction*) {
-    [weakSelf moveFAB];
-    [_actionImageView setActive:NO animated:YES];
-  };
-  [alert addAction:[UIAlertAction
-                       actionWithTitle:l10n_util::GetNSString(
-                                           (_fabIsRight)
-                                               ? IDS_MOVE_FAB_LEFT_BUTTON
-                                               : IDS_MOVE_FAB_RIGHT_BUTTON)
-                                 style:UIAlertActionStyleDefault
-                               handler:moveFABHandler]];
+  [self addActionToAlert:alert
+                   title:(_fabIsRight) ? IDS_MOVE_FAB_LEFT_BUTTON
+                                       : IDS_MOVE_FAB_RIGHT_BUTTON
+                 handler:^() {
+                   [weakSelf moveFAB];
+                 }];
 
   __weak UIAlertController* weakAlert = alert;
   void (^cancelHandler)() = ^() {
@@ -489,7 +468,7 @@
         restoresKeyboard:YES
                  handler:cancelHandler];
 
-  alert.popoverPresentationController.sourceView = self.view;
+  alert.popoverPresentationController.sourceView = _hostView;
   // Target the alert menu at the top middle of the FAB.
   alert.popoverPresentationController.sourceRect = CGRectMake(
       _floatingButton.center.x, _floatingButton.frame.origin.y, 1.0, 1.0);
@@ -541,4 +520,22 @@
                  handler:handler];
 }
 
+- (void)setKeyboardSize:(CGSize)keyboardSize needsLayout:(BOOL)needsLayout {
+  _keyboardSize = keyboardSize;
+  if (_keyboardHeightConstraint) {
+    _keyboardHeightConstraint.active = NO;
+  }
+  _keyboardHeightConstraint =
+      [_hostView.bottomAnchor constraintEqualToAnchor:self.view.bottomAnchor
+                                             constant:-keyboardSize.height];
+  _keyboardHeightConstraint.active = YES;
+
+  if (needsLayout) {
+    [UIView animateWithDuration:kKeyboardAnimationTime
+                     animations:^{
+                       [self.view setNeedsLayout];
+                     }];
+  }
+}
+
 @end
diff --git a/services/preferences/pref_service_factory_unittest.cc b/services/preferences/pref_service_factory_unittest.cc
index 9166e96a..a875339 100644
--- a/services/preferences/pref_service_factory_unittest.cc
+++ b/services/preferences/pref_service_factory_unittest.cc
@@ -419,7 +419,7 @@
         EXPECT_TRUE(out);
       },
       [](ScopedDictionaryPrefUpdate* update) {
-        (*update)->SetBooleanWithoutPathExpansion("key.for.boolean", false);
+        (*update)->SetKey("key.for.boolean", base::Value(false));
         bool out = 0;
         ASSERT_TRUE(
             (*update)->GetBooleanWithoutPathExpansion("key.for.boolean", &out));
diff --git a/services/preferences/public/cpp/dictionary_value_update.cc b/services/preferences/public/cpp/dictionary_value_update.cc
index afd7ae8..4fb6e719 100644
--- a/services/preferences/public/cpp/dictionary_value_update.cc
+++ b/services/preferences/public/cpp/dictionary_value_update.cc
@@ -86,6 +86,15 @@
       report_update_, dictionary_value, ConcatPath(path_, path));
 }
 
+void DictionaryValueUpdate::SetKey(base::StringPiece key, base::Value value) {
+  auto found = value_->FindKey(key);
+  if (found != value_->DictEnd() && found->second == value)
+    return;
+
+  RecordKey(key);
+  value_->SetKey(key, std::move(value));
+}
+
 void DictionaryValueUpdate::SetWithoutPathExpansion(
     base::StringPiece key,
     std::unique_ptr<base::Value> in_value) {
@@ -98,12 +107,6 @@
   value_->SetWithoutPathExpansion(key, std::move(in_value));
 }
 
-void DictionaryValueUpdate::SetBooleanWithoutPathExpansion(
-    base::StringPiece path,
-    bool in_value) {
-  SetWithoutPathExpansion(path, base::MakeUnique<base::Value>(in_value));
-}
-
 void DictionaryValueUpdate::SetIntegerWithoutPathExpansion(
     base::StringPiece path,
     int in_value) {
diff --git a/services/preferences/public/cpp/dictionary_value_update.h b/services/preferences/public/cpp/dictionary_value_update.h
index fb3dc4d..2de37507 100644
--- a/services/preferences/public/cpp/dictionary_value_update.h
+++ b/services/preferences/public/cpp/dictionary_value_update.h
@@ -66,11 +66,11 @@
 
   // Like Set(), but without special treatment of '.'.  This allows e.g. URLs to
   // be used as paths.
+  void SetKey(base::StringPiece key, base::Value value);
   void SetWithoutPathExpansion(base::StringPiece key,
                                std::unique_ptr<base::Value> in_value);
 
   // Convenience forms of SetWithoutPathExpansion().
-  void SetBooleanWithoutPathExpansion(base::StringPiece path, bool in_value);
   void SetIntegerWithoutPathExpansion(base::StringPiece path, int in_value);
   void SetDoubleWithoutPathExpansion(base::StringPiece path, double in_value);
   void SetStringWithoutPathExpansion(base::StringPiece path,
diff --git a/services/ui/service.cc b/services/ui/service.cc
index e937362..60a3932 100644
--- a/services/ui/service.cc
+++ b/services/ui/service.cc
@@ -144,7 +144,9 @@
       threaded_image_cursors_factory_(
           base::MakeUnique<ThreadedImageCursorsFactoryImpl>(config)),
       test_config_(false),
-      ime_registrar_(&ime_driver_) {}
+      ime_registrar_(&ime_driver_),
+      discardable_shared_memory_manager_(config ? config->memory_manager
+                                                : nullptr) {}
 
 Service::~Service() {
   // Destroy |window_server_| first, since it depends on |event_source_|.
@@ -279,9 +281,12 @@
 
   ime_driver_.Init(context()->connector(), test_config_);
 
-  discardable_shared_memory_manager_ =
-      base::MakeUnique<discardable_memory::DiscardableSharedMemoryManager>();
-
+  if (!discardable_shared_memory_manager_) {
+    owned_discardable_shared_memory_manager_ =
+        base::MakeUnique<discardable_memory::DiscardableSharedMemoryManager>();
+    discardable_shared_memory_manager_ =
+        owned_discardable_shared_memory_manager_.get();
+  }
   registry_.AddInterface<mojom::AccessibilityManager>(base::Bind(
       &Service::BindAccessibilityManagerRequest, base::Unretained(this)));
   registry_.AddInterface<mojom::Clipboard>(
diff --git a/services/ui/service.h b/services/ui/service.h
index f57d9fe..1cb7c2a 100644
--- a/services/ui/service.h
+++ b/services/ui/service.h
@@ -79,6 +79,10 @@
     // Can only be de-referenced on |resource_runner_|.
     base::WeakPtr<ImageCursorsSet> image_cursors_set_weak_ptr = nullptr;
 
+    // If null Service creates a DiscardableSharedMemoryManager.
+    discardable_memory::DiscardableSharedMemoryManager* memory_manager =
+        nullptr;
+
    private:
     DISALLOW_COPY_AND_ASSIGN(InProcessConfig);
   };
@@ -207,9 +211,14 @@
   IMERegistrarImpl ime_registrar_;
   IMEDriverBridge ime_driver_;
 
-  std::unique_ptr<discardable_memory::DiscardableSharedMemoryManager>
+  discardable_memory::DiscardableSharedMemoryManager*
       discardable_shared_memory_manager_;
 
+  // non-null if this created the DiscardableSharedMemoryManager. Null when
+  // running in-process.
+  std::unique_ptr<discardable_memory::DiscardableSharedMemoryManager>
+      owned_discardable_shared_memory_manager_;
+
   service_manager::BinderRegistryWithArgs<
       const service_manager::BindSourceInfo&>
       registry_;
diff --git a/services/ui/ws/window_server.cc b/services/ui/ws/window_server.cc
index 6c72adba..7c22256a 100644
--- a/services/ui/ws/window_server.cc
+++ b/services/ui/ws/window_server.cc
@@ -717,9 +717,10 @@
 
   WindowManagerDisplayRoot* display_root =
       display_manager_->GetWindowManagerDisplayRoot(window);
-  if (display_root)
+  if (display_root) {
     display_root->window_manager_state()
         ->ReleaseCaptureBlockedByAnyModalWindow();
+  }
 
   ProcessWindowHierarchyChanged(window, new_parent, old_parent);
 
@@ -732,6 +733,25 @@
                                                     window->frame_sink_id());
   }
 
+  if (!pending_system_modal_windows_.windows().empty()) {
+    // Windows that are now in a display are put here, then removed. We do this
+    // in two passes to avoid removing from a list we're iterating over.
+    std::set<ServerWindow*> no_longer_pending;
+    for (ServerWindow* system_modal_window :
+         pending_system_modal_windows_.windows()) {
+      DCHECK_EQ(MODAL_TYPE_SYSTEM, system_modal_window->modal_type());
+      WindowManagerDisplayRoot* display_root =
+          display_manager_->GetWindowManagerDisplayRoot(system_modal_window);
+      if (display_root) {
+        no_longer_pending.insert(system_modal_window);
+        display_root->window_manager_state()->AddSystemModalWindow(window);
+      }
+    }
+
+    for (ServerWindow* system_modal_window : no_longer_pending)
+      pending_system_modal_windows_.Remove(system_modal_window);
+  }
+
   UpdateNativeCursorFromMouseLocation(window);
 }
 
@@ -864,6 +884,25 @@
   }
 }
 
+void WindowServer::OnWindowModalTypeChanged(ServerWindow* window,
+                                            ModalType old_modal_type) {
+  WindowManagerDisplayRoot* display_root =
+      display_manager_->GetWindowManagerDisplayRoot(window);
+  if (window->modal_type() == MODAL_TYPE_SYSTEM) {
+    if (display_root)
+      display_root->window_manager_state()->AddSystemModalWindow(window);
+    else
+      pending_system_modal_windows_.Add(window);
+  } else {
+    pending_system_modal_windows_.Remove(window);
+  }
+
+  if (display_root && window->modal_type() != MODAL_TYPE_NONE) {
+    display_root->window_manager_state()
+        ->ReleaseCaptureBlockedByAnyModalWindow();
+  }
+}
+
 void WindowServer::OnGpuServiceInitialized() {
   delegate_->StartDisplayInit();
 }
diff --git a/services/ui/ws/window_server.h b/services/ui/ws/window_server.h
index 8f846ad..f29d8c09c 100644
--- a/services/ui/ws/window_server.h
+++ b/services/ui/ws/window_server.h
@@ -22,6 +22,7 @@
 #include "services/ui/ws/operation.h"
 #include "services/ui/ws/server_window_delegate.h"
 #include "services/ui/ws/server_window_observer.h"
+#include "services/ui/ws/server_window_tracker.h"
 #include "services/ui/ws/user_display_manager_delegate.h"
 #include "services/ui/ws/user_id_tracker.h"
 #include "services/ui/ws/user_id_tracker_observer.h"
@@ -357,6 +358,8 @@
                               ServerWindow* transient_child) override;
   void OnTransientWindowRemoved(ServerWindow* window,
                                 ServerWindow* transient_child) override;
+  void OnWindowModalTypeChanged(ServerWindow* window,
+                                ModalType old_modal_type) override;
 
   // GpuHostDelegate:
   void OnGpuServiceInitialized() override;
@@ -412,6 +415,10 @@
   // Provides interfaces to create and manage FrameSinks.
   std::unique_ptr<viz::mojom::FrameSinkManager> frame_sink_manager_;
 
+  // System modal windows not attached to a display are added here. Once
+  // attached to a display they are removed.
+  ServerWindowTracker pending_system_modal_windows_;
+
   DisplayCreationConfig display_creation_config_;
 
   DISALLOW_COPY_AND_ASSIGN(WindowServer);
diff --git a/services/ui/ws/window_tree.cc b/services/ui/ws/window_tree.cc
index 29dd309..125f69ac 100644
--- a/services/ui/ws/window_tree.cc
+++ b/services/ui/ws/window_tree.cc
@@ -552,26 +552,7 @@
   if (window->modal_type() == modal_type)
     return true;
 
-  auto* display_root = GetWindowManagerDisplayRoot(window);
-  switch (modal_type) {
-    case MODAL_TYPE_SYSTEM:
-      if (!display_root) {
-        DVLOG(1) << "SetModalType failed (no display root)";
-        return false;
-      }
-      window->SetModalType(modal_type);
-      display_root->window_manager_state()->AddSystemModalWindow(window);
-      break;
-    case MODAL_TYPE_NONE:
-    case MODAL_TYPE_WINDOW:
-    case MODAL_TYPE_CHILD:
-      window->SetModalType(modal_type);
-      break;
-  }
-  if (display_root && modal_type != MODAL_TYPE_NONE) {
-    display_root->window_manager_state()->ReleaseCaptureBlockedByModalWindow(
-        window);
-  }
+  window->SetModalType(modal_type);
   return true;
 }
 
diff --git a/services/ui/ws/window_tree_unittest.cc b/services/ui/ws/window_tree_unittest.cc
index ae9d0b0..35f1ede5 100644
--- a/services/ui/ws/window_tree_unittest.cc
+++ b/services/ui/ws/window_tree_unittest.cc
@@ -745,6 +745,29 @@
             modal_window_controller_test_api.GetActiveSystemModalWindow());
 }
 
+TEST_F(WindowTreeTest, ModalTypeSystemUnparentedThenParented) {
+  const ClientWindowId test_window_id = BuildClientWindowId(wm_tree(), 21);
+  EXPECT_TRUE(wm_tree()->NewWindow(test_window_id, ServerWindow::Properties()));
+  ServerWindow* test_window = wm_tree()->GetWindowByClientId(test_window_id);
+  ASSERT_TRUE(test_window);
+  test_window->SetVisible(true);
+  const ClientWindowId wm_root_id = FirstRootId(wm_tree());
+  EXPECT_TRUE(wm_tree()->SetModalType(test_window_id, MODAL_TYPE_SYSTEM));
+  WindowManagerState* wms =
+      display()->GetActiveWindowManagerDisplayRoot()->window_manager_state();
+  ModalWindowControllerTestApi modal_window_controller_test_api(
+      EventDispatcherTestApi(wms->event_dispatcher())
+          .modal_window_controller());
+  EXPECT_EQ(nullptr,
+            modal_window_controller_test_api.GetActiveSystemModalWindow());
+  EXPECT_TRUE(wm_tree()->AddWindow(wm_root_id, test_window_id));
+  EXPECT_EQ(test_window,
+            modal_window_controller_test_api.GetActiveSystemModalWindow());
+  EXPECT_TRUE(wm_tree()->SetModalType(test_window_id, MODAL_TYPE_NONE));
+  EXPECT_EQ(nullptr,
+            modal_window_controller_test_api.GetActiveSystemModalWindow());
+}
+
 // Establish client, call NewTopLevelWindow(), make sure get id, and make
 // sure client paused.
 TEST_F(WindowTreeTest, NewTopLevelWindow) {
@@ -1117,7 +1140,7 @@
   EXPECT_NO_FATAL_FAILURE(SetupEventTargeting(&embed_client, &tree, &w1));
 
   w1->SetBounds(gfx::Rect(10, 10, 30, 30));
-  const ServerWindow* root_window = *tree->roots().begin();
+  ServerWindow* root_window = FirstRoot(tree);
   ClientWindowId root_window_id = ClientWindowIdForWindow(tree, root_window);
   ClientWindowId w1_id = ClientWindowIdForWindow(tree, w1);
   Display* display = tree->GetDisplay(w1);
diff --git a/services/viz/public/interfaces/hit_test/hit_test_region_list.mojom b/services/viz/public/interfaces/hit_test/hit_test_region_list.mojom
index 3c36743..ff251be 100644
--- a/services/viz/public/interfaces/hit_test/hit_test_region_list.mojom
+++ b/services/viz/public/interfaces/hit_test/hit_test_region_list.mojom
@@ -20,8 +20,13 @@
 // Irregular boundary - send HitTestRequest to resolve.
 const uint32 kHitTestAsk = 0x08;
 
-// Touch event handler exists.
-const uint32 kHitTestTouchEventHandler = 0x10;
+// TODO(varkha): Add other kHitTest* flags as necessary for other event sources
+// such as mouse-wheel, stylus or perhaps even mouse-move.
+// Hit-testing for mouse events.
+const uint32 kHitTestMouse = 0x10;
+
+// Hit-testing for touch events.
+const uint32 kHitTestTouch = 0x20;
 
 struct HitTestRegion {
   // Flags to indicate the type of HitTestRegion.
diff --git a/skia/config/SkUserConfig.h b/skia/config/SkUserConfig.h
index ade91ab..757c0d9 100644
--- a/skia/config/SkUserConfig.h
+++ b/skia/config/SkUserConfig.h
@@ -216,6 +216,10 @@
 #define SK_SUPPORT_LEGACY_DELTA_AA
 #endif
 
+#ifndef SK_JUMPER_LEGACY_LOWP
+#define SK_JUMPER_LEGACY_LOWP
+#endif
+
 ///////////////////////// Imported from BUILD.gn and skia_common.gypi
 
 /* In some places Skia can use static initializers for global initialization,
diff --git a/testing/buildbot/chromium.perf.json b/testing/buildbot/chromium.perf.json
index 2172e91f2..a8f92d2 100644
--- a/testing/buildbot/chromium.perf.json
+++ b/testing/buildbot/chromium.perf.json
@@ -2095,6 +2095,128 @@
       },
       {
         "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build14-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build14-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build48-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build48-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
           "scheduler.tough_scheduling_cases",
           "-v",
           "--upload-results",
@@ -2339,67 +2461,6 @@
       },
       {
         "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build14-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build14-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "smoothness.gpu_rasterization.top_25_smooth",
           "-v",
           "--upload-results",
@@ -3925,67 +3986,6 @@
       },
       {
         "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build14-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build14-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "thread_times.key_idle_power_cases",
           "-v",
           "--upload-results",
@@ -6807,6 +6807,128 @@
       },
       {
         "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build74-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build74-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build75-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build75-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
           "scheduler.tough_scheduling_cases",
           "-v",
           "--upload-results",
@@ -7051,67 +7173,6 @@
       },
       {
         "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build74-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build74-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "smoothness.gpu_rasterization.top_25_smooth",
           "-v",
           "--upload-results",
@@ -8637,67 +8698,6 @@
       },
       {
         "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build74-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build74-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "thread_times.key_idle_power_cases",
           "-v",
           "--upload-results",
@@ -10539,6 +10539,68 @@
       },
       {
         "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-webview",
+          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
+        ],
+        "isolate_name": "telemetry_perf_webview_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation",
+        "override_compile_targets": [
+          "telemetry_perf_webview_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build166-b1--device5",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-webview",
+          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
+        ],
+        "isolate_name": "telemetry_perf_webview_tests",
+        "name": "rasterize_and_record_micro.top_25",
+        "override_compile_targets": [
+          "telemetry_perf_webview_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build166-b1--device5",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
           "scheduler.tough_scheduling_cases",
           "-v",
           "--upload-results",
@@ -10663,37 +10725,6 @@
       },
       {
         "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-webview",
-          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
-        ],
-        "isolate_name": "telemetry_perf_webview_tests",
-        "name": "smoothness.gpu_rasterization.polymer",
-        "override_compile_targets": [
-          "telemetry_perf_webview_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build165-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "smoothness.gpu_rasterization.top_25_smooth",
           "-v",
           "--upload-results",
@@ -11469,37 +11500,6 @@
       },
       {
         "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-webview",
-          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
-        ],
-        "isolate_name": "telemetry_perf_webview_tests",
-        "name": "thread_times.key_hit_test_cases",
-        "override_compile_targets": [
-          "telemetry_perf_webview_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build166-b1--device2",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "thread_times.key_idle_power_cases",
           "-v",
           "--upload-results",
@@ -13992,6 +13992,128 @@
       },
       {
         "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build16-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build16-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build45-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build45-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
           "scheduler.tough_scheduling_cases",
           "-v",
           "--upload-results",
@@ -14236,67 +14358,6 @@
       },
       {
         "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build16-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build16-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "smoothness.gpu_rasterization.top_25_smooth",
           "-v",
           "--upload-results",
@@ -15822,67 +15883,6 @@
       },
       {
         "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build16-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build16-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "thread_times.key_idle_power_cases",
           "-v",
           "--upload-results",
@@ -17755,6 +17755,68 @@
       },
       {
         "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-webview",
+          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
+        ],
+        "isolate_name": "telemetry_perf_webview_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation",
+        "override_compile_targets": [
+          "telemetry_perf_webview_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build114-b1--device5",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-webview",
+          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
+        ],
+        "isolate_name": "telemetry_perf_webview_tests",
+        "name": "rasterize_and_record_micro.top_25",
+        "override_compile_targets": [
+          "telemetry_perf_webview_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build114-b1--device5",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
           "scheduler.tough_scheduling_cases",
           "-v",
           "--upload-results",
@@ -17879,37 +17941,6 @@
       },
       {
         "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-webview",
-          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
-        ],
-        "isolate_name": "telemetry_perf_webview_tests",
-        "name": "smoothness.gpu_rasterization.polymer",
-        "override_compile_targets": [
-          "telemetry_perf_webview_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build113-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "smoothness.gpu_rasterization.top_25_smooth",
           "-v",
           "--upload-results",
@@ -18685,37 +18716,6 @@
       },
       {
         "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-webview",
-          "--webview-embedder-apk=../../out/Release/apks/SystemWebViewShell.apk"
-        ],
-        "isolate_name": "telemetry_perf_webview_tests",
-        "name": "thread_times.key_hit_test_cases",
-        "override_compile_targets": [
-          "telemetry_perf_webview_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build114-b1--device2",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "thread_times.key_idle_power_cases",
           "-v",
           "--upload-results",
@@ -21208,6 +21208,128 @@
       },
       {
         "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build10-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build10-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build49-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build49-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
           "scheduler.tough_scheduling_cases",
           "-v",
           "--upload-results",
@@ -21452,67 +21574,6 @@
       },
       {
         "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build10-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build10-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "smoothness.gpu_rasterization.top_25_smooth",
           "-v",
           "--upload-results",
@@ -23038,67 +23099,6 @@
       },
       {
         "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build10-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build10-b1--device1",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "thread_times.key_idle_power_cases",
           "-v",
           "--upload-results",
@@ -25798,6 +25798,128 @@
       },
       {
         "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build18-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.partial_invalidation",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.partial_invalidation.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build18-b1--device4",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=android-chromium"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build18-b1--device5",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": false,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
+          "rasterize_and_record_micro.top_25",
+          "-v",
+          "--upload-results",
+          "--output-format=chartjson",
+          "--browser=reference",
+          "--output-trace-tag=_ref"
+        ],
+        "isolate_name": "telemetry_perf_tests",
+        "name": "rasterize_and_record_micro.top_25.reference",
+        "override_compile_targets": [
+          "telemetry_perf_tests"
+        ],
+        "swarming": {
+          "can_use_on_swarming_builders": true,
+          "dimension_sets": [
+            {
+              "android_devices": "1",
+              "id": "build18-b1--device5",
+              "os": "Android",
+              "pool": "Chrome-perf"
+            }
+          ],
+          "expiration": 36000,
+          "hard_timeout": 10800,
+          "ignore_task_failure": true,
+          "io_timeout": 3600,
+          "upload_test_results": false
+        }
+      },
+      {
+        "args": [
           "scheduler.tough_scheduling_cases",
           "-v",
           "--upload-results",
@@ -26042,67 +26164,6 @@
       },
       {
         "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build18-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "smoothness.gpu_rasterization.polymer",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "smoothness.gpu_rasterization.polymer.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build18-b1--device4",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "smoothness.gpu_rasterization.top_25_smooth",
           "-v",
           "--upload-results",
@@ -27628,67 +27689,6 @@
       },
       {
         "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=android-chromium"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build47-b1--device7",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": false,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
-          "thread_times.key_hit_test_cases",
-          "-v",
-          "--upload-results",
-          "--output-format=chartjson",
-          "--browser=reference",
-          "--output-trace-tag=_ref"
-        ],
-        "isolate_name": "telemetry_perf_tests",
-        "name": "thread_times.key_hit_test_cases.reference",
-        "override_compile_targets": [
-          "telemetry_perf_tests"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "android_devices": "1",
-              "id": "build47-b1--device7",
-              "os": "Android",
-              "pool": "Chrome-perf"
-            }
-          ],
-          "expiration": 36000,
-          "hard_timeout": 10800,
-          "ignore_task_failure": true,
-          "io_timeout": 3600,
-          "upload_test_results": false
-        }
-      },
-      {
-        "args": [
           "thread_times.key_idle_power_cases",
           "-v",
           "--upload-results",
diff --git a/testing/buildbot/gn_isolate_map.pyl b/testing/buildbot/gn_isolate_map.pyl
index e60c57be..680580b 100644
--- a/testing/buildbot/gn_isolate_map.pyl
+++ b/testing/buildbot/gn_isolate_map.pyl
@@ -1112,7 +1112,6 @@
       "../../third_party/WebKit/Tools/Scripts/run-webkit-tests",
       "--seed", "4",
       "--no-show-results",
-      "--full-results-html",
       "--clobber-old-results",
       "--exit-after-n-failures", "5000",
       "--exit-after-n-crashes-or-timeouts", "100",
diff --git a/testing/variations/fieldtrial_testing_config.json b/testing/variations/fieldtrial_testing_config.json
index 3bbd16a..82c6f2c 100644
--- a/testing/variations/fieldtrial_testing_config.json
+++ b/testing/variations/fieldtrial_testing_config.json
@@ -1332,6 +1332,21 @@
             ]
         }
     ],
+    "MacV2Sandbox": [
+        {
+            "platforms": [
+                "mac"
+            ],
+            "experiments": [
+                {
+                    "name": "Enabled",
+                    "enable_features": [
+                        "MacV2Sandbox"
+                    ]
+                }
+            ]
+        }
+    ],
     "MaxDelayableRequestsNetworkOverride": [
         {
             "platforms": [
@@ -1732,6 +1747,31 @@
             ]
         }
     ],
+    "OffMainThreadFetch": [
+        {
+            "platforms": [
+                "android",
+                "chromeos",
+                "linux",
+                "mac",
+                "win"
+            ],
+            "experiments": [
+                {
+                    "name": "Enabled",
+                    "enable_features": [
+                        "OffMainThreadFetch"
+                    ]
+                },
+                {
+                    "name": "Disabled",
+                    "disable_features": [
+                        "OffMainThreadFetch"
+                    ]
+                }
+            ]
+        }
+    ],
     "OfferUploadCreditCards": [
         {
             "platforms": [
diff --git a/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch-blocked.html b/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch-blocked.html
index 2c1614d..e24f097 100644
--- a/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch-blocked.html
+++ b/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch-blocked.html
@@ -5,9 +5,6 @@
 <script>
 function test()
 {
-    // Need to enable networkInWorkers experiment for off-main-thread-fetch virtual test.
-    Runtime.experiments.enableForTest("networkInWorkers");
-
     InspectorTest.recordNetwork();
     SDK.multitargetNetworkManager.setBlockingEnabled(true);
     SDK.multitargetNetworkManager.setBlockedPatterns([{url: 'resources/resource.php', enabled: true}]);
diff --git a/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch.html b/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch.html
index 2f1cc71..60f98f1 100644
--- a/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch.html
+++ b/third_party/WebKit/LayoutTests/http/tests/inspector/network/network-worker-fetch.html
@@ -5,9 +5,6 @@
 <script>
 function test()
 {
-    // Need to enable networkInWorkers experiment for off-main-thread-fetch virtual test.
-    Runtime.experiments.enableForTest("networkInWorkers");
-
     InspectorTest.recordNetwork();
 
     InspectorTest.makeFetchInWorker('resource.php', {}, fetchCallback);
diff --git a/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch-blocked.html b/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch-blocked.html
index 7a37b5a..585baea 100644
--- a/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch-blocked.html
+++ b/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch-blocked.html
@@ -11,9 +11,6 @@
 {
     let scope = "http://127.0.0.1:8000/inspector/service-workers/resources/network-fetch-worker-blocked-scope";
 
-    // Need to enable networkInWorkers experiment for off-main-thread-fetch virtual test.
-    Runtime.experiments.enableForTest("networkInWorkers");
-
     InspectorTest.recordNetwork();
     SDK.multitargetNetworkManager.setBlockingEnabled(true);
     SDK.multitargetNetworkManager.setBlockedPatterns([{url: 'resources/resource.php', enabled: true}]);
diff --git a/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch.html b/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch.html
index aeaea0e..33207d9 100644
--- a/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch.html
+++ b/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/service-worker-network-fetch.html
@@ -11,9 +11,6 @@
 {
     let scope = "http://127.0.0.1:8000/inspector/service-workers/resources/network-fetch-worker-scope";
 
-    // Need to enable networkInWorkers experiment for off-main-thread-fetch virtual test.
-    Runtime.experiments.enableForTest("networkInWorkers");
-
     InspectorTest.recordNetwork();
 
     InspectorTest.makeFetchInServiceWorker(scope, '../../network/resources/resource.php', {}, fetchCallback);
diff --git a/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/user-agent-override.html b/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/user-agent-override.html
index a155382..c1908f82 100644
--- a/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/user-agent-override.html
+++ b/third_party/WebKit/LayoutTests/http/tests/inspector/service-workers/user-agent-override.html
@@ -7,9 +7,6 @@
 <script>
 function test()
 {
-    // Need to enable networkInWorkers experiment for off-main-thread-fetch virtual test.
-    Runtime.experiments.enableForTest("networkInWorkers");
-
     function waitForTarget()
     {
         return new Promise(function(resolve) {
diff --git a/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/clear-integrity-attribute-expected.txt b/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/clear-integrity-attribute-expected.txt
index 98696d4..f5ff0f2 100644
--- a/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/clear-integrity-attribute-expected.txt
+++ b/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/clear-integrity-attribute-expected.txt
@@ -1,5 +1,6 @@
 CONSOLE ERROR: Failed to find a valid digest in the 'integrity' attribute for resource 'http://127.0.0.1:8000/security/subresourceIntegrity/resources/clear-integrity-attribute.js' with computed SHA-256 integrity 'yM5ZyzNsyKfaXRY78zSGapeQKtl0oGdpPpYxgwl8XW8='. The resource has been blocked.
 ALERT: FAIL
+CONSOLE ERROR: line 15: Failed to find a valid digest in the 'integrity' attribute for resource 'http://127.0.0.1:8000/security/subresourceIntegrity/resources/clear-integrity-attribute.js' with computed SHA-256 integrity 'yM5ZyzNsyKfaXRY78zSGapeQKtl0oGdpPpYxgwl8XW8='. The resource has been blocked.
 This test passes if only one 'FAIL' alert appears.
 
 
diff --git a/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/shared-with-xhtml-expected.txt b/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/shared-with-xhtml-expected.txt
index fc1fcdd..b426507 100644
--- a/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/shared-with-xhtml-expected.txt
+++ b/third_party/WebKit/LayoutTests/http/tests/security/subresourceIntegrity/shared-with-xhtml-expected.txt
@@ -1,4 +1,5 @@
 CONSOLE ERROR: Failed to find a valid digest in the 'integrity' attribute for resource 'http://127.0.0.1:8000/security/subresourceIntegrity/resources/shared-with-xhtml.js' with computed SHA-256 integrity 'yM5ZyzNsyKfaXRY78zSGapeQKtl0oGdpPpYxgwl8XW8='. The resource has been blocked.
+CONSOLE ERROR: Failed to find a valid digest in the 'integrity' attribute for resource 'http://127.0.0.1:8000/security/subresourceIntegrity/resources/shared-with-xhtml.js' with computed SHA-256 integrity 'yM5ZyzNsyKfaXRY78zSGapeQKtl0oGdpPpYxgwl8XW8='. The resource has been blocked.
 This test passes if no 'FAIL' alert appears.
 
   
diff --git a/third_party/WebKit/LayoutTests/mojo/bind-interface.html b/third_party/WebKit/LayoutTests/mojo/bind-interface.html
index eaa08c3..26c4867 100644
--- a/third_party/WebKit/LayoutTests/mojo/bind-interface.html
+++ b/third_party/WebKit/LayoutTests/mojo/bind-interface.html
@@ -77,25 +77,41 @@
   return Promise.reject();
 }, "interface interceptors are mutually exclusive");
 
-test(() => {
+test(async t => {
   const kTestInterfaceName = "foo::mojom::Bar";
-  let interceptedHandle = null;
 
+  // First check that the interceptor can be started and intercepts requests.
   let interceptor = new MojoInterfaceInterceptor(kTestInterfaceName);
-  interceptor.oninterfacerequest = e => { interceptedHandle = e.handle; };
+  let promise = new Promise(resolve => {
+    interceptor.oninterfacerequest = e => {
+      resolve(e.handle);
+    };
+  });
   interceptor.start();
 
-  let {handle0, handle1} = Mojo.createMessagePipe();
-  Mojo.bindInterface(kTestInterfaceName, handle0);
-  interceptor.stop();
-
+  let pipe = Mojo.createMessagePipe();
+  Mojo.bindInterface(kTestInterfaceName, pipe.handle0);
+  let interceptedHandle = await promise;
   assert_true(interceptedHandle instanceof MojoHandle);
   interceptedHandle.close();
-  interceptedHandle = null;
+  pipe.handle1.close();
 
-  Mojo.bindInterface(kTestInterfaceName, handle1);
-  assert_equals(interceptedHandle, null);
-  handle1.close();
+  // Stop the interceptor and make another request.
+  interceptor.stop();
+
+  pipe = Mojo.createMessagePipe();
+  interceptor.oninterfacerequest = t.step_func(() => {
+    assert_unreached("unexpected 'interfacerequest' event after stop");
+  });
+  promise = new Promise(resolve => {
+    let watcher = pipe.handle1.watch({peerClosed: true}, () => {
+      watcher.cancel();  // Necessary to avoid a DCHECK when handle1 is closed.
+      resolve();
+    });
+  });
+  Mojo.bindInterface(kTestInterfaceName, pipe.handle0);
+  await promise;
+  pipe.handle1.close();
 
   interceptor = new MojoInterfaceInterceptor(kTestInterfaceName);
   interceptor.oninterfacerequest = e => {};
diff --git a/third_party/WebKit/Source/bindings/core/v8/DictionaryIterator.cpp b/third_party/WebKit/Source/bindings/core/v8/DictionaryIterator.cpp
index a95c695a..19b77052 100644
--- a/third_party/WebKit/Source/bindings/core/v8/DictionaryIterator.cpp
+++ b/third_party/WebKit/Source/bindings/core/v8/DictionaryIterator.cpp
@@ -17,9 +17,9 @@
                                        v8::Isolate* isolate)
     : isolate_(isolate),
       iterator_(iterator),
-      next_key_(V8String(isolate, "next")),
-      done_key_(V8String(isolate, "done")),
-      value_key_(V8String(isolate, "value")),
+      next_key_(V8AtomicString(isolate, "next")),
+      done_key_(V8AtomicString(isolate, "done")),
+      value_key_(V8AtomicString(isolate, "value")),
       done_(false) {
   DCHECK(!iterator.IsEmpty());
 }
diff --git a/third_party/WebKit/Source/bindings/core/v8/NativeValueTraitsImpl.h b/third_party/WebKit/Source/bindings/core/v8/NativeValueTraitsImpl.h
index f693688..c0f27809e 100644
--- a/third_party/WebKit/Source/bindings/core/v8/NativeValueTraitsImpl.h
+++ b/third_party/WebKit/Source/bindings/core/v8/NativeValueTraitsImpl.h
@@ -351,9 +351,9 @@
     if (exception_state.HadException())
       return;
 
-    v8::Local<v8::String> next_key = V8String(isolate, "next");
-    v8::Local<v8::String> value_key = V8String(isolate, "value");
-    v8::Local<v8::String> done_key = V8String(isolate, "done");
+    v8::Local<v8::String> next_key = V8AtomicString(isolate, "next");
+    v8::Local<v8::String> value_key = V8AtomicString(isolate, "value");
+    v8::Local<v8::String> done_key = V8AtomicString(isolate, "done");
     v8::Local<v8::Context> context = isolate->GetCurrentContext();
     while (true) {
       v8::Local<v8::Value> next;
diff --git a/third_party/WebKit/Source/bindings/core/v8/V0CustomElementConstructorBuilder.cpp b/third_party/WebKit/Source/bindings/core/v8/V0CustomElementConstructorBuilder.cpp
index d0a24586..3e7d5c9 100644
--- a/third_party/WebKit/Source/bindings/core/v8/V0CustomElementConstructorBuilder.cpp
+++ b/third_party/WebKit/Source/bindings/core/v8/V0CustomElementConstructorBuilder.cpp
@@ -164,7 +164,7 @@
   v8::Local<v8::Value> value;
   if (!prototype_
            ->Get(script_state_->GetContext(),
-                 V8String(script_state_->GetIsolate(), name))
+                 V8AtomicString(script_state_->GetIsolate(), name))
            .ToLocal(&value) ||
       !value->IsFunction())
     return v8::MaybeLocal<v8::Function>();
@@ -215,7 +215,7 @@
   constructor_->SetName(v8_type->IsNull() ? v8_tag_name
                                           : v8_type.As<v8::String>());
 
-  v8::Local<v8::String> prototype_key = V8String(isolate, "prototype");
+  v8::Local<v8::String> prototype_key = V8AtomicString(isolate, "prototype");
   if (!V8CallBoolean(constructor_->HasOwnProperty(context, prototype_key)))
     return false;
   // This sets the property *value*; calling Set is safe because
@@ -231,7 +231,8 @@
           v8::PropertyAttribute(v8::ReadOnly | v8::DontEnum | v8::DontDelete))))
     return false;
 
-  v8::Local<v8::String> constructor_key = V8String(isolate, "constructor");
+  v8::Local<v8::String> constructor_key =
+      V8AtomicString(isolate, "constructor");
   v8::Local<v8::Value> constructor_prototype;
   if (!prototype_->Get(context, constructor_key)
            .ToLocal(&constructor_prototype))
@@ -244,7 +245,7 @@
   V8PrivateProperty::GetCustomElementIsInterfacePrototypeObject(isolate).Set(
       prototype_, v8::True(isolate));
   if (!V8CallBoolean(prototype_->DefineOwnProperty(
-          context, V8String(isolate, "constructor"), constructor_,
+          context, V8AtomicString(isolate, "constructor"), constructor_,
           v8::DontEnum)))
     return false;
 
@@ -267,7 +268,8 @@
 
   v8::PropertyAttribute property_attribute;
   if (!prototype_
-           ->GetPropertyAttributes(context, V8String(isolate, "constructor"))
+           ->GetPropertyAttributes(context,
+                                   V8AtomicString(isolate, "constructor"))
            .To(&property_attribute) ||
       (property_attribute & v8::DontDelete)) {
     V0CustomElementException::ThrowException(
diff --git a/third_party/WebKit/Source/bindings/core/v8/V8BindingForCore.h b/third_party/WebKit/Source/bindings/core/v8/V8BindingForCore.h
index c77d5584..8f48c37 100644
--- a/third_party/WebKit/Source/bindings/core/v8/V8BindingForCore.h
+++ b/third_party/WebKit/Source/bindings/core/v8/V8BindingForCore.h
@@ -181,20 +181,21 @@
   DCHECK(descriptor.has_writable());
   v8::Local<v8::Object> desc = v8::Object::New(callback_info.GetIsolate());
   desc->Set(callback_info.GetIsolate()->GetCurrentContext(),
-            V8String(callback_info.GetIsolate(), "configurable"),
+            V8AtomicString(callback_info.GetIsolate(), "configurable"),
             ToV8(descriptor.configurable(), callback_info.Holder(),
                  callback_info.GetIsolate()))
       .ToChecked();
   desc->Set(callback_info.GetIsolate()->GetCurrentContext(),
-            V8String(callback_info.GetIsolate(), "enumerable"),
+            V8AtomicString(callback_info.GetIsolate(), "enumerable"),
             ToV8(descriptor.enumerable(), callback_info.Holder(),
                  callback_info.GetIsolate()))
       .ToChecked();
   desc->Set(callback_info.GetIsolate()->GetCurrentContext(),
-            V8String(callback_info.GetIsolate(), "value"), descriptor.value())
+            V8AtomicString(callback_info.GetIsolate(), "value"),
+            descriptor.value())
       .ToChecked();
   desc->Set(callback_info.GetIsolate()->GetCurrentContext(),
-            V8String(callback_info.GetIsolate(), "writable"),
+            V8AtomicString(callback_info.GetIsolate(), "writable"),
             ToV8(descriptor.writable(), callback_info.Holder(),
                  callback_info.GetIsolate()))
       .ToChecked();
diff --git a/third_party/WebKit/Source/bindings/core/v8/V8IteratorResultValue.cpp b/third_party/WebKit/Source/bindings/core/v8/V8IteratorResultValue.cpp
index 3f327bb..788a7f9 100644
--- a/third_party/WebKit/Source/bindings/core/v8/V8IteratorResultValue.cpp
+++ b/third_party/WebKit/Source/bindings/core/v8/V8IteratorResultValue.cpp
@@ -13,10 +13,11 @@
   if (value.IsEmpty())
     value = v8::Undefined(isolate);
   if (!V8CallBoolean(result->CreateDataProperty(
-          isolate->GetCurrentContext(), V8String(isolate, "done"),
+          isolate->GetCurrentContext(), V8AtomicString(isolate, "done"),
           v8::Boolean::New(isolate, done))) ||
-      !V8CallBoolean(result->CreateDataProperty(
-          isolate->GetCurrentContext(), V8String(isolate, "value"), value)))
+      !V8CallBoolean(
+          result->CreateDataProperty(isolate->GetCurrentContext(),
+                                     V8AtomicString(isolate, "value"), value)))
     return v8::Local<v8::Object>();
   return result;
 }
@@ -26,13 +27,13 @@
                                                  bool* done) {
   v8::MaybeLocal<v8::Value> maybe_value =
       result->Get(script_state->GetContext(),
-                  V8String(script_state->GetIsolate(), "value"));
+                  V8AtomicString(script_state->GetIsolate(), "value"));
   if (maybe_value.IsEmpty())
     return maybe_value;
   v8::Local<v8::Value> done_value;
   if (!result
            ->Get(script_state->GetContext(),
-                 V8String(script_state->GetIsolate(), "done"))
+                 V8AtomicString(script_state->GetIsolate(), "done"))
            .ToLocal(&done_value) ||
       !done_value->BooleanValue(script_state->GetContext()).To(done)) {
     return v8::MaybeLocal<v8::Value>();
diff --git a/third_party/WebKit/Source/bindings/core/v8/V8ObjectBuilder.cpp b/third_party/WebKit/Source/bindings/core/v8/V8ObjectBuilder.cpp
index 8046bbd..3a14f96 100644
--- a/third_party/WebKit/Source/bindings/core/v8/V8ObjectBuilder.cpp
+++ b/third_party/WebKit/Source/bindings/core/v8/V8ObjectBuilder.cpp
@@ -62,9 +62,9 @@
     return;
   if (value.IsEmpty() ||
       object_
-          ->CreateDataProperty(script_state_->GetContext(),
-                               V8String(script_state_->GetIsolate(), name),
-                               value)
+          ->CreateDataProperty(
+              script_state_->GetContext(),
+              V8AtomicString(script_state_->GetIsolate(), name), value)
           .IsNothing())
     object_.Clear();
 }
diff --git a/third_party/WebKit/Source/bindings/templates/methods.cpp.tmpl b/third_party/WebKit/Source/bindings/templates/methods.cpp.tmpl
index cd7c2c7..77bad2d9 100644
--- a/third_party/WebKit/Source/bindings/templates/methods.cpp.tmpl
+++ b/third_party/WebKit/Source/bindings/templates/methods.cpp.tmpl
@@ -146,7 +146,7 @@
 {% if argument.is_callback_interface %}
 {# FIXME: remove EventListener/NodeFilter special case. crbug.com/630986 #}
 {% if argument.idl_type == 'EventListener' %}
-{% if method.name == 'RemoveEventListener' or method.name == 'RemoveListener' %}
+{% if method.name == 'removeEventListener' or method.name == 'removeListener' %}
 {{argument.name}} = V8EventListenerHelper::GetEventListener(ScriptState::Current(info.GetIsolate()), info[{{argument.index}}], false, kListenerFindOnly);
 {% else %}{# method.name == 'AddEventListener' #}
 {{argument.name}} = V8EventListenerHelper::GetEventListener(ScriptState::Current(info.GetIsolate()), info[{{argument.index}}], false, kListenerFindOrCreate);
diff --git a/third_party/WebKit/Source/core/dom/ClassicPendingScript.cpp b/third_party/WebKit/Source/core/dom/ClassicPendingScript.cpp
index 1f8b53ac..1725e05 100644
--- a/third_party/WebKit/Source/core/dom/ClassicPendingScript.cpp
+++ b/third_party/WebKit/Source/core/dom/ClassicPendingScript.cpp
@@ -10,6 +10,7 @@
 #include "core/dom/Document.h"
 #include "core/dom/TaskRunnerHelper.h"
 #include "core/frame/LocalFrame.h"
+#include "core/loader/SubresourceIntegrityHelper.h"
 #include "platform/bindings/ScriptState.h"
 #include "platform/loader/fetch/MemoryCache.h"
 
@@ -124,7 +125,8 @@
   CheckState();
   ScriptElementBase* element = GetElement();
   if (element) {
-    GetResource()->CheckResourceIntegrity(element->GetDocument());
+    SubresourceIntegrityHelper::DoReport(element->GetDocument(),
+                                         GetResource()->IntegrityReportInfo());
 
     // It is possible to get back a script resource with integrity metadata
     // for a request with an empty integrity attribute. In that case, the
diff --git a/third_party/WebKit/Source/core/exported/WebFrameTest.cpp b/third_party/WebKit/Source/core/exported/WebFrameTest.cpp
index 1a47123e..dd4dacf 100644
--- a/third_party/WebKit/Source/core/exported/WebFrameTest.cpp
+++ b/third_party/WebKit/Source/core/exported/WebFrameTest.cpp
@@ -11127,6 +11127,43 @@
       document->GetFrame()->GetChromeClient().LastSetTooltipNodeForTesting());
 }
 
+// Ensure mouse curosr should be pointer when hover scrollbar.
+TEST_P(ParameterizedWebFrameTest, MouseOverScrollbarInCustomCursorElement) {
+  RegisterMockedHttpURLLoad("scrollbar-in-custom-cursor-element.html");
+  FrameTestHelpers::WebViewHelper web_view_helper;
+  WebViewBase* web_view = web_view_helper.InitializeAndLoad(
+      base_url_ + "scrollbar-in-custom-cursor-element.html");
+
+  web_view_helper.Resize(WebSize(250, 250));
+
+  web_view->UpdateAllLifecyclePhases();
+
+  Document* document =
+      ToLocalFrame(web_view->GetPage()->MainFrame())->GetDocument();
+
+  Element* div = document->getElementById("d1");
+
+  // Ensure hittest has DIV and scrollbar.
+  HitTestResult hit_test_result =
+      web_view->CoreHitTestResultAt(WebPoint(195, 5));
+
+  EXPECT_EQ(hit_test_result.InnerElement(), div);
+  EXPECT_TRUE(hit_test_result.GetScrollbar());
+
+  WebMouseEvent mouse_over_scrollbar(
+      WebInputEvent::kMouseMove, WebFloatPoint(195, 5), WebFloatPoint(195, 5),
+      WebPointerProperties::Button::kNoButton, 0, WebInputEvent::kNoModifiers,
+      TimeTicks::Now().InSeconds());
+  mouse_over_scrollbar.SetFrameScale(1);
+  document->GetFrame()->GetEventHandler().HandleMouseMoveEvent(
+      mouse_over_scrollbar, Vector<WebMouseEvent>());
+
+  EXPECT_EQ(Cursor::Type::kPointer, document->GetFrame()
+                                        ->GetChromeClient()
+                                        .LastSetCursorForTesting()
+                                        .GetType());
+}
+
 // Makes sure that mouse hover over an overlay scrollbar doesn't activate
 // elements below(except the Element that owns the scrollbar) unless the
 // scrollbar is faded out.
diff --git a/third_party/WebKit/Source/core/html/LinkStyle.cpp b/third_party/WebKit/Source/core/html/LinkStyle.cpp
index 9573083..fe077133 100644
--- a/third_party/WebKit/Source/core/html/LinkStyle.cpp
+++ b/third_party/WebKit/Source/core/html/LinkStyle.cpp
@@ -83,30 +83,8 @@
     ResourceIntegrityDisposition disposition =
         cached_style_sheet->IntegrityDisposition();
 
-    if (disposition == ResourceIntegrityDisposition::kNotChecked &&
-        !cached_style_sheet->LoadFailedOrCanceled()) {
-      bool check_result;
-
-      // cachedStyleSheet->resourceBuffer() can be nullptr on load success.
-      // If response size == 0.
-      const char* data = nullptr;
-      size_t size = 0;
-      if (cached_style_sheet->ResourceBuffer()) {
-        data = cached_style_sheet->ResourceBuffer()->Data();
-        size = cached_style_sheet->ResourceBuffer()->size();
-      }
-      SubresourceIntegrity::ReportInfo report_info;
-      check_result = SubresourceIntegrity::CheckSubresourceIntegrity(
-          cached_style_sheet->IntegrityMetadata(), data, size,
-          cached_style_sheet->Url(), *cached_style_sheet, report_info);
-      SubresourceIntegrityHelper::DoReport(GetDocument(), report_info);
-      disposition = check_result ? ResourceIntegrityDisposition::kPassed
-                                 : ResourceIntegrityDisposition::kFailed;
-
-      // TODO(kouhei): Remove this const_cast crbug.com/653502
-      const_cast<CSSStyleSheetResource*>(cached_style_sheet)
-          ->SetIntegrityDisposition(disposition);
-    }
+    SubresourceIntegrityHelper::DoReport(
+        GetDocument(), cached_style_sheet->IntegrityReportInfo());
 
     if (disposition == ResourceIntegrityDisposition::kFailed) {
       loading_ = false;
diff --git a/third_party/WebKit/Source/core/input/EventHandler.cpp b/third_party/WebKit/Source/core/input/EventHandler.cpp
index 951d2b4..94a56f70 100644
--- a/third_party/WebKit/Source/core/input/EventHandler.cpp
+++ b/third_party/WebKit/Source/core/input/EventHandler.cpp
@@ -414,6 +414,9 @@
   if (scroll_manager_->MiddleClickAutoscrollInProgress())
     return kNoCursorChange;
 
+  if (result.GetScrollbar())
+    return PointerCursor();
+
   Node* node = result.InnerPossiblyPseudoNode();
   if (!node)
     return SelectAutoCursor(result, node, IBeamCursor());
@@ -550,9 +553,6 @@
 OptionalCursor EventHandler::SelectAutoCursor(const HitTestResult& result,
                                               Node* node,
                                               const Cursor& i_beam) {
-  if (result.GetScrollbar())
-    return PointerCursor();
-
   const bool is_over_link =
       !GetSelectionController().MouseDownMayStartSelect() &&
       result.IsOverLink();
diff --git a/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp b/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp
index f053603..2735e97c3 100644
--- a/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp
+++ b/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp
@@ -219,7 +219,7 @@
                         v8::ConstructorBehavior::kThrow)
           .ToLocal(&to_string_function))
     CreateDataProperty(context, func,
-                       V8String(context->GetIsolate(), "toString"),
+                       V8AtomicString(context->GetIsolate(), "toString"),
                        to_string_function);
   CreateDataProperty(context, object, func_name, func);
 }
@@ -405,21 +405,25 @@
       current_event_type = info.event_type;
       listeners = v8::Array::New(isolate);
       output_index = 0;
-      CreateDataProperty(context, result, V8String(isolate, current_event_type),
+      CreateDataProperty(context, result,
+                         V8AtomicString(isolate, current_event_type),
                          listeners);
     }
 
     v8::Local<v8::Object> listener_object = v8::Object::New(isolate);
-    CreateDataProperty(context, listener_object, V8String(isolate, "listener"),
-                       info.handler);
     CreateDataProperty(context, listener_object,
-                       V8String(isolate, "useCapture"),
+                       V8AtomicString(isolate, "listener"), info.handler);
+    CreateDataProperty(context, listener_object,
+                       V8AtomicString(isolate, "useCapture"),
                        v8::Boolean::New(isolate, info.use_capture));
-    CreateDataProperty(context, listener_object, V8String(isolate, "passive"),
+    CreateDataProperty(context, listener_object,
+                       V8AtomicString(isolate, "passive"),
                        v8::Boolean::New(isolate, info.passive));
-    CreateDataProperty(context, listener_object, V8String(isolate, "once"),
+    CreateDataProperty(context, listener_object,
+                       V8AtomicString(isolate, "once"),
                        v8::Boolean::New(isolate, info.once));
-    CreateDataProperty(context, listener_object, V8String(isolate, "type"),
+    CreateDataProperty(context, listener_object,
+                       V8AtomicString(isolate, "type"),
                        V8String(isolate, current_event_type));
     CreateDataPropertyInArray(context, listeners, output_index++,
                               listener_object);
diff --git a/third_party/WebKit/Source/core/loader/resource/ScriptResource.cpp b/third_party/WebKit/Source/core/loader/resource/ScriptResource.cpp
index 85beaa1..e8e02cd 100644
--- a/third_party/WebKit/Source/core/loader/resource/ScriptResource.cpp
+++ b/third_party/WebKit/Source/core/loader/resource/ScriptResource.cpp
@@ -120,46 +120,4 @@
   return kNotSharableCrossOrigin;
 }
 
-void ScriptResource::CheckResourceIntegrity(Document& document) {
-  // Already checked? Retain existing result.
-  //
-  // TODO(vogelheim): If IntegrityDisposition() is kFailed, this should
-  // probably also generate a console message identical to the one produced
-  // by the CheckSubresourceIntegrity call below. See crbug.com/585267.
-  if (IntegrityDisposition() != ResourceIntegrityDisposition::kNotChecked)
-    return;
-
-  CHECK(source_text_.IsNull());
-
-  // Loading error occurred? Then result is uncheckable.
-  if (ErrorOccurred())
-    return;
-
-  // No integrity attributes to check? Then we're passing.
-  if (IntegrityMetadata().IsEmpty()) {
-    SetIntegrityDisposition(ResourceIntegrityDisposition::kPassed);
-    return;
-  }
-
-  const char* data = nullptr;
-  size_t data_length = 0;
-
-  // Edge case: If a resource actually has zero bytes then it will not
-  // typically have a resource buffer, but we still need to check integrity
-  // because people might want to assert a zero-length resource.
-  CHECK(EncodedSize() + DecodedSize() == 0 || ResourceBuffer());
-  if (ResourceBuffer()) {
-    data = ResourceBuffer()->Data();
-    data_length = ResourceBuffer()->size();
-  }
-
-  SubresourceIntegrity::ReportInfo report_info;
-  bool passed = SubresourceIntegrity::CheckSubresourceIntegrity(
-      IntegrityMetadata(), data, data_length, Url(), *this, report_info);
-  SubresourceIntegrityHelper::DoReport(document, report_info);
-  SetIntegrityDisposition(passed ? ResourceIntegrityDisposition::kPassed
-                                 : ResourceIntegrityDisposition::kFailed);
-  DCHECK_NE(IntegrityDisposition(), ResourceIntegrityDisposition::kNotChecked);
-}
-
 }  // namespace blink
diff --git a/third_party/WebKit/Source/core/loader/resource/ScriptResource.h b/third_party/WebKit/Source/core/loader/resource/ScriptResource.h
index 6309f5e..3fa422f 100644
--- a/third_party/WebKit/Source/core/loader/resource/ScriptResource.h
+++ b/third_party/WebKit/Source/core/loader/resource/ScriptResource.h
@@ -36,7 +36,6 @@
 
 namespace blink {
 
-class Document;
 class FetchParameters;
 class KURL;
 class ResourceFetcher;
@@ -85,8 +84,6 @@
 
   AccessControlStatus CalculateAccessControlStatus() const;
 
-  void CheckResourceIntegrity(Document&);
-
  private:
   class ScriptResourceFactory : public ResourceFactory {
    public:
diff --git a/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.cpp b/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.cpp
index 3e930b7..e570adee 100644
--- a/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.cpp
+++ b/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.cpp
@@ -7,6 +7,7 @@
 #include "bindings/core/v8/ExceptionState.h"
 #include "core/dom/Document.h"
 #include "core/dom/ExecutionContext.h"
+#include "core/dom/TaskRunnerHelper.h"
 #include "core/frame/LocalDOMWindow.h"
 #include "core/frame/LocalFrame.h"
 #include "core/frame/LocalFrameClient.h"
@@ -14,6 +15,7 @@
 #include "core/mojo/test/MojoInterfaceRequestEvent.h"
 #include "core/workers/WorkerGlobalScope.h"
 #include "core/workers/WorkerThread.h"
+#include "platform/WebTaskRunner.h"
 #include "platform/bindings/ScriptState.h"
 #include "platform/wtf/text/StringUTF8Adaptor.h"
 #include "services/service_manager/public/cpp/interface_provider.h"
@@ -118,6 +120,20 @@
 
 void MojoInterfaceInterceptor::OnInterfaceRequest(
     mojo::ScopedMessagePipeHandle handle) {
+  // Execution of JavaScript may be forbidden in this context as this method is
+  // called synchronously by the InterfaceProvider. Dispatching of the
+  // 'interfacerequest' event is therefore scheduled to take place in the next
+  // microtask. This also more closely mirrors the behavior when an interface
+  // request is being satisfied by another process.
+  TaskRunnerHelper::Get(TaskType::kMicrotask, GetExecutionContext())
+      ->PostTask(
+          BLINK_FROM_HERE,
+          WTF::Bind(&MojoInterfaceInterceptor::DispatchInterfaceRequestEvent,
+                    WrapPersistent(this), WTF::Passed(std::move(handle))));
+}
+
+void MojoInterfaceInterceptor::DispatchInterfaceRequestEvent(
+    mojo::ScopedMessagePipeHandle handle) {
   DispatchEvent(MojoInterfaceRequestEvent::Create(
       MojoHandle::Create(mojo::ScopedHandle::From(std::move(handle)))));
 }
diff --git a/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.h b/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.h
index ff73826..9877b32a 100644
--- a/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.h
+++ b/third_party/WebKit/Source/core/mojo/test/MojoInterfaceInterceptor.h
@@ -65,6 +65,7 @@
 
   service_manager::InterfaceProvider* GetInterfaceProvider() const;
   void OnInterfaceRequest(mojo::ScopedMessagePipeHandle);
+  void DispatchInterfaceRequestEvent(mojo::ScopedMessagePipeHandle);
 
   const String interface_name_;
   bool started_ = false;
diff --git a/third_party/WebKit/Source/core/paint/PaintLayerClipper.cpp b/third_party/WebKit/Source/core/paint/PaintLayerClipper.cpp
index 7b5ecc9..bcd01c4 100644
--- a/third_party/WebKit/Source/core/paint/PaintLayerClipper.cpp
+++ b/third_party/WebKit/Source/core/paint/PaintLayerClipper.cpp
@@ -281,26 +281,18 @@
     layer_.ConvertToLayerCoords(context.root_layer, offset);
   layer_bounds = LayoutRect(offset, LayoutSize(layer_.size()));
 
-  // TODO(chrishtr): fix the underlying bug that causes this situation.
-  if (!layer_.GetLayoutObject().FirstFragment()->PaintProperties() &&
-      !layer_.GetLayoutObject().FirstFragment()->LocalBorderBoxProperties()) {
-    background_rect = ClipRect(LayoutRect(LayoutRect::InfiniteIntRect()));
-    foreground_rect = ClipRect(LayoutRect(LayoutRect::InfiniteIntRect()));
-  } else {
-    CalculateBackgroundClipRectWithGeometryMapper(context, background_rect);
-    background_rect.Intersect(paint_dirty_rect);
+  CalculateBackgroundClipRectWithGeometryMapper(context, background_rect);
+  background_rect.Intersect(paint_dirty_rect);
 
-    foreground_rect = background_rect;
-    if (ShouldClipOverflow(context)) {
-      LayoutBoxModelObject& layout_object = layer_.GetLayoutObject();
-      LayoutRect overflow_and_clip_rect =
-          ToLayoutBox(layout_object)
-              .OverflowClipRect(offset,
-                                context.overlay_scrollbar_clip_behavior);
-      foreground_rect.Intersect(overflow_and_clip_rect);
-      if (layout_object.StyleRef().HasBorderRadius())
-        foreground_rect.SetHasRadius(true);
-    }
+  foreground_rect = background_rect;
+  if (ShouldClipOverflow(context)) {
+    LayoutBoxModelObject& layout_object = layer_.GetLayoutObject();
+    LayoutRect overflow_and_clip_rect =
+        ToLayoutBox(layout_object)
+            .OverflowClipRect(offset, context.overlay_scrollbar_clip_behavior);
+    foreground_rect.Intersect(overflow_and_clip_rect);
+    if (layout_object.StyleRef().HasBorderRadius())
+      foreground_rect.SetHasRadius(true);
   }
 }
 
@@ -535,13 +527,6 @@
     const ClipRectsContext& context,
     ClipRect& output) const {
   if (use_geometry_mapper_) {
-    // TODO(chrishtr): fix the underlying bug that causes this situation.
-    if (!layer_.GetLayoutObject().FirstFragment()->PaintProperties() &&
-        !layer_.GetLayoutObject().FirstFragment()->LocalBorderBoxProperties()) {
-      output.SetRect(FloatClipRect());
-      return;
-    }
-
     CalculateBackgroundClipRectWithGeometryMapper(context, output);
     return;
   }
diff --git a/third_party/WebKit/Source/core/testing/data/scrollbar-in-custom-cursor-element.html b/third_party/WebKit/Source/core/testing/data/scrollbar-in-custom-cursor-element.html
new file mode 100644
index 0000000..fa0230a
--- /dev/null
+++ b/third_party/WebKit/Source/core/testing/data/scrollbar-in-custom-cursor-element.html
@@ -0,0 +1,22 @@
+<!DOCTYPE html>
+
+<style>
+body {
+  margin: 0;
+}
+
+#d1 {
+  width: 200px;
+  height: 200px;
+  overflow: auto;
+  cursor: move;
+}
+
+#d2 {
+  height: 400px;
+}
+</style>
+
+<div id='d1'>
+    <div id='d2'></div>
+</div>
\ No newline at end of file
diff --git a/third_party/WebKit/Source/devtools/front_end/main/Main.js b/third_party/WebKit/Source/devtools/front_end/main/Main.js
index 750108e..8d483093 100644
--- a/third_party/WebKit/Source/devtools/front_end/main/Main.js
+++ b/third_party/WebKit/Source/devtools/front_end/main/Main.js
@@ -122,7 +122,6 @@
     Runtime.experiments.register('liveSASS', 'Live SASS');
     Runtime.experiments.register('networkGroupingRequests', 'Network request groups support', true);
     Runtime.experiments.register('objectPreviews', 'Object previews', true);
-    Runtime.experiments.register('networkInWorkers', 'Network in workers', true);
     Runtime.experiments.register('persistence2', 'Persistence 2.0');
     Runtime.experiments.register('sourceDiff', 'Source diff');
     Runtime.experiments.register('terminalInDrawer', 'Terminal in drawer', true);
diff --git a/third_party/WebKit/Source/devtools/front_end/sdk/TargetManager.js b/third_party/WebKit/Source/devtools/front_end/sdk/TargetManager.js
index 29ed4bed..451086e 100644
--- a/third_party/WebKit/Source/devtools/front_end/sdk/TargetManager.js
+++ b/third_party/WebKit/Source/devtools/front_end/sdk/TargetManager.js
@@ -466,12 +466,8 @@
    * @return {number}
    */
   _capabilitiesForType(type) {
-    if (type === 'worker') {
-      if (Runtime.experiments.isEnabled('networkInWorkers'))
-        return SDK.Target.Capability.JS | SDK.Target.Capability.Log | SDK.Target.Capability.Network;
-      else
-        return SDK.Target.Capability.JS | SDK.Target.Capability.Log;
-    }
+    if (type === 'worker')
+      return SDK.Target.Capability.JS | SDK.Target.Capability.Log | SDK.Target.Capability.Network;
     if (type === 'service_worker')
       return SDK.Target.Capability.Log | SDK.Target.Capability.Network | SDK.Target.Capability.Target;
     if (type === 'iframe') {
diff --git a/third_party/WebKit/Source/modules/compositorworker/AnimationWorkletGlobalScope.cpp b/third_party/WebKit/Source/modules/compositorworker/AnimationWorkletGlobalScope.cpp
index 1f8849b..6f94703 100644
--- a/third_party/WebKit/Source/modules/compositorworker/AnimationWorkletGlobalScope.cpp
+++ b/third_party/WebKit/Source/modules/compositorworker/AnimationWorkletGlobalScope.cpp
@@ -110,7 +110,7 @@
       v8::Local<v8::Function>::Cast(ctorValue.V8Value());
 
   v8::Local<v8::Value> prototypeValue;
-  if (!constructor->Get(context, V8String(isolate, "prototype"))
+  if (!constructor->Get(context, V8AtomicString(isolate, "prototype"))
            .ToLocal(&prototypeValue))
     return;
 
@@ -129,7 +129,7 @@
   v8::Local<v8::Object> prototype = v8::Local<v8::Object>::Cast(prototypeValue);
 
   v8::Local<v8::Value> animateValue;
-  if (!prototype->Get(context, V8String(isolate, "animate"))
+  if (!prototype->Get(context, V8AtomicString(isolate, "animate"))
            .ToLocal(&animateValue))
     return;
 
diff --git a/third_party/WebKit/Source/modules/csspaint/PaintWorkletGlobalScope.cpp b/third_party/WebKit/Source/modules/csspaint/PaintWorkletGlobalScope.cpp
index 244d319b..cb4fb7f 100644
--- a/third_party/WebKit/Source/modules/csspaint/PaintWorkletGlobalScope.cpp
+++ b/third_party/WebKit/Source/modules/csspaint/PaintWorkletGlobalScope.cpp
@@ -90,7 +90,7 @@
       v8::Local<v8::Function>::Cast(ctor_value.V8Value());
 
   v8::Local<v8::Value> input_properties_value;
-  if (!constructor->Get(context, V8String(isolate, "inputProperties"))
+  if (!constructor->Get(context, V8AtomicString(isolate, "inputProperties"))
            .ToLocal(&input_properties_value))
     return;
 
@@ -120,7 +120,7 @@
   Vector<CSSSyntaxDescriptor> input_argument_types;
   if (RuntimeEnabledFeatures::CSSPaintAPIArgumentsEnabled()) {
     v8::Local<v8::Value> input_argument_type_values;
-    if (!constructor->Get(context, V8String(isolate, "inputArguments"))
+    if (!constructor->Get(context, V8AtomicString(isolate, "inputArguments"))
              .ToLocal(&input_argument_type_values))
       return;
 
@@ -145,7 +145,7 @@
 
   // Parse 'alpha' AKA hasAlpha property.
   v8::Local<v8::Value> alpha_value;
-  if (!constructor->Get(context, V8String(isolate, "alpha"))
+  if (!constructor->Get(context, V8AtomicString(isolate, "alpha"))
            .ToLocal(&alpha_value))
     return;
   if (!IsUndefinedOrNull(alpha_value) && !alpha_value->IsBoolean()) {
@@ -158,7 +158,7 @@
                        : true;
 
   v8::Local<v8::Value> prototype_value;
-  if (!constructor->Get(context, V8String(isolate, "prototype"))
+  if (!constructor->Get(context, V8AtomicString(isolate, "prototype"))
            .ToLocal(&prototype_value))
     return;
 
@@ -178,7 +178,7 @@
       v8::Local<v8::Object>::Cast(prototype_value);
 
   v8::Local<v8::Value> paint_value;
-  if (!prototype->Get(context, V8String(isolate, "paint"))
+  if (!prototype->Get(context, V8AtomicString(isolate, "paint"))
            .ToLocal(&paint_value))
     return;
 
diff --git a/third_party/WebKit/Source/modules/webaudio/AudioWorkletGlobalScope.cpp b/third_party/WebKit/Source/modules/webaudio/AudioWorkletGlobalScope.cpp
index 75fd1c8c..325d95f 100644
--- a/third_party/WebKit/Source/modules/webaudio/AudioWorkletGlobalScope.cpp
+++ b/third_party/WebKit/Source/modules/webaudio/AudioWorkletGlobalScope.cpp
@@ -83,7 +83,7 @@
 
   v8::Local<v8::Value> prototype_value_local;
   bool prototype_extracted =
-      class_definition_local->Get(context, V8String(isolate, "prototype"))
+      class_definition_local->Get(context, V8AtomicString(isolate, "prototype"))
           .ToLocal(&prototype_value_local);
   DCHECK(prototype_extracted);
 
@@ -92,7 +92,7 @@
 
   v8::Local<v8::Value> process_value_local;
   bool process_extracted =
-      prototype_object_local->Get(context, V8String(isolate, "process"))
+      prototype_object_local->Get(context, V8AtomicString(isolate, "process"))
           .ToLocal(&process_value_local);
   DCHECK(process_extracted);
 
@@ -121,8 +121,8 @@
 
   v8::Local<v8::Value> parameter_descriptors_value_local;
   bool did_get_parameter_descriptor =
-      class_definition_local->Get(context,
-                                  V8String(isolate, "parameterDescriptors"))
+      class_definition_local
+          ->Get(context, V8AtomicString(isolate, "parameterDescriptors"))
           .ToLocal(&parameter_descriptors_value_local);
 
   // If parameterDescriptor() is parsed and has a valid value, create a vector
diff --git a/third_party/WebKit/Source/modules/webaudio/OfflineAudioContext.cpp b/third_party/WebKit/Source/modules/webaudio/OfflineAudioContext.cpp
index d9293ee6..e925cdab 100644
--- a/third_party/WebKit/Source/modules/webaudio/OfflineAudioContext.cpp
+++ b/third_party/WebKit/Source/modules/webaudio/OfflineAudioContext.cpp
@@ -353,14 +353,14 @@
   // that the context has been closed.
   SetContextState(kClosed);
 
-  AudioBuffer* rendered_buffer = DestinationHandler().RenderTarget();
-
-  DCHECK(rendered_buffer);
-  if (!rendered_buffer)
-    return;
-
   // Avoid firing the event if the document has already gone away.
   if (GetExecutionContext()) {
+    AudioBuffer* rendered_buffer = DestinationHandler().RenderTarget();
+
+    DCHECK(rendered_buffer);
+    if (!rendered_buffer)
+      return;
+
     // Call the offline rendering completion event listener and resolve the
     // promise too.
     DispatchEvent(OfflineAudioCompletionEvent::Create(rendered_buffer));
diff --git a/third_party/WebKit/Source/platform/bindings/V8PerContextData.cpp b/third_party/WebKit/Source/platform/bindings/V8PerContextData.cpp
index 5aadd390..010be97 100644
--- a/third_party/WebKit/Source/platform/bindings/V8PerContextData.cpp
+++ b/third_party/WebKit/Source/platform/bindings/V8PerContextData.cpp
@@ -148,7 +148,7 @@
   if (constructor.IsEmpty())
     return v8::Local<v8::Object>();
   v8::Local<v8::Value> prototype_value;
-  if (!constructor->Get(GetContext(), V8String(isolate_, "prototype"))
+  if (!constructor->Get(GetContext(), V8AtomicString(isolate_, "prototype"))
            .ToLocal(&prototype_value) ||
       !prototype_value->IsObject())
     return v8::Local<v8::Object>();
diff --git a/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridge.cpp b/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridge.cpp
index 6630beb..a299748 100644
--- a/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridge.cpp
+++ b/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridge.cpp
@@ -65,11 +65,18 @@
                                   // two animation frames behind.
 };
 
-static void ReleaseMailboxImageResource(gpu::gles2::GLES2Interface* gl,
-                                        const gpu::SyncToken& sync_token,
-                                        sk_sp<SkImage> skImage,
-                                        const gpu::Mailbox& mailbox,
-                                        bool lost_resource) {
+static void ReleaseMailboxImageResource(
+    WeakPtr<blink::WebGraphicsContext3DProviderWrapper>
+        context_provider_wrapper,
+    const gpu::SyncToken& sync_token,
+    sk_sp<SkImage> skImage,
+    const gpu::Mailbox& mailbox,
+    bool lost_resource) {
+  if (!context_provider_wrapper)
+    return;
+  gpu::gles2::GLES2Interface* gl =
+      context_provider_wrapper->ContextProvider()->ContextGL();
+
   if (sync_token.HasData() && gl)
     gl->WaitSyncTokenCHROMIUM(sync_token.GetConstData());
   GrTexture* texture = skImage->getTexture();
@@ -106,7 +113,7 @@
     std::unique_ptr<gfx::GpuMemoryBuffer> gpu_memory_buffer,
     const GLuint& image_id,
     const GLuint& texture_id) {
-  if (!context_provider_wrapper->ContextProvider())
+  if (!context_provider_wrapper)
     return;
   gpu::gles2::GLES2Interface* gl =
       context_provider_wrapper->ContextProvider()->ContextGL();
@@ -1042,10 +1049,10 @@
     bool layer_bridge_with_valid_context =
         layer_bridge && !context_or_layer_bridge_lost;
     if (layer_bridge_with_valid_context || !layer_bridge) {
-      ReleaseMailboxImageResource(
-          context_provider_wrapper->ContextProvider()->ContextGL(), sync_token,
-          std::move(released_mailbox_info->image_),
-          released_mailbox_info->mailbox_, lost_resource);
+      ReleaseMailboxImageResource(context_provider_wrapper, sync_token,
+                                  std::move(released_mailbox_info->image_),
+                                  released_mailbox_info->mailbox_,
+                                  lost_resource);
     }
   }
 
diff --git a/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridgeTest.cpp b/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridgeTest.cpp
index 193fc8b..c11cff86 100644
--- a/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridgeTest.cpp
+++ b/third_party/WebKit/Source/platform/graphics/Canvas2DLayerBridgeTest.cpp
@@ -277,6 +277,28 @@
         bridge->PrepareTextureMailbox(&texture_mailbox, &release_callback));
   }
 
+  void ReleaseCallbackWithNullContextProviderWrapperTest() {
+    viz::TextureMailbox texture_mailbox;
+    std::unique_ptr<viz::SingleReleaseCallback> release_callback;
+
+    {
+      Canvas2DLayerBridgePtr bridge(AdoptRef(new Canvas2DLayerBridge(
+          IntSize(300, 150), 0, kNonOpaque,
+          Canvas2DLayerBridge::kForceAccelerationForTesting,
+          CanvasColorParams())));
+      EXPECT_TRUE(
+          bridge->PrepareTextureMailbox(&texture_mailbox, &release_callback));
+    }
+
+    bool lost_resource = true;
+    gl_.SetIsContextLost(true);
+    // Get a new context provider so that the WeakPtr to the old one is null.
+    // This is the test to make sure that ReleaseMailboxImageResource() handles
+    // null context_provider_wrapper properly.
+    SharedGpuContext::ContextProviderWrapper();
+    release_callback->Run(gpu::SyncToken(), lost_resource);
+  }
+
   void PrepareMailboxAndLoseResourceTest() {
     // Prepare a mailbox, then report the resource as lost.
     // This test passes by not crashing and not triggering assertions.
@@ -367,6 +389,10 @@
   PrepareMailboxAndLoseResourceTest();
 }
 
+TEST_F(Canvas2DLayerBridgeTest, ReleaseCallbackWithNullContextProviderWrapper) {
+  ReleaseCallbackWithNullContextProviderWrapperTest();
+}
+
 TEST_F(Canvas2DLayerBridgeTest, AccelerationHint) {
   AccelerationHintTest();
 }
diff --git a/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.cpp b/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.cpp
index eb730a5..e9d3b40 100644
--- a/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.cpp
+++ b/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.cpp
@@ -60,6 +60,11 @@
   console_error_messages_.push_back(message);
 }
 
+void SubresourceIntegrity::ReportInfo::Clear() {
+  use_counts_.clear();
+  console_error_messages_.clear();
+}
+
 HashAlgorithm SubresourceIntegrity::GetPrioritizedHashFunction(
     HashAlgorithm algorithm1,
     HashAlgorithm algorithm2) {
diff --git a/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.h b/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.h
index ba29bfcf..11bb2d02e 100644
--- a/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.h
+++ b/third_party/WebKit/Source/platform/loader/SubresourceIntegrity.h
@@ -33,6 +33,7 @@
 
     void AddUseCount(UseCounterFeature);
     void AddConsoleErrorMessage(const String&);
+    void Clear();
 
     const Vector<UseCounterFeature>& UseCounts() const { return use_counts_; }
     const Vector<String>& ConsoleErrorMessages() const {
diff --git a/third_party/WebKit/Source/platform/loader/fetch/Resource.cpp b/third_party/WebKit/Source/platform/loader/fetch/Resource.cpp
index c3a2686..155f2bb5e 100644
--- a/third_party/WebKit/Source/platform/loader/fetch/Resource.cpp
+++ b/third_party/WebKit/Source/platform/loader/fetch/Resource.cpp
@@ -324,6 +324,42 @@
   status_ = ResourceStatus::kPending;
 }
 
+void Resource::CheckResourceIntegrity() {
+  // Loading error occurred? Then result is uncheckable.
+  integrity_report_info_.Clear();
+  if (ErrorOccurred()) {
+    CHECK(!Data());
+    integrity_disposition_ = ResourceIntegrityDisposition::kFailed;
+    return;
+  }
+
+  // No integrity attributes to check? Then we're passing.
+  if (IntegrityMetadata().IsEmpty()) {
+    integrity_disposition_ = ResourceIntegrityDisposition::kPassed;
+    return;
+  }
+
+  const char* data = nullptr;
+  size_t data_length = 0;
+
+  // Edge case: If a resource actually has zero bytes then it will not
+  // typically have a resource buffer, but we still need to check integrity
+  // because people might want to assert a zero-length resource.
+  CHECK(EncodedSize() + DecodedSize() == 0 || Data());
+  if (Data()) {
+    data = Data()->Data();
+    data_length = Data()->size();
+  }
+
+  if (SubresourceIntegrity::CheckSubresourceIntegrity(IntegrityMetadata(), data,
+                                                      data_length, Url(), *this,
+                                                      integrity_report_info_))
+    integrity_disposition_ = ResourceIntegrityDisposition::kPassed;
+  else
+    integrity_disposition_ = ResourceIntegrityDisposition::kFailed;
+  DCHECK_NE(IntegrityDisposition(), ResourceIntegrityDisposition::kNotChecked);
+}
+
 void Resource::CheckNotify() {
   if (IsLoading())
     return;
@@ -408,6 +444,7 @@
   DCHECK(ErrorOccurred());
   ClearData();
   loader_ = nullptr;
+  CheckResourceIntegrity();
   CheckNotify();
 }
 
@@ -417,6 +454,7 @@
   if (!ErrorOccurred())
     status_ = ResourceStatus::kCached;
   loader_ = nullptr;
+  CheckResourceIntegrity();
   CheckNotify();
 }
 
@@ -424,13 +462,6 @@
   return GetResponse().HttpContentType();
 }
 
-void Resource::SetIntegrityDisposition(
-    ResourceIntegrityDisposition disposition) {
-  DCHECK_NE(disposition, ResourceIntegrityDisposition::kNotChecked);
-  DCHECK(type_ == Resource::kScript || type_ == Resource::kCSSStyleSheet);
-  integrity_disposition_ = disposition;
-}
-
 bool Resource::MustRefetchDueToIntegrityMetadata(
     const FetchParameters& params) const {
   if (params.IntegrityMetadata().IsEmpty())
diff --git a/third_party/WebKit/Source/platform/loader/fetch/Resource.h b/third_party/WebKit/Source/platform/loader/fetch/Resource.h
index 884f5fd..74b692e2 100644
--- a/third_party/WebKit/Source/platform/loader/fetch/Resource.h
+++ b/third_party/WebKit/Source/platform/loader/fetch/Resource.h
@@ -31,6 +31,7 @@
 #include "platform/Timer.h"
 #include "platform/WebTaskRunner.h"
 #include "platform/instrumentation/tracing/web_process_memory_dump.h"
+#include "platform/loader/SubresourceIntegrity.h"
 #include "platform/loader/fetch/CachedMetadataHandler.h"
 #include "platform/loader/fetch/IntegrityMetadata.h"
 #include "platform/loader/fetch/ResourceError.h"
@@ -248,11 +249,12 @@
   const IntegrityMetadataSet& IntegrityMetadata() const {
     return integrity_metadata_;
   }
-  // The argument must never be |NotChecked|.
-  void SetIntegrityDisposition(ResourceIntegrityDisposition);
   ResourceIntegrityDisposition IntegrityDisposition() const {
     return integrity_disposition_;
   }
+  const SubresourceIntegrity::ReportInfo& IntegrityReportInfo() const {
+    return integrity_report_info_;
+  }
   bool MustRefetchDueToIntegrityMetadata(const FetchParameters&) const;
 
   bool IsAlive() const { return is_alive_; }
@@ -421,6 +423,8 @@
   // MemoryCoordinatorClient overrides:
   void OnPurgeMemory() override;
 
+  void CheckResourceIntegrity();
+
   Type type_;
   ResourceStatus status_;
   CORSStatus cors_status_;
@@ -458,6 +462,7 @@
 
   ResourceIntegrityDisposition integrity_disposition_;
   IntegrityMetadataSet integrity_metadata_;
+  SubresourceIntegrity::ReportInfo integrity_report_info_;
 
   // Ordered list of all redirects followed while fetching this resource.
   Vector<RedirectPair> redirect_chain_;
diff --git a/third_party/WebKit/public/platform/InterfaceProvider.h b/third_party/WebKit/public/platform/InterfaceProvider.h
index 4225e7a..fb349a7 100644
--- a/third_party/WebKit/public/platform/InterfaceProvider.h
+++ b/third_party/WebKit/public/platform/InterfaceProvider.h
@@ -12,7 +12,7 @@
 namespace blink {
 
 // Implementations of blink::InterfaceProvider should be thread safe. As such it
-// is okay to call |getInterface| from any thread, without the thread hopping
+// is okay to call |GetInterface| from any thread, without the thread hopping
 // that would have been necesary with service_manager::InterfaceProvider.
 class BLINK_PLATFORM_EXPORT InterfaceProvider {
  public:
diff --git a/third_party/WebKit/public/platform/Platform.h b/third_party/WebKit/public/platform/Platform.h
index 4c32e4a..1c51787f 100644
--- a/third_party/WebKit/public/platform/Platform.h
+++ b/third_party/WebKit/public/platform/Platform.h
@@ -153,7 +153,7 @@
 #endif
 
   // Initialize platform and wtf. If you need to initialize the entire Blink,
-  // you should use blink::initialize.
+  // you should use blink::Initialize.
   static void Initialize(Platform*);
   static Platform* Current();
 
@@ -191,7 +191,8 @@
   virtual unsigned AudioHardwareOutputChannels() { return 0; }
 
   // Creates a device for audio I/O.
-  // Pass in (numberOfInputChannels > 0) if live/local audio input is desired.
+  // Pass in (number_of_input_channels > 0) if live/local audio input is
+  // desired.
   virtual std::unique_ptr<WebAudioDevice> CreateAudioDevice(
       unsigned number_of_input_channels,
       unsigned number_of_channels,
@@ -216,36 +217,35 @@
 
   // Database ------------------------------------------------------------
 
-  // Opens a database file; dirHandle should be 0 if the caller does not need
-  // a handle to the directory containing this file
+  // Opens a database file.
   virtual FileHandle DatabaseOpenFile(const WebString& vfs_file_name,
                                       int desired_flags) {
     return FileHandle();
   }
 
-  // Deletes a database file and returns the error code
+  // Deletes a database file and returns the error code.
   virtual int DatabaseDeleteFile(const WebString& vfs_file_name,
                                  bool sync_dir) {
     return 0;
   }
 
-  // Returns the attributes of the given database file
+  // Returns the attributes of the given database file.
   virtual long DatabaseGetFileAttributes(const WebString& vfs_file_name) {
     return 0;
   }
 
-  // Returns the size of the given database file
+  // Returns the size of the given database file.
   virtual long long DatabaseGetFileSize(const WebString& vfs_file_name) {
     return 0;
   }
 
-  // Returns the space available for the given origin
+  // Returns the space available for the given origin.
   virtual long long DatabaseGetSpaceAvailableForOrigin(
       const WebSecurityOrigin& origin) {
     return 0;
   }
 
-  // Set the size of the given database file
+  // Set the size of the given database file.
   virtual bool DatabaseSetFileSize(const WebString& vfs_file_name,
                                    long long size) {
     return false;
@@ -313,7 +313,7 @@
   static const size_t kNoDecodedImageByteLimit = static_cast<size_t>(-1);
 
   // Returns the maximum amount of memory a decoded image should be allowed.
-  // See comments on ImageDecoder::m_maxDecodedBytes.
+  // See comments on ImageDecoder::max_decoded_bytes_.
   virtual size_t MaxDecodedImageBytes() { return kNoDecodedImageByteLimit; }
 
   // Returns true if this is a low-end device.
@@ -427,8 +427,7 @@
   virtual WebData GetDataResource(const char* name) { return WebData(); }
 
   // Decodes the in-memory audio file data and returns the linear PCM audio data
-  // in the destinationBus.  A sample-rate conversion to sampleRate will occur
-  // if the file data is at a different sample-rate.
+  // in the |destination_bus|.
   // Returns true on success.
   virtual bool DecodeAudioFileData(WebAudioBus* destination_bus,
                                    const char* audio_file_data,
@@ -445,7 +444,7 @@
 
   // Disable/Enable sudden termination on a process level. When possible, it
   // is preferable to disable sudden termination on a per-frame level via
-  // WebFrameClient::suddenTerminationDisablerChanged.
+  // WebFrameClient::SuddenTerminationDisablerChanged.
   virtual void SuddenTerminationChanged(bool enabled) {}
 
   // System --------------------------------------------------------------
@@ -473,7 +472,7 @@
 
   // Record to a RAPPOR privacy-preserving metric, see:
   // https://www.chromium.org/developers/design-documents/rappor.
-  // recordRappor records a sample string, while recordRapporURL records the
+  // RecordRappor records a sample string, while RecordRapporURL records the
   // eTLD+1 of a url.
   virtual void RecordRappor(const char* metric, const WebString& sample) {}
   virtual void RecordRapporURL(const char* metric, const blink::WebURL& url) {}
@@ -481,7 +480,7 @@
   // Record a UMA sequence action.  The UserMetricsAction construction must
   // be on a single line for extract_actions.py to find it.  Please see
   // that script for more details.  Intended use is:
-  // recordAction(UserMetricsAction("MyAction"))
+  // RecordAction(UserMetricsAction("MyAction"))
   virtual void RecordAction(const UserMetricsAction&) {}
 
   typedef uint64_t WebMemoryAllocatorDumpGuid;
@@ -515,7 +514,7 @@
   // Returns a newly allocated and initialized offscreen context provider,
   // backed by an independent context. Returns null if the context cannot be
   // created or initialized.
-  // Passing an existing provider to shareContext will create the new context
+  // Passing an existing provider to |share_context| will create the new context
   // in the same share group as the one passed.
   virtual std::unique_ptr<WebGraphicsContext3DProvider>
   CreateOffscreenGraphicsContext3DProvider(
@@ -544,8 +543,8 @@
 
   virtual WebCompositorSupport* CompositorSupport() { return nullptr; }
 
-  // Creates a new fling animation curve instance for device |deviceSource|
-  // with |velocity| and already scrolled |cumulativeScroll| pixels.
+  // Creates a new fling animation curve instance for device |device_source|
+  // with |velocity| and already scrolled |cumulative_scroll| pixels.
   virtual std::unique_ptr<WebGestureCurve> CreateFlingAnimationCurve(
       WebGestureDevice device_source,
       const WebFloatPoint& velocity,
@@ -634,41 +633,41 @@
   virtual void StopListening(WebPlatformEventType type) {}
 
   // This method converts from the supplied DOM code enum to the
-  // embedder's DOM code value for the key pressed. |domCode| values are
+  // embedder's DOM code value for the key pressed. |dom_code| values are
   // based on the value defined in
   // ui/events/keycodes/dom4/keycode_converter_data.h.
   // Returns null string, if DOM code value is not found.
   virtual WebString DomCodeStringFromEnum(int dom_code) { return WebString(); }
 
   // This method converts from the suppled DOM code value to the
-  // embedder's DOM code enum for the key pressed. |codeString| is defined in
+  // embedder's DOM code enum for the key pressed. |code_string| is defined in
   // ui/events/keycodes/dom4/keycode_converter_data.h.
   // Returns 0, if DOM code enum is not found.
   virtual int DomEnumFromCodeString(const WebString& code_string) { return 0; }
 
   // This method converts from the supplied DOM |key| enum to the
-  // corresponding DOM |key| string value for the key pressed. |domKey| values
+  // corresponding DOM |key| string value for the key pressed. |dom_key| values
   // are based on the value defined in ui/events/keycodes/dom3/dom_key_data.h.
   // Returns empty string, if DOM key value is not found.
   virtual WebString DomKeyStringFromEnum(int dom_key) { return WebString(); }
 
   // This method converts from the suppled DOM |key| value to the
-  // embedder's DOM |key| enum for the key pressed. |keyString| is defined in
+  // embedder's DOM |key| enum for the key pressed. |key_string| is defined in
   // ui/events/keycodes/dom3/dom_key_data.h.
   // Returns 0 if DOM key enum is not found.
   virtual int DomKeyEnumFromString(const WebString& key_string) { return 0; }
 
-  // This method returns whether the specified |domKey| is a modifier key.
-  // |domKey| values are based on the value defined in
+  // This method returns whether the specified |dom_key| is a modifier key.
+  // |dom_key| values are based on the value defined in
   // ui/events/keycodes/dom3/dom_key_data.h.
   virtual bool IsDomKeyForModifier(int dom_key) { return false; }
 
   // Quota -----------------------------------------------------------
 
   // Queries the storage partition's storage usage and quota information.
-  // WebStorageQuotaCallbacks::didQueryStorageUsageAndQuota will be called
+  // WebStorageQuotaCallbacks::DidQueryStorageUsageAndQuota will be called
   // with the current usage and quota information for the partition. When
-  // an error occurs WebStorageQuotaCallbacks::didFail is called with an
+  // an error occurs WebStorageQuotaCallbacks::DidFail is called with an
   // error code.
   virtual void QueryStorageUsageAndQuota(const WebURL& storage_partition,
                                          WebStorageQuotaType,
diff --git a/third_party/WebKit/public/platform/WebApplicationCacheHost.h b/third_party/WebKit/public/platform/WebApplicationCacheHost.h
index ff592285e..09cc8ef 100644
--- a/third_party/WebKit/public/platform/WebApplicationCacheHost.h
+++ b/third_party/WebKit/public/platform/WebApplicationCacheHost.h
@@ -42,7 +42,7 @@
 class WebURLResponse;
 
 // This interface is used by webkit to call out to the embedder. Webkit uses
-// the WebFrameClient::createApplicationCacheHost method to create instances,
+// the WebFrameClient::CreateApplicationCacheHost method to create instances,
 // and calls delete when the instance is no longer needed.
 class WebApplicationCacheHost {
  public:
diff --git a/third_party/WebKit/public/platform/WebAudioBus.h b/third_party/WebKit/public/platform/WebAudioBus.h
index 67cf14f..6d3ecd3 100644
--- a/third_party/WebKit/public/platform/WebAudioBus.h
+++ b/third_party/WebKit/public/platform/WebAudioBus.h
@@ -47,18 +47,18 @@
   WebAudioBus() : private_(0) {}
   ~WebAudioBus() { Reset(); }
 
-  // initialize() allocates memory of the given length for the given number of
+  // Initialize() allocates memory of the given length for the given number of
   // channels.
   void Initialize(unsigned number_of_channels,
                   size_t length,
                   double sample_rate);
 
-  // resizeSmaller() can only be called after initialize() with a new length <=
+  // ResizeSmaller() can only be called after Initialize() with a new length <=
   // the initialization length.  The data stored in the bus will remain
   // undisturbed.
   void ResizeSmaller(size_t new_length);
 
-  // reset() releases the memory allocated from initialize().
+  // Reset() releases the memory allocated from Initialize().
   void Reset();
 
   unsigned NumberOfChannels() const;
diff --git a/third_party/WebKit/public/platform/WebAudioDestinationConsumer.h b/third_party/WebKit/public/platform/WebAudioDestinationConsumer.h
index b09361e..32a3532 100644
--- a/third_party/WebKit/public/platform/WebAudioDestinationConsumer.h
+++ b/third_party/WebKit/public/platform/WebAudioDestinationConsumer.h
@@ -35,9 +35,9 @@
 
   virtual void SetFormat(size_t number_of_channels, float sample_rate) = 0;
 
-  // The size of the vector is the number of audio channels, and numberOfFrames
-  // is the number of audio frames in the (possibly multi-channel) buffer in a
-  // planar format.
+  // The size of the vector is the number of audio channels, and
+  // |number_of_frames| is the number of audio frames in the (possibly
+  // multi-channel) buffer in a planar format.
   virtual void ConsumeAudio(const WebVector<const float*>&,
                             size_t number_of_frames) = 0;
 };
diff --git a/third_party/WebKit/public/platform/WebAudioDevice.h b/third_party/WebKit/public/platform/WebAudioDevice.h
index 79fbdd5..0191d5b 100644
--- a/third_party/WebKit/public/platform/WebAudioDevice.h
+++ b/third_party/WebKit/public/platform/WebAudioDevice.h
@@ -39,7 +39,7 @@
  public:
   class BLINK_PLATFORM_EXPORT RenderCallback {
    public:
-    // Note: |delay| and |delayTimestamp| arguments are high-precision
+    // Note: |delay| and |delay_timestamp| arguments are high-precision
     // measurements of the state of the system in the recent past. To be clear,
     // |delay| does *not* represent the point-in-time at which the first
     // rendered sample will be played out.
diff --git a/third_party/WebKit/public/platform/WebAudioSourceProvider.h b/third_party/WebKit/public/platform/WebAudioSourceProvider.h
index dc82e60..7a25f277 100644
--- a/third_party/WebKit/public/platform/WebAudioSourceProvider.h
+++ b/third_party/WebKit/public/platform/WebAudioSourceProvider.h
@@ -36,14 +36,14 @@
  public:
   virtual ~WebAudioSourceProvider() {}
 
-  // provideInput() gets called repeatedly to render time-slices of a continuous
+  // ProvideInput() gets called repeatedly to render time-slices of a continuous
   // audio stream. May be called from any thread.
   virtual void ProvideInput(const WebVector<float*>& audio_data,
                             size_t number_of_frames) = 0;
 
   // If a client is set, we call it back when the audio format is available.
   // Must always be called from the same thread. I.e., once called on a thread,
-  // all future calls to setClient must be issued from that same thread.
+  // all future calls to SetClient must be issued from that same thread.
   virtual void SetClient(WebAudioSourceProviderClient*) {}
 };
 
diff --git a/third_party/WebKit/public/platform/WebBlobRegistry.h b/third_party/WebKit/public/platform/WebBlobRegistry.h
index fa5e2b05..33e1697 100644
--- a/third_party/WebKit/public/platform/WebBlobRegistry.h
+++ b/third_party/WebKit/public/platform/WebBlobRegistry.h
@@ -51,12 +51,12 @@
 class WebBlobRegistry {
  public:
   // Builder class for creating blobs. The blob is built on calling the
-  // build() method, where IPCs are sent to the browser.
+  // Build() method, where IPCs are sent to the browser.
   // Preconditions:
   // * Not meant to be used on multiple threads.
   // * Must not be kept alive longer than creator WebBlobRegistry (shouldn't
   //   be an issue because of the singleton nature of the WebBlobRegistry)
-  // * append.* methods are invalid after build() is called.
+  // * Append.* methods are invalid after Build() is called.
   class Builder {
    public:
     virtual ~Builder() {}
@@ -75,17 +75,17 @@
                                      uint64_t length,
                                      double expected_modification_time) = 0;
 
-    // Builds the blob. All calls to append* are invalid after calling this
+    // Builds the blob. All calls to Append* are invalid after calling this
     // method.
     virtual void Build() = 0;
   };
 
   virtual ~WebBlobRegistry() {}
 
-  // TODO(dmurph): Deprecate and migrate to createBuilder
+  // TODO(dmurph): Deprecate and migrate to CreateBuilder
   virtual void RegisterBlobData(const WebString& uuid, const WebBlobData&) {}
 
-  // The blob is finalized (and sent to the browser) on calling build() on the
+  // The blob is finalized (and sent to the browser) on calling Build() on the
   // Builder object.
   virtual std::unique_ptr<Builder> CreateBuilder(
       const WebString& uuid,
diff --git a/third_party/WebKit/public/platform/WebClipboard.h b/third_party/WebKit/public/platform/WebClipboard.h
index b2328a4..63633904 100644
--- a/third_party/WebKit/public/platform/WebClipboard.h
+++ b/third_party/WebKit/public/platform/WebClipboard.h
@@ -71,11 +71,11 @@
     return WebVector<WebString>();
   }
   virtual WebString ReadPlainText(Buffer) { return WebString(); }
-  // fragmentStart and fragmentEnd are indexes into the returned markup that
-  // indicate the start and end of the fragment if the returned markup
+  // |fragment_start| and |fragment_end| are indexes into the returned markup
+  // that indicate the start and end of the fragment if the returned markup
   // contains additional context. If there is no additional context,
-  // fragmentStart will be zero and fragmentEnd will be the same as the length
-  // of the returned markup.
+  // |fragment_start| will be zero and |fragment_end| will be the same as the
+  // length of the returned markup.
   virtual WebString ReadHTML(Buffer buffer,
                              WebURL* page_url,
                              unsigned* fragment_start,
diff --git a/third_party/WebKit/public/platform/WebContentDecryptionModuleSession.h b/third_party/WebKit/public/platform/WebContentDecryptionModuleSession.h
index 25fd288d..277c01c 100644
--- a/third_party/WebKit/public/platform/WebContentDecryptionModuleSession.h
+++ b/third_party/WebKit/public/platform/WebContentDecryptionModuleSession.h
@@ -58,12 +58,12 @@
     virtual void Close() = 0;
 
     // Called when the expiration time for the session changes.
-    // |updatedExpiryTimeInMS| is specified as the number of milliseconds
+    // |updated_expiry_time_in_ms| is specified as the number of milliseconds
     // since 01 January, 1970 UTC.
     virtual void ExpirationChanged(double updated_expiry_time_in_ms) = 0;
 
     // Called when the set of keys for this session changes or existing keys
-    // change state. |hasAdditionalUsableKey| is set if a key is newly
+    // change state. |has_additional_usable_key| is set if a key is newly
     // usable (e.g. new key available, previously expired key has been
     // renewed, etc.) and the browser should attempt to resume playback
     // if necessary.
diff --git a/third_party/WebKit/public/platform/WebContentLayerClient.h b/third_party/WebKit/public/platform/WebContentLayerClient.h
index 2b933c15..02f6566 100644
--- a/third_party/WebKit/public/platform/WebContentLayerClient.h
+++ b/third_party/WebKit/public/platform/WebContentLayerClient.h
@@ -41,7 +41,8 @@
   enum PaintingControlSetting {
     // Returns the last PaintArtifact produced.
     kPaintDefaultBehavior,
-    // Paints the content to simulate the behavior of FrameView::paintTree().
+    // Paints the content to simulate the behavior of
+    // LocalFrameView::PaintTree().
     kPaintDefaultBehaviorForTest,
     // Puts the GraphicsContext in disabled mode and disables display item
     // construction in PaintController.
@@ -54,7 +55,7 @@
 
   // The paintable region is the rectangular region, within the bounds of the
   // layer this client paints, that the client is capable of painting via
-  // paintContents().  Calling paintContents will return a WebDisplayitemList
+  // PaintContents().  Calling PaintContents will return a WebDisplayitemList
   // that is guaranteed valid only within this region.  In particular, this is
   // used to represent the interest rect in Blink.
   virtual gfx::Rect PaintableRegion() = 0;
@@ -70,7 +71,7 @@
 
   // Returns an estimate of the current memory usage within this object,
   // excluding memory shared with painting artifacts (i.e.,
-  // WebDisplayItemList). Should be invoked after paintContents, so that the
+  // WebDisplayItemList). Should be invoked after PaintContents, so that the
   // result includes data cached internally during painting.
   virtual size_t ApproximateUnsharedMemoryUsage() const { return 0; }
 
diff --git a/third_party/WebKit/public/platform/WebCrypto.h b/third_party/WebKit/public/platform/WebCrypto.h
index 3e4b9b6..8d3a6e2 100644
--- a/third_party/WebKit/public/platform/WebCrypto.h
+++ b/third_party/WebKit/public/platform/WebCrypto.h
@@ -112,18 +112,18 @@
  public:
   virtual ~WebCryptoDigestor() {}
 
-  // consume() will return |true| on the successful addition of data to the
+  // Consume() will return |true| on the successful addition of data to the
   // partially generated digest. It will return |false| when that fails. After
-  // a return of |false|, consume() should not be called again (nor should
-  // finish() be called).
+  // a return of |false|, Consume() should not be called again (nor should
+  // Finish() be called).
   virtual bool Consume(const unsigned char* data, unsigned data_size) {
     return false;
   }
 
-  // finish() will return |true| if the digest has been successfully computed
+  // Finish() will return |true| if the digest has been successfully computed
   // and put into the result buffer, otherwise it will return |false|. In
-  // either case, neither finish() nor consume() should be called again after
-  // a call to finish(). resultData is valid until the WebCrytpoDigestor
+  // either case, neither Finish() nor Consume() should be called again after
+  // a call to Finish(). |result_data| is valid until the WebCrytpoDigestor
   // object is destroyed.
   virtual bool Finish(unsigned char*& result_data, unsigned& result_data_size) {
     return false;
@@ -179,9 +179,9 @@
   //   * Data buffers are transfered as WebVectors. Implementations are free
   //     to re-use or transfer their storage.
   //
-  //   * All WebCryptoKeys are guaranteeed to be !isNull().
+  //   * All WebCryptoKeys are guaranteeed to be !IsNull().
   //
-  //   * All WebCryptoAlgorithms are guaranteed to be !isNull()
+  //   * All WebCryptoAlgorithms are guaranteed to be !IsNull()
   //
   //   * Look to the Web Crypto spec for an explanation of the parameter. The
   //     method names here have a 1:1 correspondence with those of
@@ -198,7 +198,7 @@
   //
   // Only the following checks can be assumed as having already passed:
   //
-  //  * The key is extractable when calling into exportKey/wrapKey.
+  //  * The key is extractable when calling into ExportKey/WrapKey.
   //  * The key usages permit the operation being requested.
   //  * The key's algorithm matches that of the requested operation.
   //
@@ -286,7 +286,7 @@
 
   // This is the exception to the "Completing the request" guarantees
   // outlined above. This is useful for Blink internal crypto and is not part
-  // of the WebCrypto standard. createDigestor must provide the result via
+  // of the WebCrypto standard. CreateDigestor must provide the result via
   // the WebCryptoDigestor object synchronously. This will never return null.
   virtual std::unique_ptr<WebCryptoDigestor> CreateDigestor(
       WebCryptoAlgorithmId algorithm_id) {
@@ -297,7 +297,7 @@
   // Structured clone
   // -----------------------
   //
-  // deserializeKeyForClone() and serializeKeyForClone() are used for
+  // DeserializeKeyForClone() and SerializeKeyForClone() are used for
   // implementing structured cloning of WebCryptoKey.
   //
   // Blink is responsible for saving and restoring all of the attributes of
@@ -334,7 +334,7 @@
   //   * The bytes to deserialize were corrupted
 
   // Creates a new key given key data which was written using
-  // serializeKeyForClone(). Returns true on success.
+  // SerializeKeyForClone(). Returns true on success.
   virtual bool DeserializeKeyForClone(const WebCryptoKeyAlgorithm&,
                                       WebCryptoKeyType,
                                       bool extractable,
diff --git a/third_party/WebKit/public/platform/WebCryptoAlgorithm.h b/third_party/WebKit/public/platform/WebCryptoAlgorithm.h
index 930ee23..242c3c40 100644
--- a/third_party/WebKit/public/platform/WebCryptoAlgorithm.h
+++ b/third_party/WebKit/public/platform/WebCryptoAlgorithm.h
@@ -147,8 +147,8 @@
 //   * Threadsafe
 //   * Copiable (cheaply)
 //
-// If WebCryptoAlgorithm "isNull()" then it is invalid to call any of the other
-// methods on it (other than destruction, assignment, or isNull()).
+// If WebCryptoAlgorithm "IsNull()" then it is invalid to call any of the other
+// methods on it (other than destruction, assignment, or IsNull()).
 class WebCryptoAlgorithm {
  public:
 #if INSIDE_BLINK
diff --git a/third_party/WebKit/public/platform/WebCryptoKey.h b/third_party/WebKit/public/platform/WebCryptoKey.h
index 8d455e6..cde45a07 100644
--- a/third_party/WebKit/public/platform/WebCryptoKey.h
+++ b/third_party/WebKit/public/platform/WebCryptoKey.h
@@ -85,8 +85,8 @@
 // safely assume any details regarding the type of the wrapped
 // WebCryptoKeyHandle*.
 //
-// If WebCryptoKey "isNull()" then it is invalid to call any of the other
-// methods on it (other than destruction, assignment, or isNull()).
+// If WebCryptoKey "IsNull()" then it is invalid to call any of the other
+// methods on it (other than destruction, assignment, or IsNull()).
 class WebCryptoKey {
  public:
   // Constructs a "null" key (One for which isNull() returns true).
diff --git a/third_party/WebKit/public/platform/WebCryptoKeyAlgorithm.h b/third_party/WebKit/public/platform/WebCryptoKeyAlgorithm.h
index 31b224234..448f8fb0 100644
--- a/third_party/WebKit/public/platform/WebCryptoKeyAlgorithm.h
+++ b/third_party/WebKit/public/platform/WebCryptoKeyAlgorithm.h
@@ -58,7 +58,7 @@
       std::unique_ptr<WebCryptoKeyAlgorithmParams>);
 #endif
 
-  // FIXME: Delete this in favor of the create*() functions.
+  // FIXME: Delete this in favor of the Create*() functions.
   BLINK_PLATFORM_EXPORT static WebCryptoKeyAlgorithm AdoptParamsAndCreate(
       WebCryptoAlgorithmId,
       WebCryptoKeyAlgorithmParams*);
diff --git a/third_party/WebKit/public/platform/WebCursorInfo.h b/third_party/WebKit/public/platform/WebCursorInfo.h
index 0d09338..68eb2ed 100644
--- a/third_party/WebKit/public/platform/WebCursorInfo.h
+++ b/third_party/WebKit/public/platform/WebCursorInfo.h
@@ -97,9 +97,9 @@
   WebImage custom_image;
 
 #ifdef WIN32
-  // On Windows, TypeCustom may alternatively reference an externally
-  // defined HCURSOR. If type is TypeCustom and externalHandle is non-
-  // null, then customData should be ignored. The WebCursorInfo is not
+  // On Windows, kTypeCustom may alternatively reference an externally
+  // defined HCURSOR. If |type| is kTypeCustom and |external_handle| is non-
+  // null, then |custom_image| should be ignored. The WebCursorInfo is not
   // responsible for managing the lifetime of this cursor handle.
   HCURSOR external_handle;
 #endif
diff --git a/third_party/WebKit/public/platform/WebDataConsumerHandle.h b/third_party/WebKit/public/platform/WebDataConsumerHandle.h
index f4ddaaa..d4477d9 100644
--- a/third_party/WebKit/public/platform/WebDataConsumerHandle.h
+++ b/third_party/WebKit/public/platform/WebDataConsumerHandle.h
@@ -16,10 +16,10 @@
 // can read data from it.
 //
 // A WebDataConsumerHandle is a thread-safe object. A user can call
-// |obtainReader| or destruct the object on any thread.
+// |ObtainReader| or destruct the object on any thread.
 // A WebDataConsumerHandle having a reader is called "locked". A
 // WebDataConsumerHandle or its reader are called "waiting" when reading from
-// the handle or reader returns ShouldWait.
+// the handle or reader returns kShouldWait.
 //
 // WebDataConsumerHandle can be created / used / destructed only on
 // Oilpan-enabled threads.
@@ -55,25 +55,25 @@
   };
 
   // This class provides a means to read data from the associated handle. A
-  // Reader object is bound to the thread on which |obtainReader| is called.
+  // Reader object is bound to the thread on which |ObtainReader| is called.
   // Any functions including the destructor should be called on the thread.
   // A reader can outlive the associated handle. In such a case, the handle
   // destruction will not affect the reader functionality.
-  // Reading functions may success (i.e. return Ok) or fail (otherwise), and
+  // Reading functions may success (i.e. return kOk) or fail (otherwise), and
   // the behavior which is not specified is unspecified.
   class BLINK_PLATFORM_EXPORT Reader {
    public:
     // Destructing a reader means it is released and a user can get another
-    // Reader by calling |obtainReader| on any thread again.
+    // Reader by calling |ObtainReader| on any thread again.
     virtual ~Reader() {}
 
     // Reads data into |data| up to |size| bytes. The actual read size will
-    // be stored in |*readSize|. This function cannot be called when a
+    // be stored in |*read_size|. This function cannot be called when a
     // two-phase read is in progress.
-    // Returns Done when it reaches to the end of the data.
-    // Returns ShouldWait when the handle does not have data to read but
+    // Returns kDone when it reaches to the end of the data.
+    // Returns kShouldWait when the handle does not have data to read but
     // it is not closed or errored.
-    // The default implementation uses beginRead and endRead.
+    // The default implementation uses BeginRead and EndRead.
     virtual Result Read(void* data,
                         size_t /* size */,
                         Flags,
@@ -81,15 +81,15 @@
 
     // Begins a two-phase read. On success, the function stores a buffer
     // that contains the read data of length |*available| into |*buffer|.
-    // Returns Done when it reaches to the end of the data.
-    // Returns ShouldWait when the handle does not have data to read but
+    // Returns kDone when it reaches to the end of the data.
+    // Returns kShouldWait when the handle does not have data to read but
     // it is not closed or errored.
-    // On fail, you don't have to (and should not) call endRead, because the
+    // On fail, you don't have to (and should not) call EndRead, because the
     // read session implicitly ends in that case.
     virtual Result BeginRead(const void** buffer, Flags, size_t* available) = 0;
 
     // Ends a two-phase read.
-    // |readSize| indicates the actual read size.
+    // |read_size| indicates the actual read size.
     virtual Result EndRead(size_t read_size) = 0;
   };
 
diff --git a/third_party/WebKit/public/platform/WebDistillability.h b/third_party/WebKit/public/platform/WebDistillability.h
index d054e28..b89062ec46 100644
--- a/third_party/WebKit/public/platform/WebDistillability.h
+++ b/third_party/WebKit/public/platform/WebDistillability.h
@@ -9,7 +9,7 @@
 
 struct WebDistillabilityFeatures {
   bool is_mobile_friendly;
-  // The rest of the fields are only valid when isMobileFriendly==false.
+  // The rest of the fields are only valid when is_mobile_friendly==false.
   bool open_graph;
   unsigned element_count;
   unsigned anchor_count;
diff --git a/third_party/WebKit/public/platform/WebDragData.h b/third_party/WebKit/public/platform/WebDragData.h
index 3da5f18..d1e2b919 100644
--- a/third_party/WebKit/public/platform/WebDragData.h
+++ b/third_party/WebKit/public/platform/WebDragData.h
@@ -63,28 +63,28 @@
     StorageType storage_type;
 
     // TODO(dcheng): This should probably be a union.
-    // Only valid when storageType == StorageTypeString.
+    // Only valid when storage_type == kStorageTypeString.
     WebString string_type;
     WebString string_data;
 
-    // Title associated with a link when stringType == "text/uri-list".
+    // Title associated with a link when string_type == "text/uri-list".
     WebString title;
 
-    // Only valid when stringType == "text/html". Stores the base URL for the
+    // Only valid when string_type == "text/html". Stores the base URL for the
     // contained markup.
     WebURL base_url;
 
-    // Only valid when storageType == StorageTypeFilename.
+    // Only valid when storage_type == kStorageTypeFilename.
     WebString filename_data;
     WebString display_name_data;
 
-    // Only valid when storageType == StorageTypeBinaryData.
+    // Only valid when storage_type == kStorageTypeBinaryData.
     WebData binary_data;
     WebURL binary_data_source_url;
     WebString binary_data_filename_extension;
     WebString binary_data_content_disposition;
 
-    // Only valid when storageType == StorageTypeFileSystemFile.
+    // Only valid when storage_type == kStorageTypeFileSystemFile.
     WebURL file_system_url;
     long long file_system_file_size;
     WebString file_system_id;
@@ -111,8 +111,8 @@
   WebVector<Item> Items() const { return item_list_; }
 
   BLINK_PLATFORM_EXPORT void SetItems(WebVector<Item> item_list);
-  // FIXME: setItems is slow because setItems copies WebVector.
-  // Instead, use swapItems.
+  // FIXME: SetItems is slow because SetItems copies WebVector.
+  // Instead, use SwapItems.
   void SwapItems(WebVector<Item>& item_list) { item_list_.Swap(item_list); }
 
   void Initialize() { valid_ = true; }
diff --git a/third_party/WebKit/public/platform/WebFileSystem.h b/third_party/WebKit/public/platform/WebFileSystem.h
index 91f94e0..33b422c6 100644
--- a/third_party/WebKit/public/platform/WebFileSystem.h
+++ b/third_party/WebKit/public/platform/WebFileSystem.h
@@ -55,25 +55,25 @@
   };
 
   // Opens a FileSystem.
-  // WebFileSystemCallbacks::didOpenFileSystem() must be called with
+  // WebFileSystemCallbacks::DidOpenFileSystem() must be called with
   // a name and root path for the requested FileSystem when the operation
-  // is completed successfully. WebFileSystemCallbacks::didFail() must be
+  // is completed successfully. WebFileSystemCallbacks::DidFail() must be
   // called otherwise.
   virtual void OpenFileSystem(const WebURL& storage_partition,
                               const WebFileSystemType,
                               WebFileSystemCallbacks) = 0;
 
   // Resolves a filesystem URL.
-  // WebFileSystemCallbacks::didSucceed() must be called with filesystem
+  // WebFileSystemCallbacks::DidSucceed() must be called with filesystem
   // information (name, root path and type) and file metadata (file path and
   // file type) when the operation is completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void ResolveURL(const WebURL& file_system_url,
                           WebFileSystemCallbacks) = 0;
 
   // Deletes FileSystem.
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation
-  // is completed successfully. WebFileSystemCallbacks::didFail() must be
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation
+  // is completed successfully. WebFileSystemCallbacks::DidFail() must be
   // called otherwise.
   // All in-flight operations and following operations may fail after the
   // FileSystem is deleted.
@@ -81,41 +81,41 @@
                                 const WebFileSystemType,
                                 WebFileSystemCallbacks) {}
 
-  // Moves a file or directory at |srcPath| to |destPath|.
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation is
+  // Moves a file or directory at |src_path| to |dest_path|.
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation is
   // completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void Move(const WebURL& src_path,
                     const WebURL& dest_path,
                     WebFileSystemCallbacks) = 0;
 
-  // Copies a file or directory at |srcPath| to |destPath|.
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation is
+  // Copies a file or directory at |src_path| to |dest_path|.
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation is
   // completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void Copy(const WebURL& src_path,
                     const WebURL& dest_path,
                     WebFileSystemCallbacks) = 0;
 
   // Deletes a file or directory at a given |path|.
   // It is an error to try to remove a directory that is not empty.
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation is
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation is
   // completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void Remove(const WebURL& path, WebFileSystemCallbacks) = 0;
 
   // Deletes a file or directory recursively at a given |path|.
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation is
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation is
   // completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void RemoveRecursively(const WebURL& path,
                                  WebFileSystemCallbacks) = 0;
 
   // Retrieves the metadata information of the file or directory at the given
   // |path|.  This may not always return the local platform path in remote
-  // filesystem cases.  WebFileSystemCallbacks::didReadMetadata() must be called
+  // filesystem cases.  WebFileSystemCallbacks::DidReadMetadata() must be called
   // with a valid metadata when the retrieval is completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void ReadMetadata(const WebURL& path, WebFileSystemCallbacks) = 0;
 
   // Creates a file at given |path|.
@@ -124,9 +124,9 @@
   // If |exclusive| is false, it succeeds if the |path| already exists or
   // it has successfully created a new file at |path|.
   //
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation is
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation is
   // completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void CreateFile(const WebURL& path,
                           bool exclusive,
                           WebFileSystemCallbacks) = 0;
@@ -137,36 +137,36 @@
   // If |exclusive| is false, it succeeds if the |path| already exists or it has
   // successfully created a new directory at |path|.
   //
-  // WebFileSystemCallbacks::didSucceed() must be called when
+  // WebFileSystemCallbacks::DidSucceed() must be called when
   // the operation is completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void CreateDirectory(const WebURL& path,
                                bool exclusive,
                                WebFileSystemCallbacks) = 0;
 
   // Checks if a file exists at a given |path|.
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation is
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation is
   // completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void FileExists(const WebURL& path, WebFileSystemCallbacks) = 0;
 
   // Checks if a directory exists at a given |path|.
-  // WebFileSystemCallbacks::didSucceed() must be called when the operation is
+  // WebFileSystemCallbacks::DidSucceed() must be called when the operation is
   // completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void DirectoryExists(const WebURL& path, WebFileSystemCallbacks) = 0;
 
   // Reads directory entries of a given directory at |path| and returns a
   // callbacks ID which can be used to wait for additional results.
-  // WebFileSystemCallbacks::didReadDirectory() must be called when the
+  // WebFileSystemCallbacks::DidReadDirectory() must be called when the
   // operation is completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual int ReadDirectory(const WebURL& path, WebFileSystemCallbacks) = 0;
 
   // Creates a WebFileWriter that can be used to write to the given file.
-  // WebFileSystemCallbacks::didCreateFileWriter() must be called with the
+  // WebFileSystemCallbacks::DidCreateFileWriter() must be called with the
   // created WebFileWriter when the operation is completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void CreateFileWriter(const WebURL& path,
                                 WebFileWriterClient*,
                                 WebFileSystemCallbacks) = 0;
@@ -181,9 +181,9 @@
   // The returned metadata is used to create a File object for the |path|.
   // The snapshot file is supposed to be deleted when the last reference to a
   // blink::File referring to it's path is dropped.
-  // WebFileSystemCallbacks::didCreateSnapshotFile() with the metadata of the
+  // WebFileSystemCallbacks::DidCreateSnapshotFile() with the metadata of the
   // snapshot file must be called when the operation is completed successfully.
-  // WebFileSystemCallbacks::didFail() must be called otherwise.
+  // WebFileSystemCallbacks::DidFail() must be called otherwise.
   virtual void CreateSnapshotFileAndReadMetadata(const WebURL& path,
                                                  WebFileSystemCallbacks) = 0;
 
@@ -191,7 +191,7 @@
   // if possible.
   // Returns false if there is no running method call corresponding for the
   // given ID.
-  // |callbacksId| must be the value returned by the original method call.
+  // |callbacks_id| must be the value returned by the original method call.
   virtual bool WaitForAdditionalResult(int callbacks_id) = 0;
 
  protected:
diff --git a/third_party/WebKit/public/platform/WebFileSystemCallbacks.h b/third_party/WebKit/public/platform/WebFileSystemCallbacks.h
index afb359f..754e997b 100644
--- a/third_party/WebKit/public/platform/WebFileSystemCallbacks.h
+++ b/third_party/WebKit/public/platform/WebFileSystemCallbacks.h
@@ -73,29 +73,29 @@
   // return values.
   BLINK_PLATFORM_EXPORT void DidSucceed();
 
-  // Callback for WebFileSystem::readMetadata. Called with the file metadata
+  // Callback for WebFileSystem::ReadMetadata. Called with the file metadata
   // for the requested path.
   BLINK_PLATFORM_EXPORT void DidReadMetadata(const WebFileInfo&);
 
-  // Callback for WebFileSystem::createSnapshot. The metadata also includes the
+  // Callback for WebFileSystem::CreateSnapshot. The metadata also includes the
   // platform file path.
   BLINK_PLATFORM_EXPORT void DidCreateSnapshotFile(const WebFileInfo&);
 
-  // Callback for WebFileSystem::readDirectory. Called with a vector of
+  // Callback for WebFileSystem::ReadDirectory. Called with a vector of
   // file entries in the requested directory. This callback might be called
-  // multiple times if the directory has many entries. |hasMore| must be
+  // multiple times if the directory has many entries. |has_more| must be
   // true when there are more entries.
   BLINK_PLATFORM_EXPORT void DidReadDirectory(
       const WebVector<WebFileSystemEntry>&,
       bool has_more);
 
-  // Callback for WebFileSystem::openFileSystem. Called with a name and
+  // Callback for WebFileSystem::OpenFileSystem. Called with a name and
   // root URL for the FileSystem when the request is accepted.
   BLINK_PLATFORM_EXPORT void DidOpenFileSystem(const WebString& name,
                                                const WebURL& root_url);
 
-  // Callback for WebFileSystem::resolveURL. Called with a name, root URL and
-  // file path for the FileSystem when the request is accepted. |isDirectory|
+  // Callback for WebFileSystem::ResolveURL. Called with a name, root URL and
+  // file path for the FileSystem when the request is accepted. |is_directory|
   // must be true when an entry to be resolved is a directory.
   BLINK_PLATFORM_EXPORT void DidResolveURL(const WebString& name,
                                            const WebURL& root_url,
@@ -103,7 +103,7 @@
                                            const WebString& file_path,
                                            bool is_directory);
 
-  // Callback for WebFileSystem::createFileWriter. Called with an instance
+  // Callback for WebFileSystem::CreateFileWriter. Called with an instance
   // of WebFileWriter and the target file length. The writer's ownership
   // is transferred to the callback.
   BLINK_PLATFORM_EXPORT void DidCreateFileWriter(WebFileWriter*,
diff --git a/third_party/WebKit/public/platform/WebFileWriterClient.h b/third_party/WebKit/public/platform/WebFileWriterClient.h
index d3e49ad5..ba7d49a 100644
--- a/third_party/WebKit/public/platform/WebFileWriterClient.h
+++ b/third_party/WebKit/public/platform/WebFileWriterClient.h
@@ -47,7 +47,7 @@
 
   // Called if the write or truncate fails, or if it is cancelled before the
   // write or truncate completes. Completion of an operation will be signalled
-  // exactly once, either by didFail, didTruncate, or didWrite(..., true).
+  // exactly once, either by DidFail, DidTruncate, or DidWrite(..., true).
   virtual void DidFail(WebFileError) = 0;
 
  protected:
diff --git a/third_party/WebKit/public/platform/WebGestureEvent.h b/third_party/WebKit/public/platform/WebGestureEvent.h
index d4cd2af..929041c5 100644
--- a/third_party/WebKit/public/platform/WebGestureEvent.h
+++ b/third_party/WebKit/public/platform/WebGestureEvent.h
@@ -45,12 +45,12 @@
   WebPointerProperties::PointerType primary_pointer_type =
       WebPointerProperties::PointerType::kUnknown;
 
-  // If the WebGestureEvent has sourceDevice=WebGestureDeviceTouchscreen, this
-  // field contains the unique identifier for the touch event that released
+  // If the WebGestureEvent has source_device == kWebGestureDeviceTouchscreen,
+  // this field contains the unique identifier for the touch event that released
   // this event at TouchDispositionGestureFilter. If the WebGestureEvents was
   // not released through a touch event (e.g. timer-released gesture events or
-  // gesture events with sourceDevice!=WebGestureDeviceTouchscreen), the field
-  // contains 0. See crbug.com/618738.
+  // gesture events with source_device != kWebGestureDeviceTouchscreen), the
+  // field contains 0. See crbug.com/618738.
   uint32_t unique_touch_event_id;
 
   // This field exists to allow BrowserPlugin to mark GestureScroll events as
@@ -99,7 +99,7 @@
       // target and instead just scroll the viewport.
       bool target_viewport;
       // The state of inertial phase scrolling. OSX has unique phases for normal
-      // and momentum scroll events. Should always be UnknownMomentumPhase for
+      // and momentum scroll events. Should always be kUnknownMomentumPhase for
       // touch based input as it generates GestureFlingStart instead.
       InertialPhaseState inertial_phase;
       // True if this event was synthesized in order to force a hit test;
@@ -129,11 +129,11 @@
     } scroll_update;
 
     struct {
-      // The original delta units the scrollBegin and scrollUpdates
+      // The original delta units the ScrollBegin and ScrollUpdates
       // were sent as.
       ScrollUnits delta_units;
       // The state of inertial phase scrolling. OSX has unique phases for normal
-      // and momentum scroll events. Should always be UnknownMomentumPhase for
+      // and momentum scroll events. Should always be kUnknownMomentumPhase for
       // touch based input as it generates GestureFlingStart instead.
       InertialPhaseState inertial_phase;
       // True if this event was synthesized in order to generate the proper
@@ -153,7 +153,7 @@
 
     struct {
       bool target_viewport;
-      // If set to true, don't treat flingCancel
+      // If set to true, don't treat fling_cancel
       // as a part of fling boost events sequence.
       bool prevent_boosting;
     } fling_cancel;
@@ -200,8 +200,8 @@
   BLINK_PLATFORM_EXPORT void ApplyTouchAdjustment(
       WebFloatPoint root_frame_coords);
 
-  // Sets any scaled values to be their computed values and sets |frameScale|
-  // back to 1 and |translateX|, |translateY| back to 0.
+  // Sets any scaled values to be their computed values and sets |frame_scale_|
+  // back to 1 and |frame_translate_| X and Y coordinates back to 0.
   BLINK_PLATFORM_EXPORT void FlattenTransform();
 
   bool PreventPropagation() const {
diff --git a/third_party/WebKit/public/platform/WebImage.h b/third_party/WebKit/public/platform/WebImage.h
index 581639d..633290b0 100644
--- a/third_party/WebKit/public/platform/WebImage.h
+++ b/third_party/WebKit/public/platform/WebImage.h
@@ -63,7 +63,7 @@
   }
 
   // Decodes the given image data. If the image has multiple frames,
-  // then the frame whose size is desiredSize is returned. Otherwise,
+  // then the frame whose size is desired_size is returned. Otherwise,
   // the first frame is returned.
   BLINK_PLATFORM_EXPORT static WebImage FromData(const WebData&,
                                                  const WebSize& desired_size);
diff --git a/third_party/WebKit/public/platform/WebImageCaptureFrameGrabber.h b/third_party/WebKit/public/platform/WebImageCaptureFrameGrabber.h
index 2871405..b181373 100644
--- a/third_party/WebKit/public/platform/WebImageCaptureFrameGrabber.h
+++ b/third_party/WebKit/public/platform/WebImageCaptureFrameGrabber.h
@@ -17,7 +17,7 @@
 
 using WebImageCaptureGrabFrameCallbacks = WebCallbacks<sk_sp<SkImage>, void>;
 
-// Platform interface of an ImageCapture class for grabFrame() calls.
+// Platform interface of an ImageCapture class for GrabFrame() calls.
 class WebImageCaptureFrameGrabber {
  public:
   virtual ~WebImageCaptureFrameGrabber() {}
diff --git a/third_party/WebKit/public/platform/WebInputEvent.h b/third_party/WebKit/public/platform/WebInputEvent.h
index b7eff4a..0335e45 100644
--- a/third_party/WebKit/public/platform/WebInputEvent.h
+++ b/third_party/WebKit/public/platform/WebInputEvent.h
@@ -41,7 +41,7 @@
 namespace blink {
 
 // The classes defined in this file are intended to be used with
-// WebWidget's handleInputEvent method.  These event types are cross-
+// WebWidget's HandleInputEvent method.  These event types are cross-
 // platform and correspond closely to WebCore's Platform*Event classes.
 //
 // WARNING! These classes must remain PODs (plain old data).  They are
diff --git a/third_party/WebKit/public/platform/WebKeyboardEvent.h b/third_party/WebKit/public/platform/WebKeyboardEvent.h
index effa08a..c77e857 100644
--- a/third_party/WebKit/public/platform/WebKeyboardEvent.h
+++ b/third_party/WebKit/public/platform/WebKeyboardEvent.h
@@ -20,7 +20,7 @@
   // them PODs.
   static const size_t kTextLengthCap = 4;
 
-  // |windowsKeyCode| is the Windows key code associated with this key
+  // |windows_key_code| is the Windows key code associated with this key
   // event.  Sometimes it's direct from the event (i.e. on Windows),
   // sometimes it's via a mapping function.  If you want a list, see
   // WebCore/platform/chromium/KeyboardCodes* . Note that this should
@@ -31,7 +31,7 @@
   int windows_key_code;
 
   // The actual key code genenerated by the platform.  The DOM spec runs
-  // on Windows-equivalent codes (thus |windowsKeyCode| above) but it
+  // on Windows-equivalent codes (thus |windows_key_code| above) but it
   // doesn't hurt to have this one around.
   int native_key_code;
 
@@ -55,7 +55,7 @@
   // shortcut-triggering RawKeyDown goes unhandled.
   bool is_browser_shortcut;
 
-  // |text| is the text generated by this keystroke.  |unmodifiedText| is
+  // |text| is the text generated by this keystroke.  |unmodified_text| is
   // |text|, but unmodified by an concurrently-held modifiers (except
   // shift).  This is useful for working out shortcut keys.  Linux and
   // Windows guarantee one character per event.  The Mac does not, but in
diff --git a/third_party/WebKit/public/platform/WebLayerTreeView.h b/third_party/WebKit/public/platform/WebLayerTreeView.h
index 76022bc..358409e9 100644
--- a/third_party/WebKit/public/platform/WebLayerTreeView.h
+++ b/third_party/WebKit/public/platform/WebLayerTreeView.h
@@ -79,7 +79,7 @@
   virtual void SetBackgroundColor(WebColor) {}
 
   // Sets whether this view is visible. In threaded mode, a view that is not
-  // visible will not composite or trigger updateAnimations() or layout() calls
+  // visible will not composite or trigger UpdateAnimations() or Layout() calls
   // until it becomes visible.
   virtual void SetVisible(bool) {}
 
@@ -113,9 +113,9 @@
                                           WebBrowserControlsState current,
                                           bool animate) {}
 
-  // Set browser controls height. If |shrinkViewport| is set to true, then Blink
-  // shrunk the viewport clip layers by the top and bottom browser controls
-  // height. Top controls will translate the web page down and do not
+  // Set browser controls height. If |shrink_viewport| is set to true, then
+  // Blink shrunk the viewport clip layers by the top and bottom browser
+  // controls height. Top controls will translate the web page down and do not
   // immediately scroll when hiding. The bottom controls scroll immediately and
   // never translate the content (only clip it).
   virtual void SetBrowserControlsHeight(float top_height,
diff --git a/third_party/WebKit/public/platform/WebLocalizedString.h b/third_party/WebKit/public/platform/WebLocalizedString.h
index ac53b8a..e98a86ee 100644
--- a/third_party/WebKit/public/platform/WebLocalizedString.h
+++ b/third_party/WebKit/public/platform/WebLocalizedString.h
@@ -109,15 +109,15 @@
     kOverflowMenuPlay,
     kOverflowMenuPause,
     kOverflowMenuDownload,
-    // PlaceholderForDayOfMonthField is for day placeholder text, e.g.
+    // kPlaceholderForDayOfMonthField is for day placeholder text, e.g.
     // "dd", for date field used in multiple fields "date", "datetime", and
     // "datetime-local" input UI instead of "--".
     kPlaceholderForDayOfMonthField,
-    // PlaceholderForfMonthField is for month placeholder text, e.g.
+    // kPlaceholderForfMonthField is for month placeholder text, e.g.
     // "mm", for month field used in multiple fields "date", "datetime", and
     // "datetime-local" input UI instead of "--".
     kPlaceholderForMonthField,
-    // PlaceholderForYearField is for year placeholder text, e.g. "yyyy",
+    // kPlaceholderForYearField is for year placeholder text, e.g. "yyyy",
     // for year field used in multiple fields "date", "datetime", and
     // "datetime-local" input UI instead of "----".
     kPlaceholderForYearField,
diff --git a/third_party/WebKit/public/platform/WebMediaPlayer.h b/third_party/WebKit/public/platform/WebMediaPlayer.h
index 5850ce7..34f5a0f 100644
--- a/third_party/WebKit/public/platform/WebMediaPlayer.h
+++ b/third_party/WebKit/public/platform/WebMediaPlayer.h
@@ -129,9 +129,9 @@
   virtual WebTimeRanges Seekable() const = 0;
 
   // Attempts to switch the audio output device.
-  // Implementations of setSinkId take ownership of the WebSetSinkCallbacks
+  // Implementations of SetSinkId take ownership of the WebSetSinkCallbacks
   // object.
-  // Note also that setSinkId implementations must make sure that all
+  // Note also that SetSinkId implementations must make sure that all
   // methods of the WebSetSinkCallbacks object, including constructors and
   // destructors, run in the same thread where the object is created
   // (i.e., the blink thread).
@@ -211,7 +211,7 @@
     return false;
   }
 
-  // Do tex(Sub)Image2D/3D for current frame. If it is not implemented for given
+  // Do Tex(Sub)Image2D/3D for current frame. If it is not implemented for given
   // parameters or fails, it returns false.
   // The method is wrapping calls to glTexImage2D, glTexSubImage2D,
   // glTexImage3D and glTexSubImage3D and parameters have the same name and
@@ -260,20 +260,20 @@
   // Inform WebMediaPlayer when the element starts/stops being the dominant
   // visible content. This will only be called after the monitoring of the
   // intersection with viewport is activated by calling
-  // WebMediaPlayerClient::activateViewportIntersectionMonitoring().
+  // WebMediaPlayerClient::ActivateViewportIntersectionMonitoring().
   virtual void BecameDominantVisibleContent(bool is_dominant) {}
 
   // Inform WebMediaPlayer when the element starts/stops being the effectively
   // fullscreen video, i.e. being the fullscreen element or child of the
   // fullscreen element, and being dominant in the viewport.
   //
-  // TODO(zqzhang): merge with becameDominantVisibleContent(). See
+  // TODO(zqzhang): merge with BecameDominantVisibleContent(). See
   // https://crbug.com/696211
   virtual void SetIsEffectivelyFullscreen(bool) {}
 
   virtual void EnabledAudioTracksChanged(
       const WebVector<TrackId>& enabled_track_ids) {}
-  // |selectedTrackId| is null if no track is selected.
+  // |selected_track_id| is null if no track is selected.
   virtual void SelectedVideoTrackChanged(TrackId* selected_track_id) {}
 
   // TODO(kainino): This is for a prototype implementation for getting the
diff --git a/third_party/WebKit/public/platform/WebMediaPlayerClient.h b/third_party/WebKit/public/platform/WebMediaPlayerClient.h
index 4f06553..237d00e 100644
--- a/third_party/WebKit/public/platform/WebMediaPlayerClient.h
+++ b/third_party/WebKit/public/platform/WebMediaPlayerClient.h
@@ -104,7 +104,7 @@
 
   // After the monitoring is activated, the client will inform WebMediaPlayer
   // when the element becomes/stops being the dominant visible content by
-  // calling WebMediaPlayer::becameDominantVisibleContent(bool).
+  // calling WebMediaPlayer::BecameDominantVisibleContent(bool).
   virtual void ActivateViewportIntersectionMonitoring(bool) {}
 
   // Returns whether the media element is in an autoplay muted state.
diff --git a/third_party/WebKit/public/platform/WebMediaRecorderHandler.h b/third_party/WebKit/public/platform/WebMediaRecorderHandler.h
index ddc064a1..836241b 100644
--- a/third_party/WebKit/public/platform/WebMediaRecorderHandler.h
+++ b/third_party/WebKit/public/platform/WebMediaRecorderHandler.h
@@ -36,7 +36,7 @@
   virtual void Resume() {}
 
   // MediaRecorder API isTypeSupported(), which boils down to
-  // canSupportMimeType() [1] "If true is returned from this method, it only
+  // CanSupportMimeType() [1] "If true is returned from this method, it only
   // indicates that the MediaRecorder implementation is capable of recording
   // Blob objects for the specified MIME type. Recording may still fail if
   // sufficient resources are not available to support the concrete media
diff --git a/third_party/WebKit/public/platform/WebMediaStream.h b/third_party/WebKit/public/platform/WebMediaStream.h
index 54e570a..66ceba9 100644
--- a/third_party/WebKit/public/platform/WebMediaStream.h
+++ b/third_party/WebKit/public/platform/WebMediaStream.h
@@ -70,7 +70,7 @@
   BLINK_PLATFORM_EXPORT void AudioTracks(WebVector<WebMediaStreamTrack>&) const;
   BLINK_PLATFORM_EXPORT void VideoTracks(WebVector<WebMediaStreamTrack>&) const;
   // If a track is not found with the specified id, the returned track's
-  // |isNull| will return true.
+  // |IsNull| will return true.
   BLINK_PLATFORM_EXPORT WebMediaStreamTrack
   GetAudioTrack(const WebString& track_id) const;
   BLINK_PLATFORM_EXPORT WebMediaStreamTrack
diff --git a/third_party/WebKit/public/platform/WebMediaStreamTrack.h b/third_party/WebKit/public/platform/WebMediaStreamTrack.h
index f493d853..4ec56c7 100644
--- a/third_party/WebKit/public/platform/WebMediaStreamTrack.h
+++ b/third_party/WebKit/public/platform/WebMediaStreamTrack.h
@@ -122,7 +122,7 @@
 
   // The lifetime of the WebAudioSourceProvider should outlive the
   // WebMediaStreamTrack, and clients are responsible for calling
-  // setSourceProvider(0) before the WebMediaStreamTrack is going away.
+  // SetSourceProvider(0) before the WebMediaStreamTrack is going away.
   BLINK_PLATFORM_EXPORT void SetSourceProvider(WebAudioSourceProvider*);
 
 #if INSIDE_BLINK
diff --git a/third_party/WebKit/public/platform/WebMessagePortChannelClient.h b/third_party/WebKit/public/platform/WebMessagePortChannelClient.h
index dafaffc..711341b2 100644
--- a/third_party/WebKit/public/platform/WebMessagePortChannelClient.h
+++ b/third_party/WebKit/public/platform/WebMessagePortChannelClient.h
@@ -40,7 +40,7 @@
 class BLINK_PLATFORM_EXPORT WebMessagePortChannelClient {
  public:
   // Alerts that new messages have arrived, which are retrieved by calling
-  // WebMessagePortChannel::tryGetMessage. Note that this may be called
+  // WebMessagePortChannel::TryGetMessage. Note that this may be called
   // on any thread.
   virtual void MessageAvailable() = 0;
 
diff --git a/third_party/WebKit/public/platform/WebMouseEvent.h b/third_party/WebKit/public/platform/WebMouseEvent.h
index 638e43ed..5f8d4b6 100644
--- a/third_party/WebKit/public/platform/WebMouseEvent.h
+++ b/third_party/WebKit/public/platform/WebMouseEvent.h
@@ -103,8 +103,8 @@
   BLINK_PLATFORM_EXPORT WebFloatPoint MovementInRootFrame() const;
   BLINK_PLATFORM_EXPORT WebFloatPoint PositionInRootFrame() const;
 
-  // Sets any scaled values to be their computed values and sets |frameScale|
-  // back to 1 and |translateX|, |translateY| back to 0.
+  // Sets any scaled values to be their computed values and sets |frame_scale_|
+  // back to 1 and |frame_translate_| X and Y coordinates back to 0.
   BLINK_PLATFORM_EXPORT WebMouseEvent FlattenTransform() const;
 #endif
 
diff --git a/third_party/WebKit/public/platform/WebMouseWheelEvent.h b/third_party/WebKit/public/platform/WebMouseWheelEvent.h
index 6db7a73..8f29eba5 100644
--- a/third_party/WebKit/public/platform/WebMouseWheelEvent.h
+++ b/third_party/WebKit/public/platform/WebMouseWheelEvent.h
@@ -102,8 +102,8 @@
   BLINK_PLATFORM_EXPORT float DeltaXInRootFrame() const;
   BLINK_PLATFORM_EXPORT float DeltaYInRootFrame() const;
 
-  // Sets any scaled values to be their computed values and sets |frameScale|
-  // back to 1 and |translateX|, |translateY| back to 0.
+  // Sets any scaled values to be their computed values and sets |frame_scale_|
+  // back to 1 and |frame_translate_| X and Y coordinates back to 0.
   BLINK_PLATFORM_EXPORT WebMouseWheelEvent FlattenTransform() const;
 
   bool IsCancelable() const { return dispatch_type == kBlocking; }
diff --git a/third_party/WebKit/public/platform/WebPageVisibilityState.h b/third_party/WebKit/public/platform/WebPageVisibilityState.h
index 02c5b8d..e88d058 100644
--- a/third_party/WebKit/public/platform/WebPageVisibilityState.h
+++ b/third_party/WebKit/public/platform/WebPageVisibilityState.h
@@ -34,7 +34,7 @@
 namespace blink {
 
 // The following enum should be consistent with the PageVisibilityState enum
-// defined in WebCore.
+// defined in core/page/PageVisibilityState.h
 enum WebPageVisibilityState {
   kWebPageVisibilityStateVisible,
   kWebPageVisibilityStateHidden,
diff --git a/third_party/WebKit/public/platform/WebPrerenderingSupport.h b/third_party/WebKit/public/platform/WebPrerenderingSupport.h
index 59b3d55c..15d388d 100644
--- a/third_party/WebKit/public/platform/WebPrerenderingSupport.h
+++ b/third_party/WebKit/public/platform/WebPrerenderingSupport.h
@@ -50,7 +50,7 @@
   virtual void Cancel(const WebPrerender&) = 0;
 
   // A prerender is abandoned when it's navigated away from or suspended in the
-  // page cache. This is a weaker signal than cancel(), since the launcher
+  // page cache. This is a weaker signal than Cancel(), since the launcher
   // hasn't indicated that the prerender isn't wanted, and we may end up using
   // it after, for instance, a short redirect chain.
   virtual void Abandon(const WebPrerender&) = 0;
diff --git a/third_party/WebKit/public/platform/WebPrivatePtr.h b/third_party/WebKit/public/platform/WebPrivatePtr.h
index e86b2f2..999fcca 100644
--- a/third_party/WebKit/public/platform/WebPrivatePtr.h
+++ b/third_party/WebKit/public/platform/WebPrivatePtr.h
@@ -240,17 +240,17 @@
 //    public:
 //        BLINK_EXPORT ~WebFoo();
 //        WebFoo() { }
-//        WebFoo(const WebFoo& other) { assign(other); }
+//        WebFoo(const WebFoo& other) { Assign(other); }
 //        WebFoo& operator=(const WebFoo& other)
 //        {
-//            assign(other);
+//            Assign(other);
 //            return *this;
 //        }
-//        BLINK_EXPORT void assign(const WebFoo&);  // Implemented in the body.
+//        BLINK_EXPORT void Assign(const WebFoo&);  // Implemented in the body.
 //
 //        // Methods that are exposed to Chromium and which are specific to
 //        // WebFoo go here.
-//        BLINK_EXPORT doWebFooThing();
+//        BLINK_EXPORT DoWebFooThing();
 //
 //        // Methods that are used only by other Blink classes should only be
 //        // declared when INSIDE_BLINK is set.
@@ -259,12 +259,12 @@
 //    #endif
 //
 //    private:
-//        WebPrivatePtr<Foo> m_private;
+//        WebPrivatePtr<Foo> private_;
 //    };
 //
 //    // WebFoo.cpp
-//    WebFoo::~WebFoo() { m_private.reset(); }
-//    void WebFoo::assign(const WebFoo& other) { ... }
+//    WebFoo::~WebFoo() { private_.Reset(); }
+//    void WebFoo::Assign(const WebFoo& other) { ... }
 //
 template <typename T,
           WebPrivatePtrDestruction crossThreadDestruction =
@@ -274,9 +274,9 @@
  public:
   WebPrivatePtr() : storage_(0) {}
   ~WebPrivatePtr() {
-    // We don't destruct the object pointed by m_ptr here because we don't
+    // We don't destruct the object pointed by storage_ here because we don't
     // want to expose destructors of core classes to embedders. We should
-    // call reset() manually in destructors of classes with WebPrivatePtr
+    // call Reset() manually in destructors of classes with WebPrivatePtr
     // members.
     DCHECK(!storage_);
   }
diff --git a/third_party/WebKit/public/platform/WebRTCCertificate.h b/third_party/WebKit/public/platform/WebRTCCertificate.h
index 322d2ba..14263c7 100644
--- a/third_party/WebKit/public/platform/WebRTCCertificate.h
+++ b/third_party/WebKit/public/platform/WebRTCCertificate.h
@@ -29,7 +29,7 @@
 };
 
 // Corresponds to |rtc::RTCCertificatePEM| in WebRTC.
-// See |WebRTCCertificate::toPEM| and |WebRTCCertificateGenerator::fromPEM|.
+// See |WebRTCCertificate::ToPEM| and |WebRTCCertificateGenerator::FromPEM|.
 class WebRTCCertificatePEM {
  public:
   WebRTCCertificatePEM(WebString private_key, WebString certificate)
@@ -63,7 +63,7 @@
   virtual uint64_t Expires() const = 0;
   virtual WebVector<WebRTCDtlsFingerprint> GetFingerprints() const = 0;
   // Creates a PEM strings representation of the certificate. See also
-  // |WebRTCCertificateGenerator::fromPEM|.
+  // |WebRTCCertificateGenerator::FromPEM|.
   virtual WebRTCCertificatePEM ToPEM() const = 0;
   // Checks if the two certificate objects represent the same certificate value,
   // as should be the case for a clone and the original.
diff --git a/third_party/WebKit/public/platform/WebRTCCertificateGenerator.h b/third_party/WebKit/public/platform/WebRTCCertificateGenerator.h
index b225e958..fb692e5 100644
--- a/third_party/WebKit/public/platform/WebRTCCertificateGenerator.h
+++ b/third_party/WebKit/public/platform/WebRTCCertificateGenerator.h
@@ -60,13 +60,13 @@
       uint64_t expires_ms,
       std::unique_ptr<WebRTCCertificateCallback> observer) = 0;
 
-  // Determines if the parameters are supported by |generateCertificate|.
+  // Determines if the parameters are supported by |GenerateCertificate|.
   // For example, if the number of bits of some parameter is too small or too
   // large we may want to reject it for security or performance reasons.
   virtual bool IsSupportedKeyParams(const WebRTCKeyParams&) = 0;
 
   // Creates a certificate from the PEM strings. See also
-  // |WebRTCCertificate::toPEM|.
+  // |WebRTCCertificate::ToPEM|.
   virtual std::unique_ptr<WebRTCCertificate> FromPEM(
       blink::WebString pem_private_key,
       blink::WebString pem_certificate) = 0;
diff --git a/third_party/WebKit/public/platform/WebRTCICECandidate.h b/third_party/WebKit/public/platform/WebRTCICECandidate.h
index de2fe6a..59dfac4ae 100644
--- a/third_party/WebKit/public/platform/WebRTCICECandidate.h
+++ b/third_party/WebKit/public/platform/WebRTCICECandidate.h
@@ -67,8 +67,8 @@
   BLINK_PLATFORM_EXPORT void SetSdpMLineIndex(unsigned short);
 
 #if INSIDE_BLINK
-  // TODO(guidou): Support setting sdpMLineIndex to -1 to indicate the absence
-  // of a value for sdpMLineIndex. crbug.com/614958
+  // TODO(guidou): Support setting sdp_m_line_index to -1 to indicate the
+  // absence of a value for sdp_m_line_index. crbug.com/614958
   WebRTCICECandidate(WebString candidate,
                      WebString sdp_mid,
                      unsigned short sdp_m_line_index) {
diff --git a/third_party/WebKit/public/platform/WebRTCLegacyStats.h b/third_party/WebKit/public/platform/WebRTCLegacyStats.h
index 7390e17..4d8603b8 100644
--- a/third_party/WebKit/public/platform/WebRTCLegacyStats.h
+++ b/third_party/WebKit/public/platform/WebRTCLegacyStats.h
@@ -44,12 +44,12 @@
   virtual WebRTCLegacyStatsMemberType GetType() const = 0;
   // Value getters. No conversion is performed; the function must match the
   // member's |type|.
-  virtual int ValueInt() const = 0;        // WebRTCLegacyStatsMemberTypeInt
-  virtual int64_t ValueInt64() const = 0;  // WebRTCLegacyStatsMemberTypeInt64
-  virtual float ValueFloat() const = 0;    // WebRTCLegacyStatsMemberTypeFloat
+  virtual int ValueInt() const = 0;        // kWebRTCLegacyStatsMemberTypeInt
+  virtual int64_t ValueInt64() const = 0;  // kWebRTCLegacyStatsMemberTypeInt64
+  virtual float ValueFloat() const = 0;    // kWebRTCLegacyStatsMemberTypeFloat
   virtual WebString ValueString()
-      const = 0;                       // WebRTCLegacyStatsMemberTypeString
-  virtual bool ValueBool() const = 0;  // WebRTCLegacyStatsMemberTypeBool
+      const = 0;                       // kWebRTCLegacyStatsMemberTypeString
+  virtual bool ValueBool() const = 0;  // kWebRTCLegacyStatsMemberTypeBool
 
   // Converts the value to string (regardless of |type|).
   virtual WebString ValueToString() const = 0;
diff --git a/third_party/WebKit/public/platform/WebRTCStatsRequest.h b/third_party/WebKit/public/platform/WebRTCStatsRequest.h
index 7de76be9..bcb64c7d 100644
--- a/third_party/WebKit/public/platform/WebRTCStatsRequest.h
+++ b/third_party/WebKit/public/platform/WebRTCStatsRequest.h
@@ -49,18 +49,14 @@
 //
 // The typical usage pattern is:
 // WebRTCStatsRequest request = <from somewhere>
-// WebRTCStatsResponse response = request.createResponse();
+// WebRTCStatsResponse response = request.CreateResponse();
 //
 // For each item on which statistics are going to be reported:
-//   size_t reportIndex = response.addReport();
-//   Add local information:
-//   size_t elementIndex = response.addElement(reportIndex, true, dateNow());
-//   For each statistic being reported on:
-//     response.addStatistic(reportIndex, true, elementIndex,
-//                           "name of statistic", "statistic value");
-//   Remote information (typically RTCP-derived) is added in the same way.
+//   WebRTCLegacyStats stats(...);
+//   (configuration of stats object depends on item type)
+//   response.AddStats(stats);
 // When finished adding information:
-// request.requestSucceeded(response);
+// request.RequestSucceeded(response);
 
 class WebRTCStatsRequest {
  public:
@@ -80,9 +76,9 @@
   // This function returns true if a selector argument was given to getStats.
   BLINK_PLATFORM_EXPORT bool HasSelector() const;
 
-  // The component() accessor give the information
+  // The Component() accessor give the information
   // required to look up a MediaStreamTrack implementation.
-  // It is only useful to call it when hasSelector() returns true.
+  // It is only useful to call it when HasSelector() returns true.
   BLINK_PLATFORM_EXPORT const WebMediaStreamTrack Component() const;
 
   BLINK_PLATFORM_EXPORT void RequestSucceeded(const WebRTCStatsResponse&) const;
diff --git a/third_party/WebKit/public/platform/WebRuntimeFeatures.h b/third_party/WebKit/public/platform/WebRuntimeFeatures.h
index 47c24ab..d64b9e4af 100644
--- a/third_party/WebKit/public/platform/WebRuntimeFeatures.h
+++ b/third_party/WebKit/public/platform/WebRuntimeFeatures.h
@@ -56,8 +56,8 @@
   // Enables or disables a feature by its string identifier from
   // Source/platform/RuntimeEnabledFeatures.in.
   // Note: We use std::string instead of WebString because this API can
-  // be called before blink::initalize(). We can't create WebString objects
-  // before blink::initialize().
+  // be called before blink::Initalize(). We can't create WebString objects
+  // before blink::Initialize().
   BLINK_PLATFORM_EXPORT static void EnableFeatureFromString(
       const std::string& name,
       bool enable);
diff --git a/third_party/WebKit/public/platform/WebSecurityOrigin.h b/third_party/WebKit/public/platform/WebSecurityOrigin.h
index 0cdb76a..93c0aa4fde 100644
--- a/third_party/WebKit/public/platform/WebSecurityOrigin.h
+++ b/third_party/WebKit/public/platform/WebSecurityOrigin.h
@@ -71,7 +71,7 @@
   BLINK_PLATFORM_EXPORT WebString Host() const;
   BLINK_PLATFORM_EXPORT unsigned short Port() const;
 
-  // |port()| will return 0 if the port is the default for an origin. This
+  // |Port()| will return 0 if the port is the default for an origin. This
   // method instead returns the effective port, even if it is the default port
   // (e.g. "http" => 80).
   BLINK_PLATFORM_EXPORT unsigned short EffectivePort() const;
diff --git a/third_party/WebKit/public/platform/WebSourceBuffer.h b/third_party/WebKit/public/platform/WebSourceBuffer.h
index e9c7a68..ddb1db4 100644
--- a/third_party/WebKit/public/platform/WebSourceBuffer.h
+++ b/third_party/WebKit/public/platform/WebSourceBuffer.h
@@ -58,16 +58,16 @@
   virtual double HighestPresentationTimestamp() = 0;
 
   // Run coded frame eviction/garbage collection algorithm.
-  // |currentPlaybackTime| is HTMLMediaElement::currentTime. The algorithm
+  // |current_playback_time| is HTMLMediaElement::currentTime. The algorithm
   // will try to preserve data around current playback position.
-  // |newDataSize| is size of new data about to be appended to SourceBuffer.
+  // |new_data_size| is size of new data about to be appended to SourceBuffer.
   // Could be zero for appendStream if stream size is unknown in advance.
   // Returns false if buffer is still full after eviction.
   virtual bool EvictCodedFrames(double current_playback_time,
                                 size_t new_data_size) = 0;
 
   // Appends data and runs the segment parser loop algorithm.
-  // The algorithm may update |*timestampOffset| if |timestampOffset| is not
+  // The algorithm may update |*timestamp_offset| if |timestamp_offset| is not
   // null.
   // Returns true on success, otherwise the append error algorithm needs to
   // run with the decode error parameter set to true.
@@ -86,7 +86,7 @@
   virtual void SetAppendWindowEnd(double) = 0;
 
   // After this method is called, this WebSourceBuffer should never use the
-  // client pointer passed to setClient().
+  // client pointer passed to SetClient().
   virtual void RemovedFromMediaSource() = 0;
 };
 
diff --git a/third_party/WebKit/public/platform/WebStorageArea.h b/third_party/WebKit/public/platform/WebStorageArea.h
index c6643402..eb4452e 100644
--- a/third_party/WebKit/public/platform/WebStorageArea.h
+++ b/third_party/WebKit/public/platform/WebStorageArea.h
@@ -52,7 +52,7 @@
   virtual unsigned length() = 0;
 
   // Get a value for a specific key. Valid key indices are 0 through
-  // length() - 1.  Indexes may change on any set/removeItem call. Will return
+  // length() - 1.  Indexes may change on any Set/RemoveItem call. Will return
   // null if the index provided is out of range.
   virtual WebString Key(unsigned index) = 0;
 
@@ -62,7 +62,7 @@
 
   // Set the value that corresponds to a specific key. Result will either be
   // ResultOK or some particular error. The value is NOT set when there's an
-  // error.  |pageUrl| is the url that should be used if a storage event fires.
+  // error.  |page_url| is the url that should be used if a storage event fires.
   virtual void SetItem(const WebString& key,
                        const WebString& new_value,
                        const WebURL& page_url,
@@ -71,14 +71,14 @@
     SetItem(key, new_value, page_url, result, unused);
   }
 
-  // Remove the value associated with a particular key. |pageUrl| is the url
+  // Remove the value associated with a particular key. |page_url| is the url
   // that should be used if a storage event fires.
   virtual void RemoveItem(const WebString& key, const WebURL& page_url) {
     WebString unused;
     RemoveItem(key, page_url, unused);
   }
 
-  // Clear all key/value pairs. |pageUrl| is the url that should be used if a
+  // Clear all key/value pairs. |page_url| is the url that should be used if a
   // storage event fires.
   virtual void Clear(const WebURL& page_url) {
     bool unused;
@@ -86,7 +86,7 @@
   }
 
   // DEPRECATED - being replaced by the async variants above which do not return
-  // oldValues or block until completion.
+  // old_values or block until completion.
   virtual void SetItem(const WebString& key,
                        const WebString& new_value,
                        const WebURL&,
diff --git a/third_party/WebKit/public/platform/WebStorageQuotaCallbacks.h b/third_party/WebKit/public/platform/WebStorageQuotaCallbacks.h
index c5ef8d8..7692ce0 100644
--- a/third_party/WebKit/public/platform/WebStorageQuotaCallbacks.h
+++ b/third_party/WebKit/public/platform/WebStorageQuotaCallbacks.h
@@ -56,12 +56,12 @@
   BLINK_PLATFORM_EXPORT WebStorageQuotaCallbacks(StorageQuotaCallbacks*);
 #endif
 
-  // Callback for WebFrameClient::queryStorageUsageAndQuota.
+  // Callback for Platform::QueryStorageUsageAndQuota.
   BLINK_PLATFORM_EXPORT void DidQueryStorageUsageAndQuota(
       unsigned long long usage_in_bytes,
       unsigned long long quota_in_bytes);
 
-  // Callback for WebFrameClient::requestStorageQuota.
+  // Callback for WebFrameClient::RequestStorageQuota.
   // This may return a smaller amount of quota than the requested.
   BLINK_PLATFORM_EXPORT void DidGrantStorageQuota(
       unsigned long long usage_in_bytes,
diff --git a/third_party/WebKit/public/platform/WebString.h b/third_party/WebKit/public/platform/WebString.h
index dd1f249..7e9312a 100644
--- a/third_party/WebKit/public/platform/WebString.h
+++ b/third_party/WebKit/public/platform/WebString.h
@@ -51,24 +51,24 @@
 // Use either one of static methods to convert ASCII, Latin1, UTF-8 or
 // UTF-16 string into WebString:
 //
-// * WebString::fromASCII(const std::string& ascii)
-// * WebString::fromLatin1(const std::string& latin1)
-// * WebString::fromUTF8(const std::string& utf8)
-// * WebString::fromUTF16(const base::string16& utf16)
-// * WebString::fromUTF16(const base::NullableString16& utf16)
+// * WebString::FromASCII(const std::string& ascii)
+// * WebString::FromLatin1(const std::string& latin1)
+// * WebString::FromUTF8(const std::string& utf8)
+// * WebString::FromUTF16(const base::string16& utf16)
+// * WebString::FromUTF16(const base::NullableString16& utf16)
 //
 // Similarly, use either of following methods to convert WebString to
 // ASCII, Latin1, UTF-8 or UTF-16:
 //
-// * webstring.ascii()
-// * webstring.latin1()
-// * webstring.utf8()
-// * webstring.utf16()
+// * webstring.Ascii()
+// * webstring.Latin1()
+// * webstring.Utf8()
+// * webstring.Utf16()
 // * WebString::toNullableString16(webstring)
 //
 // Note that if you need to convert the UTF8 string converted from WebString
-// back to WebString with fromUTF8() you may want to specify Strict
-// UTF8ConversionMode when you call utf8(), as fromUTF8 rejects strings
+// back to WebString with FromUTF8() you may want to specify Strict
+// UTF8ConversionMode when you call Utf8(), as FromUTF8 rejects strings
 // with invalid UTF8 characters.
 //
 // Some types like GURL and base::FilePath can directly take either utf-8 or
@@ -161,7 +161,7 @@
   // Use this rather than calling base::IsStringASCII().
   BLINK_PLATFORM_EXPORT bool ContainsOnlyASCII() const;
 
-  // Does same as fromLatin1 but asserts if the given string has non-ascii char.
+  // Does same as FromLatin1 but asserts if the given string has non-ascii char.
   BLINK_PLATFORM_EXPORT static WebString FromASCII(const std::string&);
 
   template <int N>
diff --git a/third_party/WebKit/public/platform/WebThread.h b/third_party/WebKit/public/platform/WebThread.h
index 6eaf71c9..1815f046 100644
--- a/third_party/WebKit/public/platform/WebThread.h
+++ b/third_party/WebKit/public/platform/WebThread.h
@@ -70,7 +70,7 @@
   //
   // Default scheduler task queue does not give scheduler enough freedom to
   // manage task priorities and should not be used.
-  // Use TaskRunnerHelper::get instead (crbug.com/624696).
+  // Use TaskRunnerHelper::Get instead (crbug.com/624696).
   virtual WebTaskRunner* GetWebTaskRunner() { return nullptr; }
   base::SingleThreadTaskRunner* GetSingleThreadTaskRunner();
 
diff --git a/third_party/WebKit/public/platform/WebTouchEvent.h b/third_party/WebKit/public/platform/WebTouchEvent.h
index 96c64aa..2ac73c8 100644
--- a/third_party/WebKit/public/platform/WebTouchEvent.h
+++ b/third_party/WebKit/public/platform/WebTouchEvent.h
@@ -54,8 +54,8 @@
 
 #if INSIDE_BLINK
 
-  // Sets any scaled values to be their computed values and sets |frameScale|
-  // back to 1 and |translateX|, |translateY| back to 0.
+  // Sets any scaled values to be their computed values and sets |frame_scale_|
+  // back to 1 and |frame_translate_| X and Y coordinates back to 0.
   BLINK_PLATFORM_EXPORT WebTouchEvent FlattenTransform() const;
 
   // Return a scaled WebTouchPoint in root frame coordinates.
diff --git a/third_party/WebKit/public/platform/WebTrialTokenValidator.h b/third_party/WebKit/public/platform/WebTrialTokenValidator.h
index 96cd007b..15cfc9d 100644
--- a/third_party/WebKit/public/platform/WebTrialTokenValidator.h
+++ b/third_party/WebKit/public/platform/WebTrialTokenValidator.h
@@ -26,7 +26,7 @@
 
   // Returns whether the given token is valid for the specified origin. If the
   // token is valid, it also returns the feature the token is valid for in
-  // |*featureName|.
+  // |*feature_name|.
   virtual WebOriginTrialTokenStatus ValidateToken(const WebString& token,
                                                   const WebSecurityOrigin&,
                                                   WebString* feature_name) = 0;
diff --git a/third_party/WebKit/public/platform/WebURLLoaderClient.h b/third_party/WebKit/public/platform/WebURLLoaderClient.h
index b241a5618..955cbdca 100644
--- a/third_party/WebKit/public/platform/WebURLLoaderClient.h
+++ b/third_party/WebKit/public/platform/WebURLLoaderClient.h
@@ -79,18 +79,18 @@
   }
 
   // Called when a chunk of response data is downloaded. This is only called
-  // if WebURLRequest's downloadToFile flag was set to true.
+  // if WebURLRequest's DownloadToFile flag was set to true.
   virtual void DidDownloadData(int data_length, int encoded_data_length) {}
 
-  // Called when a chunk of response data is received. |dataLength| is the
-  // number of bytes pointed to by |data|. |encodedDataLength| is the number
+  // Called when a chunk of response data is received. |data_length| is the
+  // number of bytes pointed to by |data|. |encoded_data_length| is the number
   // of bytes actually received from network to serve this chunk, including
   // HTTP headers and framing if relevant. It is 0 if the response was served
   // from cache, and -1 if this information is unavailable.
   virtual void DidReceiveData(const char* data, int data_length) {}
 
   // Called when the number of bytes actually received from network including
-  // HTTP headers is updated. |transferSizeDiff| is positive.
+  // HTTP headers is updated. |transfer_size_diff| is positive.
   virtual void DidReceiveTransferSizeUpdate(int transfer_size_diff) {}
 
   // Called when a chunk of renderer-generated metadata is received from the
@@ -98,20 +98,20 @@
   virtual void DidReceiveCachedMetadata(const char* data, int data_length) {}
 
   // Called when the load completes successfully.
-  // |totalEncodedDataLength| may be equal to kUnknownEncodedDataLength.
+  // |total_encoded_data_length| may be equal to kUnknownEncodedDataLength.
   virtual void DidFinishLoading(double finish_time,
                                 int64_t total_encoded_data_length,
                                 int64_t total_encoded_body_length,
                                 int64_t total_decoded_body_length) {}
 
   // Called when the load completes with an error.
-  // |totalEncodedDataLength| may be equal to kUnknownEncodedDataLength.
+  // |total_encoded_data_length| may be equal to kUnknownEncodedDataLength.
   virtual void DidFail(const WebURLError&,
                        int64_t total_encoded_data_length,
                        int64_t total_encoded_body_length,
                        int64_t total_decoded_body_length) {}
 
-  // Value passed to didFinishLoading when total encoded data length isn't
+  // Value passed to DidFinishLoading when total encoded data length isn't
   // known.
   static const int64_t kUnknownEncodedDataLength = -1;
 
diff --git a/third_party/WebKit/public/platform/WebURLLoaderTestDelegate.h b/third_party/WebKit/public/platform/WebURLLoaderTestDelegate.h
index 7b979b7..68a2e27 100644
--- a/third_party/WebKit/public/platform/WebURLLoaderTestDelegate.h
+++ b/third_party/WebKit/public/platform/WebURLLoaderTestDelegate.h
@@ -13,7 +13,7 @@
 class WebURLLoaderClient;
 struct WebURLError;
 
-// Use with WebUnitTestSupport::setLoaderDelegate to intercept calls to a
+// Use with WebURLLoaderMockFactory::SetLoaderDelegate to intercept calls to a
 // WebURLLoaderClient for controlling network responses in a test. Default
 // implementations of all methods just call the original method on the
 // WebURLLoaderClient.
diff --git a/third_party/WebKit/public/platform/WebURLRequest.h b/third_party/WebKit/public/platform/WebURLRequest.h
index bc536c1..fa00b59 100644
--- a/third_party/WebKit/public/platform/WebURLRequest.h
+++ b/third_party/WebKit/public/platform/WebURLRequest.h
@@ -225,7 +225,7 @@
 
   BLINK_PLATFORM_EXPORT WebString HttpHeaderField(const WebString& name) const;
   // It's not possible to set the referrer header using this method. Use
-  // setHTTPReferrer instead.
+  // SetHTTPReferrer instead.
   BLINK_PLATFORM_EXPORT void SetHTTPHeaderField(const WebString& name,
                                                 const WebString& value);
   BLINK_PLATFORM_EXPORT void SetHTTPReferrer(const WebString& referrer,
@@ -282,7 +282,7 @@
   BLINK_PLATFORM_EXPORT void SetAppCacheHostID(int);
 
   // If true, the response body will be downloaded to a file managed by the
-  // WebURLLoader. See WebURLResponse::downloadedFilePath.
+  // WebURLLoader. See WebURLResponse::DownloadFilePath.
   BLINK_PLATFORM_EXPORT bool DownloadToFile() const;
   BLINK_PLATFORM_EXPORT void SetDownloadToFile(bool);
 
@@ -375,15 +375,15 @@
 
  protected:
   // Permit subclasses to set arbitrary ResourceRequest pointer as
-  // |m_resourceRequest|. |m_ownedResourceRequest| is not set in this case.
+  // |resource_request_|. |owned_resource_request_| is not set in this case.
   BLINK_PLATFORM_EXPORT explicit WebURLRequest(ResourceRequest&);
 #endif
 
  private:
   struct ResourceRequestContainer;
 
-  // If this instance owns a ResourceRequest then |m_ownedResourceRequest|
-  // is non-null and |m_resourceRequest| points to the ResourceRequest
+  // If this instance owns a ResourceRequest then |owned_resource_request_|
+  // is non-null and |resource_request_| points to the ResourceRequest
   // instance it contains.
   std::unique_ptr<ResourceRequestContainer> owned_resource_request_;
 
diff --git a/third_party/WebKit/public/platform/WebURLResponse.h b/third_party/WebKit/public/platform/WebURLResponse.h
index 489a8c2..1473594b 100644
--- a/third_party/WebKit/public/platform/WebURLResponse.h
+++ b/third_party/WebKit/public/platform/WebURLResponse.h
@@ -298,15 +298,15 @@
 #if INSIDE_BLINK
  protected:
   // Permit subclasses to set arbitrary ResourceResponse pointer as
-  // |m_resourceResponse|. |m_ownedResourceResponse| is not set in this case.
+  // |resource_response_|. |owned_resource_response_| is not set in this case.
   BLINK_PLATFORM_EXPORT explicit WebURLResponse(ResourceResponse&);
 #endif
 
  private:
   struct ResourceResponseContainer;
 
-  // If this instance owns a ResourceResponse then |m_ownedResourceResponse|
-  // is non-null and |m_resourceResponse| points to the ResourceResponse
+  // If this instance owns a ResourceResponse then |owned_resource_response_|
+  // is non-null and |resource_response_| points to the ResourceResponse
   // instance it contains.
   std::unique_ptr<ResourceResponseContainer> owned_resource_response_;
 
diff --git a/third_party/WebKit/public/platform/WebVector.h b/third_party/WebKit/public/platform/WebVector.h
index 1e53e71..6fa6056 100644
--- a/third_party/WebKit/public/platform/WebVector.h
+++ b/third_party/WebKit/public/platform/WebVector.h
@@ -112,7 +112,7 @@
 
   size_t size() const { return data_.size(); }
   bool empty() const { return data_.empty(); }
-  // TODO(slangley): Remove all uses of isEmpty.
+  // TODO(slangley): Remove all uses of IsEmpty.
   bool IsEmpty() const { return empty(); }
 
   T& operator[](size_t i) {
diff --git a/tools/gn/desc_builder.cc b/tools/gn/desc_builder.cc
index 965ec92..bcf4dc6 100644
--- a/tools/gn/desc_builder.cc
+++ b/tools/gn/desc_builder.cc
@@ -273,13 +273,12 @@
                                    target_->visibility().AsValue());
 
     if (what(variables::kTestonly))
-      res->SetBooleanWithoutPathExpansion(variables::kTestonly,
-                                          target_->testonly());
+      res->SetKey(variables::kTestonly, base::Value(target_->testonly()));
 
     if (is_binary_output) {
       if (what(variables::kCheckIncludes))
-        res->SetBooleanWithoutPathExpansion(variables::kCheckIncludes,
-                                            target_->check_includes());
+        res->SetKey(variables::kCheckIncludes,
+                    base::Value(target_->check_includes()));
 
       if (what(variables::kAllowCircularIncludesFrom)) {
         auto labels = base::MakeUnique<base::ListValue>();
diff --git a/tools/ipc_fuzzer/fuzzer/fuzzer.cc b/tools/ipc_fuzzer/fuzzer/fuzzer.cc
index 64056b0b..5581c1dc 100644
--- a/tools/ipc_fuzzer/fuzzer/fuzzer.cc
+++ b/tools/ipc_fuzzer/fuzzer/fuzzer.cc
@@ -590,7 +590,7 @@
         case base::Value::Type::BOOLEAN: {
           bool tmp;
           fuzzer->FuzzBool(&tmp);
-          p->SetBooleanWithoutPathExpansion(property, tmp);
+          p->SetKey(property, base::Value(tmp));
           break;
         }
         case base::Value::Type::INTEGER: {
diff --git a/tools/ipc_fuzzer/ipc_fuzzer.gni b/tools/ipc_fuzzer/ipc_fuzzer.gni
index f4f41ac5..492bc50 100644
--- a/tools/ipc_fuzzer/ipc_fuzzer.gni
+++ b/tools/ipc_fuzzer/ipc_fuzzer.gni
@@ -5,6 +5,7 @@
 import("//build/config/chrome_build.gni")
 import("//build/config/chromecast_build.gni")
 import("//build/config/sanitizers/sanitizers.gni")
+import("//build/config/ui.gni")
 
 declare_args() {
   # Build IPC fuzzer by default if it's a supported configuration. For
@@ -12,5 +13,5 @@
   # (especially MSan).
   enable_ipc_fuzzer =
       is_clang && !is_component_build && !is_official_build && !is_chromecast &&
-      !using_sanitizer && (is_linux || is_mac || is_win)
+      !using_sanitizer && (is_linux || is_mac || is_win) && !use_ozone
 }
diff --git a/tools/json_schema_compiler/test/simple_api_unittest.cc b/tools/json_schema_compiler/test/simple_api_unittest.cc
index ef6f9e20..7a37dfb 100644
--- a/tools/json_schema_compiler/test/simple_api_unittest.cc
+++ b/tools/json_schema_compiler/test/simple_api_unittest.cc
@@ -17,7 +17,7 @@
   value->SetDoubleWithoutPathExpansion("number", 1.1);
   value->SetIntegerWithoutPathExpansion("integer", 4);
   value->SetStringWithoutPathExpansion("string", "bling");
-  value->SetBooleanWithoutPathExpansion("boolean", true);
+  value->SetKey("boolean", base::Value(true));
   return value;
 }
 
diff --git a/tools/metrics/histograms/histograms.xml b/tools/metrics/histograms/histograms.xml
index dd73292d..3a1426f 100644
--- a/tools/metrics/histograms/histograms.xml
+++ b/tools/metrics/histograms/histograms.xml
@@ -54434,6 +54434,9 @@
 </histogram>
 
 <histogram name="Pepper.SecureOrigin.MediaStreamRequest" enum="BooleanSecure">
+  <obsolete>
+    Deprecated as of 8/2017.
+  </obsolete>
   <owner>raymes@chromium.org</owner>
   <summary>
     Whether a Pepper media stream request (mic/cam access) comes from a plugin
@@ -90966,7 +90969,10 @@
 <histogram_suffixes name="CompositorPendingTreeType" separator=".">
   <suffix name="Main" label="Commit initiated pending tree"/>
   <suffix name="Impl" label="Impl side invalidation initiated pending tree"/>
-  <affected-histogram name="Scheduling.ReadyToActivateToActivationDuration2"/>
+  <affected-histogram
+      name="Scheduling.Browser.ReadyToActivateToActivationDuration2"/>
+  <affected-histogram
+      name="Scheduling.Renderer.ReadyToActivateToActivationDuration2"/>
 </histogram_suffixes>
 
 <histogram_suffixes name="CompositorTimingHistoryProcess" separator="."
diff --git a/tools/perf/benchmarks/rasterize_and_record_micro.py b/tools/perf/benchmarks/rasterize_and_record_micro.py
index c9e2e25d..77db426 100644
--- a/tools/perf/benchmarks/rasterize_and_record_micro.py
+++ b/tools/perf/benchmarks/rasterize_and_record_micro.py
@@ -6,7 +6,6 @@
 
 from measurements import rasterize_and_record_micro
 import page_sets
-from telemetry import benchmark
 from telemetry import story
 
 
@@ -44,10 +43,6 @@
         options.record_repeat, options.timeout, options.report_detailed_results)
 
 
-# RasterizeAndRecord disabled on mac because of crbug.com/350684.
-# RasterizeAndRecord disabled on windows because of crbug.com/338057.
-@benchmark.Disabled('mac', 'win',
-                    'android')  # http://crbug.com/610018
 class RasterizeAndRecordMicroTop25(_RasterizeAndRecordMicro):
   """Measures rasterize and record performance on the top 25 web pages.
 
@@ -69,10 +64,6 @@
     return StoryExpectations()
 
 
-
-# New benchmark only enabled on Linux until we've observed behavior for a
-# reasonable period of time.
-@benchmark.Disabled('mac', 'win', 'android')
 class RasterizeAndRecordMicroPartialInvalidation(_RasterizeAndRecordMicro):
   """Measures rasterize and record performance for partial inval. on big pages.
 
diff --git a/tools/perf/benchmarks/smoothness.py b/tools/perf/benchmarks/smoothness.py
index c7d8b466..c299cc2 100644
--- a/tools/perf/benchmarks/smoothness.py
+++ b/tools/perf/benchmarks/smoothness.py
@@ -500,7 +500,9 @@
     return StoryExpectations()
 
 
-@benchmark.Enabled('android')
+# This benchmark runs only on android, but is disabled because the page set
+# uses deprecated web platform features.  See http://crbug.com/750876
+@benchmark.Disabled('all')
 @benchmark.Owner(emails=['vmiura@chromium.org'])
 class SmoothnessGpuRasterizationPolymer(_Smoothness):
   """Measures rendering statistics for the Polymer cases with GPU rasterization.
diff --git a/tools/perf/benchmarks/thread_times.py b/tools/perf/benchmarks/thread_times.py
index 6afc3681..177ef4d 100644
--- a/tools/perf/benchmarks/thread_times.py
+++ b/tools/perf/benchmarks/thread_times.py
@@ -48,7 +48,10 @@
     return page_sets.KeySilkCasesStoryExpectations()
 
 
-@benchmark.Enabled('android', 'linux')
+# This benchmark runs only on android & linux, but is disabled because the page
+# set uses deprecated web platform features.  See http://crbug.com/750876
+# @benchmark.Enabled('android', 'linux')
+@benchmark.Disabled('all')
 class ThreadTimesKeyHitTestCases(_ThreadTimes):
   """Measure timeline metrics while performing smoothness action on key hit
   testing cases."""
diff --git a/ui/app_list/views/app_list_view.cc b/ui/app_list/views/app_list_view.cc
index ed7165d..d0dbc50 100644
--- a/ui/app_list/views/app_list_view.cc
+++ b/ui/app_list/views/app_list_view.cc
@@ -490,16 +490,14 @@
   // Update the bounds of the widget while maintaining the
   // relative position of the top of the widget and the mouse/gesture.
   // Block drags north of 0 and recalculate the initial_drag_point_.
-  int const new_y_position = location.y() - initial_drag_point_.y() +
-                             fullscreen_widget_->GetWindowBoundsInScreen().y();
-  gfx::Rect new_widget_bounds = fullscreen_widget_->GetWindowBoundsInScreen();
-  if (new_y_position < 0) {
-    new_widget_bounds.set_y(0);
+  int new_y_position = location.y() - initial_drag_point_.y() +
+                       fullscreen_widget_->GetWindowBoundsInScreen().y();
+  if (new_y_position < 0)
     initial_drag_point_ = location;
-  } else {
-    new_widget_bounds.set_y(new_y_position);
-  }
-  fullscreen_widget_->SetBounds(new_widget_bounds);
+
+  UpdateYPositionAndOpacity(new_y_position,
+                            GetAppListBackgroundOpacityDuringDragging(),
+                            false /* is_end_gesture */);
 }
 
 void AppListView::EndDrag(const gfx::Point& location) {
@@ -507,6 +505,8 @@
   if (app_list_state_ == CLOSED)
     return;
 
+  // Restores opacity of all the items in app list if dragging ends.
+  UpdateOpacity(kAppListOpacity, true /* is_end_gesture */);
   // Change the app list state based on where the drag ended. If fling velocity
   // was over the threshold, snap to the next state in the direction of the
   // fling.
@@ -972,13 +972,7 @@
   new_widget_bounds.set_y(std::max(y_position_in_screen, 0));
   fullscreen_widget_->SetBounds(new_widget_bounds);
 
-  app_list_background_shield_->layer()->SetOpacity(background_opacity);
-  gfx::Rect work_area_bounds = fullscreen_widget_->GetWorkAreaBoundsInScreen();
-  search_box_view_->UpdateOpacity(work_area_bounds.bottom(), is_end_gesture);
-  app_list_main_view_->contents_view()
-      ->apps_container_view()
-      ->apps_grid_view()
-      ->UpdateOpacity(work_area_bounds.bottom(), is_end_gesture);
+  UpdateOpacity(background_opacity, is_end_gesture);
 }
 
 PaginationModel* AppListView::GetAppsPaginationModel() {
@@ -1072,4 +1066,30 @@
   SetState(app_list_state_);
 }
 
+void AppListView::UpdateOpacity(float background_opacity, bool is_end_gesture) {
+  app_list_background_shield_->layer()->SetOpacity(background_opacity);
+  gfx::Rect work_area_bounds = fullscreen_widget_->GetWorkAreaBoundsInScreen();
+  search_box_view_->UpdateOpacity(work_area_bounds.bottom(), is_end_gesture);
+  app_list_main_view_->contents_view()
+      ->apps_container_view()
+      ->apps_grid_view()
+      ->UpdateOpacity(work_area_bounds.bottom(), is_end_gesture);
+
+  if (app_list_state_ == PEEKING) {
+    app_list_main_view_->contents_view()->start_page_view()->UpdateOpacity(
+        work_area_bounds.bottom(), is_end_gesture);
+  }
+}
+
+float AppListView::GetAppListBackgroundOpacityDuringDragging() {
+  float top_of_applist = fullscreen_widget_->GetWindowBoundsInScreen().y();
+  float work_area_bottom =
+      fullscreen_widget_->GetWorkAreaBoundsInScreen().bottom();
+
+  float dragging_height = std::max((work_area_bottom - top_of_applist), 0.f);
+  float coefficient =
+      std::min(dragging_height / (kNumOfShelfSize * kShelfSize), 1.0f);
+  return coefficient * kAppListOpacity;
+}
+
 }  // namespace app_list
diff --git a/ui/app_list/views/app_list_view.h b/ui/app_list/views/app_list_view.h
index 090b417..f13eddc9 100644
--- a/ui/app_list/views/app_list_view.h
+++ b/ui/app_list/views/app_list_view.h
@@ -224,6 +224,12 @@
   void OnDisplayMetricsChanged(const display::Display& display,
                                uint32_t changed_metrics) override;
 
+  // Updates opacity of both background and items in the app list.
+  void UpdateOpacity(float background_opacity, bool is_end_gesture);
+
+  // Gets app list background opacity during dragging.
+  float GetAppListBackgroundOpacityDuringDragging();
+
   AppListViewDelegate* delegate_;  // Weak. Owned by AppListService.
 
   AppListMainView* app_list_main_view_;
diff --git a/ui/app_list/views/apps_grid_view.cc b/ui/app_list/views/apps_grid_view.cc
index 6a56f21..c34e623 100644
--- a/ui/app_list/views/apps_grid_view.cc
+++ b/ui/app_list/views/apps_grid_view.cc
@@ -1739,13 +1739,10 @@
   UpdateOpacityOfItem(all_apps_indicator_,
                       all_apps_indicator_bounds.CenterPoint().y());
 
-  // Updates the opacity of the apps in the first page.
+  // Updates the opacity of all apps.
   for (int i = 0; i < view_model_.view_size(); ++i) {
     AppListItemView* item_view = GetItemViewAt(i);
     if (item_view != drag_view_) {
-      Index index = GetIndexOfView(item_view);
-      if (index.page != 0)
-        break;
       gfx::Rect view_bounds = view_model_.ideal_bounds(i);
       views::View::ConvertRectToScreen(this, &view_bounds);
       UpdateOpacityOfItem(item_view, view_bounds.CenterPoint().y());
diff --git a/ui/app_list/views/expand_arrow_view.cc b/ui/app_list/views/expand_arrow_view.cc
index b69c81e..9a1be87 100644
--- a/ui/app_list/views/expand_arrow_view.cc
+++ b/ui/app_list/views/expand_arrow_view.cc
@@ -40,6 +40,9 @@
     : views::CustomButton(this),
       contents_view_(contents_view),
       app_list_view_(app_list_view) {
+  SetPaintToLayer();
+  layer()->SetFillsBoundsOpaquely(false);
+
   icon_ = new views::ImageView;
   icon_->SetVerticalAlignment(views::ImageView::CENTER);
   icon_->SetImage(gfx::CreateVectorIcon(kIcArrowUpIcon, kExpandArrowIconSize,
diff --git a/ui/app_list/views/start_page_view.cc b/ui/app_list/views/start_page_view.cc
index 14e487f..d5a7711 100644
--- a/ui/app_list/views/start_page_view.cc
+++ b/ui/app_list/views/start_page_view.cc
@@ -479,8 +479,39 @@
   return selected_index >= 0 ? selected_index : kNoSelection;
 }
 
+void StartPageView::UpdateOpacity(float work_area_bottom, bool is_end_gesture) {
+  work_area_bottom_ = work_area_bottom;
+  is_end_gesture_ = is_end_gesture;
+
+  // Updates opacity of suggested apps indicator.
+  gfx::Rect indicator_bounds = indicator_->GetLabelBoundsInScreen();
+  UpdateOpacityOfItem(indicator_, indicator_bounds.CenterPoint().y());
+
+  // Updates opacity of suggested apps.
+  const std::vector<SearchResultTileItemView*>& suggested_apps =
+      suggestions_container_->tile_views();
+  gfx::Rect suggested_app_bounds;
+  for (auto* suggested_app : suggested_apps) {
+    suggested_app_bounds = suggested_app->GetBoundsInScreen();
+    UpdateOpacityOfItem(suggested_app, suggested_app_bounds.CenterPoint().y());
+  }
+
+  // Updates opacity of expand arrow.
+  gfx::Rect expand_arrow_bounds = expand_arrow_view_->GetBoundsInScreen();
+  UpdateOpacityOfItem(expand_arrow_view_,
+                      expand_arrow_bounds.CenterPoint().y());
+}
+
 TileItemView* StartPageView::GetTileItemView(size_t index) {
   return suggestions_container_->GetTileItemView(index);
 }
 
+void StartPageView::UpdateOpacityOfItem(views::View* view_item,
+                                        float centroid_y) {
+  float delta_y = std::max(work_area_bottom_ - centroid_y, 0.f);
+  float opacity = std::min(
+      delta_y / (AppListView::kNumOfShelfSize * AppListView::kShelfSize), 1.0f);
+  view_item->layer()->SetOpacity(is_end_gesture_ ? 1.0f : opacity);
+}
+
 }  // namespace app_list
diff --git a/ui/app_list/views/start_page_view.h b/ui/app_list/views/start_page_view.h
index 9cddd36..d1d4ddd 100644
--- a/ui/app_list/views/start_page_view.h
+++ b/ui/app_list/views/start_page_view.h
@@ -63,6 +63,9 @@
   // the selected index in suggestions container view.
   int GetSelectedIndexForTest() const;
 
+  // Updates the opacity of the items in start page during dragging.
+  void UpdateOpacity(float work_area_bottom, bool is_end_gesture);
+
  private:
   void InitInstantContainer();
 
@@ -70,6 +73,9 @@
 
   void SetCustomLauncherPageSelected(bool selected);
 
+  // Updates opacity of |view_item| in the start page based on |centroid_y|.
+  void UpdateOpacityOfItem(views::View* view_item, float centroid_y);
+
   TileItemView* GetTileItemView(size_t index);
 
   AppListView* app_list_view_;
@@ -94,6 +100,12 @@
 
   const bool is_fullscreen_app_list_enabled_;
 
+  // The bottom of work area.
+  float work_area_bottom_ = 0.f;
+
+  // True if it is the end gesture of dragging.
+  bool is_end_gesture_ = false;
+
   DISALLOW_COPY_AND_ASSIGN(StartPageView);
 };
 
diff --git a/ui/aura/BUILD.gn b/ui/aura/BUILD.gn
index 6d67370..8677c428 100644
--- a/ui/aura/BUILD.gn
+++ b/ui/aura/BUILD.gn
@@ -44,6 +44,7 @@
     "mus/focus_synchronizer.h",
     "mus/focus_synchronizer_delegate.h",
     "mus/focus_synchronizer_observer.h",
+    "mus/hit_test_data_provider_aura.h",
     "mus/in_flight_change.h",
     "mus/input_method_mus.h",
     "mus/mus_context_factory.h",
@@ -106,6 +107,7 @@
     "mus/client_surface_embedder.cc",
     "mus/drag_drop_controller_mus.cc",
     "mus/focus_synchronizer.cc",
+    "mus/hit_test_data_provider_aura.cc",
     "mus/in_flight_change.cc",
     "mus/input_method_mus.cc",
     "mus/mus_context_factory.cc",
@@ -336,6 +338,7 @@
   sources = [
     "gestures/gesture_recognizer_unittest.cc",
     "mus/drag_drop_controller_mus_unittest.cc",
+    "mus/hit_test_data_provider_aura_unittest.cc",
     "mus/input_method_mus_unittest.cc",
     "mus/os_exchange_data_provider_mus_unittest.cc",
     "mus/property_converter_unittest.cc",
@@ -352,6 +355,7 @@
   deps = [
     ":test_support",
     "//base/test:test_support",
+    "//components/viz/client",
     "//mojo/common",
     "//mojo/edk/system",
     "//net",
diff --git a/ui/aura/mus/hit_test_data_provider_aura.cc b/ui/aura/mus/hit_test_data_provider_aura.cc
new file mode 100644
index 0000000..eab1156
--- /dev/null
+++ b/ui/aura/mus/hit_test_data_provider_aura.cc
@@ -0,0 +1,89 @@
+// Copyright 2017 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.
+
+#include "ui/aura/mus/hit_test_data_provider_aura.h"
+
+#include "base/containers/adapters.h"
+#include "ui/aura/mus/window_port_mus.h"
+#include "ui/aura/window.h"
+#include "ui/aura/window_targeter.h"
+
+namespace aura {
+
+HitTestDataProviderAura::HitTestDataProviderAura(aura::Window* window)
+    : window_(window) {}
+
+HitTestDataProviderAura::~HitTestDataProviderAura() {}
+
+viz::mojom::HitTestRegionListPtr HitTestDataProviderAura::GetHitTestData()
+    const {
+  auto hit_test_region_list = viz::mojom::HitTestRegionList::New();
+  GetHitTestDataRecursively(window_, hit_test_region_list.get());
+  return hit_test_region_list;
+}
+
+void HitTestDataProviderAura::GetHitTestDataRecursively(
+    aura::Window* window,
+    viz::mojom::HitTestRegionList* hit_test_region_list) const {
+  WindowTargeter* targeter =
+      static_cast<WindowTargeter*>(window->GetEventTargeter());
+
+  // Walk the children in Z-order (reversed order of children()) to produce
+  // the hit-test data. Each child's hit test data is added before the hit-test
+  // data from the child's descendants because the child could clip its
+  // descendants for the purpose of event handling.
+  for (aura::Window* child : base::Reversed(window->children())) {
+    const ui::mojom::EventTargetingPolicy event_targeting_policy =
+        child->event_targeting_policy();
+    if (event_targeting_policy == ui::mojom::EventTargetingPolicy::NONE)
+      continue;
+    if (event_targeting_policy !=
+        ui::mojom::EventTargetingPolicy::DESCENDANTS_ONLY) {
+      gfx::Rect rect_mouse(child->bounds());
+      gfx::Rect rect_touch;
+      bool touch_and_mouse_are_same = true;
+      const WindowMus* window_mus = WindowMus::Get(child);
+      const WindowPortMus* window_port = WindowPortMus::Get(child);
+      // TODO(varkha): Use a surface ID for windows that submit their own
+      // compositor frames and a frame sink ID otherwise.
+      viz::SurfaceId surface_id(window_port->frame_sink_id(),
+                                window_mus->GetLocalSurfaceId());
+      uint32_t flags = window_port->client_surface_embedder()
+                           ? viz::mojom::kHitTestChildSurface
+                           : viz::mojom::kHitTestMine;
+      // Use the |targeter| to query for possibly expanded hit-test area.
+      // Use the |child| bounds with mouse and touch flags when there is no
+      // |targeter|.
+      if (targeter &&
+          targeter->GetHitTestRects(child, &rect_mouse, &rect_touch)) {
+        touch_and_mouse_are_same = rect_mouse == rect_touch;
+      }
+      if (!rect_mouse.IsEmpty()) {
+        auto hit_test_region = viz::mojom::HitTestRegion::New();
+        hit_test_region->surface_id = surface_id;
+        hit_test_region->flags =
+            flags | (touch_and_mouse_are_same ? (viz::mojom::kHitTestMouse |
+                                                 viz::mojom::kHitTestTouch)
+                                              : viz::mojom::kHitTestMouse);
+        hit_test_region->rect = rect_mouse;
+        if (child->layer())
+          hit_test_region->transform = child->layer()->transform();
+        hit_test_region_list->regions.push_back(std::move(hit_test_region));
+      }
+      if (!touch_and_mouse_are_same && !rect_touch.IsEmpty()) {
+        auto hit_test_region = viz::mojom::HitTestRegion::New();
+        hit_test_region->surface_id = surface_id;
+        hit_test_region->flags = flags | viz::mojom::kHitTestTouch;
+        hit_test_region->rect = rect_touch;
+        if (child->layer())
+          hit_test_region->transform = child->layer()->transform();
+        hit_test_region_list->regions.push_back(std::move(hit_test_region));
+      }
+    }
+    if (event_targeting_policy != ui::mojom::EventTargetingPolicy::TARGET_ONLY)
+      GetHitTestDataRecursively(child, hit_test_region_list);
+  }
+}
+
+}  // namespace aura
\ No newline at end of file
diff --git a/ui/aura/mus/hit_test_data_provider_aura.h b/ui/aura/mus/hit_test_data_provider_aura.h
new file mode 100644
index 0000000..04b7748
--- /dev/null
+++ b/ui/aura/mus/hit_test_data_provider_aura.h
@@ -0,0 +1,41 @@
+// Copyright 2017 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 UI_AURA_MUS_HIT_TEST_DATA_PROVIDER_AURA_H_
+#define UI_AURA_MUS_HIT_TEST_DATA_PROVIDER_AURA_H_
+
+#include "base/macros.h"
+#include "components/viz/client/hit_test_data_provider.h"
+
+namespace aura {
+
+class Window;
+
+// A HitTestDataProvider that captures hit-test areas from a aura::Window tree
+// and packages it to be submitted to compositor frame sink. The |window| used
+// when creating the HitTestDataProviderAura should outlive the data provider.
+class HitTestDataProviderAura : public viz::HitTestDataProvider {
+ public:
+  explicit HitTestDataProviderAura(Window* window);
+  ~HitTestDataProviderAura() override;
+
+  // HitTestDataProvider:
+  viz::mojom::HitTestRegionListPtr GetHitTestData() const override;
+
+ private:
+  // Recursively walks the children of |window| and uses |window|'s
+  // EventTargeter to generate hit-test data for the |window|'s descendants.
+  // Populates |hit_test_region_list|.
+  void GetHitTestDataRecursively(
+      aura::Window* window,
+      viz::mojom::HitTestRegionList* hit_test_region_list) const;
+
+  aura::Window* const window_ = nullptr;
+
+  DISALLOW_COPY_AND_ASSIGN(HitTestDataProviderAura);
+};
+
+}  // namespace aura
+
+#endif  // UI_AURA_MUS_HIT_TEST_DATA_PROVIDER_AURA_H_
\ No newline at end of file
diff --git a/ui/aura/mus/hit_test_data_provider_aura_unittest.cc b/ui/aura/mus/hit_test_data_provider_aura_unittest.cc
new file mode 100644
index 0000000..609051e
--- /dev/null
+++ b/ui/aura/mus/hit_test_data_provider_aura_unittest.cc
@@ -0,0 +1,181 @@
+// Copyright 2017 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.
+
+#include "ui/aura/mus/window_tree_client.h"
+
+#include "components/viz/client/hit_test_data_provider.h"
+#include "ui/aura/client/aura_constants.h"
+#include "ui/aura/mus/window_mus.h"
+#include "ui/aura/mus/window_port_mus.h"
+#include "ui/aura/test/aura_mus_test_base.h"
+#include "ui/aura/window.h"
+#include "ui/aura/window_targeter.h"
+#include "ui/gfx/geometry/rect.h"
+
+namespace aura {
+
+namespace {
+
+const int kMouseInset = -5;
+const int kTouchInset = -10;
+
+}  // namespace
+
+// Creates a root window and child windows. Maintains a cc:LayerTreeFrameSink
+// to help exercise its viz::HitTestDataProvider.
+class HitTestDataProviderAuraTest : public test::AuraTestBaseMus {
+ public:
+  HitTestDataProviderAuraTest() {}
+  ~HitTestDataProviderAuraTest() override {}
+
+  void SetUp() override {
+    test::AuraTestBaseMus::SetUp();
+
+    root_ = base::MakeUnique<Window>(nullptr);
+    root_->Init(ui::LAYER_NOT_DRAWN);
+    root_->SetEventTargeter(base::MakeUnique<WindowTargeter>());
+    root_->SetBounds(gfx::Rect(0, 0, 300, 200));
+
+    window2_ = new Window(nullptr);
+    window2_->Init(ui::LAYER_TEXTURED);
+    window2_->SetBounds(gfx::Rect(20, 30, 40, 60));
+
+    window3_ = new Window(nullptr);
+    window3_->Init(ui::LAYER_TEXTURED);
+    window3_->SetEventTargeter(base::MakeUnique<WindowTargeter>());
+    window3_->SetBounds(gfx::Rect(50, 60, 100, 40));
+
+    window4_ = new Window(nullptr);
+    window4_->Init(ui::LAYER_TEXTURED);
+    window4_->SetBounds(gfx::Rect(25, 10, 50, 20));
+
+    window3_->AddChild(window4_);
+    root_->AddChild(window2_);
+    root_->AddChild(window3_);
+
+    WindowPort* port = WindowPortMus::Get(root_.get());
+    sink_ = port->CreateLayerTreeFrameSink();
+  }
+
+ protected:
+  const viz::HitTestDataProvider* hit_test_data_provider() const {
+    WindowPortMus* port = WindowPortMus::Get(root_.get());
+    return port->local_layer_tree_frame_sink_->hit_test_data_provider();
+  }
+
+  Window* root() { return root_.get(); }
+  Window* window2() { return window2_; }
+  Window* window3() { return window3_; }
+  Window* window4() { return window4_; }
+
+ private:
+  std::unique_ptr<cc::LayerTreeFrameSink> sink_;
+  std::unique_ptr<Window> root_;
+  Window* window2_;
+  Window* window3_;
+  Window* window4_;
+
+  DISALLOW_COPY_AND_ASSIGN(HitTestDataProviderAuraTest);
+};
+
+// Custom WindowTargeter that expands hit-test regions of child windows.
+class TestWindowTargeter : public WindowTargeter {
+ public:
+  TestWindowTargeter() {}
+  ~TestWindowTargeter() override {}
+
+ protected:
+  // WindowTargeter:
+  bool GetHitTestRects(aura::Window* window,
+                       gfx::Rect* rect_mouse,
+                       gfx::Rect* rect_touch) const override {
+    if (rect_mouse) {
+      *rect_mouse = gfx::Rect(window->bounds());
+      rect_mouse->Inset(gfx::Insets(kMouseInset));
+    }
+    if (rect_touch) {
+      *rect_touch = gfx::Rect(window->bounds());
+      rect_touch->Inset(gfx::Insets(kTouchInset));
+    }
+    return true;
+  }
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(TestWindowTargeter);
+};
+
+// Tests that the order of reported hit-test regions matches windows Z-order.
+TEST_F(HitTestDataProviderAuraTest, Stacking) {
+  const auto hit_test_data_1 = hit_test_data_provider()->GetHitTestData();
+  Window* expected_order_1[] = {window3(), window4(), window2()};
+  EXPECT_EQ(arraysize(expected_order_1), hit_test_data_1->regions.size());
+  int i = 0;
+  for (const auto& region : hit_test_data_1->regions) {
+    EXPECT_EQ(region->flags, viz::mojom::kHitTestMine |
+                                 viz::mojom::kHitTestMouse |
+                                 viz::mojom::kHitTestTouch);
+    viz::SurfaceId surface_id(
+        WindowPortMus::Get(expected_order_1[i])->frame_sink_id(),
+        WindowMus::Get(expected_order_1[i])->GetLocalSurfaceId());
+    EXPECT_EQ(region->surface_id, surface_id);
+    EXPECT_EQ(region->rect.ToString(),
+              expected_order_1[i]->bounds().ToString());
+    i++;
+  }
+
+  root()->StackChildAbove(window2(), window3());
+  const auto hit_test_data_2 = hit_test_data_provider()->GetHitTestData();
+
+  Window* expected_order_2[] = {window2(), window3(), window4()};
+  EXPECT_EQ(arraysize(expected_order_2), hit_test_data_2->regions.size());
+  i = 0;
+  for (const auto& region : hit_test_data_2->regions) {
+    EXPECT_EQ(region->flags, viz::mojom::kHitTestMine |
+                                 viz::mojom::kHitTestMouse |
+                                 viz::mojom::kHitTestTouch);
+    viz::SurfaceId surface_id(
+        WindowPortMus::Get(expected_order_2[i])->frame_sink_id(),
+        WindowMus::Get(expected_order_2[i])->GetLocalSurfaceId());
+    EXPECT_EQ(region->surface_id, surface_id);
+    EXPECT_EQ(region->rect.ToString(),
+              expected_order_2[i]->bounds().ToString());
+    i++;
+  }
+}
+
+// Tests that the hit-test regions get expanded with a custom event targeter.
+TEST_F(HitTestDataProviderAuraTest, CustomTargeter) {
+  window3()->SetEventTargeter(base::MakeUnique<TestWindowTargeter>());
+  const auto hit_test_data = hit_test_data_provider()->GetHitTestData();
+
+  // Children of a container that has the custom targeter installed will get
+  // reported twice, once with hit-test bounds optimized for mouse events and
+  // another time with bounds expanded more for touch input.
+  Window* expected_windows[] = {window3(), window4(), window4(), window2()};
+  uint32_t expected_flags[] = {
+      viz::mojom::kHitTestMine | viz::mojom::kHitTestMouse |
+          viz::mojom::kHitTestTouch,
+      viz::mojom::kHitTestMine | viz::mojom::kHitTestMouse,
+      viz::mojom::kHitTestMine | viz::mojom::kHitTestTouch,
+      viz::mojom::kHitTestMine | viz::mojom::kHitTestMouse |
+          viz::mojom::kHitTestTouch};
+  int expected_insets[] = {0, kMouseInset, kTouchInset, 0};
+  ASSERT_EQ(arraysize(expected_windows), hit_test_data->regions.size());
+  ASSERT_EQ(arraysize(expected_flags), hit_test_data->regions.size());
+  ASSERT_EQ(arraysize(expected_insets), hit_test_data->regions.size());
+  int i = 0;
+  for (const auto& region : hit_test_data->regions) {
+    viz::SurfaceId surface_id(
+        WindowPortMus::Get(expected_windows[i])->frame_sink_id(),
+        WindowMus::Get(expected_windows[i])->GetLocalSurfaceId());
+    EXPECT_EQ(region->surface_id, surface_id);
+    EXPECT_EQ(region->flags, expected_flags[i]);
+    gfx::Rect expected_bounds = expected_windows[i]->bounds();
+    expected_bounds.Inset(gfx::Insets(expected_insets[i]));
+    EXPECT_EQ(region->rect.ToString(), expected_bounds.ToString());
+    i++;
+  }
+}
+
+}  // namespace aura
diff --git a/ui/aura/mus/window_mus.h b/ui/aura/mus/window_mus.h
index 7e9077d9..c2d4996 100644
--- a/ui/aura/mus/window_mus.h
+++ b/ui/aura/mus/window_mus.h
@@ -103,7 +103,7 @@
   // Returns the currently used viz::LocalSurfaceId to embed this Window. Local
   // windows or windows that have not been embedded yet will have an invalid
   // viz::LocalSurfaceId.
-  virtual const viz::LocalSurfaceId& GetLocalSurfaceId() = 0;
+  virtual const viz::LocalSurfaceId& GetLocalSurfaceId() const = 0;
 
   // Called in the rare case when WindowTreeClient needs to change state and
   // can't go through one of the SetFooFromServer() functions above. Generally
diff --git a/ui/aura/mus/window_port_mus.cc b/ui/aura/mus/window_port_mus.cc
index 37b9751..200ef05 100644
--- a/ui/aura/mus/window_port_mus.cc
+++ b/ui/aura/mus/window_port_mus.cc
@@ -10,6 +10,7 @@
 #include "ui/aura/client/transient_window_client.h"
 #include "ui/aura/env.h"
 #include "ui/aura/mus/client_surface_embedder.h"
+#include "ui/aura/mus/hit_test_data_provider_aura.h"
 #include "ui/aura/mus/property_converter.h"
 #include "ui/aura/mus/window_tree_client.h"
 #include "ui/aura/mus/window_tree_client_delegate.h"
@@ -119,6 +120,7 @@
       gpu_memory_buffer_manager, nullptr /* shared_bitmap_manager */,
       nullptr /* synthetic_begin_frame_source */, std::move(sink_info),
       std::move(client_request),
+      base::MakeUnique<HitTestDataProviderAura>(window_),
       base::MakeUnique<viz::DefaultLocalSurfaceIdProvider>(),
       enable_surface_synchronization);
   window_tree_client_->AttachCompositorFrameSink(
@@ -392,7 +394,7 @@
              : ChangeSource::LOCAL;
 }
 
-const viz::LocalSurfaceId& WindowPortMus::GetLocalSurfaceId() {
+const viz::LocalSurfaceId& WindowPortMus::GetLocalSurfaceId() const {
   return local_surface_id_;
 }
 
diff --git a/ui/aura/mus/window_port_mus.h b/ui/aura/mus/window_port_mus.h
index ea5eeb54..6a82dd2b 100644
--- a/ui/aura/mus/window_port_mus.h
+++ b/ui/aura/mus/window_port_mus.h
@@ -58,6 +58,8 @@
   Window* window() { return window_; }
   const Window* window() const { return window_; }
 
+  viz::FrameSinkId frame_sink_id() const { return frame_sink_id_; }
+
   ClientSurfaceEmbedder* client_surface_embedder() const {
     return client_surface_embedder_.get();
   }
@@ -98,6 +100,7 @@
   friend class WindowTreeClient;
   friend class WindowTreeClientPrivate;
   friend class WindowTreeHostMus;
+  friend class HitTestDataProviderAuraTest;
 
   using ServerChangeIdType = uint8_t;
 
@@ -242,7 +245,7 @@
   void RemoveTransientChildFromServer(WindowMus* child) override;
   ChangeSource OnTransientChildAdded(WindowMus* child) override;
   ChangeSource OnTransientChildRemoved(WindowMus* child) override;
-  const viz::LocalSurfaceId& GetLocalSurfaceId() override;
+  const viz::LocalSurfaceId& GetLocalSurfaceId() const override;
   std::unique_ptr<WindowMusChangeData> PrepareForServerBoundsChange(
       const gfx::Rect& bounds) override;
   std::unique_ptr<WindowMusChangeData> PrepareForServerVisibilityChange(
diff --git a/ui/aura/window.h b/ui/aura/window.h
index eecf4fa6..6e5f215 100644
--- a/ui/aura/window.h
+++ b/ui/aura/window.h
@@ -332,6 +332,7 @@
                            int64_t old_value,
                            std::unique_ptr<ui::PropertyData> data) override;
  private:
+  friend class HitTestDataProviderAura;
   friend class LayoutManager;
   friend class PropertyConverter;
   friend class WindowPort;
diff --git a/ui/keyboard/content/keyboard_ui_content.cc b/ui/keyboard/content/keyboard_ui_content.cc
index 4a40c654..7a01622 100644
--- a/ui/keyboard/content/keyboard_ui_content.cc
+++ b/ui/keyboard/content/keyboard_ui_content.cc
@@ -230,7 +230,6 @@
       TRACE_EVENT0("vk", "ReloadKeyboardIfNeeded");
       GetContentsWindow()->SetBounds(gfx::Rect());
       keyboard_contents_->ClosePage();
-      keyboard_controller()->SetKeyboardMode(FULL_WIDTH);
     }
     LoadContents(GetVirtualKeyboardUrl());
   }
diff --git a/ui/keyboard/keyboard_controller.cc b/ui/keyboard/keyboard_controller.cc
index 2cba7ae..4d35958 100644
--- a/ui/keyboard/keyboard_controller.cc
+++ b/ui/keyboard/keyboard_controller.cc
@@ -259,7 +259,6 @@
       layout_delegate_(delegate),
       show_on_resize_(false),
       keyboard_locked_(false),
-      keyboard_mode_(FULL_WIDTH),
       state_(KeyboardControllerState::UNKNOWN),
       weak_factory_report_lingering_state_(this),
       weak_factory_will_hide_(this) {
@@ -362,14 +361,10 @@
     }
   }
 
-  if (keyboard_mode() == FULL_WIDTH) {
-    // We need to send out this notification only if keyboard is visible since
-    // the contents window is resized even if keyboard is hidden.
-    if (keyboard_visible())
-      NotifyContentsBoundsChanging(new_bounds);
-  } else if (keyboard_mode() == FLOATING) {
-    NotifyContentsBoundsChanging(gfx::Rect());
-  }
+  // We need to send out this notification only if keyboard is visible since
+  // the contents window is resized even if keyboard is hidden.
+  if (keyboard_visible())
+    NotifyContentsBoundsChanging(new_bounds);
 }
 
 void KeyboardController::AddObserver(KeyboardControllerObserver* observer) {
@@ -385,23 +380,6 @@
   observer_list_.RemoveObserver(observer);
 }
 
-void KeyboardController::SetKeyboardMode(KeyboardMode mode) {
-  if (keyboard_mode_ == mode)
-    return;
-
-  keyboard_mode_ = mode;
-  // When keyboard is floating, no overscroll or resize is necessary. Sets
-  // keyboard bounds to zero so overscroll or resize is disabled.
-  if (keyboard_mode_ == FLOATING) {
-    NotifyContentsBoundsChanging(gfx::Rect());
-  } else if (keyboard_mode_ == FULL_WIDTH) {
-    AdjustKeyboardBounds();
-    // No animation is needed. Just change the bounds and ensure caret in
-    // workarea.
-    NotifyKeyboardBoundsChangingAndEnsrueCaretInWorkArea();
-  }
-}
-
 void KeyboardController::HideKeyboard(HideReason reason) {
   TRACE_EVENT0("vk", "HideKeyboard");
 
@@ -500,21 +478,10 @@
     return;
 
   int container_height = container_->bounds().height();
-  if (keyboard_mode_ == FULL_WIDTH) {
-    container_->SetBounds(gfx::Rect(new_bounds.x(),
-                                    new_bounds.bottom() - container_height,
-                                    new_bounds.width(),
-                                    container_height));
-  } else if (keyboard_mode_ == FLOATING) {
-    // When screen rotate, horizontally center floating virtual keyboard
-    // window and vertically align it to the bottom.
-    int container_width = container_->bounds().width();
-    container_->SetBounds(gfx::Rect(
-        new_bounds.x() + (new_bounds.width() - container_width) / 2,
-        new_bounds.bottom() - container_height,
-        container_width,
-        container_height));
-  }
+
+  container_->SetBounds(gfx::Rect(new_bounds.x(),
+                                  new_bounds.bottom() - container_height,
+                                  new_bounds.width(), container_height));
 }
 
 void KeyboardController::Reload() {
@@ -687,15 +654,11 @@
   container_animator->set_preemption_strategy(
       ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
 
-  if (keyboard_mode_ == FLOATING) {
-    animation_observer_.reset();
-  } else {
-    animation_observer_.reset(new CallbackAnimationObserver(
-        container_animator,
-        base::BindOnce(&KeyboardController::ShowAnimationFinished,
-                       base::Unretained(this))));
-    container_animator->AddObserver(animation_observer_.get());
-  }
+  animation_observer_.reset(new CallbackAnimationObserver(
+      container_animator,
+      base::BindOnce(&KeyboardController::ShowAnimationFinished,
+                     base::Unretained(this))));
+  container_animator->AddObserver(animation_observer_.get());
 
   ui_->ShowKeyboardContainer(container_.get());
 
@@ -750,20 +713,12 @@
 }
 
 void KeyboardController::AdjustKeyboardBounds() {
-  // When keyboard is floating, no resize is necessary.
-  if (keyboard_mode_ == FLOATING)
-    return;
-
-  if (keyboard_mode_ == FULL_WIDTH) {
-    // TODO(bshe): revisit this logic after we decide to support resize virtual
-    // keyboard.
-    int keyboard_height = GetContainerWindow()->bounds().height();
-    const gfx::Rect& root_bounds = container_->GetRootWindow()->bounds();
-    gfx::Rect new_bounds = root_bounds;
-    new_bounds.set_y(root_bounds.height() - keyboard_height);
-    new_bounds.set_height(keyboard_height);
-    GetContainerWindow()->SetBounds(new_bounds);
-  }
+  int keyboard_height = GetContainerWindow()->bounds().height();
+  const gfx::Rect& root_bounds = container_->GetRootWindow()->bounds();
+  gfx::Rect new_bounds = root_bounds;
+  new_bounds.set_y(root_bounds.height() - keyboard_height);
+  new_bounds.set_height(keyboard_height);
+  GetContainerWindow()->SetBounds(new_bounds);
 }
 
 void KeyboardController::CheckStateTransition(KeyboardControllerState prev,
diff --git a/ui/keyboard/keyboard_controller.h b/ui/keyboard/keyboard_controller.h
index 7315938..77eff28c 100644
--- a/ui/keyboard/keyboard_controller.h
+++ b/ui/keyboard/keyboard_controller.h
@@ -35,17 +35,6 @@
 // or hide animation finishes.
 constexpr int kAnimationDistance = 30;
 
-enum KeyboardMode {
-  // Invalid mode.
-  NONE,
-  // Full width virtual keyboard. The virtual keyboard window has the same width
-  // as the display.
-  FULL_WIDTH,
-  // Floating virtual keyboard. The virtual keyboard window has customizable
-  // width and is draggable.
-  FLOATING,
-};
-
 // Represents the current state of the keyboard managed by the controller.
 // Don't change the numeric value of the members because they are used in UMA
 // - VirtualKeyboard.ControllerStateTransition.
@@ -117,10 +106,6 @@
 
   bool keyboard_locked() const { return keyboard_locked_; }
 
-  KeyboardMode keyboard_mode() const { return keyboard_mode_; }
-
-  void SetKeyboardMode(KeyboardMode mode);
-
   // Immediately starts hiding animation of virtual keyboard and notifies
   // observers bounds change. This method forcibly sets keyboard_locked_
   // false while closing the keyboard.
@@ -230,7 +215,6 @@
   bool show_on_resize_;
   // If true, the keyboard is always visible even if no window has input focus.
   bool keyboard_locked_;
-  KeyboardMode keyboard_mode_;
   KeyboardEventFilter event_filter_;
 
   base::ObserverList<KeyboardControllerObserver> observer_list_;
diff --git a/ui/keyboard/keyboard_controller_unittest.cc b/ui/keyboard/keyboard_controller_unittest.cc
index 3e80c02a..460b08cc1 100644
--- a/ui/keyboard/keyboard_controller_unittest.cc
+++ b/ui/keyboard/keyboard_controller_unittest.cc
@@ -345,16 +345,16 @@
   ASSERT_EQ(screen_bounds.height(), initial_bounds.y());
   VerifyKeyboardWindowSize(container, keyboard);
 
-  // In FULL_WIDTH mode, attempt to change window width or move window up from
-  // the bottom are ignored. Changing window height is supported.
+  // Attempt to change window width or move window up from the bottom are
+  // ignored. Changing window height is supported.
   gfx::Rect expected_bounds(0,
                             screen_bounds.height() - 50,
                             screen_bounds.width(),
                             50);
 
   // The x position of new bounds may not be 0 if shelf is on the left side of
-  // screen. In FULL_WIDTH mode, the virtual keyboard should always align with
-  // the left edge of screen. See http://crbug.com/510595.
+  // screen. The virtual keyboard should always align with the left edge of
+  // screen. See http://crbug.com/510595.
   gfx::Rect new_bounds(10, 0, 50, 50);
   keyboard->SetBounds(new_bounds);
   ASSERT_EQ(expected_bounds, container->bounds());
@@ -403,18 +403,6 @@
   VerifyKeyboardWindowSize(container, keyboard);
 }
 
-TEST_P(KeyboardControllerTest, FloatingKeyboardSize) {
-  aura::Window* container(controller()->GetContainerWindow());
-  aura::Window* keyboard(ui()->GetContentsWindow());
-  root_window()->AddChild(container);
-  controller()->SetKeyboardMode(FLOATING);
-  container->AddChild(keyboard);
-  gfx::Rect new_bounds(0, 50, 50, 50);
-  keyboard->SetBounds(new_bounds);
-  ASSERT_EQ(new_bounds, container->bounds());
-  VerifyKeyboardWindowSize(container, keyboard);
-}
-
 // Tests that tapping/clicking inside the keyboard does not give it focus.
 TEST_P(KeyboardControllerTest, ClickDoesNotFocusKeyboard) {
   ScopedAccessibilityKeyboardEnabler scoped_keyboard_enabler;
@@ -523,66 +511,6 @@
   EXPECT_TRUE(ShouldEnableInsets(ui()->GetContentsWindow()));
 }
 
-// Verify switch to FLOATING mode will reset the overscroll or resize and when
-// in FLOATING mode, overscroll or resize wont be triggered.
-TEST_P(KeyboardControllerTest, FloatingKeyboardDontOverscrollOrResize) {
-  ScopedAccessibilityKeyboardEnabler scoped_keyboard_enabler;
-  ui::DummyTextInputClient input_client(ui::TEXT_INPUT_TYPE_TEXT);
-  ui::DummyTextInputClient no_input_client(ui::TEXT_INPUT_TYPE_NONE);
-
-  base::RunLoop run_loop;
-  aura::Window* container(controller()->GetContainerWindow());
-  root_window()->AddChild(container);
-  std::unique_ptr<KeyboardContainerObserver> keyboard_container_observer(
-      new KeyboardContainerObserver(container, &run_loop));
-  gfx::Rect screen_bounds = root_window()->bounds();
-  ScopedTouchKeyboardEnabler scoped_touch_keyboard_enabler;
-
-  SetFocus(&input_client);
-  gfx::Rect expected_bounds(
-      0, screen_bounds.height() - kDefaultVirtualKeyboardHeight,
-      screen_bounds.width(), kDefaultVirtualKeyboardHeight);
-  // Verify overscroll or resize is in effect.
-  EXPECT_EQ(expected_bounds, notified_bounds());
-  EXPECT_EQ(1, number_of_calls());
-
-  controller()->SetKeyboardMode(FLOATING);
-  // Switch to FLOATING should clear overscroll or resize.
-  EXPECT_EQ(gfx::Rect(), notified_bounds());
-  EXPECT_EQ(2, number_of_calls());
-  SetFocus(&no_input_client);
-  run_loop.Run();
-  EXPECT_EQ(gfx::Rect(), notified_bounds());
-  EXPECT_EQ(3, number_of_calls());
-  SetFocus(&input_client);
-  // In FLOATING mode, no overscroll or resize should be triggered.
-  EXPECT_EQ(3, number_of_calls());
-  EXPECT_EQ(gfx::Rect(), controller()->current_keyboard_bounds());
-}
-
-// Verify switch to FULL_WIDTH mode will move virtual keyboard to the right
-// place and sets the correct overscroll.
-TEST_P(KeyboardControllerTest, SwitchToFullWidthVirtualKeyboard) {
-  ScopedTouchKeyboardEnabler scoped_keyboard_enabler;
-  ui::DummyTextInputClient input_client(ui::TEXT_INPUT_TYPE_TEXT);
-
-  aura::Window* container(controller()->GetContainerWindow());
-  root_window()->AddChild(container);
-  gfx::Rect screen_bounds = root_window()->bounds();
-  SetFocus(&input_client);
-
-  controller()->SetKeyboardMode(FLOATING);
-  EXPECT_EQ(gfx::Rect(), notified_bounds());
-  EXPECT_EQ(gfx::Rect(), controller()->current_keyboard_bounds());
-
-  controller()->SetKeyboardMode(FULL_WIDTH);
-  gfx::Rect expected_bounds(
-      0, screen_bounds.height() - kDefaultVirtualKeyboardHeight,
-      screen_bounds.width(), kDefaultVirtualKeyboardHeight);
-  EXPECT_EQ(expected_bounds, notified_bounds());
-  EXPECT_EQ(expected_bounds, controller()->current_keyboard_bounds());
-}
-
 TEST_P(KeyboardControllerTest, AlwaysVisibleWhenLocked) {
   ScopedAccessibilityKeyboardEnabler scoped_keyboard_enabler;
   ui::DummyTextInputClient input_client_0(ui::TEXT_INPUT_TYPE_TEXT);
@@ -741,26 +669,6 @@
   EXPECT_EQ(gfx::Transform(), layer->transform());
 }
 
-// Test for crbug.com/568274.
-TEST_P(KeyboardControllerTest, FloatingKeyboardShowOnFirstTap) {
-  ScopedTouchKeyboardEnabler scoped_keyboard_enabler;
-  aura::Window* container(controller()->GetContainerWindow());
-  aura::Window* keyboard(ui()->GetContentsWindow());
-  root_window()->AddChild(container);
-
-  controller()->SetKeyboardMode(FLOATING);
-  container->AddChild(keyboard);
-  // Mock focus on an input field.
-  ui()->GetInputMethod()->ShowImeIfNeeded();
-  // Mock set keyboard size from javascript side. In floating mode, virtual
-  // keyboard's size is decided by client.
-  gfx::Rect new_bounds(0, 50, 50, 50);
-  keyboard->SetBounds(new_bounds);
-  ASSERT_EQ(new_bounds, container->bounds());
-  EXPECT_TRUE(keyboard->IsVisible());
-  EXPECT_TRUE(container->IsVisible());
-}
-
 TEST_P(KeyboardControllerTest, DisplayChangeShouldNotifyBoundsChange) {
   ScopedTouchKeyboardEnabler scoped_keyboard_enabler;
   ui::DummyTextInputClient input_client(ui::TEXT_INPUT_TYPE_TEXT);
@@ -768,7 +676,6 @@
   aura::Window* container(controller()->GetContainerWindow());
   root_window()->AddChild(container);
 
-  controller()->SetKeyboardMode(FULL_WIDTH);
   SetFocus(&input_client);
   gfx::Rect new_bounds(0, 0, 1280, 800);
   ASSERT_NE(new_bounds, root_window()->bounds());
diff --git a/ui/keyboard/keyboard_layout_manager.cc b/ui/keyboard/keyboard_layout_manager.cc
index 8b718c1..1f6fa8e 100644
--- a/ui/keyboard/keyboard_layout_manager.cc
+++ b/ui/keyboard/keyboard_layout_manager.cc
@@ -16,24 +16,14 @@
   if (contents_window_) {
     gfx::Rect container_bounds = controller_->GetContainerWindow()->bounds();
     // Always align container window and keyboard window.
-    if (controller_->keyboard_mode() == FULL_WIDTH) {
-      SetChildBounds(contents_window_, gfx::Rect(container_bounds.size()));
-    } else {
-      SetChildBoundsDirect(contents_window_,
-                           gfx::Rect(container_bounds.size()));
-    }
+    SetChildBounds(contents_window_, gfx::Rect(container_bounds.size()));
   }
 }
 
 void KeyboardLayoutManager::OnWindowAddedToLayout(aura::Window* child) {
   DCHECK(!contents_window_);
   contents_window_ = child;
-  if (controller_->keyboard_mode() == FULL_WIDTH) {
-    controller_->GetContainerWindow()->SetBounds(gfx::Rect());
-  } else if (controller_->keyboard_mode() == FLOATING) {
-    controller_->GetContainerWindow()->SetBounds(child->bounds());
-    SetChildBoundsDirect(contents_window_, gfx::Rect(child->bounds().size()));
-  }
+  controller_->GetContainerWindow()->SetBounds(gfx::Rect());
 }
 
 void KeyboardLayoutManager::SetChildBounds(aura::Window* child,
@@ -50,16 +40,16 @@
   const aura::Window* root_window =
       controller_->GetContainerWindow()->GetRootWindow();
   gfx::Rect new_bounds = requested_bounds;
-  if (controller_->keyboard_mode() == FULL_WIDTH) {
-    // Honors only the height of the request bounds
-    const gfx::Rect& window_bounds = root_window->bounds();
-    new_bounds.set_y(window_bounds.height() - requested_bounds.height());
-    // If shelf is positioned on the left side of screen, x is not 0. In
-    // FULL_WIDTH mode, the virtual keyboard should always align with the left
-    // edge of the screen. So manually set x to 0 here.
-    new_bounds.set_x(0);
-    new_bounds.set_width(window_bounds.width());
-  }
+
+  // Honors only the height of the request bounds
+  const gfx::Rect& window_bounds = root_window->bounds();
+  new_bounds.set_y(window_bounds.height() - requested_bounds.height());
+  // If shelf is positioned on the left side of screen, x is not 0. In
+  // FULL_WIDTH mode, the virtual keyboard should always align with the left
+  // edge of the screen. So manually set x to 0 here.
+  new_bounds.set_x(0);
+  new_bounds.set_width(window_bounds.width());
+
   // Containar bounds should only be reset when the contents window bounds
   // actually change. Otherwise it interrupts the initial animation of showing
   // the keyboard. Described in crbug.com/356753.
diff --git a/ui/keyboard/keyboard_test_util.h b/ui/keyboard/keyboard_test_util.h
index 7d2e110..798d23c 100644
--- a/ui/keyboard/keyboard_test_util.h
+++ b/ui/keyboard/keyboard_test_util.h
@@ -25,8 +25,7 @@
 void WaitControllerStateChangesTo(const KeyboardControllerState state);
 
 // Gets the calculated keyboard bounds from |root_bounds|. The keyboard height
-// is specified by |keyboard_height|. This should be only called when keyboard
-// is in FULL_WDITH mode.
+// is specified by |keyboard_height|.
 gfx::Rect FullWidthKeyboardBoundsFromRootBounds(const gfx::Rect& root_bounds,
                                                 int keyboard_height);