diff --git a/DEPS b/DEPS index 2b194c6..bbc0c3a2 100644 --- a/DEPS +++ b/DEPS
@@ -105,11 +105,11 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling Skia # and whatever else without interference from each other. - 'skia_revision': '5953a476d9f74baa9e61ab14f71b2d211fca9721', + 'skia_revision': '9db44ed0ef7f4f1e548fdc3f3b9bb4674f9ee4ef', # 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': '0c05bf73b422ca9c849cec08fa23cf4589b0b508', + 'v8_revision': '132145aaee8c9e4c7d089763a3dd40646e686516', # 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. @@ -165,7 +165,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling catapult # and whatever else without interference from each other. - 'catapult_revision': 'd95dde6e066fe1b0ef88d3e0e5ccb5cae48b05a9', + 'catapult_revision': 'a7fb87b3a3d1dde21cc2cb1e0fd10e6c3bf3496c', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling libFuzzer # and whatever else without interference from each other. @@ -181,7 +181,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling feed # and whatever else without interference from each other. - 'feed_revision': 'a4e91c7238e329ad11e48b068fe3b1e935c0de9b', + 'feed_revision': '831b51c0ac199fea3278ceb9de361c22486da935', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling android_sdk_build-tools_version # and whatever else without interference from each other. @@ -604,7 +604,7 @@ }, 'src/third_party/depot_tools': - Var('chromium_git') + '/chromium/tools/depot_tools.git' + '@' + '0ec9d15571fb274b817e3f0336a78bfd35b75e50', + Var('chromium_git') + '/chromium/tools/depot_tools.git' + '@' + '81db1d50324a9f2df87c05ff7cc6d082b27db242', 'src/third_party/devtools-node-modules': Var('chromium_git') + '/external/github.com/ChromeDevTools/devtools-node-modules' + '@' + Var('devtools_node_modules_revision'), @@ -954,7 +954,7 @@ }, 'src/third_party/perfetto': - Var('android_git') + '/platform/external/perfetto.git' + '@' + '46ef92275f435ab46cfa6e848e844d50a9067da9', + Var('android_git') + '/platform/external/perfetto.git' + '@' + 'de2476bcaacf85f60bb6d8f13fadbe871dd1e3ce', 'src/third_party/perl': { 'url': Var('chromium_git') + '/chromium/deps/perl.git' + '@' + 'ac0d98b5cee6c024b0cffeb4f8f45b6fc5ccdb78',
diff --git a/android_webview/browser/aw_content_browser_client.cc b/android_webview/browser/aw_content_browser_client.cc index 1e026c1..e5c9d537 100644 --- a/android_webview/browser/aw_content_browser_client.cc +++ b/android_webview/browser/aw_content_browser_client.cc
@@ -5,6 +5,7 @@ #include "android_webview/browser/aw_content_browser_client.h" #include <utility> +#include <vector> #include "android_webview/browser/aw_browser_context.h" #include "android_webview/browser/aw_browser_main_parts.h" @@ -354,7 +355,7 @@ void AwContentBrowserClient::AllowWorkerFileSystem( const GURL& url, content::ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback) { callback.Run(true); } @@ -363,7 +364,7 @@ const GURL& url, const base::string16& name, content::ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames) { + const std::vector<content::GlobalFrameRoutingId>& render_frames) { return true; }
diff --git a/android_webview/browser/aw_content_browser_client.h b/android_webview/browser/aw_content_browser_client.h index 17725d9..7f01296 100644 --- a/android_webview/browser/aw_content_browser_client.h +++ b/android_webview/browser/aw_content_browser_client.h
@@ -79,13 +79,13 @@ void AllowWorkerFileSystem( const GURL& url, content::ResourceContext* context, - const std::vector<std::pair<int, int>>& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback) override; bool AllowWorkerIndexedDB( const GURL& url, const base::string16& name, content::ResourceContext* context, - const std::vector<std::pair<int, int>>& render_frames) override; + const std::vector<content::GlobalFrameRoutingId>& render_frames) override; content::QuotaPermissionContext* CreateQuotaPermissionContext() override; void GetQuotaSettings( content::BrowserContext* context,
diff --git a/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.cc b/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.cc index bbe8c8ca..522110b9 100644 --- a/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.cc +++ b/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.cc
@@ -6,6 +6,7 @@ #include <memory> #include <string> +#include <utility> #include "android_webview/browser/aw_browser_context.h" #include "android_webview/browser/aw_contents_client_bridge.h" @@ -249,7 +250,7 @@ request_, net::LOAD_ONLY_FROM_CACHE | net::LOAD_SKIP_CACHE_VALIDATION); } else { AwContentsIoThreadClient::CacheMode cache_mode = io_client->GetCacheMode(); - switch(cache_mode) { + switch (cache_mode) { case AwContentsIoThreadClient::LOAD_CACHE_ELSE_NETWORK: SetCacheControlFlag(request_, net::LOAD_SKIP_CACHE_VALIDATION); break; @@ -428,9 +429,9 @@ void AwResourceDispatcherHostDelegate::RemovePendingThrottleOnIoThread( IoThreadClientThrottle* throttle) { DCHECK_CURRENTLY_ON(BrowserThread::IO); - PendingThrottleMap::iterator it = pending_throttles_.find( - FrameRouteIDPair(throttle->render_process_id(), - throttle->render_frame_id())); + PendingThrottleMap::iterator it = + pending_throttles_.find(content::GlobalFrameRoutingId( + throttle->render_process_id(), throttle->render_frame_id())); if (it != pending_throttles_.end()) { pending_throttles_.erase(it); } @@ -469,8 +470,8 @@ IoThreadClientThrottle* pending_throttle) { DCHECK_CURRENTLY_ON(BrowserThread::IO); pending_throttles_.insert( - std::pair<FrameRouteIDPair, IoThreadClientThrottle*>( - FrameRouteIDPair(render_process_id, render_frame_id_id), + std::pair<content::GlobalFrameRoutingId, IoThreadClientThrottle*>( + content::GlobalFrameRoutingId(render_process_id, render_frame_id_id), pending_throttle)); } @@ -478,8 +479,9 @@ int new_render_process_id, int new_render_frame_id) { DCHECK_CURRENTLY_ON(BrowserThread::IO); - PendingThrottleMap::iterator it = pending_throttles_.find( - FrameRouteIDPair(new_render_process_id, new_render_frame_id)); + PendingThrottleMap::iterator it = + pending_throttles_.find(content::GlobalFrameRoutingId( + new_render_process_id, new_render_frame_id)); if (it != pending_throttles_.end()) { IoThreadClientThrottle* throttle = it->second;
diff --git a/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.h b/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.h index 790c0dd..5ab886e 100644 --- a/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.h +++ b/android_webview/browser/renderer_host/aw_resource_dispatcher_host_delegate.h
@@ -11,6 +11,7 @@ #include "base/lazy_instance.h" #include "base/macros.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/resource_context.h" #include "content/public/browser/resource_dispatcher_host_delegate.h" @@ -76,8 +77,7 @@ content::ResourceContext* resource_context); // Pair of render_process_id and render_frame_id. - typedef std::pair<int, int> FrameRouteIDPair; - typedef std::map<FrameRouteIDPair, IoThreadClientThrottle*> + typedef std::map<content::GlobalFrameRoutingId, IoThreadClientThrottle*> PendingThrottleMap; // Only accessed on the IO thread.
diff --git a/base/test/android/junit/src/org/chromium/base/test/asynctask/BackgroundShadowAsyncTask.java b/base/test/android/junit/src/org/chromium/base/test/asynctask/BackgroundShadowAsyncTask.java index 83e0ce8..f8ba988e 100644 --- a/base/test/android/junit/src/org/chromium/base/test/asynctask/BackgroundShadowAsyncTask.java +++ b/base/test/android/junit/src/org/chromium/base/test/asynctask/BackgroundShadowAsyncTask.java
@@ -29,13 +29,13 @@ @Override @Implementation - public final AsyncTask<Result> execute() { + public final AsyncTask<Result> executeOnExecutor(Executor e) { try { return sExecutorService .submit(new Callable<AsyncTask<Result>>() { @Override public AsyncTask<Result> call() throws Exception { - return BackgroundShadowAsyncTask.super.execute(); + return BackgroundShadowAsyncTask.super.executeInRobolectric(); } }) .get(); @@ -47,12 +47,6 @@ @Override @Implementation - public final AsyncTask<Result> executeOnExecutor(Executor e) { - return execute(); - } - - @Override - @Implementation public final Result get() { try { runBackgroundTasks();
diff --git a/base/test/android/junit/src/org/chromium/base/test/asynctask/CustomShadowAsyncTask.java b/base/test/android/junit/src/org/chromium/base/test/asynctask/CustomShadowAsyncTask.java index 069e298..e84c84b 100644 --- a/base/test/android/junit/src/org/chromium/base/test/asynctask/CustomShadowAsyncTask.java +++ b/base/test/android/junit/src/org/chromium/base/test/asynctask/CustomShadowAsyncTask.java
@@ -22,6 +22,6 @@ @Override @Implementation public final AsyncTask<Result> executeOnExecutor(Executor executor) { - return super.execute(); + return super.executeInRobolectric(); } }
diff --git a/chrome/android/java/res/drawable-hdpi/btn_new_tab_incognito_normal.png b/chrome/android/java/res/drawable-hdpi/btn_new_tab_incognito_normal.png deleted file mode 100644 index 576c6d7..0000000 --- a/chrome/android/java/res/drawable-hdpi/btn_new_tab_incognito_normal.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-hdpi/btn_new_tab_incognito_pressed.png b/chrome/android/java/res/drawable-hdpi/btn_new_tab_incognito_pressed.png deleted file mode 100644 index 6b092685..0000000 --- a/chrome/android/java/res/drawable-hdpi/btn_new_tab_incognito_pressed.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-hdpi/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-hdpi/ic_omnibox_incognito_badge.png deleted file mode 100644 index 23bf4cb..0000000 --- a/chrome/android/java/res/drawable-hdpi/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-ldrtl-hdpi-v17/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-ldrtl-hdpi-v17/ic_omnibox_incognito_badge.png deleted file mode 100644 index 005cf9bd..0000000 --- a/chrome/android/java/res/drawable-ldrtl-hdpi-v17/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-ldrtl-mdpi-v17/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-ldrtl-mdpi-v17/ic_omnibox_incognito_badge.png deleted file mode 100644 index b40745e..0000000 --- a/chrome/android/java/res/drawable-ldrtl-mdpi-v17/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-ldrtl-xhdpi-v17/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-ldrtl-xhdpi-v17/ic_omnibox_incognito_badge.png deleted file mode 100644 index 2645aee..0000000 --- a/chrome/android/java/res/drawable-ldrtl-xhdpi-v17/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-ldrtl-xxhdpi-v17/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-ldrtl-xxhdpi-v17/ic_omnibox_incognito_badge.png deleted file mode 100644 index cb033ef8..0000000 --- a/chrome/android/java/res/drawable-ldrtl-xxhdpi-v17/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-ldrtl-xxxhdpi-v17/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-ldrtl-xxxhdpi-v17/ic_omnibox_incognito_badge.png deleted file mode 100644 index 7517752..0000000 --- a/chrome/android/java/res/drawable-ldrtl-xxxhdpi-v17/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-mdpi/btn_new_tab_incognito_normal.png b/chrome/android/java/res/drawable-mdpi/btn_new_tab_incognito_normal.png deleted file mode 100644 index ef804ae..0000000 --- a/chrome/android/java/res/drawable-mdpi/btn_new_tab_incognito_normal.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-mdpi/btn_new_tab_incognito_pressed.png b/chrome/android/java/res/drawable-mdpi/btn_new_tab_incognito_pressed.png deleted file mode 100644 index befee8e..0000000 --- a/chrome/android/java/res/drawable-mdpi/btn_new_tab_incognito_pressed.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-mdpi/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-mdpi/ic_omnibox_incognito_badge.png deleted file mode 100644 index 39768de50..0000000 --- a/chrome/android/java/res/drawable-mdpi/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xhdpi/btn_new_tab_incognito_normal.png b/chrome/android/java/res/drawable-xhdpi/btn_new_tab_incognito_normal.png deleted file mode 100644 index c2190cd..0000000 --- a/chrome/android/java/res/drawable-xhdpi/btn_new_tab_incognito_normal.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xhdpi/btn_new_tab_incognito_pressed.png b/chrome/android/java/res/drawable-xhdpi/btn_new_tab_incognito_pressed.png deleted file mode 100644 index 44e3289..0000000 --- a/chrome/android/java/res/drawable-xhdpi/btn_new_tab_incognito_pressed.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xhdpi/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-xhdpi/ic_omnibox_incognito_badge.png deleted file mode 100644 index 42b591c..0000000 --- a/chrome/android/java/res/drawable-xhdpi/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xxhdpi/btn_new_tab_incognito_normal.png b/chrome/android/java/res/drawable-xxhdpi/btn_new_tab_incognito_normal.png deleted file mode 100644 index 03003443..0000000 --- a/chrome/android/java/res/drawable-xxhdpi/btn_new_tab_incognito_normal.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xxhdpi/btn_new_tab_incognito_pressed.png b/chrome/android/java/res/drawable-xxhdpi/btn_new_tab_incognito_pressed.png deleted file mode 100644 index 4d5b881..0000000 --- a/chrome/android/java/res/drawable-xxhdpi/btn_new_tab_incognito_pressed.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xxhdpi/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-xxhdpi/ic_omnibox_incognito_badge.png deleted file mode 100644 index 8e5e7967..0000000 --- a/chrome/android/java/res/drawable-xxhdpi/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xxxhdpi/btn_new_tab_incognito_normal.png b/chrome/android/java/res/drawable-xxxhdpi/btn_new_tab_incognito_normal.png deleted file mode 100644 index 258d7f0..0000000 --- a/chrome/android/java/res/drawable-xxxhdpi/btn_new_tab_incognito_normal.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xxxhdpi/btn_new_tab_incognito_pressed.png b/chrome/android/java/res/drawable-xxxhdpi/btn_new_tab_incognito_pressed.png deleted file mode 100644 index ff86c7b..0000000 --- a/chrome/android/java/res/drawable-xxxhdpi/btn_new_tab_incognito_pressed.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable-xxxhdpi/ic_omnibox_incognito_badge.png b/chrome/android/java/res/drawable-xxxhdpi/ic_omnibox_incognito_badge.png deleted file mode 100644 index 5e5b21b..0000000 --- a/chrome/android/java/res/drawable-xxxhdpi/ic_omnibox_incognito_badge.png +++ /dev/null Binary files differ
diff --git a/chrome/android/java/res/drawable/btn_new_tab_incognito.xml b/chrome/android/java/res/drawable/btn_new_tab_incognito.xml deleted file mode 100644 index b2ec0147..0000000 --- a/chrome/android/java/res/drawable/btn_new_tab_incognito.xml +++ /dev/null
@@ -1,11 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright 2015 The Chromium Authors. All rights reserved. - Use of this source code is governed by a BSD-style license that can be - found in the LICENSE file. --> - -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/btn_new_tab_incognito_pressed" /> - <item android:state_selected="true" android:drawable="@drawable/btn_new_tab_incognito_pressed" /> - <item android:state_focused="true" android:drawable="@drawable/btn_new_tab_incognito_pressed" /> - <item android:drawable="@drawable/btn_new_tab_incognito_normal" /> -</selector>
diff --git a/chrome/android/java/res/layout/control_container.xml b/chrome/android/java/res/layout/control_container.xml index 8470dd5..0484e201 100644 --- a/chrome/android/java/res/layout/control_container.xml +++ b/chrome/android/java/res/layout/control_container.xml
@@ -21,9 +21,9 @@ android:layout_height="@dimen/toolbar_height_no_shadow" /> <ImageView android:id="@+id/toolbar_shadow" - android:src="@drawable/toolbar_shadow" + android:src="@drawable/modern_toolbar_shadow" android:layout_width="match_parent" - android:layout_height="wrap_content" + android:layout_height="@dimen/toolbar_shadow_height" android:layout_marginTop="@dimen/tab_strip_and_toolbar_height" android:scaleType="fitXY" tools:ignore="ContentDescription" />
diff --git a/chrome/android/java/res/layout/keyboard_accessory.xml b/chrome/android/java/res/layout/keyboard_accessory.xml index d0c9528..4a73188 100644 --- a/chrome/android/java/res/layout/keyboard_accessory.xml +++ b/chrome/android/java/res/layout/keyboard_accessory.xml
@@ -17,7 +17,6 @@ android:layout_height="@dimen/keyboard_accessory_height" android:layout_width="match_parent" android:paddingEnd="0dp" - android:paddingStart="@dimen/keyboard_accessory_padding" android:clickable="true" android:focusable="true"> @@ -25,11 +24,13 @@ android:id="@+id/tabs" app:tabIndicatorHeight="0dp" android:layout_width="wrap_content" - android:layout_height="match_parent" /> + android:layout_height="match_parent"/> + + <View style="@style/VerticalDivider" /> <android.support.v7.widget.RecyclerView android:id="@+id/actions_view" android:layout_width="wrap_content" - android:layout_height="match_parent" /> + android:layout_height="match_parent"/> </org.chromium.chrome.browser.autofill.keyboard_accessory.KeyboardAccessoryView>
diff --git a/chrome/android/java/res/layout/keyboard_accessory_action.xml b/chrome/android/java/res/layout/keyboard_accessory_action.xml index 2de4c8c..3635972a 100644 --- a/chrome/android/java/res/layout/keyboard_accessory_action.xml +++ b/chrome/android/java/res/layout/keyboard_accessory_action.xml
@@ -12,8 +12,8 @@ android:minHeight="0dp" android:minWidth="0dp" android:paddingBottom="0dp" - android:paddingEnd="@dimen/keyboard_accessory_half_padding" - android:paddingStart="@dimen/keyboard_accessory_half_padding" + android:paddingEnd="@dimen/keyboard_accessory_action_padding" + android:paddingStart="@dimen/keyboard_accessory_action_padding" android:paddingTop="0dp" android:layout_marginBottom="@dimen/keyboard_accessory_half_padding" android:layout_marginTop="@dimen/keyboard_accessory_half_padding"
diff --git a/chrome/android/java/res/layout/location_bar_base.xml b/chrome/android/java/res/layout/location_bar_base.xml index d678d61..6d9c528 100644 --- a/chrome/android/java/res/layout/location_bar_base.xml +++ b/chrome/android/java/res/layout/location_bar_base.xml
@@ -8,17 +8,7 @@ --> <merge xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:app="http://schemas.android.com/apk/res-auto" - xmlns:tools="http://schemas.android.com/tools"> - - <ImageView android:id="@+id/incognito_badge" - style="@style/LocationBarButton" - android:layout_width="wrap_content" - android:layout_height="match_parent" - android:scaleType="center" - android:src="@drawable/ic_omnibox_incognito_badge" - tools:ignore="ContentDescription" - android:visibility="gone" /> + xmlns:app="http://schemas.android.com/apk/res-auto"> <FrameLayout android:id="@+id/location_bar_icon" android:layout_width="@dimen/location_bar_icon_width"
diff --git a/chrome/android/java/res/layout/password_accessory_sheet_label.xml b/chrome/android/java/res/layout/password_accessory_sheet_label.xml index 4e85e90..e922c3df 100644 --- a/chrome/android/java/res/layout/password_accessory_sheet_label.xml +++ b/chrome/android/java/res/layout/password_accessory_sheet_label.xml
@@ -11,5 +11,6 @@ android:paddingEnd="16dp" android:fillViewport="true" android:layout_height="48dp" + android:gravity="center_vertical" android:textAppearance="@style/BlackHint1" - android:layout_width="match_parent"/> \ No newline at end of file + android:layout_width="match_parent"/>
diff --git a/chrome/android/java/res/layout/password_accessory_sheet_option.xml b/chrome/android/java/res/layout/password_accessory_sheet_option.xml index 81934f0b..06bfd64 100644 --- a/chrome/android/java/res/layout/password_accessory_sheet_option.xml +++ b/chrome/android/java/res/layout/password_accessory_sheet_option.xml
@@ -12,4 +12,5 @@ android:fillViewport="true" android:layout_height="48dp" android:textAppearance="@style/BlackTitle1" - android:layout_width="match_parent"/> \ No newline at end of file + android:layout_width="match_parent" + android:background="?android:attr/selectableItemBackground"/> \ No newline at end of file
diff --git a/chrome/android/java/res/layout/password_accessory_sheet_suggestion.xml b/chrome/android/java/res/layout/password_accessory_sheet_suggestion.xml index d7cbb66..8d0eb919 100644 --- a/chrome/android/java/res/layout/password_accessory_sheet_suggestion.xml +++ b/chrome/android/java/res/layout/password_accessory_sheet_suggestion.xml
@@ -6,10 +6,8 @@ <TextView xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/suggestion_text" - android:layout_marginStart="@dimen/keyboard_accessory_suggestion_margin" - android:paddingEnd="@dimen/keyboard_accessory_suggestion_margin" android:gravity="center_vertical|start" android:fillViewport="true" android:layout_height="@dimen/keyboard_accessory_suggestion_height" - android:textAppearance="@style/BlackTitle1" - android:layout_width="match_parent"/> \ No newline at end of file + android:layout_width="match_parent" + android:textAppearance="@style/BlackTitle1"/> \ No newline at end of file
diff --git a/chrome/android/java/res/values-v17/styles.xml b/chrome/android/java/res/values-v17/styles.xml index fccda2d1..07aee30 100644 --- a/chrome/android/java/res/values-v17/styles.xml +++ b/chrome/android/java/res/values-v17/styles.xml
@@ -220,12 +220,21 @@ <item name="android:layout_marginTop">2dp</item> <item name="android:background">@color/google_grey_600</item> </style> + + <!-- Dividers --> <style name="Divider"> <item name="android:layout_width">match_parent</item> <item name="android:layout_height">@dimen/divider_height</item> <item name="android:background">@color/google_grey_300</item> <item name="android:importantForAccessibility">no</item> </style> + <style name="VerticalDivider"> + <item name="android:layout_width">@dimen/divider_height</item> + <item name="android:layout_height">match_parent</item> + <item name="android:background">@color/google_grey_300</item> + <item name="android:importantForAccessibility">no</item> + </style> + <style name="ThemeWithActionBarBase" parent="Theme.AppCompat.Light"> <item name="android:windowBackground">@drawable/action_bar_activity_bg</item>
diff --git a/chrome/android/java/res/values/dimens.xml b/chrome/android/java/res/values/dimens.xml index 836c9b3..dc7b16b 100644 --- a/chrome/android/java/res/values/dimens.xml +++ b/chrome/android/java/res/values/dimens.xml
@@ -125,11 +125,12 @@ <!-- Autofill keyboard accessory dimensions --> <dimen name="keyboard_accessory_action_height">36dp</dimen> + <dimen name="keyboard_accessory_action_padding">16dp</dimen> <dimen name="keyboard_accessory_half_padding">6dp</dimen> <dimen name="keyboard_accessory_height">48dp</dimen> <dimen name="keyboard_accessory_padding">6dp</dimen> <dimen name="keyboard_accessory_sheet_height">330dp</dimen> - <dimen name="keyboard_accessory_suggestion_margin">16dp</dimen> + <dimen name="keyboard_accessory_suggestion_padding">16dp</dimen> <dimen name="keyboard_accessory_suggestion_height">48dp</dimen> <dimen name="keyboard_accessory_suggestion_icon_size">20dp</dimen> @@ -272,9 +273,7 @@ <dimen name="location_bar_google_g_container_width">40dp</dimen> <dimen name="location_bar_vertical_margin">8dp</dimen> <dimen name="location_bar_url_text_size">16sp</dimen> - <dimen name="location_bar_incognito_badge_padding">7dp</dimen> <dimen name="location_bar_icon_width">32dp</dimen> - <dimen name="location_bar_corner_radius">1dp</dimen> <dimen name="tablet_toolbar_start_padding">4dp</dimen> <dimen name="tablet_toolbar_start_padding_no_buttons">6dp</dimen>
diff --git a/chrome/android/java/res/xml/account_management_preferences.xml b/chrome/android/java/res/xml/account_management_preferences.xml index 5c5581d..2f38746 100644 --- a/chrome/android/java/res/xml/account_management_preferences.xml +++ b/chrome/android/java/res/xml/account_management_preferences.xml
@@ -38,8 +38,7 @@ <TextView android:id="@android:id/summary" android:layout_width="wrap_content" android:layout_height="wrap_content" - android:textAppearance="?android:attr/textAppearanceSmall" - android:textColor="?android:attr/textColorSecondary"/> + android:textAppearance="@style/BlackBody"/> <LinearLayout android:id="@android:id/widget_frame" android:layout_width="wrap_content" @@ -62,6 +61,7 @@ android:title="@string/sign_in_sync"/> <Preference + android:key="sync_settings_divider" android:layout="@layout/divider_preference"/> <Preference @@ -71,6 +71,7 @@ android:summary="@string/sign_in_google_activity_controls_message"/> <Preference + android:key="google_activity_controls_divider" android:layout="@layout/divider_preference"/> <Preference
diff --git a/chrome/android/java/res/xml/sync_and_services_preferences.xml b/chrome/android/java/res/xml/sync_and_services_preferences.xml index e39171d..702a825 100644 --- a/chrome/android/java/res/xml/sync_and_services_preferences.xml +++ b/chrome/android/java/res/xml/sync_and_services_preferences.xml
@@ -32,11 +32,11 @@ android:title="@string/sync_bookmarks"/> <org.chromium.chrome.browser.preferences.ChromeBaseCheckBoxPreference android:persistent="false" - android:key="payments_integration" - android:title="@string/payments_integration"/> + android:key="sync_payments_integration" + android:title="@string/sync_payments_integration"/> <org.chromium.chrome.browser.preferences.ChromeBaseCheckBoxPreference android:persistent="false" - android:key="sync_omnibox" + android:key="sync_history" android:title="@string/sync_history"/> <org.chromium.chrome.browser.preferences.ChromeBaseCheckBoxPreference android:persistent="false"
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/KeyboardAccessoryView.java b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/KeyboardAccessoryView.java index fa52318..d0be972 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/KeyboardAccessoryView.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/KeyboardAccessoryView.java
@@ -7,11 +7,10 @@ import static org.chromium.ui.base.LocalizationUtils.isLayoutRtl; import android.content.Context; -import android.graphics.Color; -import android.graphics.PorterDuff; import android.graphics.Rect; import android.graphics.drawable.Drawable; import android.support.design.widget.TabLayout; +import android.support.v4.graphics.drawable.DrawableCompat; import android.support.v4.view.ViewPager; import android.support.v7.widget.LinearLayoutManager; import android.support.v7.widget.RecyclerView; @@ -94,6 +93,7 @@ if (mTabLayout == null) return; // Inflation not done yet. Will be invoked again afterwards. TabLayout.Tab tab = mTabLayout.newTab(); tab.setIcon(icon.mutate()); // mutate() needed to change the active tint. + DrawableCompat.setTint(tab.getIcon(), getResources().getColor(R.color.default_icon_color)); tab.setContentDescription(contentDescription); mTabLayout.addTab(tab, position, false); } @@ -129,11 +129,10 @@ for (int i = mTabLayout.getTabCount() - 1; i >= 0; i--) { TabLayout.Tab t = mTabLayout.getTabAt(i); if (t == null || t.getIcon() == null) continue; - if (activeTab == null || i != activeTab) { - t.getIcon().clearColorFilter(); - } else { - t.getIcon().setColorFilter(Color.BLUE, PorterDuff.Mode.SRC_ATOP); - } + int activeStateColor = (activeTab == null || i != activeTab) + ? R.color.default_icon_color + : R.color.default_icon_color_blue; + DrawableCompat.setTint(t.getIcon(), getResources().getColor(activeStateColor)); } }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingCoordinator.java index a86d5880..614a397 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingCoordinator.java
@@ -72,10 +72,10 @@ } /** - * Tries to reopen the keyboard which will implicitly show the keyboard accessory bar again. + * Opens the keyboard which implicitly dismisses the sheet. Without open sheet, this is a NoOp. */ - public void openKeyboard() { - mMediator.onOpenKeyboard(); + public void swapSheetWithKeyboard() { + mMediator.swapSheetWithKeyboard(); } void registerActionProvider(
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingMediator.java b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingMediator.java index a1f8184..47435db 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingMediator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingMediator.java
@@ -155,8 +155,13 @@ } @Override - public void willCloseTab(Tab tab, boolean animate) { + public void tabClosureCommitted(Tab tab) { mModel.remove(tab); + } + + @Override + public void willCloseTab(Tab tab, boolean animate) { + if (mActiveBrowserTab == tab) mActiveBrowserTab = null; restoreCachedState(mActiveBrowserTab); } }; @@ -257,6 +262,13 @@ mAccessorySheet.hide(); } + /** + * Opens the keyboard which implicitly dismisses the sheet. Without open sheet, this is a NoOp. + */ + void swapSheetWithKeyboard() { + if (mAccessorySheet.isShown()) onOpenKeyboard(); + } + @Override public void onOpenKeyboard() { assert mActivity != null : "ManualFillingMediator needs initialization.";
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessoryBridge.java b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessoryBridge.java index c93217a..6e1be89 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessoryBridge.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessoryBridge.java
@@ -75,8 +75,8 @@ } @CalledByNative - private void openKeyboard() { - mManualFillingCoordinator.openKeyboard(); + private void swapSheetWithKeyboard() { + mManualFillingCoordinator.swapSheetWithKeyboard(); } @CalledByNative
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessorySheetViewBinder.java b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessorySheetViewBinder.java index 70d6b1d..49f2ab6 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessorySheetViewBinder.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/autofill/keyboard_accessory/PasswordAccessorySheetViewBinder.java
@@ -4,11 +4,11 @@ package org.chromium.chrome.browser.autofill.keyboard_accessory; +import android.content.res.TypedArray; import android.graphics.Bitmap; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; import android.support.annotation.Nullable; -import android.support.v4.view.MarginLayoutParamsCompat; import android.support.v7.content.res.AppCompatResources; import android.support.v7.widget.LinearLayoutManager; import android.support.v7.widget.RecyclerView; @@ -111,14 +111,14 @@ */ static class IconTextViewHolder extends TextViewHolder { private final TextView mSuggestionText; - private final int mMargin; + private final int mPadding; private final int mIconSize; IconTextViewHolder(View itemView) { super(itemView); mSuggestionText = itemView.findViewById(R.id.suggestion_text); - mMargin = itemView.getContext().getResources().getDimensionPixelSize( - R.dimen.keyboard_accessory_suggestion_margin); + mPadding = itemView.getContext().getResources().getDimensionPixelSize( + R.dimen.keyboard_accessory_suggestion_padding); mIconSize = itemView.getContext().getResources().getDimensionPixelSize( R.dimen.keyboard_accessory_suggestion_icon_size); } @@ -131,19 +131,27 @@ @Override protected void bind(Item item) { super.bind(item); - ViewGroup.MarginLayoutParams params = - new ViewGroup.MarginLayoutParams(mSuggestionText.getLayoutParams()); - MarginLayoutParamsCompat.setMarginEnd(params, mMargin); if (!item.isPassword()) { setIconForBitmap(null); // Set the default icon, then try to get a better one. item.fetchFavicon(this::setIconForBitmap); - MarginLayoutParamsCompat.setMarginStart(params, mMargin); + mSuggestionText.setPadding(mPadding, 0, mPadding, 0); } else { ApiCompatibilityUtils.setCompoundDrawablesRelative( mSuggestionText, null, null, null, null); - MarginLayoutParamsCompat.setMarginStart(params, 2 * mMargin + mIconSize); + mSuggestionText.setPadding(2 * mPadding + mIconSize, 0, mPadding, 0); } - mSuggestionText.setLayoutParams(params); + + if (item.getItemSelectedCallback() == null) { + mSuggestionText.setEnabled(false); + mSuggestionText.setBackground(null); + } else { + mSuggestionText.setEnabled(true); + TypedArray a = mSuggestionText.getContext().obtainStyledAttributes( + new int[] {R.attr.selectableItemBackground}); + Drawable suggestionBackground = a.getDrawable(0); + a.recycle(); + mSuggestionText.setBackground(suggestionBackground); + } } private void setIconForBitmap(@Nullable Bitmap favicon) { @@ -157,7 +165,7 @@ if (icon != null) { // AppCompatResources.getDrawable is @Nullable. icon.setBounds(0, 0, mIconSize, mIconSize); } - mSuggestionText.setCompoundDrawablePadding(mMargin); + mSuggestionText.setCompoundDrawablePadding(mPadding); ApiCompatibilityUtils.setCompoundDrawablesRelative( mSuggestionText, icon, null, null, null); }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarLayout.java b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarLayout.java index fc7045ef..944fc2a 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarLayout.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarLayout.java
@@ -2037,9 +2037,7 @@ if (visible && (!locationBarShownInNTP || ignoreNtpChecks)) { mScrimParams.backgroundColor = - useModernDesign() && !mIsTablet && !mToolbarDataProvider.isIncognito() - ? mLightScrimColor - : null; + !mIsTablet && !mToolbarDataProvider.isIncognito() ? mLightScrimColor : null; // If the location bar is shown in the NTP, the toolbar will eventually trigger a // fade in.
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarPhone.java b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarPhone.java index 610891a..e66a2f7 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarPhone.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/LocationBarPhone.java
@@ -8,9 +8,7 @@ import android.content.Context; import android.graphics.Canvas; import android.graphics.Rect; -import android.support.annotation.Nullable; import android.support.v4.view.MarginLayoutParamsCompat; -import android.support.v4.view.ViewCompat; import android.support.v4.view.animation.FastOutLinearInInterpolator; import android.util.AttributeSet; import android.view.TouchDelegate; @@ -42,10 +40,8 @@ new FastOutLinearInInterpolator(); private View mFirstVisibleFocusedView; - private @Nullable View mIncognitoBadge; private View mGoogleGContainer; private View mGoogleG; - private int mIncognitoBadgePadding; private int mGoogleGWidth; private int mGoogleGMargin; @@ -64,9 +60,6 @@ super.onFinishInflate(); mFirstVisibleFocusedView = findViewById(R.id.url_bar); - mIncognitoBadge = findViewById(R.id.incognito_badge); - mIncognitoBadgePadding = - getResources().getDimensionPixelSize(R.dimen.location_bar_incognito_badge_padding); mGoogleGContainer = findViewById(R.id.google_g_container); mGoogleG = findViewById(R.id.google_g); @@ -242,53 +235,10 @@ } @Override - protected void updateLocationBarIconContainerVisibility() { - super.updateLocationBarIconContainerVisibility(); - updateIncognitoBadgePadding(); - } - - private void updateIncognitoBadgePadding() { - // This can be triggered in the super.onFinishInflate, so we need to null check in this - // place only. - if (mIncognitoBadge == null) return; - - if (findViewById(R.id.location_bar_icon).getVisibility() == GONE) { - ViewCompat.setPaddingRelative(mIncognitoBadge, 0, 0, mIncognitoBadgePadding, 0); - } else { - ViewCompat.setPaddingRelative(mIncognitoBadge, 0, 0, 0, 0); - } - } - - @Override - public void updateVisualsForState() { - super.updateVisualsForState(); - - if (mIncognitoBadge == null) return; - - boolean showIncognitoBadge = - getToolbarDataProvider() != null && getToolbarDataProvider().isIncognito(); - mIncognitoBadge.setVisibility(showIncognitoBadge ? VISIBLE : GONE); - updateIncognitoBadgePadding(); - } - - @Override protected boolean shouldAnimateIconChanges() { return super.shouldAnimateIconChanges() || isUrlFocusChangeInProgress(); } - @Override - public void setLayoutDirection(int layoutDirection) { - super.setLayoutDirection(layoutDirection); - updateIncognitoBadgePadding(); - } - - /** - * @return Whether the incognito badge is currently visible. - */ - public boolean isIncognitoBadgeVisible() { - return mIncognitoBadge != null && mIncognitoBadge.getVisibility() == View.VISIBLE; - } - /** * @param softInputMode The software input resize mode. * @param delay Delay the change in input mode. @@ -348,24 +298,7 @@ } }); - // Chrome Home does not use the incognito badge. Remove the View to save memory. - removeView(mIncognitoBadge); - mIncognitoBadge = null; - // TODO(twellington): remove and null out mGoogleG and mGoogleGContainer if we remove // support for the Google 'G' to save memory. } - - @Override - public void onNativeLibraryReady() { - super.onNativeLibraryReady(); - - // TODO(twellington): Move this to constructor when isModernUiEnabled() is available before - // native is loaded. - if (useModernDesign()) { - // Modern does not use the incognito badge. Remove the View to save memory. - removeView(mIncognitoBadge); - mIncognitoBadge = null; - } - } }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/preferences/SyncAndServicesPreferences.java b/chrome/android/java/src/org/chromium/chrome/browser/preferences/SyncAndServicesPreferences.java index 0a4e93f1..c022c46 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/preferences/SyncAndServicesPreferences.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/preferences/SyncAndServicesPreferences.java
@@ -69,47 +69,39 @@ public class SyncAndServicesPreferences extends PreferenceFragment implements PassphraseDialogFragment.Listener, PassphraseCreationDialogFragment.Listener, PassphraseTypeDialogFragment.Listener, Preference.OnPreferenceChangeListener, - Preference.OnPreferenceClickListener, ProfileSyncService.SyncStateChangedListener { - private static final String USE_SYNC_AND_ALL_SERVICES = "use_sync_and_all_services"; - private static final String SYNC_AND_PERSONALIZATION = "sync_and_personalization"; - private static final String NONPERSONALIZED_SERVICES = "nonpersonalized_services"; - private static final String PREF_NAVIGATION_ERROR = "navigation_error"; - private static final String PREF_SEARCH_SUGGESTIONS = "search_suggestions"; - private static final String PREF_SAFE_BROWSING_EXTENDED_REPORTING = - "safe_browsing_extended_reporting"; - private static final String PREF_SAFE_BROWSING_SCOUT_REPORTING = - "safe_browsing_scout_reporting"; - private static final String PREF_SAFE_BROWSING = "safe_browsing"; - private static final String PREF_CONTEXTUAL_SEARCH = "contextual_search"; - private static final String PREF_NETWORK_PREDICTIONS = "network_predictions"; - private static final String PREF_USAGE_AND_CRASH_REPORTING = "usage_and_crash_reports"; - @VisibleForTesting public static final String FRAGMENT_ENTER_PASSPHRASE = "enter_password"; @VisibleForTesting public static final String FRAGMENT_CUSTOM_PASSPHRASE = "custom_password"; @VisibleForTesting public static final String FRAGMENT_PASSPHRASE_TYPE = "password_type"; - @VisibleForTesting - public static final String PREFERENCE_SYNC_AUTOFILL = "sync_autofill"; - @VisibleForTesting - public static final String PREFERENCE_SYNC_BOOKMARKS = "sync_bookmarks"; - @VisibleForTesting - public static final String PREFERENCE_SYNC_OMNIBOX = "sync_omnibox"; - @VisibleForTesting - public static final String PREFERENCE_SYNC_PASSWORDS = "sync_passwords"; - @VisibleForTesting - public static final String PREFERENCE_SYNC_RECENT_TABS = "sync_recent_tabs"; - @VisibleForTesting - public static final String PREFERENCE_SYNC_SETTINGS = "sync_settings"; - @VisibleForTesting - public static final String PREFERENCE_PAYMENTS_INTEGRATION = "payments_integration"; - @VisibleForTesting - public static final String PREFERENCE_ENCRYPTION = "encryption"; - @VisibleForTesting - public static final String PREFERENCE_SYNC_MANAGE_DATA = "sync_manage_data"; - public static final String PREFERENCE_SYNC_ERROR_CARD = "sync_error_card"; + + private static final String PREF_USE_SYNC_AND_ALL_SERVICES = "use_sync_and_all_services"; + + private static final String PREF_SYNC_AND_PERSONALIZATION = "sync_and_personalization"; + private static final String PREF_SYNC_AUTOFILL = "sync_autofill"; + private static final String PREF_SYNC_BOOKMARKS = "sync_bookmarks"; + private static final String PREF_SYNC_PAYMENTS_INTEGRATION = "sync_payments_integration"; + private static final String PREF_SYNC_HISTORY = "sync_history"; + private static final String PREF_SYNC_PASSWORDS = "sync_passwords"; + private static final String PREF_SYNC_RECENT_TABS = "sync_recent_tabs"; + private static final String PREF_SYNC_SETTINGS = "sync_settings"; + private static final String PREF_ENCRYPTION = "encryption"; + private static final String PREF_SYNC_MANAGE_DATA = "sync_manage_data"; + private static final String PREF_SYNC_ERROR_CARD = "sync_error_card"; + + private static final String PREF_NONPERSONALIZED_SERVICES = "nonpersonalized_services"; + private static final String PREF_SEARCH_SUGGESTIONS = "search_suggestions"; + private static final String PREF_NETWORK_PREDICTIONS = "network_predictions"; + private static final String PREF_NAVIGATION_ERROR = "navigation_error"; + private static final String PREF_SAFE_BROWSING = "safe_browsing"; + private static final String PREF_SAFE_BROWSING_EXTENDED_REPORTING = + "safe_browsing_extended_reporting"; + private static final String PREF_SAFE_BROWSING_SCOUT_REPORTING = + "safe_browsing_scout_reporting"; + private static final String PREF_USAGE_AND_CRASH_REPORTING = "usage_and_crash_reports"; + private static final String PREF_CONTEXTUAL_SEARCH = "contextual_search"; @IntDef({SyncError.NO_ERROR, SyncError.ANDROID_SYNC_DISABLED, SyncError.AUTH_ERROR, SyncError.PASSPHRASE_REQUIRED, SyncError.CLIENT_OUT_OF_DATE, SyncError.OTHER_ERRORS}) @@ -137,26 +129,26 @@ private SigninExpandablePreferenceGroup mSyncGroup; private CheckBoxPreference mSyncAutofill; private CheckBoxPreference mSyncBookmarks; - private CheckBoxPreference mSyncOmnibox; + private CheckBoxPreference mSyncPaymentsIntegration; + private CheckBoxPreference mSyncHistory; private CheckBoxPreference mSyncPasswords; private CheckBoxPreference mSyncRecentTabs; private CheckBoxPreference mSyncSettings; - private CheckBoxPreference mPaymentsIntegration; // Contains preferences for all sync data types. - private CheckBoxPreference[] mAllTypes; + private CheckBoxPreference[] mSyncAllTypes; private Preference mSyncEncryption; private Preference mManageSyncData; private Preference mSyncErrorCard; private SigninExpandablePreferenceGroup mNonpersonalizedServices; - private ChromeBaseCheckBoxPreference mNavigationError; - private ChromeBaseCheckBoxPreference mNetworkPredictions; private ChromeBaseCheckBoxPreference mSearchSuggestions; - private Preference mContextualSearch; - private ChromeBaseCheckBoxPreference mSafeBrowsingReporting; + private ChromeBaseCheckBoxPreference mNetworkPredictions; + private ChromeBaseCheckBoxPreference mNavigationError; private ChromeBaseCheckBoxPreference mSafeBrowsing; + private ChromeBaseCheckBoxPreference mSafeBrowsingReporting; private Preference mUsageAndCrashReporting; + private Preference mContextualSearch; private boolean mIsEngineInitialized; private boolean mIsPassphraseRequired; @@ -178,33 +170,44 @@ PreferenceUtils.addPreferencesFromResource(this, R.xml.sync_and_services_preferences); - mUseSyncAndAllServices = (ChromeSwitchPreference) findPreference(USE_SYNC_AND_ALL_SERVICES); + mUseSyncAndAllServices = + (ChromeSwitchPreference) findPreference(PREF_USE_SYNC_AND_ALL_SERVICES); mUseSyncAndAllServices.setOnPreferenceChangeListener(this); - mSyncGroup = (SigninExpandablePreferenceGroup) findPreference(SYNC_AND_PERSONALIZATION); + mSyncGroup = + (SigninExpandablePreferenceGroup) findPreference(PREF_SYNC_AND_PERSONALIZATION); mNonpersonalizedServices = - (SigninExpandablePreferenceGroup) findPreference(NONPERSONALIZED_SERVICES); + (SigninExpandablePreferenceGroup) findPreference(PREF_NONPERSONALIZED_SERVICES); - mSyncAutofill = (CheckBoxPreference) findPreference(PREFERENCE_SYNC_AUTOFILL); - mSyncBookmarks = (CheckBoxPreference) findPreference(PREFERENCE_SYNC_BOOKMARKS); - mSyncOmnibox = (CheckBoxPreference) findPreference(PREFERENCE_SYNC_OMNIBOX); - mSyncPasswords = (CheckBoxPreference) findPreference(PREFERENCE_SYNC_PASSWORDS); - mSyncRecentTabs = (CheckBoxPreference) findPreference(PREFERENCE_SYNC_RECENT_TABS); - mSyncSettings = (CheckBoxPreference) findPreference(PREFERENCE_SYNC_SETTINGS); - mPaymentsIntegration = (CheckBoxPreference) findPreference(PREFERENCE_PAYMENTS_INTEGRATION); + mSyncAutofill = (CheckBoxPreference) findPreference(PREF_SYNC_AUTOFILL); + mSyncBookmarks = (CheckBoxPreference) findPreference(PREF_SYNC_BOOKMARKS); + mSyncPaymentsIntegration = + (CheckBoxPreference) findPreference(PREF_SYNC_PAYMENTS_INTEGRATION); + mSyncHistory = (CheckBoxPreference) findPreference(PREF_SYNC_HISTORY); + mSyncPasswords = (CheckBoxPreference) findPreference(PREF_SYNC_PASSWORDS); + mSyncRecentTabs = (CheckBoxPreference) findPreference(PREF_SYNC_RECENT_TABS); + mSyncSettings = (CheckBoxPreference) findPreference(PREF_SYNC_SETTINGS); - mSyncEncryption = findPreference(PREFERENCE_ENCRYPTION); - mSyncEncryption.setOnPreferenceClickListener(this); - mManageSyncData = findPreference(PREFERENCE_SYNC_MANAGE_DATA); - mManageSyncData.setOnPreferenceClickListener(this); - mSyncErrorCard = findPreference(PREFERENCE_SYNC_ERROR_CARD); - mSyncErrorCard.setOnPreferenceClickListener(this); + mSyncEncryption = findPreference(PREF_ENCRYPTION); + mSyncEncryption.setOnPreferenceClickListener( + toOnClickListener(this::onSyncEncryptionClicked)); + mManageSyncData = findPreference(PREF_SYNC_MANAGE_DATA); + mManageSyncData.setOnPreferenceClickListener( + toOnClickListener(this::openDashboardTabInNewActivityStack)); + mSyncErrorCard = findPreference(PREF_SYNC_ERROR_CARD); + mSyncErrorCard.setOnPreferenceClickListener( + toOnClickListener(this::onSyncErrorCardClicked)); - mAllTypes = new CheckBoxPreference[] {mSyncAutofill, mSyncBookmarks, mSyncOmnibox, - mSyncPasswords, mSyncRecentTabs, mSyncSettings, mPaymentsIntegration}; - for (CheckBoxPreference type : mAllTypes) { + mSyncAllTypes = + new CheckBoxPreference[] {mSyncAutofill, mSyncBookmarks, mSyncPaymentsIntegration, + mSyncHistory, mSyncPasswords, mSyncRecentTabs, mSyncSettings}; + for (CheckBoxPreference type : mSyncAllTypes) { type.setOnPreferenceChangeListener(this); } + mSearchSuggestions = (ChromeBaseCheckBoxPreference) findPreference(PREF_SEARCH_SUGGESTIONS); + mSearchSuggestions.setOnPreferenceChangeListener(this); + mSearchSuggestions.setManagedPreferenceDelegate(mManagedPreferenceDelegate); + mNetworkPredictions = (ChromeBaseCheckBoxPreference) findPreference(PREF_NETWORK_PREDICTIONS); mNetworkPredictions.setOnPreferenceChangeListener(this); @@ -214,15 +217,9 @@ mNavigationError.setOnPreferenceChangeListener(this); mNavigationError.setManagedPreferenceDelegate(mManagedPreferenceDelegate); - mSearchSuggestions = (ChromeBaseCheckBoxPreference) findPreference(PREF_SEARCH_SUGGESTIONS); - mSearchSuggestions.setOnPreferenceChangeListener(this); - mSearchSuggestions.setManagedPreferenceDelegate(mManagedPreferenceDelegate); - - mContextualSearch = findPreference(PREF_CONTEXTUAL_SEARCH); - if (!ContextualSearchFieldTrial.isEnabled()) { - removePreference(mNonpersonalizedServices, mContextualSearch); - mContextualSearch = null; - } + mSafeBrowsing = (ChromeBaseCheckBoxPreference) findPreference(PREF_SAFE_BROWSING); + mSafeBrowsing.setOnPreferenceChangeListener(this); + mSafeBrowsing.setManagedPreferenceDelegate(mManagedPreferenceDelegate); Preference extendedReporting = findPreference(PREF_SAFE_BROWSING_EXTENDED_REPORTING); Preference scoutReporting = findPreference(PREF_SAFE_BROWSING_SCOUT_REPORTING); @@ -237,15 +234,29 @@ mSafeBrowsingReporting.setOnPreferenceChangeListener(this); mSafeBrowsingReporting.setManagedPreferenceDelegate(mManagedPreferenceDelegate); - mSafeBrowsing = (ChromeBaseCheckBoxPreference) findPreference(PREF_SAFE_BROWSING); - mSafeBrowsing.setOnPreferenceChangeListener(this); - mSafeBrowsing.setManagedPreferenceDelegate(mManagedPreferenceDelegate); - mUsageAndCrashReporting = findPreference(PREF_USAGE_AND_CRASH_REPORTING); + mContextualSearch = findPreference(PREF_CONTEXTUAL_SEARCH); + if (!ContextualSearchFieldTrial.isEnabled()) { + removePreference(mNonpersonalizedServices, mContextualSearch); + mContextualSearch = null; + } + updatePreferences(); } + private Preference.OnPreferenceClickListener toOnClickListener(Runnable runnable) { + return preference -> { + if (!isResumed()) { + // This event could come in after onPause if the user clicks back and the preference + // at roughly the same time. See http://b/5983282. + return false; + } + runnable.run(); + return false; + }; + } + @Override public void onActivityCreated(@Nullable Bundle savedInstanceState) { super.onActivityCreated(savedInstanceState); @@ -301,7 +312,7 @@ // Inform sync that the user has finished setting up sync at least once. mProfileSyncService.setFirstSetupComplete(); } - PersonalDataManager.setPaymentsIntegrationEnabled(mPaymentsIntegration.isChecked()); + PersonalDataManager.setPaymentsIntegrationEnabled(mSyncPaymentsIntegration.isChecked()); // Setup is done. This was preventing sync from turning on even if it was enabled. // TODO(crbug/557784): This needs to be set only when we think the user is done with // setting up. This means: 1) If the user leaves the Sync Settings screen (via back) @@ -318,7 +329,7 @@ @Override public boolean onPreferenceChange(Preference preference, Object newValue) { String key = preference.getKey(); - if (USE_SYNC_AND_ALL_SERVICES.equals(key)) { + if (PREF_USE_SYNC_AND_ALL_SERVICES.equals(key)) { boolean enabled = (boolean) newValue; if (enabled) { mSyncGroup.setExpanded(true); @@ -350,8 +361,8 @@ // // If the user unchecks the autofill sync checkbox, then disable and uncheck // the payments integration checkbox. - mPaymentsIntegration.setEnabled(preferenceChecked); - mPaymentsIntegration.setChecked(preferenceChecked); + mSyncPaymentsIntegration.setEnabled(preferenceChecked); + mSyncPaymentsIntegration.setChecked(preferenceChecked); } updateSyncStateFromSelectedModelTypes(); }); @@ -359,31 +370,6 @@ return true; } - /** Callback for OnPreferenceClickListener */ - @Override - public boolean onPreferenceClick(Preference preference) { - if (!isResumed()) { - // This event could come in after onPause if the user clicks back and the preference at - // roughly the same time. See http://b/5983282 - return false; - } - if (preference == mSyncEncryption && mProfileSyncService.isEngineInitialized()) { - if (mProfileSyncService.isPassphraseRequiredForDecryption()) { - displayPassphraseDialog(); - } else { - displayPassphraseTypeDialog(); - return true; - } - } else if (preference == mManageSyncData) { - openDashboardTabInNewActivityStack(); - return true; - } else if (preference == mSyncErrorCard) { - onSyncErrorCardClicked(); - return true; - } - return false; - } - /** * ProfileSyncService.SyncStateChangedListener implementation, listens to sync state changes. * @@ -412,7 +398,7 @@ } private boolean isSyncTypePreference(Preference preference) { - for (Preference pref : mAllTypes) { + for (Preference pref : mSyncAllTypes) { if (pref == preference) return true; } return false; @@ -502,7 +488,7 @@ Set<Integer> types = new HashSet<>(); if (mSyncAutofill.isChecked()) types.add(ModelType.AUTOFILL); if (mSyncBookmarks.isChecked()) types.add(ModelType.BOOKMARKS); - if (mSyncOmnibox.isChecked()) types.add(ModelType.TYPED_URLS); + if (mSyncHistory.isChecked()) types.add(ModelType.TYPED_URLS); if (mSyncPasswords.isChecked()) types.add(ModelType.PASSWORDS); if (mSyncRecentTabs.isChecked()) types.add(ModelType.PROXY_TABS); if (mSyncSettings.isChecked()) types.add(ModelType.PREFERENCES); @@ -607,6 +593,16 @@ displayCustomPassphraseDialog(); } + private void onSyncEncryptionClicked() { + if (!mProfileSyncService.isEngineInitialized()) return; + + if (mProfileSyncService.isPassphraseRequiredForDecryption()) { + displayPassphraseDialog(); + } else { + displayPassphraseTypeDialog(); + } + } + /** Opens the Google Dashboard where the user can control the data stored for the account. */ private void openDashboardTabInNewActivityStack() { Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(DASHBOARD_URL)); @@ -628,11 +624,11 @@ && mProfileSyncService.isCryptographerReady(); Set<Integer> syncTypes = mProfileSyncService.getPreferredDataTypes(); boolean syncAutofill = syncTypes.contains(ModelType.AUTOFILL); - for (CheckBoxPreference pref : mAllTypes) { + for (CheckBoxPreference pref : mSyncAllTypes) { // Set the default state of each data type checkbox. boolean canSyncType = true; if (pref == mSyncPasswords) canSyncType = passwordSyncConfigurable; - if (pref == mPaymentsIntegration) { + if (pref == mSyncPaymentsIntegration) { canSyncType = syncAutofill || syncEverything; } @@ -647,13 +643,13 @@ // to match the prefs. mSyncAutofill.setChecked(syncAutofill); mSyncBookmarks.setChecked(syncTypes.contains(ModelType.BOOKMARKS)); - mSyncOmnibox.setChecked(syncTypes.contains(ModelType.TYPED_URLS)); + mSyncPaymentsIntegration.setChecked( + syncAutofill && PersonalDataManager.isPaymentsIntegrationEnabled()); + mSyncHistory.setChecked(syncTypes.contains(ModelType.TYPED_URLS)); mSyncPasswords.setChecked( passwordSyncConfigurable && syncTypes.contains(ModelType.PASSWORDS)); mSyncRecentTabs.setChecked(syncTypes.contains(ModelType.PROXY_TABS)); mSyncSettings.setChecked(syncTypes.contains(ModelType.PREFERENCES)); - mPaymentsIntegration.setChecked( - syncAutofill && PersonalDataManager.isPaymentsIntegrationEnabled()); } } @@ -783,21 +779,21 @@ private void updatePreferences() { mUseSyncAndAllServices.setChecked(UnifiedConsentServiceBridge.isUnifiedConsentGiven()); - mNavigationError.setChecked(mPrefServiceBridge.isResolveNavigationErrorEnabled()); - mNetworkPredictions.setChecked(mPrefServiceBridge.getNetworkPredictionEnabled()); mSearchSuggestions.setChecked(mPrefServiceBridge.isSearchSuggestEnabled()); + mNetworkPredictions.setChecked(mPrefServiceBridge.getNetworkPredictionEnabled()); + mNavigationError.setChecked(mPrefServiceBridge.isResolveNavigationErrorEnabled()); mSafeBrowsing.setChecked(mPrefServiceBridge.isSafeBrowsingEnabled()); mSafeBrowsingReporting.setChecked( mPrefServiceBridge.isSafeBrowsingExtendedReportingEnabled()); CharSequence textOn = getActivity().getResources().getText(R.string.text_on); CharSequence textOff = getActivity().getResources().getText(R.string.text_off); + mUsageAndCrashReporting.setSummary( + mPrivacyPrefManager.isUsageAndCrashReportingPermittedByUser() ? textOn : textOff); if (mContextualSearch != null) { boolean isContextualSearchEnabled = !mPrefServiceBridge.isContextualSearchDisabled(); mContextualSearch.setSummary(isContextualSearchEnabled ? textOn : textOff); } - mUsageAndCrashReporting.setSummary( - mPrivacyPrefManager.isUsageAndCrashReportingPermittedByUser() ? textOn : textOff); } private ManagedPreferenceDelegate createManagedPreferenceDelegate() {
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/signin/AccountManagementFragment.java b/chrome/android/java/src/org/chromium/chrome/browser/signin/AccountManagementFragment.java index a07af7d..589bccf 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/signin/AccountManagementFragment.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/signin/AccountManagementFragment.java
@@ -34,6 +34,7 @@ import org.chromium.base.metrics.RecordUserAction; import org.chromium.chrome.R; import org.chromium.chrome.browser.AppHooks; +import org.chromium.chrome.browser.ChromeFeatureList; import org.chromium.chrome.browser.preferences.ChromeBasePreference; import org.chromium.chrome.browser.preferences.PrefServiceBridge; import org.chromium.chrome.browser.preferences.Preferences; @@ -87,7 +88,10 @@ public static final String PREF_CHILD_CONTENT = "child_content"; public static final String PREF_CHILD_CONTENT_DIVIDER = "child_content_divider"; public static final String PREF_GOOGLE_ACTIVITY_CONTROLS = "google_activity_controls"; + public static final String PREF_GOOGLE_ACTIVITY_CONTROLS_DIVIDER = + "google_activity_controls_divider"; public static final String PREF_SYNC_SETTINGS = "sync_settings"; + public static final String PREF_SYNC_SETTINGS_DIVIDER = "sync_settings_divider"; public static final String PREF_SIGN_OUT = "sign_out"; public static final String PREF_SIGN_OUT_DIVIDER = "sign_out_divider"; @@ -221,6 +225,10 @@ getPreferenceScreen().removePreference(signOutSwitch); getPreferenceScreen().removePreference(findPreference(PREF_SIGN_OUT_DIVIDER)); } else { + signOutSwitch.setTitle(ChromeFeatureList.isEnabled(ChromeFeatureList.UNIFIED_CONSENT) + ? R.string.sign_out_and_turn_off_sync + : R.string.account_management_sign_out); + signOutSwitch.setEnabled(getSignOutAllowedPreferenceValue()); signOutSwitch.setOnPreferenceClickListener(preference -> { if (!isVisible() || !isResumed()) return false; @@ -260,8 +268,14 @@ } private void configureSyncSettings() { + Preference syncSettings = findPreference(PREF_SYNC_SETTINGS); + if (ChromeFeatureList.isEnabled(ChromeFeatureList.UNIFIED_CONSENT)) { + getPreferenceScreen().removePreference(syncSettings); + getPreferenceScreen().removePreference(findPreference(PREF_SYNC_SETTINGS_DIVIDER)); + return; + } final Preferences preferences = (Preferences) getActivity(); - findPreference(PREF_SYNC_SETTINGS).setOnPreferenceClickListener(preference -> { + syncSettings.setOnPreferenceClickListener(preference -> { if (!isVisible() || !isResumed()) return false; if (ProfileSyncService.get() == null) return true; @@ -273,6 +287,12 @@ private void configureGoogleActivityControls() { Preference pref = findPreference(PREF_GOOGLE_ACTIVITY_CONTROLS); + if (ChromeFeatureList.isEnabled(ChromeFeatureList.UNIFIED_CONSENT)) { + getPreferenceScreen().removePreference(pref); + getPreferenceScreen().removePreference( + findPreference(PREF_GOOGLE_ACTIVITY_CONTROLS_DIVIDER)); + return; + } if (mProfile.isChild()) { pref.setSummary(R.string.sign_in_google_activity_controls_message_child_account); }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/CustomTabToolbar.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/CustomTabToolbar.java index de3ac47..2a6366b 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/CustomTabToolbar.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/CustomTabToolbar.java
@@ -827,7 +827,7 @@ @Override public boolean useModernDesign() { - return false; + return true; } @Override
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarPhone.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarPhone.java index 3d98256..ba89f9e 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarPhone.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarPhone.java
@@ -22,7 +22,6 @@ import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.ColorDrawable; import android.graphics.drawable.Drawable; -import android.graphics.drawable.TransitionDrawable; import android.os.Build; import android.os.SystemClock; import android.support.annotation.IntDef; @@ -261,8 +260,6 @@ protected final int mToolbarSidePadding; private final int mModernLocationBarLateralInset; - protected int mLocationBarBackgroundCornerRadius; - protected int mLocationBarVerticalMargin; private ValueAnimator mBrandColorTransitionAnimation; private boolean mBrandColorTransitionActive; @@ -415,33 +412,19 @@ * Initializes the background, padding, margins, etc. for the location bar background. */ protected void initLocationBarBackground() { - if (mLocationBar.useModernDesign()) { - Resources res = getResources(); - mModernLocationBarBackgroundHeight = - res.getDimensionPixelSize(R.dimen.modern_toolbar_background_size); - mLocationBarBackground = createModernLocationBarBackground(getResources()); - mLocationBarBackground.getPadding(mLocationBarBackgroundPadding); - mLocationBarBackground.mutate(); - mLocationBar.setPadding(mLocationBarBackgroundPadding.left, - mLocationBarBackgroundPadding.top, mLocationBarBackgroundPadding.right, - mLocationBarBackgroundPadding.bottom); + Resources res = getResources(); + mModernLocationBarBackgroundHeight = + res.getDimensionPixelSize(R.dimen.modern_toolbar_background_size); + mLocationBarBackground = createModernLocationBarBackground(getResources()); + mLocationBarBackground.getPadding(mLocationBarBackgroundPadding); + mLocationBarBackground.mutate(); + mLocationBar.setPadding(mLocationBarBackgroundPadding.left, + mLocationBarBackgroundPadding.top, mLocationBarBackgroundPadding.right, + mLocationBarBackgroundPadding.bottom); - mModernLocationBarExtraFocusedStartMargin = getResources().getDimensionPixelSize( - R.dimen.modern_toolbar_background_focused_left_margin); - mLocationBarBackgroundCornerRadius = 0; - } else { - mLocationBarVerticalMargin = - getResources().getDimensionPixelOffset(R.dimen.location_bar_vertical_margin); - mLocationBarBackgroundCornerRadius = - getResources().getDimensionPixelOffset(R.dimen.location_bar_corner_radius); + mModernLocationBarExtraFocusedStartMargin = getResources().getDimensionPixelSize( + R.dimen.modern_toolbar_background_focused_left_margin); - mLocationBarBackground = - ApiCompatibilityUtils.getDrawable(getResources(), R.drawable.card_single); - mLocationBarBackground.getPadding(mLocationBarBackgroundPadding); - mLocationBar.setPadding(mLocationBarBackgroundPadding.left, - mLocationBarBackgroundPadding.top, mLocationBarBackgroundPadding.right, - mLocationBarBackgroundPadding.bottom); - } mActiveLocationBarBackground = mLocationBarBackground; } @@ -474,7 +457,7 @@ */ private int getLocationBarColorForToolbarColor(int toolbarColor) { return ColorUtils.getTextBoxColorForToolbarBackground( - getResources(), false, toolbarColor, mLocationBar.useModernDesign()); + getResources(), false, toolbarColor, true); } private void inflateTabSwitchingResources() { @@ -560,7 +543,7 @@ }); onHomeButtonUpdate(HomepageManager.isHomepageEnabled()); - if (mNewTabButton != null && mLocationBar.useModernDesign()) mNewTabButton.setIsModern(); + if (mNewTabButton != null) mNewTabButton.postNativeInitialization(); setTabSwitcherAnimationMenuDrawable(); updateVisualsForToolbarState(); @@ -771,12 +754,9 @@ * @return The width of the location bar when it has focus. */ protected int getFocusedLocationBarWidth(int containerWidth, int priorVisibleWidth) { - int width = containerWidth - (2 * mToolbarSidePadding) + priorVisibleWidth; - - if (mLocationBar.useModernDesign()) { - width = width - mModernLocationBarExtraFocusedStartMargin - - mLocationBarBackgroundPadding.left - mLocationBarBackgroundPadding.right; - } + int width = containerWidth - (2 * mToolbarSidePadding) + priorVisibleWidth + - mModernLocationBarExtraFocusedStartMargin - mLocationBarBackgroundPadding.left + - mLocationBarBackgroundPadding.right; return width; } @@ -786,19 +766,11 @@ * @return The left margin of the location bar when it has focus. */ protected int getFocusedLocationBarLeftMargin(int priorVisibleWidth) { - if (mLocationBar.useModernDesign()) { - int baseMargin = mToolbarSidePadding + mLocationBarBackgroundPadding.left; - if (ApiCompatibilityUtils.isLayoutRtl(mLocationBar)) { - return baseMargin; - } else { - return baseMargin - priorVisibleWidth + mModernLocationBarExtraFocusedStartMargin; - } - } - + int baseMargin = mToolbarSidePadding + mLocationBarBackgroundPadding.left; if (ApiCompatibilityUtils.isLayoutRtl(mLocationBar)) { - return mToolbarSidePadding; + return baseMargin; } else { - return -priorVisibleWidth + mToolbarSidePadding; + return baseMargin - priorVisibleWidth + mModernLocationBarExtraFocusedStartMargin; } } @@ -811,7 +783,7 @@ // Uses getMeasuredWidth()s instead of getLeft() because this is called in onMeasure // and the layout values have not yet been set. if (visualState == VisualState.NEW_TAB_NORMAL) { - return mLocationBar.useModernDesign() ? mToolbarSidePadding : 0; + return mToolbarSidePadding; } else if (ApiCompatibilityUtils.isLayoutRtl(this)) { return getBoundsAfterAccountingForRightButtons(); } else { @@ -839,7 +811,7 @@ // Uses getMeasuredWidth()s instead of getRight() because this is called in onMeasure // and the layout values have not yet been set. if (visualState == VisualState.NEW_TAB_NORMAL) { - return getMeasuredWidth() - (mLocationBar.useModernDesign() ? mToolbarSidePadding : 0); + return getMeasuredWidth() - mToolbarSidePadding; } else if (ApiCompatibilityUtils.isLayoutRtl(this)) { return getMeasuredWidth() - getBoundsAfterAccountingForLeftButton(); } else { @@ -888,34 +860,29 @@ Resources res = getResources(); switch (visualState) { case VisualState.NEW_TAB_NORMAL: - if (mLocationBar.useModernDesign() && mUrlExpansionPercent == 1.f) { + if (mUrlExpansionPercent == 1.f) { // When the location bar reaches the top of the screen, the background needs // to change back to the default, solid color so that the NTP content is // not visible beneath the toolbar. - return ColorUtils.getDefaultThemeColor( - getResources(), mLocationBar.useModernDesign(), false); + return ColorUtils.getDefaultThemeColor(getResources(), true, false); } return Color.TRANSPARENT; case VisualState.NORMAL: - return ColorUtils.getDefaultThemeColor( - getResources(), mLocationBar.useModernDesign(), false); + return ColorUtils.getDefaultThemeColor(getResources(), true, false); case VisualState.INCOGNITO: - return ColorUtils.getDefaultThemeColor( - getResources(), mLocationBar.useModernDesign(), true); + return ColorUtils.getDefaultThemeColor(getResources(), true, true); case VisualState.BRAND_COLOR: return getToolbarDataProvider().getPrimaryColor(); case VisualState.TAB_SWITCHER_NORMAL: case VisualState.TAB_SWITCHER_INCOGNITO: - if (usingHorizontalTabSwitcher()) return Color.TRANSPARENT; - - if (mLocationBar.useModernDesign()) { - if (!DeviceClassManager.enableAccessibilityLayout()) return Color.TRANSPARENT; + if (DeviceClassManager.enableAccessibilityLayout()) { int colorId = visualState == VisualState.TAB_SWITCHER_NORMAL ? R.color.modern_primary_color : R.color.incognito_modern_primary_color; return ApiCompatibilityUtils.getColor(res, colorId); } - return ApiCompatibilityUtils.getColor(res, R.color.tab_switcher_background); + + return Color.TRANSPARENT; default: assert false; return ApiCompatibilityUtils.getColor(res, R.color.default_primary_color); @@ -1001,7 +968,7 @@ // - The right most visible location bar child view. // - The bottom of the viewport is aligned with the bottom of the location bar. // Additional padding can be applied for use during animations. - int verticalMargin = getLocationBarBackgroundVerticalMargin(expansion); + int verticalMargin = getLocationBarBackgroundVerticalMargin(); out.set(leftViewPosition, mLocationBar.getTop() + verticalMargin, rightViewPosition, @@ -1009,16 +976,11 @@ } /** - * @param expansion The current url expansion percent. * @return The vertical margin to apply to the location bar background. The margin is used to * clip the background. */ - protected int getLocationBarBackgroundVerticalMargin(float expansion) { - if (mLocationBar.useModernDesign()) { - return (int) ((mLocationBar.getHeight() - mModernLocationBarBackgroundHeight) / 2); - } - - return (int) MathUtils.interpolate(mLocationBarVerticalMargin, 0, expansion); + protected int getLocationBarBackgroundVerticalMargin() { + return (int) ((mLocationBar.getHeight() - mModernLocationBarBackgroundHeight) / 2); } /** @@ -1038,8 +1000,7 @@ * has focus. */ protected int getFocusedLeftPositionOfLocationBarBackground() { - if (mLocationBar.useModernDesign()) return mToolbarSidePadding; - return -mLocationBarBackgroundCornerRadius; + return mToolbarSidePadding; } /** @@ -1060,8 +1021,7 @@ * has focus. */ protected int getFocusedRightPositionOfLocationBarBackground() { - if (mLocationBar.useModernDesign()) return getWidth() - mToolbarSidePadding; - return getWidth() + mLocationBarBackgroundCornerRadius; + return getWidth() - mToolbarSidePadding; } private float getExpansionPercentForVisualState(@VisualState int visualState) { @@ -1165,8 +1125,7 @@ // Only transition theme colors if in static tab mode that is not the NTP. In practice this // only runs when you focus the omnibox on a web page. - if (mLocationBar.useModernDesign() && !isLocationBarShownInNTP() - && mTabSwitcherState == STATIC_TAB) { + if (!isLocationBarShownInNTP() && mTabSwitcherState == STATIC_TAB) { int defaultColor = ColorUtils.getDefaultThemeColor(getResources(), true, isIncognito()); int defaultLocationBarColor = getLocationBarColorForToolbarColor(defaultColor); int primaryColor = getToolbarDataProvider().getPrimaryColor(); @@ -1227,9 +1186,8 @@ if (mHomeButton != null) mHomeButton.setTranslationY(0); } - if (!(mLocationBar.useModernDesign() && mUrlFocusChangeInProgress)) { - mToolbarShadow.setAlpha( - mLocationBar.useModernDesign() && mUrlBar.hasFocus() ? 0.f : 1.f); + if (!mUrlFocusChangeInProgress) { + mToolbarShadow.setAlpha(mUrlBar.hasFocus() ? 0.f : 1.f); } mLocationBar.setAlpha(1); @@ -1255,11 +1213,10 @@ if (mTabSwitcherState == TAB_SWITCHER || mTabSwitcherState == ENTERING_TAB_SWITCHER) return; boolean isExpanded = mUrlExpansionPercent > 0f; - boolean useModern = mLocationBar.useModernDesign(); setAncestorsShouldClipChildren(!isExpanded); - if (!(useModern && mUrlFocusChangeInProgress)) { + if (!mUrlFocusChangeInProgress) { float alpha = 0.f; - if (useModern && !mUrlBar.hasFocus() && mNtpSearchBoxScrollPercent == 1.f) { + if (!mUrlBar.hasFocus() && mNtpSearchBoxScrollPercent == 1.f) { alpha = 1.f; } mToolbarShadow.setAlpha(alpha); @@ -1281,12 +1238,9 @@ int leftBoundDifference = mNtpSearchBoxBounds.left - mLocationBarBackgroundBounds.left; int rightBoundDifference = mNtpSearchBoxBounds.right - mLocationBarBackgroundBounds.right; - int verticalInset = 0; - if (useModern) { - verticalInset = (int) (getResources().getDimensionPixelSize( + int verticalInset = (int) (getResources().getDimensionPixelSize( R.dimen.ntp_search_box_bounds_vertical_inset_modern) - * (1.f - mUrlExpansionPercent)); - } + * (1.f - mUrlExpansionPercent)); mLocationBarBackgroundNtpOffset.set( Math.round(leftBoundDifference * shrinkage), locationBarTranslationY, @@ -1294,13 +1248,8 @@ locationBarTranslationY); mLocationBarBackgroundNtpOffset.inset(0, verticalInset); - // The omnibox background bounds are outset by |mLocationBarBackgroundCornerRadius| in the - // fully expanded state (and only there!) to hide the rounded corners, so undo that before - // applying the shrinkage factor. - mLocationBarNtpOffsetLeft = - (leftBoundDifference - mLocationBarBackgroundCornerRadius) * shrinkage; - mLocationBarNtpOffsetRight = - (rightBoundDifference + mLocationBarBackgroundCornerRadius) * shrinkage; + mLocationBarNtpOffsetLeft = leftBoundDifference * shrinkage; + mLocationBarNtpOffsetRight = rightBoundDifference * shrinkage; mLocationBarBackgroundAlpha = isExpanded ? 255 : 0; mForceDrawLocationBarBackground = mLocationBarBackgroundAlpha > 0; @@ -1549,28 +1498,6 @@ boolean clipped = false; if (shouldDrawLocationBar()) { canvas.save(); - int backgroundAlpha; - if (mTabSwitcherModeAnimation != null) { - // Fade out/in the location bar towards the beginning of the animations to avoid - // large jumps of stark white. - backgroundAlpha = - (int) (Math.pow(mLocationBar.getAlpha(), 3) * mLocationBarBackgroundAlpha); - } else if (getToolbarDataProvider().isUsingBrandColor() - && !mBrandColorTransitionActive) { - backgroundAlpha = mUnfocusedLocationBarUsesTransparentBg - ? (int) (MathUtils.interpolate(LOCATION_BAR_TRANSPARENT_BACKGROUND_ALPHA, - 255, mUrlExpansionPercent)) - : 255; - } else { - backgroundAlpha = mLocationBarBackgroundAlpha; - } - - // If modern is enabled the location bar background is opaque. - // TODO(mdjones): The location bar background should always be opaque. We have the - // capability to determine the foreground color without alpha and it reduces the amount - // of state that this class tracks. - if (mLocationBar.useModernDesign()) backgroundAlpha = 255; - mLocationBarBackground.setAlpha(backgroundAlpha); if (shouldDrawLocationBarBackground()) { if (mActiveLocationBarBackground instanceof NtpSearchBoxDrawable) { @@ -1649,26 +1576,10 @@ // This is a workaround for http://crbug.com/574928. Since Jelly Bean is the lowest version // we support now and the next deprecation target, we decided to simply workaround. - // The drawable also has to be set here when using modern design. - // TODO(twellington): Update XML for modern and remove || check after modern launches. - if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.JELLY_BEAN - || mLocationBar.useModernDesign()) { - mToolbarShadow.setImageDrawable(getToolbarShadowDrawable()); + if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.JELLY_BEAN) { + mToolbarShadow.setImageDrawable(ApiCompatibilityUtils.getDrawable( + getResources(), R.drawable.modern_toolbar_shadow)); } - if (mLocationBar.useModernDesign()) { - mToolbarShadow.getLayoutParams().height = - getResources().getDimensionPixelSize(R.dimen.toolbar_shadow_height); - mToolbarShadow.setScaleType(ImageView.ScaleType.FIT_XY); - } - } - - /** - * @return The {@link Drawable} to use for the toolbar shadow. - */ - private Drawable getToolbarShadowDrawable() { - return ApiCompatibilityUtils.getDrawable(getResources(), - mLocationBar.useModernDesign() ? R.drawable.modern_toolbar_shadow - : R.drawable.toolbar_shadow); } @Override @@ -1749,17 +1660,15 @@ @Override public void getLocationBarContentRect(Rect outRect) { updateLocationBarBackgroundBounds(outRect, VisualState.NORMAL); - if (mLocationBar.useModernDesign()) { - // Remove the insets for the composited version. - // TODO(mdjones): The image asset used to render the location bar in java is different - // from the one used in the compositor. The java asset has padding applied to both sides - // while the compositor one does not. The value manipulation here is to account for that - // difference. Instead we should just remove the padding from the toolbar asset, but - // there is much more overhead in updating the animations. Fix this once modern is the - // new default. - outRect.left -= mModernLocationBarLateralInset; - outRect.right += mModernLocationBarLateralInset; - } + // Remove the insets for the composited version. + // TODO(mdjones): The image asset used to render the location bar in java is different + // from the one used in the compositor. The java asset has padding applied to both sides + // while the compositor one does not. The value manipulation here is to account for that + // difference. Instead we should just remove the padding from the toolbar asset, but + // there is much more overhead in updating the animations. Fix this once modern is the + // new default. + outRect.left -= mModernLocationBarLateralInset; + outRect.right += mModernLocationBarLateralInset; } @Override @@ -2154,12 +2063,10 @@ animators.add(animator); } - if (mLocationBar.useModernDesign()) { - animator = ObjectAnimator.ofFloat(mToolbarShadow, ALPHA, 0); - animator.setDuration(URL_FOCUS_CHANGE_ANIMATION_DURATION_MS); - animator.setInterpolator(BakedBezierInterpolator.TRANSFORM_CURVE); - animators.add(animator); - } + animator = ObjectAnimator.ofFloat(mToolbarShadow, ALPHA, 0); + animator.setDuration(URL_FOCUS_CHANGE_ANIMATION_DURATION_MS); + animator.setInterpolator(BakedBezierInterpolator.TRANSFORM_CURVE); + animators.add(animator); } private void populateUrlClearFocusingAnimatorSet(List<Animator> animators) { @@ -2236,12 +2143,10 @@ } } - if (mLocationBar.useModernDesign()) { - animator = ObjectAnimator.ofFloat(mToolbarShadow, ALPHA, 1); - animator.setDuration(URL_FOCUS_CHANGE_ANIMATION_DURATION_MS); - animator.setInterpolator(BakedBezierInterpolator.TRANSFORM_CURVE); - animators.add(animator); - } + animator = ObjectAnimator.ofFloat(mToolbarShadow, ALPHA, 1); + animator.setDuration(URL_FOCUS_CHANGE_ANIMATION_DURATION_MS); + animator.setInterpolator(BakedBezierInterpolator.TRANSFORM_CURVE); + animators.add(animator); } @Override @@ -2251,8 +2156,6 @@ triggerUrlFocusAnimation(hasFocus); if (hasFocus) dismissTabSwitcherCallout(); - - transitionShadowDrawable(hasFocus); } protected void triggerUrlFocusAnimation(final boolean hasFocus) { @@ -2417,10 +2320,8 @@ } updateToolbarBackground( ColorUtils.getColorWithOverlay(initialColor, finalColor, fraction)); - if (mLocationBar.useModernDesign()) { - updateModernLocationBarColor(ColorUtils.getColorWithOverlay( - initialLocationBarColor, finalLocationBarColor, fraction)); - } + updateModernLocationBarColor(ColorUtils.getColorWithOverlay( + initialLocationBarColor, finalLocationBarColor, fraction)); } }); mBrandColorTransitionAnimation.addListener(new AnimatorListenerAdapter() { @@ -2447,11 +2348,11 @@ mVisibleNewTabPage = getToolbarDataProvider().getNewTabPageForCurrentTab(); if (mVisibleNewTabPage != null && mVisibleNewTabPage.isLocationBarShownInNTP()) { mVisibleNewTabPage.setSearchBoxScrollListener(this); - if (mLocationBar.useModernDesign()) { - NtpSearchBoxDrawable ntpSearchBox = new NtpSearchBoxDrawable(getContext(), this); - mVisibleNewTabPage.setSearchBoxBackground(ntpSearchBox); - mActiveLocationBarBackground = ntpSearchBox; - } + + NtpSearchBoxDrawable ntpSearchBox = new NtpSearchBoxDrawable(getContext(), this); + mVisibleNewTabPage.setSearchBoxBackground(ntpSearchBox); + mActiveLocationBarBackground = ntpSearchBox; + requestLayout(); } else if (wasShowingNtp) { // Convert the previous NTP scroll percentage to URL focus percentage because that @@ -2487,27 +2388,6 @@ @Override protected void handleFindToolbarStateChange(boolean showing) { setVisibility(showing ? View.GONE : View.VISIBLE); - - transitionShadowDrawable(showing); - } - - /** - * Transition the shadow drawable, if a transition drawable is being used. - * @param startTransition Whether the transition, showing the second layer on top of the first, - * should begin. See {@link TransitionDrawable#startTransition(int)}. - * If false, the transition will be reversed. - * See {@link TransitionDrawable#reverseTransition(int)}. - */ - private void transitionShadowDrawable(boolean startTransition) { - // Modern does not use a transition drawable for the shadow. - if (mLocationBar.useModernDesign()) return; - - TransitionDrawable shadowDrawable = (TransitionDrawable) mToolbarShadow.getDrawable(); - if (startTransition) { - shadowDrawable.startTransition(URL_FOCUS_CHANGE_ANIMATION_DURATION_MS); - } else { - shadowDrawable.reverseTransition(URL_FOCUS_CHANGE_ANIMATION_DURATION_MS); - } } private boolean isLocationBarShownInNTP() { @@ -2538,13 +2418,11 @@ } private boolean hideShadowForIncognitoNtp() { - return mLocationBar.useModernDesign() && isIncognito() - && NewTabPage.isNTPUrl(getToolbarDataProvider().getCurrentUrl()); + return isIncognito() && NewTabPage.isNTPUrl(getToolbarDataProvider().getCurrentUrl()); } private boolean hideShadowForInterstitial() { - return mLocationBar.useModernDesign() && getToolbarDataProvider() != null - && getToolbarDataProvider().getTab() != null + return getToolbarDataProvider() != null && getToolbarDataProvider().getTab() != null && (getToolbarDataProvider().getTab().isShowingInterstitialPage() || getToolbarDataProvider().getTab().isShowingErrorPage()); } @@ -2688,9 +2566,7 @@ getMenuButton().setTint(mUseLightToolbarDrawables ? mLightModeTint : mDarkModeTint); } - if (mLocationBar.useModernDesign()) { - updateModernLocationBarColor(getLocationBarColorForToolbarColor(currentPrimaryColor)); - } + updateModernLocationBarColor(getLocationBarColorForToolbarColor(currentPrimaryColor)); if (mExperimentalButton != null) { mExperimentalButton.setTint(mUseLightToolbarDrawables ? mLightModeTint : mDarkModeTint); } @@ -2703,16 +2579,6 @@ if (mIsHomeButtonEnabled && mHomeButton != null) mHomeButton.setTint(tint); mLocationBar.updateVisualsForState(); - // Remove the side padding for incognito to ensure the badge icon aligns correctly with the - // background of the location bar. - if (mLocationBar.isIncognitoBadgeVisible()) { - mLocationBar.setPadding( - 0, mLocationBarBackgroundPadding.top, 0, mLocationBarBackgroundPadding.bottom); - } else { - mLocationBar.setPadding( - mLocationBarBackgroundPadding.left, mLocationBarBackgroundPadding.top, - mLocationBarBackgroundPadding.right, mLocationBarBackgroundPadding.bottom); - } // We update the alpha before comparing the visual state as we need to change // its value when entering and exiting TabSwitcher mode. @@ -2742,12 +2608,10 @@ getMenuButtonWrapper().setVisibility(View.VISIBLE); } - if (mLocationBar.useModernDesign()) { - DrawableCompat.setTint(mLocationBarBackground, - isIncognito() ? Color.WHITE - : ApiCompatibilityUtils.getColor( - getResources(), R.color.modern_light_grey)); - } + DrawableCompat.setTint(mLocationBarBackground, + isIncognito() ? Color.WHITE + : ApiCompatibilityUtils.getColor( + getResources(), R.color.modern_light_grey)); } @Override
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/vr/VR_JAVA_OWNERS b/chrome/android/java/src/org/chromium/chrome/browser/vr/VR_JAVA_OWNERS index 88f07e7..c356d956 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/vr/VR_JAVA_OWNERS +++ b/chrome/android/java/src/org/chromium/chrome/browser/vr/VR_JAVA_OWNERS
@@ -1,4 +1,3 @@ -asimjour@chromium.org mthiesse@chromium.org # TEAM: xr-dev@chromium.org
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/widget/newtab/NewTabButton.java b/chrome/android/java/src/org/chromium/chrome/browser/widget/newtab/NewTabButton.java index ca8f0ae6..8897d03 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/widget/newtab/NewTabButton.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/widget/newtab/NewTabButton.java
@@ -4,9 +4,6 @@ package org.chromium.chrome.browser.widget.newtab; -import android.animation.Animator; -import android.animation.AnimatorSet; -import android.animation.ObjectAnimator; import android.content.Context; import android.content.res.ColorStateList; import android.graphics.Canvas; @@ -21,10 +18,6 @@ import org.chromium.chrome.R; import org.chromium.chrome.browser.ChromeFeatureList; import org.chromium.chrome.browser.device.DeviceClassManager; -import org.chromium.chrome.browser.widget.animation.AnimatorProperties; - -import java.util.ArrayList; -import java.util.List; /** * Button for creating new tabs. @@ -33,43 +26,39 @@ private final ColorStateList mLightModeTint; private final ColorStateList mDarkModeTint; - private Drawable mNormalDrawable; - private Drawable mIncognitoDrawable; private VectorDrawableCompat mModernDrawable; private boolean mIsIncognito; - private AnimatorSet mTransitionAnimation; + private boolean mIsNativeReady; /** * Constructor for inflating from XML. */ public NewTabButton(Context context, AttributeSet attrs) { super(context, attrs); - mNormalDrawable = ApiCompatibilityUtils.getDrawable( - getResources(), R.drawable.btn_new_tab_white); - mNormalDrawable.setBounds( - 0, 0, mNormalDrawable.getIntrinsicWidth(), mNormalDrawable.getIntrinsicHeight()); - mNormalDrawable.setCallback(this); - mIncognitoDrawable = ApiCompatibilityUtils.getDrawable( - getResources(), R.drawable.btn_new_tab_incognito); - mIncognitoDrawable.setBounds( - 0, 0, - mIncognitoDrawable.getIntrinsicWidth(), mIncognitoDrawable.getIntrinsicHeight()); - mIncognitoDrawable.setCallback(this); + mIsIncognito = false; mLightModeTint = AppCompatResources.getColorStateList(getContext(), R.color.light_mode_tint); mDarkModeTint = AppCompatResources.getColorStateList(getContext(), R.color.dark_mode_tint); + mModernDrawable = VectorDrawableCompat.create( + getContext().getResources(), R.drawable.new_tab_icon, getContext().getTheme()); + mModernDrawable.setBounds( + 0, 0, mModernDrawable.getIntrinsicWidth(), mModernDrawable.getIntrinsicHeight()); + mModernDrawable.setCallback(this); + } + + /** + * Called to finish initializing the NewTabButton. Must be called after native initialization + * is finished. + */ + public void postNativeInitialization() { + mIsNativeReady = true; + updateDrawableTint(); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { - int desiredWidth; - if (mModernDrawable != null) { - desiredWidth = mModernDrawable.getIntrinsicWidth(); - } else { - desiredWidth = Math.max( - mIncognitoDrawable.getIntrinsicWidth(), mNormalDrawable.getIntrinsicWidth()); - } + int desiredWidth = mModernDrawable.getIntrinsicWidth(); desiredWidth += getPaddingLeft() + getPaddingRight(); widthMeasureSpec = MeasureSpec.makeMeasureSpec(desiredWidth, MeasureSpec.EXACTLY); super.onMeasure(widthMeasureSpec, heightMeasureSpec); @@ -86,15 +75,7 @@ canvas.save(); if (!isRtl) canvas.translate(paddingStart, 0); - if (mModernDrawable != null) { - drawIcon(canvas, mModernDrawable, isRtl, widthWithoutPadding); - } else { - drawIcon(canvas, mNormalDrawable, isRtl, widthWithoutPadding); - if (mIsIncognito - || (mTransitionAnimation != null && mTransitionAnimation.isRunning())) { - drawIcon(canvas, mIncognitoDrawable, isRtl, widthWithoutPadding); - } - } + drawIcon(canvas, mModernDrawable, isRtl, widthWithoutPadding); canvas.restore(); } @@ -111,7 +92,7 @@ @Override public void invalidateDrawable(Drawable dr) { - if (dr == mIncognitoDrawable || dr == mNormalDrawable || dr == mModernDrawable) { + if (dr == mModernDrawable) { invalidate(); } else { super.invalidateDrawable(dr); @@ -119,22 +100,6 @@ } /** - * Set the icon to use the drawable for Chrome Modern. - */ - public void setIsModern() { - mModernDrawable = VectorDrawableCompat.create( - getContext().getResources(), R.drawable.new_tab_icon, getContext().getTheme()); - mModernDrawable.setState(getDrawableState()); - updateDrawableTint(); - mModernDrawable.setBounds( - 0, 0, mModernDrawable.getIntrinsicWidth(), mModernDrawable.getIntrinsicHeight()); - mModernDrawable.setCallback(this); - - mNormalDrawable = null; - mIncognitoDrawable = null; - } - - /** * Updates the visual state based on whether incognito or normal tabs are being created. * @param incognito Whether the button is now used for creating incognito tabs. */ @@ -142,41 +107,8 @@ if (mIsIncognito == incognito) return; mIsIncognito = incognito; - if (mModernDrawable != null) { - updateDrawableTint(); - invalidateDrawable(mModernDrawable); - return; - } - - if (mTransitionAnimation != null) { - mTransitionAnimation.cancel(); - mTransitionAnimation = null; - } - - Drawable fadeOutDrawable = incognito ? mNormalDrawable : mIncognitoDrawable; - Drawable fadeInDrawable = incognito ? mIncognitoDrawable : mNormalDrawable; - - if (getVisibility() != VISIBLE) { - fadeOutDrawable.setAlpha(0); - fadeInDrawable.setAlpha(255); - return; - } - - List<Animator> animations = new ArrayList<Animator>(); - Animator animation = ObjectAnimator.ofInt( - fadeOutDrawable, AnimatorProperties.DRAWABLE_ALPHA_PROPERTY, 255, 0); - animation.setDuration(100); - animations.add(animation); - - animation = ObjectAnimator.ofInt( - fadeInDrawable, AnimatorProperties.DRAWABLE_ALPHA_PROPERTY, 0, 255); - animation.setStartDelay(150); - animation.setDuration(100); - animations.add(animation); - - mTransitionAnimation = new AnimatorSet(); - mTransitionAnimation.playTogether(animations); - mTransitionAnimation.start(); + updateDrawableTint(); + invalidateDrawable(mModernDrawable); } /** Called when accessibility status is changed. */ @@ -188,20 +120,15 @@ protected void drawableStateChanged() { super.drawableStateChanged(); - if (mModernDrawable != null) { - mModernDrawable.setState(getDrawableState()); - } else { - mNormalDrawable.setState(getDrawableState()); - mIncognitoDrawable.setState(getDrawableState()); - } + mModernDrawable.setState(getDrawableState()); } /** Update the tint for the icon drawable for Chrome Modern. */ private void updateDrawableTint() { - final boolean shouldUseLightMode = - (DeviceClassManager.enableAccessibilityLayout() - || ChromeFeatureList.isEnabled( - ChromeFeatureList.HORIZONTAL_TAB_SWITCHER_ANDROID)) + final boolean shouldUseLightMode = mIsNativeReady + && (DeviceClassManager.enableAccessibilityLayout() + || ChromeFeatureList.isEnabled( + ChromeFeatureList.HORIZONTAL_TAB_SWITCHER_ANDROID)) && mIsIncognito; mModernDrawable.setTintList(shouldUseLightMode ? mLightModeTint : mDarkModeTint); }
diff --git a/chrome/android/java/strings/OWNERS b/chrome/android/java/strings/OWNERS new file mode 100644 index 0000000..8cb2f0b --- /dev/null +++ b/chrome/android/java/strings/OWNERS
@@ -0,0 +1,6 @@ +# Please ensure you check for duplicate strings before adding new ones. +# +# Prefer generalizing feature specific existing strings instead of creating +# a new version of the same (or an extremely similiar string). + +*
diff --git a/chrome/android/java/strings/android_chrome_strings.grd b/chrome/android/java/strings/android_chrome_strings.grd index ce32e6ab..d1c134c 100644 --- a/chrome/android/java/strings/android_chrome_strings.grd +++ b/chrome/android/java/strings/android_chrome_strings.grd
@@ -313,6 +313,9 @@ Sync error occurred, tap to get details. </message> <!-- Unified consent preferences --> + <message name="IDS_SIGN_OUT_AND_TURN_OFF_SYNC" desc="The text for a preferences row that for signs out the user and turns off sync."> + Sign out and turn off sync + </message> <message name="IDS_USE_SYNC_AND_ALL_SERVICES" desc="Title for switch preference which enables sync'ing of all data types and turns on all Chrome services that communicate with Google."> Use sync and all services </message> @@ -1589,7 +1592,7 @@ <message name="IDS_PAYMENTS_INTEGRATION_LEGACY" desc="Title for preference which enables import of Google Pay data for Autofill. 'Google Pay' should not be translated as it is the product name."> Cards and addresses using Google Pay </message> - <message name="IDS_PAYMENTS_INTEGRATION" desc="Title for preference which enables import of Google Pay data for Autofill. 'Google Pay' should not be translated as it is the product name."> + <message name="IDS_SYNC_PAYMENTS_INTEGRATION" desc="Title for preference which enables import of Google Pay data for Autofill. 'Google Pay' should not be translated as it is the product name."> Credit cards and addresses using Google Pay </message> <message name="IDS_SYNC_ACTIVITY_AND_INTERACTIONS_TITLE" desc="Title for preference which enables sync'ing of activity and interactions.">
diff --git a/chrome/android/junit/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingControllerTest.java b/chrome/android/junit/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingControllerTest.java index 51787c3..6ee61d26 100644 --- a/chrome/android/junit/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingControllerTest.java +++ b/chrome/android/junit/src/org/chromium/chrome/browser/autofill/keyboard_accessory/ManualFillingControllerTest.java
@@ -262,6 +262,36 @@ } @Test + public void testPasswordTabRestoredWhenClosingTabIsUndone() { + ManualFillingMediator mediator = mController.getMediatorForTesting(); + KeyboardAccessoryModel keyboardAccessoryModel = + mediator.getKeyboardAccessory().getMediatorForTesting().getModelForTesting(); + assertThat(keyboardAccessoryModel.getTabList().size(), is(0)); + + // Create a new tab with a passwords tab: + Tab tab = addTab(mediator, 1111, null); + mController.registerPasswordProvider(new PropertyProvider<>()); + assertThat(keyboardAccessoryModel.getTabList().size(), is(1)); + + // Simulate closing the tab: + mediator.getTabModelObserverForTesting().willCloseTab(tab, false); + mediator.getTabObserverForTesting().onHidden(tab); + // Temporary removes the tab, but keeps it in memory so it can be brought back on undo: + assertThat(keyboardAccessoryModel.getTabList().size(), is(0)); + + // Simulate undo closing the tab and selecting it: + mediator.getTabModelObserverForTesting().tabClosureUndone(tab); + switchTab(mediator, null, tab); + // There should still be a tab in the accessory: + assertThat(keyboardAccessoryModel.getTabList().size(), is(1)); + + // Simulate closing the tab and committing to it (i.e. wait out undo message): + closeTab(mediator, tab, null); + mediator.getTabModelObserverForTesting().tabClosureCommitted(tab); + assertThat(keyboardAccessoryModel.getTabList().size(), is(0)); + } + + @Test public void testRecoversFromInvalidState() { ManualFillingMediator mediator = mController.getMediatorForTesting();
diff --git a/chrome/android/webapk/libs/common/src/org/chromium/webapk/lib/common/WebApkMetaDataKeys.java b/chrome/android/webapk/libs/common/src/org/chromium/webapk/lib/common/WebApkMetaDataKeys.java index e060f056..7f0cf03 100644 --- a/chrome/android/webapk/libs/common/src/org/chromium/webapk/lib/common/WebApkMetaDataKeys.java +++ b/chrome/android/webapk/libs/common/src/org/chromium/webapk/lib/common/WebApkMetaDataKeys.java
@@ -31,5 +31,7 @@ "org.chromium.webapk.shell_apk.iconUrlsAndIconMurmur2Hashes"; public static final String WEB_MANIFEST_URL = "org.chromium.webapk.shell_apk.webManifestUrl"; public static final String BADGE_ICON_ID = "org.chromium.webapk.shell_apk.badgeIconId"; - public static final String SHARE_TEMPLATE = "org.chromium.webapk.shell_apk.shareTemplate"; + public static final String SHARE_ACTION = "org.chromium.webapk.shell_apk.shareAction"; + public static final String SHARE_PARAM_TITLE = "org.chromium.webapk.shell_apk.shareParamTitle"; + public static final String SHARE_PARAM_TEXT = "org.chromium.webapk.shell_apk.shareParamText"; }
diff --git a/chrome/android/webapk/shell_apk/AndroidManifest.xml b/chrome/android/webapk/shell_apk/AndroidManifest.xml index 4d9094a..c38a779 100644 --- a/chrome/android/webapk/shell_apk/AndroidManifest.xml +++ b/chrome/android/webapk/shell_apk/AndroidManifest.xml
@@ -43,7 +43,10 @@ android:label="{{{title}}}" android:theme="@android:style/Theme.Translucent.NoTitleBar" android:excludeFromRecents="true"> - <meta-data android:name="org.chromium.webapk.shell_apk.shareTemplate" android:value="{{{url_template}}}" /> + <meta-data android:name="org.chromium.webapk.shell_apk.shareAction" android:value="{{{action}}}" /> + <meta-data android:name="org.chromium.webapk.shell_apk.shareParamTitle" android:value="{{{param_title}}}" /> + <meta-data android:name="org.chromium.webapk.shell_apk.shareParamText" android:value="{{{param_text}}}" /> + <meta-data android:name="org.chromium.webapk.shell_apk.shareParamUrl" android:value="{{{param_url}}}" /> <intent-filter> <action android:name="android.intent.action.SEND" /> <category android:name="android.intent.category.DEFAULT" />
diff --git a/chrome/android/webapk/shell_apk/BUILD.gn b/chrome/android/webapk/shell_apk/BUILD.gn index 019d3ac..820c183 100644 --- a/chrome/android/webapk/shell_apk/BUILD.gn +++ b/chrome/android/webapk/shell_apk/BUILD.gn
@@ -221,6 +221,7 @@ java_files = [ "junit/src/org/chromium/webapk/shell_apk/HostBrowserClassLoaderTest.java", "junit/src/org/chromium/webapk/shell_apk/MainActivityTest.java", + "junit/src/org/chromium/webapk/shell_apk/ShareActivityTest.java", "junit/src/org/chromium/webapk/shell_apk/WebApkServiceImplWrapperTest.java", "junit/src/org/chromium/webapk/shell_apk/WebApkUtilsTest.java", ]
diff --git a/chrome/android/webapk/shell_apk/bound_manifest_config.json b/chrome/android/webapk/shell_apk/bound_manifest_config.json index 51be5688..1f07f4b 100644 --- a/chrome/android/webapk/shell_apk/bound_manifest_config.json +++ b/chrome/android/webapk/shell_apk/bound_manifest_config.json
@@ -24,11 +24,18 @@ "share_template": [{ "index": "0", "title": "Share All", - "url_template": "https://pwa.rocks/share_public?title={title}&text={text}&url={url}" + "action": "https://pwa.rocks/share.html", + "param_title": "title", + "param_text": "text", + "param_url": "url" }, { "index": "1", "title": "Share Title", - "url_template": "https://pwa.rocks/share_private?title={title}" + "action": "https://pwa.rocks/share_title.html", + "param_title": "title", + "param_text": "text", + "param_url": "url" }] + }
diff --git a/chrome/android/webapk/shell_apk/http_manifest_config.json b/chrome/android/webapk/shell_apk/http_manifest_config.json index 044c4cd..064d5952 100644 --- a/chrome/android/webapk/shell_apk/http_manifest_config.json +++ b/chrome/android/webapk/shell_apk/http_manifest_config.json
@@ -24,11 +24,17 @@ "share_template": [{ "index": "0", "title": "Share All", - "url_template": "http://pwa.rocks/share_public?title={title}&text={text}&url={url}" + "action": "http://pwa.rocks/share.html", + "param_title": "title", + "param_text": "text", + "param_url": "url" }, { "index": "1", "title": "Share Title", - "url_template": "http://pwa.rocks/share_private?title={title}" + "action": "http://pwa.rocks/share_title.html", + "param_title": "title", + "param_text": "text", + "param_url": "url" }] }
diff --git a/chrome/android/webapk/shell_apk/junit/src/org/chromium/webapk/shell_apk/ShareActivityTest.java b/chrome/android/webapk/shell_apk/junit/src/org/chromium/webapk/shell_apk/ShareActivityTest.java new file mode 100644 index 0000000..751b37c8 --- /dev/null +++ b/chrome/android/webapk/shell_apk/junit/src/org/chromium/webapk/shell_apk/ShareActivityTest.java
@@ -0,0 +1,96 @@ +// Copyright 2018 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. + +package org.chromium.webapk.shell_apk; + +import android.util.Pair; + +import org.junit.Assert; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.robolectric.annotation.Config; + +import org.chromium.testing.local.LocalRobolectricTestRunner; + +import java.util.ArrayList; + +/** + * Tests for ShareActivity's WebShareTarget parsing. + */ +@RunWith(LocalRobolectricTestRunner.class) +@Config(manifest = Config.NONE) +public class ShareActivityTest { + /* + * Test that {@link ShareActivity#createWebShareTargetUriString()} handles adding query + * parameters to an action url with different path formats. + */ + @Test + public void testCreateWebShareTargetUriStringBasic() { + ArrayList<Pair<String, String>> params = new ArrayList<>(); + params.add(new Pair<>("title", "mytitle")); + params.add(new Pair<>("foo", "bar")); + + String uri = + ShareActivity.createWebShareTargetUriString("https://www.chromium.org/wst", params); + Assert.assertEquals("https://www.chromium.org/wst?title=mytitle&foo=bar", uri); + + uri = ShareActivity.createWebShareTargetUriString("https://www.chromium.org/wst/", params); + Assert.assertEquals("https://www.chromium.org/wst/?title=mytitle&foo=bar", uri); + + uri = ShareActivity.createWebShareTargetUriString( + "https://www.chromium.org/base/wst.html", params); + Assert.assertEquals("https://www.chromium.org/base/wst.html?title=mytitle&foo=bar", uri); + + uri = ShareActivity.createWebShareTargetUriString( + "https://www.chromium.org/base/wst.html/", params); + Assert.assertEquals("https://www.chromium.org/base/wst.html/?title=mytitle&foo=bar", uri); + } + + /* + * Test that {@link ShareActivity#createWebShareTargetUriString()} skips null names or values. + */ + @Test + public void testCreateWebShareTargetUriStringNull() { + ArrayList<Pair<String, String>> params = new ArrayList<>(); + params.add(new Pair<>(null, "mytitle")); + params.add(new Pair<>("foo", null)); + params.add(new Pair<>("hello", "world")); + params.add(new Pair<>(null, null)); + // The baseUrl, shareAction and params are checked to be non-null in + // ShareActivity#extractShareTarget. + String uri = + ShareActivity.createWebShareTargetUriString("https://www.chromium.org/wst", params); + Assert.assertEquals("https://www.chromium.org/wst?hello=world", uri); + } + + /* + * Test that {@link ShareActivity#createWebShareTargetUriString()} handles replacing the query + * string of an action url with an existing query. + */ + @Test + public void testCreateWebShareTargetClearQuery() { + ArrayList<Pair<String, String>> params = new ArrayList<>(); + params.add(new Pair<>("hello", "world")); + params.add(new Pair<>("foobar", "baz")); + String uri = ShareActivity.createWebShareTargetUriString( + "https://www.chromium.org/wst?a=b&c=d", params); + Assert.assertEquals("https://www.chromium.org/wst?hello=world&foobar=baz", uri); + } + + /* + * Test that {@link ShareActivity#createWebShareTargetUriString()} escapes characters. + */ + @Test + public void testCreateWebShareTargetEscaping() { + ArrayList<Pair<String, String>> params = new ArrayList<>(); + params.add(new Pair<>("hello", "world !\"#$%&'()*+,-./0?@[\\]^_a`{}~")); + params.add(new Pair<>("foo bar", "baz")); + params.add(new Pair<>("a!\"#$%&'()*+,-./0?@[\\]^_a`{}~", "b")); + String uri = ShareActivity.createWebShareTargetUriString( + "https://www.chromium.org/wst%25%20space", params); + Assert.assertEquals( + "https://www.chromium.org/wst%25%20space?hello=world+!%22%23%24%25%26'()*%2B%2C-.%2F0%3F%40%5B%5C%5D%5E_a%60%7B%7D~&foo+bar=baz&a!%22%23%24%25%26'()*%2B%2C-.%2F0%3F%40%5B%5C%5D%5E_a%60%7B%7D~=b", + uri); + } +}
diff --git a/chrome/android/webapk/shell_apk/shell_apk_version.gni b/chrome/android/webapk/shell_apk/shell_apk_version.gni index ccbdc1d..db6bfe1 100644 --- a/chrome/android/webapk/shell_apk/shell_apk_version.gni +++ b/chrome/android/webapk/shell_apk/shell_apk_version.gni
@@ -6,7 +6,7 @@ # (including AndroidManifest.xml) is updated. This version should be incremented # prior to uploading a new ShellAPK to the WebAPK Minting Server. # Does not affect Chrome.apk -template_shell_apk_version = 48 +template_shell_apk_version = 49 # The ShellAPK version expected by Chrome. Chrome will try to update the WebAPK # if the WebAPK's ShellAPK version is less than |expected_shell_apk_version|.
diff --git a/chrome/android/webapk/shell_apk/src/org/chromium/webapk/shell_apk/ShareActivity.java b/chrome/android/webapk/shell_apk/src/org/chromium/webapk/shell_apk/ShareActivity.java index 2aa7e6f..3d76f7d3c 100644 --- a/chrome/android/webapk/shell_apk/src/org/chromium/webapk/shell_apk/ShareActivity.java +++ b/chrome/android/webapk/shell_apk/src/org/chromium/webapk/shell_apk/ShareActivity.java
@@ -12,14 +12,12 @@ import android.os.Bundle; import android.os.SystemClock; import android.text.TextUtils; +import android.util.Pair; import org.chromium.webapk.lib.common.WebApkConstants; import org.chromium.webapk.lib.common.WebApkMetaDataKeys; -import java.io.UnsupportedEncodingException; -import java.net.URLEncoder; -import java.util.regex.Matcher; -import java.util.regex.Pattern; +import java.util.ArrayList; /** * WebAPK's share handler Activity. @@ -43,65 +41,60 @@ } private String extractShareTarget() { - ActivityInfo ai; + ActivityInfo shareActivityInfo; try { - ai = getPackageManager().getActivityInfo( + shareActivityInfo = getPackageManager().getActivityInfo( getComponentName(), PackageManager.GET_META_DATA); } catch (PackageManager.NameNotFoundException e) { return null; } - if (ai == null || ai.metaData == null) { + if (shareActivityInfo == null || shareActivityInfo.metaData == null) { + return null; + } + Bundle metaData = shareActivityInfo.metaData; + + String shareAction = metaData.getString(WebApkMetaDataKeys.SHARE_ACTION); + if (TextUtils.isEmpty(shareAction)) { return null; } - String shareTemplate = ai.metaData.getString(WebApkMetaDataKeys.SHARE_TEMPLATE); - if (TextUtils.isEmpty(shareTemplate)) { - return null; - } + // These can be null, they are checked downstream. + ArrayList<Pair<String, String>> entryList = new ArrayList<>(); + entryList.add(new Pair<>(metaData.getString(WebApkMetaDataKeys.SHARE_PARAM_TITLE), + getIntent().getStringExtra(Intent.EXTRA_SUBJECT))); + entryList.add(new Pair<>(metaData.getString(WebApkMetaDataKeys.SHARE_PARAM_TEXT), + getIntent().getStringExtra(Intent.EXTRA_TEXT))); - String text = getIntent().getStringExtra(Intent.EXTRA_TEXT); - String shareUrl = getIntent().getStringExtra(Intent.EXTRA_SUBJECT); - Uri shareTemplateUri = Uri.parse(shareTemplate); - return shareTemplateUri.buildUpon() - .encodedQuery( - replacePlaceholders(shareTemplateUri.getEncodedQuery(), text, shareUrl)) - .encodedFragment( - replacePlaceholders(shareTemplateUri.getEncodedFragment(), text, shareUrl)) - .build() - .toString(); + return createWebShareTargetUriString(shareAction, entryList); } /** - * Replace {} placeholders in {@link toFill}. "{text}" and "{title}" are replaced with the - * supplied strings. All other placeholders are deleted. + * Converts the action url and parameters of a webshare target into a URI. + * Example: + * - action = "https://example.org/includinator/share.html" + * - params + * title param: "title" + * title intent: "news" + * text param: "description" + * text intent: "story" + * Becomes: + * https://example.org/includinator/share.html?title=news&description=story + * TODO(ckitagawa): The escaping behavior isn't entirely correct. The exact encoding is still + * being discussed at https://github.com/WICG/web-share-target/issues/59. */ - private String replacePlaceholders(String toFill, String text, String title) { - if (toFill == null) { - return null; - } - - Pattern placeholder = Pattern.compile("\\{.*?\\}"); - Matcher matcher = placeholder.matcher(toFill); - StringBuffer buffer = new StringBuffer(); - while (matcher.find()) { - String replacement = ""; - if (matcher.group().equals("{text}")) { - replacement = text; - } else if (matcher.group().equals("{title}")) { - replacement = title; + protected static String createWebShareTargetUriString( + String action, ArrayList<Pair<String, String>> entryList) { + Uri.Builder queryBuilder = new Uri.Builder(); + for (Pair<String, String> nameValue : entryList) { + if (!TextUtils.isEmpty(nameValue.first) && !TextUtils.isEmpty(nameValue.second)) { + // Uri.Builder does URL escaping. + queryBuilder.appendQueryParameter(nameValue.first, nameValue.second); } - - String encodedReplacement = ""; - if (replacement != null) { - try { - encodedReplacement = URLEncoder.encode(replacement, "UTF-8"); - } catch (UnsupportedEncodingException e) { - // Should not be reached. - } - } - matcher.appendReplacement(buffer, encodedReplacement); } - matcher.appendTail(buffer); - return buffer.toString(); + Uri shareUri = Uri.parse(action); + Uri.Builder builder = shareUri.buildUpon(); + // Uri.Builder uses %20 rather than + for spaces, the spec requires +. + builder.encodedQuery(queryBuilder.build().toString().replace("%20", "+").substring(1)); + return builder.build().toString(); } }
diff --git a/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.cc b/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.cc index d715b55..f6de6db6 100644 --- a/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.cc +++ b/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.cc
@@ -55,6 +55,18 @@ java_assistant_ui_controller_); } +void AssistantUiControllerAndroid::ChooseAddress( + base::OnceCallback<void(const std::string&)> callback) { + // TODO(crbug.com/806868): Implement ChooseAddress. + std::move(callback).Run(""); +} + +void AssistantUiControllerAndroid::ChooseCard( + base::OnceCallback<void(const std::string&)> callback) { + // TODO(crbug.com/806868): Implement ChooseCard. + std::move(callback).Run(""); +} + void AssistantUiControllerAndroid::Destroy(JNIEnv* env, const JavaParamRef<jobject>& obj) { ui_delegate_->OnDestroy();
diff --git a/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.h b/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.h index f943ce1..97bf928e 100644 --- a/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.h +++ b/chrome/browser/android/autofill_assistant/assistant_ui_controller_android.h
@@ -27,6 +27,10 @@ void ShowStatusMessage(const std::string& message) override; void ShowOverlay() override; void HideOverlay() override; + void ChooseAddress( + base::OnceCallback<void(const std::string&)> callback) override; + void ChooseCard( + base::OnceCallback<void(const std::string&)> callback) override; // Called by Java. void Destroy(JNIEnv* env, const base::android::JavaParamRef<jobject>& obj); @@ -41,4 +45,4 @@ }; } // namespace autofill_assistant. -#endif // CHROME_BROWSER_ANDROID_AUTOFILL_ASSISTANT_ASSISTANT_UI_CONTROLLER_ANDROID_H_ \ No newline at end of file +#endif // CHROME_BROWSER_ANDROID_AUTOFILL_ASSISTANT_ASSISTANT_UI_CONTROLLER_ANDROID_H_
diff --git a/chrome/browser/android/chrome_feature_list.cc b/chrome/browser/android/chrome_feature_list.cc index ee168e3..f6f3a49 100644 --- a/chrome/browser/android/chrome_feature_list.cc +++ b/chrome/browser/android/chrome_feature_list.cc
@@ -221,7 +221,7 @@ base::FEATURE_ENABLED_BY_DEFAULT}; const base::Feature kCCTResourcePrefetch{"CCTResourcePrefetch", - base::FEATURE_DISABLED_BY_DEFAULT}; + base::FEATURE_ENABLED_BY_DEFAULT}; const base::Feature kChromeDuetFeature{"ChromeDuet", base::FEATURE_DISABLED_BY_DEFAULT};
diff --git a/chrome/browser/android/password_manager/password_accessory_view_android.cc b/chrome/browser/android/password_manager/password_accessory_view_android.cc index 37acb1c..424a322 100644 --- a/chrome/browser/android/password_manager/password_accessory_view_android.cc +++ b/chrome/browser/android/password_manager/password_accessory_view_android.cc
@@ -69,8 +69,8 @@ base::android::AttachCurrentThread(), java_object_); } -void PasswordAccessoryViewAndroid::OpenKeyboard() { - Java_PasswordAccessoryBridge_openKeyboard( +void PasswordAccessoryViewAndroid::SwapSheetWithKeyboard() { + Java_PasswordAccessoryBridge_swapSheetWithKeyboard( base::android::AttachCurrentThread(), java_object_); }
diff --git a/chrome/browser/android/password_manager/password_accessory_view_android.h b/chrome/browser/android/password_manager/password_accessory_view_android.h index 413b9f1..3d0d2f9 100644 --- a/chrome/browser/android/password_manager/password_accessory_view_android.h +++ b/chrome/browser/android/password_manager/password_accessory_view_android.h
@@ -30,7 +30,7 @@ void OnItemsAvailable(const std::vector<AccessoryItem>& items) override; void OnAutomaticGenerationStatusChanged(bool available) override; void CloseAccessorySheet() override; - void OpenKeyboard() override; + void SwapSheetWithKeyboard() override; // Called from Java via JNI: void OnFaviconRequested(
diff --git a/chrome/browser/android/shortcut_info.cc b/chrome/browser/android/shortcut_info.cc index 864d9926..ca946dc 100644 --- a/chrome/browser/android/shortcut_info.cc +++ b/chrome/browser/android/shortcut_info.cc
@@ -71,8 +71,16 @@ for (const auto& icon : manifest.icons) icon_urls.push_back(icon.src.spec()); - if (manifest.share_target) - share_target_url_template = manifest.share_target->url_template; + if (manifest.share_target) { + share_target = ShareTarget(); + share_target->action = manifest.share_target->action; + if (!manifest.share_target->params.text.is_null()) + share_target->params.text = manifest.share_target->params.text.string(); + if (!manifest.share_target->params.title.is_null()) + share_target->params.title = manifest.share_target->params.title.string(); + if (!manifest.share_target->params.url.is_null()) + share_target->params.url = manifest.share_target->params.url.string(); + } } void ShortcutInfo::UpdateSource(const Source new_source) {
diff --git a/chrome/browser/android/shortcut_info.h b/chrome/browser/android/shortcut_info.h index 809b37b..b594bd88 100644 --- a/chrome/browser/android/shortcut_info.h +++ b/chrome/browser/android/shortcut_info.h
@@ -16,6 +16,19 @@ #include "third_party/skia/include/core/SkColor.h" #include "url/gurl.h" +// https://wicg.github.io/web-share-target/#dom-sharetargetparams +struct ShareTargetParams { + base::string16 title; + base::string16 text; + base::string16 url; +}; + +// https://wicg.github.io/web-share-target/#dom-sharetarget +struct ShareTarget { + GURL action; + ShareTargetParams params; +}; + // Information needed to create a shortcut via ShortcutHelper. struct ShortcutInfo { @@ -96,7 +109,7 @@ GURL best_primary_icon_url; GURL best_badge_icon_url; std::vector<std::string> icon_urls; - GURL share_target_url_template; + base::Optional<ShareTarget> share_target; }; #endif // CHROME_BROWSER_ANDROID_SHORTCUT_INFO_H_
diff --git a/chrome/browser/android/vr/OWNERS b/chrome/browser/android/vr/OWNERS index 26161de..7b73e4ba45 100644 --- a/chrome/browser/android/vr/OWNERS +++ b/chrome/browser/android/vr/OWNERS
@@ -1,4 +1,3 @@ -asimjour@chromium.org cjgrant@chromium.org mthiesse@chromium.org tiborg@chromium.org
diff --git a/chrome/browser/android/webapk/webapk.proto b/chrome/browser/android/webapk/webapk.proto index d889523..183c5b8 100644 --- a/chrome/browser/android/webapk/webapk.proto +++ b/chrome/browser/android/webapk/webapk.proto
@@ -95,7 +95,6 @@ } message Image { - enum Usage { PRIMARY_ICON = 1; BADGE_ICON = 2; @@ -118,8 +117,25 @@ reserved 2, 3, 4, 7; } +// A proto representing ShareTargetParams +// https://wicg.github.io/web-share-target/#dom-sharetargetparams +// Each field corresponds to key in ShareData. These are the query parameter +// keys to be used for the data supplied in a ShareData instance. +// ShareData: https://wicg.github.io/web-share#dom-sharedata +message ShareTargetParams { + optional string title = 1; + optional string text = 2; + optional string url = 3; +} + +// A proto representing a ShareTarget. +// https://wicg.github.io/web-share-target/#dom-sharetarget message ShareTarget { - // The URL template that contains placeholders to be replaced with shared - // data. - optional string url_template = 1; + // The URL to be resolved when sharing. + optional string action = 2; + optional ShareTargetParams params = 3; + // TODO(ckitagawa): + // Add method and enctype for POST (GET by default). + + reserved 1; }
diff --git a/chrome/browser/android/webapk/webapk_installer.cc b/chrome/browser/android/webapk/webapk_installer.cc index 510af09..67651b0 100644 --- a/chrome/browser/android/webapk/webapk_installer.cc +++ b/chrome/browser/android/webapk/webapk_installer.cc
@@ -214,10 +214,17 @@ std::string* scope = web_app_manifest->add_scopes(); scope->assign(GetScope(shortcut_info).spec()); - if (!shortcut_info.share_target_url_template.is_empty()) { + if (shortcut_info.share_target) { webapk::ShareTarget* share_target = web_app_manifest->add_share_targets(); - share_target->set_url_template( - shortcut_info.share_target_url_template.spec()); + share_target->set_action(shortcut_info.share_target->action.spec()); + webapk::ShareTargetParams* share_target_params = + share_target->mutable_params(); + share_target_params->set_title( + base::UTF16ToUTF8(shortcut_info.share_target->params.title)); + share_target_params->set_text( + base::UTF16ToUTF8(shortcut_info.share_target->params.text)); + share_target_params->set_url( + base::UTF16ToUTF8(shortcut_info.share_target->params.url)); } if (shortcut_info.best_primary_icon_url.is_empty()) {
diff --git a/chrome/browser/apps/guest_view/web_view_browsertest.cc b/chrome/browser/apps/guest_view/web_view_browsertest.cc index 1ab4de97b..6d53e3d 100644 --- a/chrome/browser/apps/guest_view/web_view_browsertest.cc +++ b/chrome/browser/apps/guest_view/web_view_browsertest.cc
@@ -4430,3 +4430,26 @@ embedder->GetRenderWidgetHostView()->GetRenderWidgetHost()->GetProcess(), guest->GetRenderWidgetHostView()->GetRenderWidgetHost())); } + +// Test that a guest sees the synthetic wheel events of a touchpad pinch. +IN_PROC_BROWSER_TEST_F(WebViewTest, TouchpadPinchSyntheticWheelEvents) { + ASSERT_TRUE(StartEmbeddedTestServer()); + LoadAppWithGuest("web_view/touchpad_pinch"); + content::WebContents* guest_contents = GetGuestWebContents(); + + // Ensure the compositor thread is aware of the wheel listener. + content::MainThreadFrameObserver synchronize_threads( + guest_contents->GetRenderWidgetHostView()->GetRenderWidgetHost()); + synchronize_threads.Wait(); + + ExtensionTestMessageListener synthetic_wheel_listener("Seen wheel event", + false); + + const gfx::Rect contents_rect = guest_contents->GetContainerBounds(); + const gfx::Point pinch_position(contents_rect.width() / 2, + contents_rect.height() / 2); + content::SimulateGesturePinchSequence(guest_contents, pinch_position, 1.23, + blink::kWebGestureDeviceTouchpad); + + ASSERT_TRUE(synthetic_wheel_listener.WaitUntilSatisfied()); +}
diff --git a/chrome/browser/apps/platform_apps/app_browsertest.cc b/chrome/browser/apps/platform_apps/app_browsertest.cc index bc99655..079e017b3 100644 --- a/chrome/browser/apps/platform_apps/app_browsertest.cc +++ b/chrome/browser/apps/platform_apps/app_browsertest.cc
@@ -1400,4 +1400,32 @@ ASSERT_TRUE(RunPlatformAppTest("platform_apps/new_window_about_blank")); } +// Test that an app window sees the synthetic wheel events of a touchpad pinch. +// While the app window itself does not scale in response to a pinch, we +// still offer the synthetic wheels for pages that want to implement custom +// pinch zoom behaviour. +IN_PROC_BROWSER_TEST_F(PlatformAppBrowserTest, + TouchpadPinchSyntheticWheelEvents) { + LoadAndLaunchPlatformApp("touchpad_pinch", "Launched"); + + WebContents* web_contents = GetFirstAppWindowWebContents(); + ASSERT_TRUE(web_contents); + + // Ensure the compositor thread is aware of the wheel listener. + content::MainThreadFrameObserver synchronize_threads( + web_contents->GetRenderWidgetHostView()->GetRenderWidgetHost()); + synchronize_threads.Wait(); + + ExtensionTestMessageListener synthetic_wheel_listener("Seen wheel event", + false); + + const gfx::Rect contents_rect = web_contents->GetContainerBounds(); + const gfx::Point pinch_position(contents_rect.width() / 2, + contents_rect.height() / 2); + content::SimulateGesturePinchSequence(web_contents, pinch_position, 1.23, + blink::kWebGestureDeviceTouchpad); + + ASSERT_TRUE(synthetic_wheel_listener.WaitUntilSatisfied()); +} + } // namespace extensions
diff --git a/chrome/browser/background_fetch/background_fetch_browsertest.cc b/chrome/browser/background_fetch/background_fetch_browsertest.cc index 653f9b97..971f9c6a 100644 --- a/chrome/browser/background_fetch/background_fetch_browsertest.cc +++ b/chrome/browser/background_fetch/background_fetch_browsertest.cc
@@ -12,6 +12,9 @@ #include "base/strings/stringprintf.h" #include "build/build_config.h" #include "chrome/browser/background_fetch/background_fetch_delegate_impl.h" +#include "chrome/browser/browser_process.h" +#include "chrome/browser/content_settings/host_content_settings_map_factory.h" +#include "chrome/browser/download/download_request_limiter.h" #include "chrome/browser/download/download_service_factory.h" #include "chrome/browser/offline_items_collection/offline_content_aggregator_factory.h" #include "chrome/browser/profiles/profile.h" @@ -19,6 +22,8 @@ #include "chrome/browser/ui/tabs/tab_strip_model.h" #include "chrome/test/base/in_process_browser_test.h" #include "chrome/test/base/ui_test_utils.h" +#include "components/content_settings/core/browser/host_content_settings_map.h" +#include "components/content_settings/core/common/content_settings_types.h" #include "components/download/public/background_service/download_service.h" #include "components/download/public/background_service/logger.h" #include "components/offline_items_collection/core/offline_content_aggregator.h" @@ -149,6 +154,8 @@ DISALLOW_COPY_AND_ASSIGN(OfflineContentProviderObserver); }; +} // namespace + class BackgroundFetchBrowserTest : public InProcessBrowserTest { public: BackgroundFetchBrowserTest() @@ -223,13 +230,13 @@ run_loop.Run(); } - // Runs the |script| and waits for a background fetch event. + // Runs the |script| and waits for a message. // Wrap in ASSERT_NO_FATAL_FAILURE(). - void RunScriptAndCheckResultingEvent(const std::string& script, - const std::string& expected_event) { + void RunScriptAndCheckResultingMessage(const std::string& script, + const std::string& expected_message) { std::string result; ASSERT_NO_FATAL_FAILURE(RunScript(script, &result)); - ASSERT_EQ(expected_event, result); + ASSERT_EQ(expected_message, result); } void GetVisualsForOfflineItemSync( @@ -292,6 +299,30 @@ std::move(quit_closure).Run(); } + void RevokeDownloadPermission() { + content::WebContents* web_contents = + browser()->tab_strip_model()->GetActiveWebContents(); + DownloadRequestLimiter::TabDownloadState* tab_download_state = + g_browser_process->download_request_limiter()->GetDownloadState( + web_contents, web_contents, true /* create */); + tab_download_state->set_download_seen(); + tab_download_state->SetDownloadStatusAndNotify( + DownloadRequestLimiter::DOWNLOADS_NOT_ALLOWED); + } + + void SetPermission(ContentSettingsType content_type, ContentSetting setting) { + auto* settings_map = + HostContentSettingsMapFactory::GetForProfile(browser()->profile()); + DCHECK(settings_map); + + ContentSettingsPattern host_pattern = + ContentSettingsPattern::FromURL(https_server_->base_url()); + + settings_map->SetContentSettingCustomScope( + host_pattern, host_pattern, content_type, + std::string() /* resource_identifier */, setting); + } + protected: download::DownloadService* download_service_{nullptr}; @@ -492,7 +523,7 @@ IN_PROC_BROWSER_TEST_F(BackgroundFetchBrowserTest, FetchesRunToCompletionAndUpdateTitle_Fetched) { - ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingEvent( + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( "RunFetchTillCompletion()", "backgroundfetchsuccess")); base::RunLoop().RunUntilIdle(); // Give `updateUI` a chance to propagate. EXPECT_TRUE( @@ -502,7 +533,7 @@ IN_PROC_BROWSER_TEST_F(BackgroundFetchBrowserTest, FetchesRunToCompletionAndUpdateTitle_Failed) { - ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingEvent( + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( "RunFetchTillCompletionWithMissingResource()", "backgroundfetchfail")); base::RunLoop().RunUntilIdle(); // Give `updateUI` a chance to propagate. EXPECT_TRUE( @@ -510,4 +541,62 @@ "New Failed Title!", base::CompareCase::SENSITIVE)); } -} // namespace +IN_PROC_BROWSER_TEST_F(BackgroundFetchBrowserTest, + FetchRejectedWithoutPermission) { + RevokeDownloadPermission(); + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( + "RunFetchAnExpectAnException()", + "This origin does not have permission to start a fetch.")); +} + +IN_PROC_BROWSER_TEST_F(BackgroundFetchBrowserTest, FetchFromServiceWorker) { + auto* settings_map = + HostContentSettingsMapFactory::GetForProfile(browser()->profile()); + DCHECK(settings_map); + + // Give the needed permissions. + SetPermission(CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS, + CONTENT_SETTING_ALLOW); + SetPermission(CONTENT_SETTINGS_TYPE_BACKGROUND_SYNC, CONTENT_SETTING_ALLOW); + + // The fetch should succeed. + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( + "StartFetchFromServiceWorker()", "backgroundfetchsuccess")); + + // Revoke Automatic Downloads permission. + SetPermission(CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS, + CONTENT_SETTING_BLOCK); + + // This should fail without the Automatic Downloads permission. + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( + "StartFetchFromServiceWorker()", "permissionerror")); + + // Reset Automatic Downloads permission and remove Background Sync permission + SetPermission(CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS, + CONTENT_SETTING_ALLOW); + SetPermission(CONTENT_SETTINGS_TYPE_BACKGROUND_SYNC, CONTENT_SETTING_BLOCK); + + // This should also fail now. + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( + "StartFetchFromServiceWorker()", "permissionerror")); +} + +IN_PROC_BROWSER_TEST_F(BackgroundFetchBrowserTest, + FetchFromChildFrameWithPermissions) { + // Give the needed permissions. + SetPermission(CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS, + CONTENT_SETTING_ALLOW); + SetPermission(CONTENT_SETTINGS_TYPE_BACKGROUND_SYNC, CONTENT_SETTING_ALLOW); + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( + "StartFetchFromIframe()", "backgroundfetchsuccess")); +} + +IN_PROC_BROWSER_TEST_F(BackgroundFetchBrowserTest, + FetchFromChildFrameWithMissingPermissions) { + SetPermission(CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS, + CONTENT_SETTING_ALLOW); + // Revoke Background Sync permission. + SetPermission(CONTENT_SETTINGS_TYPE_BACKGROUND_SYNC, CONTENT_SETTING_BLOCK); + ASSERT_NO_FATAL_FAILURE(RunScriptAndCheckResultingMessage( + "StartFetchFromIframe()", "permissionerror")); +}
diff --git a/chrome/browser/background_fetch/background_fetch_delegate_factory.cc b/chrome/browser/background_fetch/background_fetch_delegate_factory.cc index 6d6eea8..6c05e1e7 100644 --- a/chrome/browser/background_fetch/background_fetch_delegate_factory.cc +++ b/chrome/browser/background_fetch/background_fetch_delegate_factory.cc
@@ -6,6 +6,7 @@ #include "base/strings/string_number_conversions.h" #include "chrome/browser/background_fetch/background_fetch_delegate_impl.h" +#include "chrome/browser/content_settings/host_content_settings_map_factory.h" #include "chrome/browser/download/download_service_factory.h" #include "chrome/browser/profiles/incognito_helpers.h" #include "chrome/browser/profiles/profile.h" @@ -33,6 +34,7 @@ "BackgroundFetchService", BrowserContextDependencyManager::GetInstance()) { DependsOn(DownloadServiceFactory::GetInstance()); + DependsOn(HostContentSettingsMapFactory::GetInstance()); } BackgroundFetchDelegateFactory::~BackgroundFetchDelegateFactory() {}
diff --git a/chrome/browser/background_fetch/background_fetch_delegate_impl.cc b/chrome/browser/background_fetch/background_fetch_delegate_impl.cc index 6f33c52..5c628adc 100644 --- a/chrome/browser/background_fetch/background_fetch_delegate_impl.cc +++ b/chrome/browser/background_fetch/background_fetch_delegate_impl.cc
@@ -12,9 +12,14 @@ #include "base/strings/string_util.h" #include "base/strings/stringprintf.h" #include "build/build_config.h" +#include "chrome/browser/browser_process.h" +#include "chrome/browser/content_settings/host_content_settings_map_factory.h" +#include "chrome/browser/download/download_request_limiter.h" #include "chrome/browser/download/download_service_factory.h" #include "chrome/browser/offline_items_collection/offline_content_aggregator_factory.h" #include "chrome/browser/profiles/profile.h" +#include "components/content_settings/core/browser/host_content_settings_map.h" +#include "components/content_settings/core/common/content_settings_types.h" #include "components/download/public/background_service/download_params.h" #include "components/download/public/background_service/download_service.h" #include "components/offline_items_collection/core/offline_content_aggregator.h" @@ -25,16 +30,19 @@ #include "third_party/skia/include/core/SkBitmap.h" #include "ui/gfx/geometry/size.h" #include "ui/gfx/image/image_skia.h" +#include "url/origin.h" BackgroundFetchDelegateImpl::BackgroundFetchDelegateImpl( Profile* profile, const std::string& provider_namespace) : profile_(profile), + provider_namespace_(provider_namespace), offline_content_aggregator_( OfflineContentAggregatorFactory::GetForBrowserContext(profile)), weak_ptr_factory_(this) { DCHECK(profile_); - offline_content_aggregator_->RegisterProvider(provider_namespace, this); + DCHECK(!provider_namespace_.empty()); + offline_content_aggregator_->RegisterProvider(provider_namespace_, this); } BackgroundFetchDelegateImpl::~BackgroundFetchDelegateImpl() = default; @@ -59,10 +67,11 @@ BackgroundFetchDelegateImpl::JobDetails::JobDetails(JobDetails&&) = default; BackgroundFetchDelegateImpl::JobDetails::JobDetails( - std::unique_ptr<content::BackgroundFetchDescription> fetch_description) + std::unique_ptr<content::BackgroundFetchDescription> fetch_description, + const std::string& provider_namespace) : cancelled(false), offline_item(offline_items_collection::ContentId( - "background_fetch", + provider_namespace, fetch_description->job_unique_id)), fetch_description(std::move(fetch_description)) { UpdateOfflineItem(); @@ -148,6 +157,52 @@ std::move(callback).Run(display_size); } +void BackgroundFetchDelegateImpl::GetPermissionForOrigin( + const url::Origin& origin, + const content::ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + + if (wc_getter) { + // There is an associated frame so we might need to expose some permission + // UI using the DownloadRequestLimiter. + DownloadRequestLimiter* limiter = + g_browser_process->download_request_limiter(); + DCHECK(limiter); + + // The fetch should be thought of as one download. So the origin will be + // used as the URL, and the |request_method| is set to GET. + limiter->CanDownload(wc_getter, origin.GetURL(), "GET", + base::AdaptCallbackForRepeating(std::move(callback))); + return; + } + + auto* host_content_settings_map = + HostContentSettingsMapFactory::GetForProfile(profile_); + DCHECK(host_content_settings_map); + + // This is running from a worker context, use the Automatic Downloads + // permission. + ContentSetting content_setting = host_content_settings_map->GetContentSetting( + origin.GetURL(), origin.GetURL(), + CONTENT_SETTINGS_TYPE_AUTOMATIC_DOWNLOADS, + std::string() /* resource_identifier */); + + if (content_setting != CONTENT_SETTING_ALLOW) { + std::move(callback).Run(/* has_permission= */ false); + return; + } + + // Also make sure that Background Sync has permission. + // TODO(crbug.com/616321): Remove this check after Automatic Downloads + // permissions can be modified from Android. + content_setting = host_content_settings_map->GetContentSetting( + origin.GetURL(), origin.GetURL(), CONTENT_SETTINGS_TYPE_BACKGROUND_SYNC, + std::string() /* resource_identifier */); + + std::move(callback).Run(content_setting == CONTENT_SETTING_ALLOW); +} + void BackgroundFetchDelegateImpl::CreateDownloadJob( std::unique_ptr<content::BackgroundFetchDescription> fetch_description) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); @@ -155,7 +210,8 @@ std::string job_unique_id = fetch_description->job_unique_id; DCHECK(!job_details_map_.count(job_unique_id)); auto emplace_result = job_details_map_.emplace( - job_unique_id, JobDetails(std::move(fetch_description))); + job_unique_id, + JobDetails(std::move(fetch_description), provider_namespace_)); const JobDetails& details = emplace_result.first->second; for (const auto& download_guid : details.fetch_description->current_guids) {
diff --git a/chrome/browser/background_fetch/background_fetch_delegate_impl.h b/chrome/browser/background_fetch/background_fetch_delegate_impl.h index 81200ea..c1356e1 100644 --- a/chrome/browser/background_fetch/background_fetch_delegate_impl.h +++ b/chrome/browser/background_fetch/background_fetch_delegate_impl.h
@@ -52,6 +52,10 @@ // BackgroundFetchDelegate implementation: void GetIconDisplaySize(GetIconDisplaySizeCallback callback) override; + void GetPermissionForOrigin( + const url::Origin& origin, + const content::ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) override; void CreateDownloadJob(std::unique_ptr<content::BackgroundFetchDescription> fetch_description) override; void DownloadUrl(const std::string& job_unique_id, @@ -110,8 +114,9 @@ private: struct JobDetails { JobDetails(JobDetails&&); - explicit JobDetails( - std::unique_ptr<content::BackgroundFetchDescription> fetch_description); + JobDetails( + std::unique_ptr<content::BackgroundFetchDescription> fetch_description, + const std::string& provider_namespace); ~JobDetails(); void UpdateOfflineItem(); @@ -146,6 +151,10 @@ // The profile this service is being created for. Profile* profile_; + // The namespace provided to the |offline_content_aggregator_| and used when + // creating Content IDs. + std::string provider_namespace_; + // The BackgroundFetchDelegateImplFactory depends on the // DownloadServiceFactory, so |download_service_| should outlive |this|. download::DownloadService* download_service_ = nullptr;
diff --git a/chrome/browser/browser_resources.grd b/chrome/browser/browser_resources.grd index 860c373..fe903f3 100644 --- a/chrome/browser/browser_resources.grd +++ b/chrome/browser/browser_resources.grd
@@ -80,7 +80,7 @@ <include name="IDR_WEBAUTHN_ILLUSTRATION_BLE_TAP_1X" file="resources\webauthn\ble_tap.png" type="BINDATA" /> <include name="IDR_WEBAUTHN_ILLUSTRATION_BLE_PIN_1X" file="resources\webauthn\ble_pin.png" type="BINDATA" /> <include name="IDR_WEBAUTHN_ILLUSTRATION_ERROR_BLUETOOTH_1X" file="resources\webauthn\error_bt.png" type="BINDATA" /> - <include name="IDR_WEBAUTHN_ILLUSTRATION_ERROR_TIMEOUT_1X" file="resources\webauthn\error_timeout.png" type="BINDATA" /> + <include name="IDR_WEBAUTHN_ILLUSTRATION_ERROR_1X" file="resources\webauthn\error.png" type="BINDATA" /> <include name="IDR_WEBAUTHN_ILLUSTRATION_PHONE_1X" file="resources\webauthn\phone.png" type="BINDATA" /> <include name="IDR_WEBAUTHN_ILLUSTRATION_USB_1X" file="resources\webauthn\usb.png" type="BINDATA" /> <include name="IDR_WEBAUTHN_ILLUSTRATION_WELCOME_1X" file="resources\webauthn\welcome.png" type="BINDATA" />
diff --git a/chrome/browser/certificate_manager_model.cc b/chrome/browser/certificate_manager_model.cc index ce279a0..4fac677f 100644 --- a/chrome/browser/certificate_manager_model.cc +++ b/chrome/browser/certificate_manager_model.cc
@@ -7,8 +7,11 @@ #include <utility> #include "base/bind.h" +#include "base/callback_helpers.h" #include "base/i18n/time_formatting.h" #include "base/logging.h" +#include "base/memory/weak_ptr.h" +#include "base/sequence_checker.h" #include "base/stl_util.h" #include "base/strings/utf_string_conversions.h" #include "build/build_config.h" @@ -25,14 +28,14 @@ #include "net/cert/x509_util_nss.h" #include "ui/base/l10n/l10n_util.h" -// TODO(wychen): ChromeOS headers should only be included when building -// ChromeOS, and the following headers should be guarded by -// #if defined(OS_CHROMEOS). However, the types are actually -// used, and it takes another CL to clean them up. -// Reference: crbug.com/720159 +#if defined(OS_CHROMEOS) #include "chrome/browser/chromeos/certificate_provider/certificate_provider.h" #include "chrome/browser/chromeos/certificate_provider/certificate_provider_service.h" #include "chrome/browser/chromeos/certificate_provider/certificate_provider_service_factory.h" +#include "chrome/browser/chromeos/policy/policy_certificate_provider.h" +#include "chrome/browser/chromeos/policy/user_network_configuration_updater.h" +#include "chrome/browser/chromeos/policy/user_network_configuration_updater_factory.h" +#endif using content::BrowserThread; @@ -71,8 +74,403 @@ return org; } +#if defined(OS_CHROMEOS) +// Log message for an operation that can not be performed on a certificate of a +// given source. +constexpr char kOperationNotPermitted[] = + "Operation not permitted on a certificate. Source: "; +#endif // OS_CHROMEOS + } // namespace +// A source of certificates that should be displayed on the certificate manager +// UI. Currently, a CertsSource yields CertInfo objects. Each CertInfo contains +// a NSS ScopedCERTCertificate. +class CertificateManagerModel::CertsSource { + public: + // |certs_source_updated_callback| will be invoked when the list of + // certificates provided by this CertsSource changes. + explicit CertsSource(base::RepeatingClosure certs_source_updated_callback) + : certs_source_updated_callback_(certs_source_updated_callback) {} + virtual ~CertsSource() = default; + + // Returns the CertInfos provided by this CertsSource. + const std::vector<std::unique_ptr<CertificateManagerModel::CertInfo>>& + cert_infos() const { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + return cert_infos_; + } + + // Returns true if |cert| is in this CertsSource's certificate list. + bool HasCert(CERTCertificate* cert) const { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + for (const auto& cert_info : cert_infos_) { + if (cert_info->cert() == cert) + return true; + } + return false; + } + + // Triggers a refresh of this CertsSource. When done, the + // |certs_source_updated_callback| passed to the constructor will be invoked. + virtual void Refresh() = 0; + + // If any CertsSource's |IsHoldBackUpdates| is returning true, the + // CertificateManagerModel will not notify its Observer about updates. + bool IsHoldBackUpdates() const { return hold_back_updates_; } + + // Set trust values for certificate. + // |trust_bits| should be a bit field of TRUST* values from NSSCertDatabase. + // Returns true on success or false on failure. + virtual bool SetCertTrust(CERTCertificate* cert, + net::CertType type, + net::NSSCertDatabase::TrustBits trust_bits) = 0; + + // Delete the cert. Returns true on success. |cert| is still valid when this + // function returns. + virtual bool Delete(CERTCertificate* cert) = 0; + + protected: + // To be called by subclasses to set the CertInfo list provided by this + // CertsSource. If this CertsSource is signalling that updates should be held + // back (|SetHoldBackUpdates(true)|, this will be set to false. The + // |certs_source_updated_callback| passed to the constructor will be invoked. + void SetCertInfos( + std::vector<std::unique_ptr<CertificateManagerModel::CertInfo>> + cert_infos) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + cert_infos_.swap(cert_infos); + SetHoldBackUpdates(false); + certs_source_updated_callback_.Run(); + } + + // Signal to |CertificateManagerModel| that updates to its Observer should be + // held back. This will be automatically taken back on |SetCertInfos|. + // This should only be used by |CertsSource|s that provide their list of + // certificates asynchronously but expect their certificate listing to be + // fast. + void SetHoldBackUpdates(bool hold_back_updates) { + hold_back_updates_ = hold_back_updates; + } + + // Used to verify that the constructor, and accessing |cert_infos_| are + // performed on the same sequence. Offered to subclasses so they can also + // check that they're being called on a valid sequence. + SEQUENCE_CHECKER(sequence_checker_); + + private: + // Cached CertInfos provided by this CertsSource. + std::vector<std::unique_ptr<CertificateManagerModel::CertInfo>> cert_infos_; + + // Invoked when the list of certificates provided by this CertsSource has + // changed. + base::RepeatingClosure certs_source_updated_callback_; + + // If true, the CertificateManagerModel should be holding back update + // notifications. + bool hold_back_updates_ = false; + + DISALLOW_COPY_AND_ASSIGN(CertsSource); +}; + +namespace { +// Provides certificates enumerable from a NSSCertDatabase. +class CertsSourcePlatformNSS : public CertificateManagerModel::CertsSource { + public: + CertsSourcePlatformNSS(base::RepeatingClosure certs_source_updated_callback, + net::NSSCertDatabase* nss_cert_database) + : CertsSource(certs_source_updated_callback), + cert_db_(nss_cert_database), + weak_ptr_factory_(this) {} + ~CertsSourcePlatformNSS() override = default; + + void Refresh() override { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + SetHoldBackUpdates(true); + DVLOG(1) << "refresh started"; + std::vector<crypto::ScopedPK11Slot> modules; + cert_db_->ListModules(&modules, false); + DVLOG(1) << "refresh waiting for unlocking..."; + chrome::UnlockSlotsIfNecessary( + std::move(modules), kCryptoModulePasswordListCerts, + net::HostPortPair(), // unused. + nullptr, // TODO(mattm): supply parent window. + base::AdaptCallbackForRepeating( + base::BindOnce(&CertsSourcePlatformNSS::RefreshSlotsUnlocked, + weak_ptr_factory_.GetWeakPtr()))); + } + + bool SetCertTrust(CERTCertificate* cert, + net::CertType type, + net::NSSCertDatabase::TrustBits trust_bits) override { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + return cert_db_->SetCertTrust(cert, type, trust_bits); + } + + bool Delete(CERTCertificate* cert) override { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + bool result = cert_db_->DeleteCertAndKey(cert); + if (result) + Refresh(); + return result; + } + + private: + void RefreshSlotsUnlocked() { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + DVLOG(1) << "refresh listing certs..."; + cert_db_->ListCerts(base::AdaptCallbackForRepeating(base::BindOnce( + &CertsSourcePlatformNSS::DidGetCerts, weak_ptr_factory_.GetWeakPtr()))); + } + + void DidGetCerts(net::ScopedCERTCertificateList certs) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + DVLOG(1) << "refresh finished for platform provided certificates"; + std::vector<std::unique_ptr<CertificateManagerModel::CertInfo>> cert_infos; + + cert_infos.reserve(certs.size()); + for (auto& cert : certs) { + net::CertType type = x509_certificate_model::GetType(cert.get()); + bool read_only = cert_db_->IsReadOnly(cert.get()); + bool untrusted = cert_db_->IsUntrusted(cert.get()); + bool hardware_backed = cert_db_->IsHardwareBacked(cert.get()); + bool web_trust_anchor = cert_db_->IsWebTrustAnchor(cert.get()); + base::string16 name = GetName(cert.get(), hardware_backed); + cert_infos.push_back(std::make_unique<CertificateManagerModel::CertInfo>( + std::move(cert), type, name, read_only, untrusted, + CertificateManagerModel::CertInfo::Source::kPlatform, + web_trust_anchor, hardware_backed)); + } + + SetCertInfos(std::move(cert_infos)); + } + + static base::string16 GetName(CERTCertificate* cert, + bool is_hardware_backed) { + base::string16 name = + base::UTF8ToUTF16(x509_certificate_model::GetCertNameOrNickname(cert)); + if (is_hardware_backed) { + name = l10n_util::GetStringFUTF16( + IDS_CERT_MANAGER_HARDWARE_BACKED_KEY_FORMAT, name, + l10n_util::GetStringUTF16(IDS_CERT_MANAGER_HARDWARE_BACKED)); + } + return name; + } + + // The source NSSCertDatabase used for listing certificates. + net::NSSCertDatabase* cert_db_; + + base::WeakPtrFactory<CertsSourcePlatformNSS> weak_ptr_factory_; + + DISALLOW_COPY_AND_ASSIGN(CertsSourcePlatformNSS); +}; + +#if defined(OS_CHROMEOS) +// Provides certificates installed through enterprise policy. +class CertsSourcePolicy : public CertificateManagerModel::CertsSource, + policy::PolicyCertificateProvider::Observer { + public: + // Defines which policy-provided certificates this CertsSourcePolicy instance + // should yield. + enum class Mode { + // Only certificates which are installed by enterprise policy, but not Web + // trusted. + kPolicyCertsWithoutWebTrust, + // Only certificates which are installed by enterprise policy and Web + // trusted. + kPolicyCertsWithWebTrust + }; + + CertsSourcePolicy(base::RepeatingClosure certs_source_updated_callback, + policy::PolicyCertificateProvider* policy_certs_provider, + Mode mode) + : CertsSource(certs_source_updated_callback), + policy_certs_provider_(policy_certs_provider), + mode_(mode) { + policy_certs_provider_->AddPolicyProvidedCertsObserver(this); + } + + ~CertsSourcePolicy() override { + policy_certs_provider_->RemovePolicyProvidedCertsObserver(this); + } + + // policy::PolicyCertificateProvider::Observer + void OnPolicyProvidedCertsChanged( + const net::CertificateList& all_server_and_authority_certs, + const net::CertificateList& web_trusted_certs) override { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + Refresh(); + } + + void Refresh() override { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + switch (mode_) { + case Mode::kPolicyCertsWithoutWebTrust: + RefreshImpl(policy_certs_provider_->GetCertificatesWithoutWebTrust(), + false /* policy_web_trusted */); + break; + case Mode::kPolicyCertsWithWebTrust: + RefreshImpl(policy_certs_provider_->GetWebTrustedCertificates(), + true /* policy_web_trusted */); + break; + default: + NOTREACHED(); + } + } + + bool SetCertTrust(CERTCertificate* cert, + net::CertType type, + net::NSSCertDatabase::TrustBits trust_bits) override { + // Trust of policy-provided certificates can not be changed. + LOG(WARNING) << kOperationNotPermitted << "Policy"; + return false; + } + + bool Delete(CERTCertificate* cert) override { + // Policy-provided certificates can not be deleted. + LOG(WARNING) << kOperationNotPermitted << "Policy"; + return false; + } + + private: + void RefreshImpl(const net::CertificateList& certificates, + bool policy_web_trusted) { + std::vector<std::unique_ptr<CertificateManagerModel::CertInfo>> cert_infos; + cert_infos.reserve(certificates.size()); + + for (const auto& policy_cert : certificates) { + net::ScopedCERTCertificate nss_cert( + net::x509_util::CreateCERTCertificateFromX509Certificate( + policy_cert.get())); + if (!nss_cert) + continue; + + net::CertType type = x509_certificate_model::GetType(nss_cert.get()); + base::string16 cert_name = base::UTF8ToUTF16( + x509_certificate_model::GetCertNameOrNickname(nss_cert.get())); + cert_infos.push_back(std::make_unique<CertificateManagerModel::CertInfo>( + std::move(nss_cert), type, std::move(cert_name), true /* read_only */, + false /* untrusted */, + CertificateManagerModel::CertInfo::Source::kPolicy, + policy_web_trusted /* web_trust_anchor */, + false /* hardware_backed */)); + } + + SetCertInfos(std::move(cert_infos)); + } + + policy::PolicyCertificateProvider* policy_certs_provider_; + Mode mode_; + + DISALLOW_COPY_AND_ASSIGN(CertsSourcePolicy); +}; + +// Provides certificates made available by extensions through the +// chrome.certificateProvider API. +class CertsSourceExtensions : public CertificateManagerModel::CertsSource { + public: + CertsSourceExtensions(base::RepeatingClosure certs_source_updated_callback, + std::unique_ptr<chromeos::CertificateProvider> + certificate_provider_service) + : CertsSource(certs_source_updated_callback), + certificate_provider_service_(std::move(certificate_provider_service)), + weak_ptr_factory_(this) {} + + void Refresh() override { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + certificate_provider_service_->GetCertificates( + base::AdaptCallbackForRepeating( + base::BindOnce(&CertsSourceExtensions::DidGetCerts, + weak_ptr_factory_.GetWeakPtr()))); + } + + bool SetCertTrust(CERTCertificate* cert, + net::CertType type, + net::NSSCertDatabase::TrustBits trust_bits) override { + // Extension-provided certificates are user certificates; changing trust + // does not make sense here. + LOG(WARNING) << kOperationNotPermitted << "Extension"; + return false; + } + + bool Delete(CERTCertificate* cert) override { + // Extension-provided certificates can not be deleted. + LOG(WARNING) << kOperationNotPermitted << "Extension"; + return false; + } + + private: + void DidGetCerts(net::ClientCertIdentityList cert_identities) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + std::vector<std::unique_ptr<CertificateManagerModel::CertInfo>> cert_infos; + + cert_infos.reserve(cert_identities.size()); + for (const auto& identity : cert_identities) { + net::ScopedCERTCertificate nss_cert( + net::x509_util::CreateCERTCertificateFromX509Certificate( + identity->certificate())); + if (!nss_cert) + continue; + + base::string16 cert_name = base::UTF8ToUTF16( + x509_certificate_model::GetCertNameOrNickname(nss_cert.get())); + base::string16 display_name = l10n_util::GetStringFUTF16( + IDS_CERT_MANAGER_EXTENSION_PROVIDED_FORMAT, std::move(cert_name)); + + cert_infos.push_back(std::make_unique<CertificateManagerModel::CertInfo>( + std::move(nss_cert), net::CertType::USER_CERT /* type */, + display_name, true /* read_only */, false /* untrusted */, + CertificateManagerModel::CertInfo::Source::kExtension, + false /* web_trust_anchor */, false /* hardware_backed */)); + } + + SetCertInfos(std::move(cert_infos)); + } + + std::unique_ptr<chromeos::CertificateProvider> certificate_provider_service_; + + base::WeakPtrFactory<CertsSourceExtensions> weak_ptr_factory_; + + DISALLOW_COPY_AND_ASSIGN(CertsSourceExtensions); +}; + +#endif // OS_CHROMEOS + +} // namespace + +CertificateManagerModel::CertInfo::CertInfo(net::ScopedCERTCertificate cert, + net::CertType type, + base::string16 name, + bool read_only, + bool untrusted, + Source source, + bool web_trust_anchor, + bool hardware_backed) + : cert_(std::move(cert)), + type_(type), + name_(std::move(name)), + read_only_(read_only), + untrusted_(untrusted), + source_(source), + web_trust_anchor_(web_trust_anchor), + hardware_backed_(hardware_backed) {} + +CertificateManagerModel::CertInfo::~CertInfo() {} + +// static +std::unique_ptr<CertificateManagerModel::CertInfo> +CertificateManagerModel::CertInfo::Clone(const CertInfo* cert_info) { + return std::make_unique<CertInfo>( + net::x509_util::DupCERTCertificate(cert_info->cert()), cert_info->type(), + cert_info->name(), cert_info->read_only(), cert_info->untrusted(), + cert_info->source(), cert_info->web_trust_anchor(), + cert_info->hardware_backed()); +} + +CertificateManagerModel::Params::Params() = default; +CertificateManagerModel::Params::~Params() = default; +CertificateManagerModel::Params::Params(Params&& other) = default; + // static void CertificateManagerModel::Create( content::BrowserContext* browser_context, @@ -80,145 +478,132 @@ const CreationCallback& callback) { DCHECK_CURRENTLY_ON(BrowserThread::UI); - std::unique_ptr<chromeos::CertificateProvider> extension_certificate_provider; + std::unique_ptr<Params> params = std::make_unique<Params>(); #if defined(OS_CHROMEOS) - chromeos::CertificateProviderService* service = + policy::UserNetworkConfigurationUpdater* user_network_configuration_updater = + policy::UserNetworkConfigurationUpdaterFactory::GetForBrowserContext( + browser_context); + params->policy_certs_provider = user_network_configuration_updater; + + chromeos::CertificateProviderService* certificate_provider_service = chromeos::CertificateProviderServiceFactory::GetForBrowserContext( browser_context); - extension_certificate_provider = service->CreateCertificateProvider(); + params->extension_certificate_provider = + certificate_provider_service->CreateCertificateProvider(); #endif BrowserThread::PostTask( BrowserThread::IO, FROM_HERE, base::BindOnce(&CertificateManagerModel::GetCertDBOnIOThread, - browser_context->GetResourceContext(), observer, - std::move(extension_certificate_provider), callback)); + std::move(params), browser_context->GetResourceContext(), + observer, callback)); } CertificateManagerModel::CertificateManagerModel( + std::unique_ptr<Params> params, + Observer* observer, net::NSSCertDatabase* nss_cert_database, bool is_user_db_available, - bool is_tpm_available, - Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider) + bool is_tpm_available) : cert_db_(nss_cert_database), is_user_db_available_(is_user_db_available), is_tpm_available_(is_tpm_available), - observer_(observer), - extension_certificate_provider_(std::move( - extension_certificate_provider)), - weak_ptr_factory_(this) { + observer_(observer) { DCHECK_CURRENTLY_ON(BrowserThread::UI); -} -CertificateManagerModel::~CertificateManagerModel() { -} + // Fill |certs_sources_|. Note that the order matters. Higher priority + // CertsSources must come first. -void CertificateManagerModel::Refresh() { - DVLOG(1) << "refresh started"; - std::vector<crypto::ScopedPK11Slot> modules; - cert_db_->ListModules(&modules, false); - DVLOG(1) << "refresh waiting for unlocking..."; - chrome::UnlockSlotsIfNecessary( - std::move(modules), kCryptoModulePasswordListCerts, - net::HostPortPair(), // unused. - NULL, // TODO(mattm): supply parent window. - base::Bind(&CertificateManagerModel::RefreshSlotsUnlocked, - base::Unretained(this))); + base::RepeatingClosure certs_source_updated_callback = base::BindRepeating( + &CertificateManagerModel::OnCertsSourceUpdated, base::Unretained(this)); #if defined(OS_CHROMEOS) - extension_certificate_provider_->GetCertificates(base::Bind( - &CertificateManagerModel::RefreshExtensionCertificates, - weak_ptr_factory_.GetWeakPtr())); + // Certificates installed and web trusted by enterprise policy is the highest + // priority CertsSource. + // UserNetworkConfigurationUpdater is only available for the primary user's + // profile. + if (params->policy_certs_provider) { + certs_sources_.push_back(std::make_unique<CertsSourcePolicy>( + certs_source_updated_callback, params->policy_certs_provider, + CertsSourcePolicy::Mode::kPolicyCertsWithWebTrust)); + } +#endif + + // Add the main NSS DB based CertsSource. + certs_sources_.push_back(std::make_unique<CertsSourcePlatformNSS>( + certs_source_updated_callback, nss_cert_database)); + +#if defined(OS_CHROMEOS) + // Certificates installed by enterprise policy without web trust are lower + // priority than the main NSS DB based CertsSource. + // Rationale: The user should be able to add trust to policy-provided + // certificates by re-importing them and modifying their trust settings. + if (params->policy_certs_provider) { + certs_sources_.push_back(std::make_unique<CertsSourcePolicy>( + certs_source_updated_callback, params->policy_certs_provider, + CertsSourcePolicy::Mode::kPolicyCertsWithoutWebTrust)); + } + + // Extensions is the lowest priority CertsSource. + if (params->extension_certificate_provider) { + certs_sources_.push_back(std::make_unique<CertsSourceExtensions>( + certs_source_updated_callback, + std::move(params->extension_certificate_provider))); + } #endif } -void CertificateManagerModel::RefreshSlotsUnlocked() { - DVLOG(1) << "refresh listing certs..."; - // TODO(tbarzic): Use async |ListCerts|. - cert_list_ = cert_db_->ListCertsSync(); +CertificateManagerModel::~CertificateManagerModel() {} + +void CertificateManagerModel::OnCertsSourceUpdated() { + if (hold_back_updates_) + return; + for (const auto& certs_source : certs_sources_) { + if (certs_source->IsHoldBackUpdates()) { + return; + } + } + observer_->CertificatesRefreshed(); - DVLOG(1) << "refresh finished for platform provided certificates"; } -void CertificateManagerModel::RefreshExtensionCertificates( - net::ClientCertIdentityList new_cert_identities) { - extension_cert_list_.clear(); - extension_cert_list_.reserve(new_cert_identities.size()); - for (const auto& identity : new_cert_identities) { - net::ScopedCERTCertificate nss_cert( - net::x509_util::CreateCERTCertificateFromX509Certificate( - identity->certificate())); - if (nss_cert) - extension_cert_list_.push_back(std::move(nss_cert)); +CertificateManagerModel::CertsSource* +CertificateManagerModel::FindCertsSourceForCert(CERTCertificate* cert) { + for (auto& certs_source : certs_sources_) { + if (certs_source->HasCert(cert)) + return certs_source.get(); } - observer_->CertificatesRefreshed(); - DVLOG(1) << "refresh finished for extension provided certificates"; + return nullptr; +} + +void CertificateManagerModel::Refresh() { + hold_back_updates_ = true; + + for (auto& certs_source : certs_sources_) + certs_source->Refresh(); + + hold_back_updates_ = false; + OnCertsSourceUpdated(); } void CertificateManagerModel::FilterAndBuildOrgGroupingMap( net::CertType filter_type, - CertificateManagerModel::OrgGroupingMap* map) const { - for (const net::ScopedCERTCertificate& cert : cert_list_) { - net::CertType type = x509_certificate_model::GetType(cert.get()); - if (type != filter_type) - continue; + CertificateManagerModel::OrgGroupingMap* out_org_grouping_map) const { + std::map<CERTCertificate*, std::unique_ptr<CertInfo>> cert_info_map; + for (const auto& certs_source : certs_sources_) { + for (const auto& cert_info : certs_source->cert_infos()) { + if (cert_info->type() != filter_type) + continue; - std::string org = GetCertificateOrg(cert.get()); - (*map)[org].push_back(net::x509_util::DupCERTCertificate(cert.get())); - } - - // Display extension provided certificates under the "Your Certificates" tab. - if (filter_type == net::USER_CERT) { - for (const auto& cert : extension_cert_list_) { - std::string org = GetCertificateOrg(cert.get()); - (*map)[org].push_back(net::x509_util::DupCERTCertificate(cert.get())); + if (cert_info_map.find(cert_info->cert()) == cert_info_map.end()) + cert_info_map[cert_info->cert()] = CertInfo::Clone(cert_info.get()); } } -} -base::string16 CertificateManagerModel::GetColumnText(CERTCertificate* cert, - Column column) const { - base::string16 rv; - switch (column) { - case COL_SUBJECT_NAME: - rv = base::UTF8ToUTF16( - x509_certificate_model::GetCertNameOrNickname(cert)); - - // Mark extension provided certificates. - if (std::find_if(extension_cert_list_.begin(), extension_cert_list_.end(), - [cert](const net::ScopedCERTCertificate& element) { - return element.get() == cert; - }) != extension_cert_list_.end()) { - rv = l10n_util::GetStringFUTF16( - IDS_CERT_MANAGER_EXTENSION_PROVIDED_FORMAT, - rv); - } else if (IsHardwareBacked(cert)) { - // TODO(xiyuan): Put this into a column when we have js tree-table. - rv = l10n_util::GetStringFUTF16( - IDS_CERT_MANAGER_HARDWARE_BACKED_KEY_FORMAT, - rv, - l10n_util::GetStringUTF16(IDS_CERT_MANAGER_HARDWARE_BACKED)); - } - break; - case COL_CERTIFICATE_STORE: - rv = base::UTF8ToUTF16(x509_certificate_model::GetTokenName(cert)); - break; - case COL_SERIAL_NUMBER: - rv = base::ASCIIToUTF16( - x509_certificate_model::GetSerialNumberHexified(cert, std::string())); - break; - case COL_EXPIRES_ON: { - base::Time not_after; - if (net::x509_util::GetValidityTimes(cert, nullptr, ¬_after)) - rv = base::TimeFormatShortDateNumeric(not_after); - break; - } - default: - NOTREACHED(); + for (auto& cert_info_kv : cert_info_map) { + std::string org = GetCertificateOrg(cert_info_kv.second->cert()); + (*out_org_grouping_map)[org].push_back(std::move(cert_info_kv.second)); } - return rv; } int CertificateManagerModel::ImportFromPKCS12(PK11SlotInfo* slot_info, @@ -266,42 +651,40 @@ CERTCertificate* cert, net::CertType type, net::NSSCertDatabase::TrustBits trust_bits) { - return cert_db_->SetCertTrust(cert, type, trust_bits); + CertsSource* certs_source = FindCertsSourceForCert(cert); + if (!certs_source) + return false; + return certs_source->SetCertTrust(cert, type, trust_bits); } bool CertificateManagerModel::Delete(CERTCertificate* cert) { - bool result = cert_db_->DeleteCertAndKey(cert); - if (result) - Refresh(); - return result; -} - -bool CertificateManagerModel::IsHardwareBacked(CERTCertificate* cert) const { - return cert_db_->IsHardwareBacked(cert); + CertsSource* certs_source = FindCertsSourceForCert(cert); + if (!certs_source) + return false; + return certs_source->Delete(cert); } // static void CertificateManagerModel::DidGetCertDBOnUIThread( + std::unique_ptr<Params> params, + CertificateManagerModel::Observer* observer, + const CreationCallback& callback, net::NSSCertDatabase* cert_db, bool is_user_db_available, - bool is_tpm_available, - CertificateManagerModel::Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider, - const CreationCallback& callback) { + bool is_tpm_available) { DCHECK_CURRENTLY_ON(BrowserThread::UI); - std::unique_ptr<CertificateManagerModel> model(new CertificateManagerModel( - cert_db, is_user_db_available, is_tpm_available, observer, - std::move(extension_certificate_provider))); + std::unique_ptr<CertificateManagerModel> model = + std::make_unique<CertificateManagerModel>(std::move(params), observer, + cert_db, is_user_db_available, + is_tpm_available); callback.Run(std::move(model)); } // static void CertificateManagerModel::DidGetCertDBOnIOThread( + std::unique_ptr<Params> params, CertificateManagerModel::Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider, const CreationCallback& callback, net::NSSCertDatabase* cert_db) { DCHECK_CURRENTLY_ON(BrowserThread::IO); @@ -313,31 +696,27 @@ #endif BrowserThread::PostTask( BrowserThread::UI, FROM_HERE, - base::BindOnce(&CertificateManagerModel::DidGetCertDBOnUIThread, cert_db, - is_user_db_available, is_tpm_available, observer, - std::move(extension_certificate_provider), callback)); + base::BindOnce(&CertificateManagerModel::DidGetCertDBOnUIThread, + std::move(params), observer, callback, cert_db, + is_user_db_available, is_tpm_available)); } // static void CertificateManagerModel::GetCertDBOnIOThread( - content::ResourceContext* context, + std::unique_ptr<Params> params, + content::ResourceContext* resource_context, CertificateManagerModel::Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider, const CreationCallback& callback) { DCHECK_CURRENTLY_ON(BrowserThread::IO); - auto did_get_cert_db_callback = base::Bind( - &CertificateManagerModel::DidGetCertDBOnIOThread, observer, - base::Passed(&extension_certificate_provider), callback); + auto did_get_cert_db_callback = base::AdaptCallbackForRepeating( + base::BindOnce(&CertificateManagerModel::DidGetCertDBOnIOThread, + std::move(params), observer, callback)); net::NSSCertDatabase* cert_db = GetNSSCertDatabaseForResourceContext( - context, did_get_cert_db_callback); - - // The callback is run here instead of the actual function call because of - // extension_certificate_provider ownership semantics, ie. ownership can only - // be released once. The callback will only be run once (either inside the - // function above or here). + resource_context, did_get_cert_db_callback); + // If the NSS database was already available, |cert_db| is non-null and + // |did_get_cert_db_callback| has not been called. Call it explicitly. if (cert_db) did_get_cert_db_callback.Run(cert_db); }
diff --git a/chrome/browser/certificate_manager_model.h b/chrome/browser/certificate_manager_model.h index 10c216bf..119a46c6 100644 --- a/chrome/browser/certificate_manager_model.h +++ b/chrome/browser/certificate_manager_model.h
@@ -12,47 +12,134 @@ #include "base/callback.h" #include "base/macros.h" #include "base/memory/ref_counted.h" -#include "base/memory/weak_ptr.h" #include "base/strings/string16.h" #include "net/cert/nss_cert_database.h" #include "net/cert/scoped_nss_types.h" #include "net/ssl/client_cert_identity.h" -namespace chromeos { -class CertificateProvider; -} // namespace chromeos - namespace content { class BrowserContext; class ResourceContext; } // namespace content +#if defined(OS_CHROMEOS) +namespace chromeos { +class CertificateProvider; +} + +namespace policy { +class PolicyCertificateProvider; +} +#endif + // CertificateManagerModel provides the data to be displayed in the certificate // manager dialog, and processes changes from the view. class CertificateManagerModel { public: + // Holds information about a certificate, along with the certificate itself. + class CertInfo { + public: + enum class Source { + // This certificate is installed in the platform certificate database. + kPlatform, + // This certificate is provided by enterprise policy. + kPolicy, + // This certificate is provided by an extension. + kExtension + }; + + CertInfo(net::ScopedCERTCertificate cert, + net::CertType type, + base::string16 name, + bool read_only, + bool untrusted, + Source source, + bool web_trust_anchor, + bool hardware_backed); + ~CertInfo(); + + CERTCertificate* cert() const { return cert_.get(); } + net::CertType type() const { return type_; } + const base::string16& name() const { return name_; } + bool read_only() const { return read_only_; } + bool untrusted() const { return untrusted_; } + Source source() const { return source_; } + bool web_trust_anchor() const { return web_trust_anchor_; } + bool hardware_backed() const { return hardware_backed_; } + + // Clones a CertInfo, duplicating the contained NSS certificate. + static std::unique_ptr<CertInfo> Clone(const CertInfo* cert_info); + + private: + // The certificate itself. + net::ScopedCERTCertificate cert_; + + // The type of the certificate. Used to filter certificates to be displayed + // on the tabs of the certificate manager UI. + net::CertType type_; + + // A user readable certificate name. + base::string16 name_; + + // true if the certificate is stored on a read-only slot or provided by + // enterprise policy or an extension. + bool read_only_; + + // true if the certificate is untrusted. + bool untrusted_; + + // Describes where this certificate originates from. + Source source_; + + // true if the certificate is given web trust (either by its platform trust + // settings, or by enterprise policy). + bool web_trust_anchor_; + + // true if the certificate is hardware-backed. Note that extension-provided + // certificates are not regarded as hardware-backed. + bool hardware_backed_; + + DISALLOW_COPY_AND_ASSIGN(CertInfo); + }; + + class CertsSource; + + // Holds parameters during construction. + struct Params { +#if defined(OS_CHROMEOS) + // May be nullptr. + policy::PolicyCertificateProvider* policy_certs_provider = nullptr; + // May be nullptr. + std::unique_ptr<chromeos::CertificateProvider> + extension_certificate_provider; +#endif + + Params(); + Params(Params&& other); + ~Params(); + + private: + DISALLOW_COPY_AND_ASSIGN(Params); + }; + // Map from the subject organization name to the list of certs from that // organization. If a cert does not have an organization name, the // subject's CertPrincipal::GetDisplayName() value is used instead. - typedef std::map<std::string, net::ScopedCERTCertificateList> OrgGroupingMap; + typedef std::map<std::string, std::vector<std::unique_ptr<CertInfo>>> + OrgGroupingMap; typedef base::Callback<void(std::unique_ptr<CertificateManagerModel>)> CreationCallback; - // Enumeration of the possible columns in the certificate manager tree view. - enum Column { - COL_SUBJECT_NAME, - COL_CERTIFICATE_STORE, - COL_SERIAL_NUMBER, - COL_EXPIRES_ON, - }; - class Observer { public: // Called to notify the view that the certificate list has been refreshed. // TODO(mattm): do a more granular updating strategy? Maybe retrieve new // list of certs, diff against past list, and then notify of the changes? virtual void CertificatesRefreshed() = 0; + + protected: + virtual ~Observer() = default; }; // Creates a CertificateManagerModel. The model will be passed to the callback @@ -62,6 +149,13 @@ Observer* observer, const CreationCallback& callback); + // Use |Create| instead to create a |CertificateManagerModel| for a + // |BrowserContext|. + CertificateManagerModel(std::unique_ptr<Params> params, + Observer* observer, + net::NSSCertDatabase* nss_cert_database, + bool is_user_db_available, + bool is_tpm_available); ~CertificateManagerModel(); bool is_user_db_available() const { return is_user_db_available_; } @@ -76,12 +170,9 @@ // refresh its tree views. void Refresh(); - // Fill |map| with the certificates matching |filter_type|. + // Fill |*out_org_grouping_map| with the certificates matching |filter_type|. void FilterAndBuildOrgGroupingMap(net::CertType filter_type, - OrgGroupingMap* map) const; - - // Get the data to be displayed in |column| for the given |cert|. - base::string16 GetColumnText(CERTCertificate* cert, Column column) const; + OrgGroupingMap* out_org_grouping_map) const; // Import private keys and certificates from PKCS #12 encoded // |data|, using the given |password|. If |is_extractable| is false, @@ -132,52 +223,43 @@ // function returns. bool Delete(CERTCertificate* cert); - // IsHardwareBacked returns true if |cert| is hardware backed. - bool IsHardwareBacked(CERTCertificate* cert) const; - private: - CertificateManagerModel( - net::NSSCertDatabase* nss_cert_database, - bool is_user_db_available, - bool is_tpm_available, - Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider); + // Called when one of the |certs_sources_| has been updated. Will notify the + // |observer_| that the certificate list has been refreshed. + void OnCertsSourceUpdated(); + + // Finds the |CertsSource| which provided |cert|. Can return nullptr (e.g. if + // the cert has been deleted in the meantime). + CertsSource* FindCertsSourceForCert(CERTCertificate* cert); // Methods used during initialization, see the comment at the top of the .cc // file for details. static void DidGetCertDBOnUIThread( + std::unique_ptr<Params> params, + CertificateManagerModel::Observer* observer, + const CreationCallback& callback, net::NSSCertDatabase* cert_db, bool is_user_db_available, - bool is_tpm_available, - CertificateManagerModel::Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider, - const CreationCallback& callback); + bool is_tpm_available); static void DidGetCertDBOnIOThread( + std::unique_ptr<Params> params, CertificateManagerModel::Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider, const CreationCallback& callback, net::NSSCertDatabase* cert_db); - static void GetCertDBOnIOThread( - content::ResourceContext* context, - CertificateManagerModel::Observer* observer, - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider, - const CreationCallback& callback); - - // Callback used by Refresh() for when the cert slots have been unlocked. - // This method does the actual refreshing. - void RefreshSlotsUnlocked(); - - // Callback used to refresh extension provided certificates. Refreshes UI. - void RefreshExtensionCertificates( - net::ClientCertIdentityList new_cert_identities); + static void GetCertDBOnIOThread(std::unique_ptr<Params> params, + content::ResourceContext* resource_context, + CertificateManagerModel::Observer* observer, + const CreationCallback& callback); net::NSSCertDatabase* cert_db_; - net::ScopedCERTCertificateList cert_list_; - net::ScopedCERTCertificateList extension_cert_list_; + + // CertsSource instances providing certificates. The order matters - if a + // certificate is provided by more than one CertsSource, only the first one is + // accepted. + std::vector<std::unique_ptr<CertsSource>> certs_sources_; + + bool hold_back_updates_ = false; + // Whether the certificate database has a public slot associated with the // profile. If not set, importing certificates is not allowed with this model. bool is_user_db_available_; @@ -186,12 +268,6 @@ // The observer to notify when certificate list is refreshed. Observer* observer_; - // Certificate provider used to fetch extension provided certificates. - std::unique_ptr<chromeos::CertificateProvider> - extension_certificate_provider_; - - base::WeakPtrFactory<CertificateManagerModel> weak_ptr_factory_; - DISALLOW_COPY_AND_ASSIGN(CertificateManagerModel); };
diff --git a/chrome/browser/certificate_manager_model_unittest.cc b/chrome/browser/certificate_manager_model_unittest.cc new file mode 100644 index 0000000..59ca003 --- /dev/null +++ b/chrome/browser/certificate_manager_model_unittest.cc
@@ -0,0 +1,639 @@ +// Copyright 2018 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/browser/certificate_manager_model.h" +#include "base/observer_list.h" +#include "base/run_loop.h" +#include "base/strings/utf_string_conversions.h" +#include "content/public/test/test_browser_thread_bundle.h" +#include "crypto/scoped_test_nss_db.h" +#include "net/cert/nss_cert_database.h" +#include "net/cert/scoped_nss_types.h" +#include "net/cert/x509_util_nss.h" +#include "net/ssl/client_cert_identity_test_util.h" +#include "net/test/cert_test_util.h" +#include "net/test/test_data_directory.h" +#include "testing/gtest/include/gtest/gtest.h" + +#if defined(OS_CHROMEOS) +#include "chrome/browser/chromeos/certificate_provider/certificate_provider.h" +#include "chrome/browser/chromeos/policy/policy_certificate_provider.h" +#endif + +namespace { + +// A fake CertificateManagerModel::Observer that has the ability to execute a +// OnceClosure passed to it when |CertificatesRefreshed| is called. +class FakeObserver : public CertificateManagerModel::Observer { + public: + void CertificatesRefreshed() override { + if (!run_on_refresh_.is_null()) + std::move(run_on_refresh_).Run(); + } + + // Execute |closure| on the next |CertificatesRefreshed| invocation. + void RunOnNextRefresh(base::OnceClosure closure) { + run_on_refresh_ = std::move(closure); + } + + private: + base::OnceClosure run_on_refresh_; +}; + +// Looks up a |CertInfo| in |org_grouping_map| corresponding to |cert|. Returns +// nullptr if no such |CertInfo| was found. +CertificateManagerModel::CertInfo* GetCertInfoFromOrgGroupingMap( + const CertificateManagerModel::OrgGroupingMap& org_grouping_map, + CERTCertificate* cert) { + for (const auto& org_and_cert_info_list : org_grouping_map) { + for (const auto& cert_info : org_and_cert_info_list.second) { + if (net::x509_util::IsSameCertificate(cert_info->cert(), cert)) + return cert_info.get(); + } + } + return nullptr; +} + +} // namespace + +class CertificateManagerModelTest : public testing::Test { + public: + CertificateManagerModelTest() {} + + protected: + void SetUp() override { + ASSERT_TRUE(test_nssdb_.is_open()); + + nss_cert_db_ = std::make_unique<net::NSSCertDatabase>( + crypto::ScopedPK11Slot( + PK11_ReferenceSlot(test_nssdb_.slot())) /* public slot */, + crypto::ScopedPK11Slot( + PK11_ReferenceSlot(test_nssdb_.slot())) /* private slot */); + + fake_observer_ = std::make_unique<FakeObserver>(); + certificate_manager_model_ = std::make_unique<CertificateManagerModel>( + GetCertificateManagerModelParams(), fake_observer_.get(), + nss_cert_db_.get(), true /* is_user_db_available */, + true /* bool is_tpm_available */); + } + + void TearDown() override { + certificate_manager_model_.reset(); + nss_cert_db_.reset(); + } + + // Provides the platform-specific |Params| (containing policy/extension + // certificate provides on Chrome OS). + virtual std::unique_ptr<CertificateManagerModel::Params> + GetCertificateManagerModelParams() { + return std::make_unique<CertificateManagerModel::Params>(); + } + + protected: + // Invoke an explicit Refresh and wait until the observer has been notified. + void RefreshAndWait() { + base::RunLoop run_loop; + fake_observer_->RunOnNextRefresh(run_loop.QuitClosure()); + certificate_manager_model_->Refresh(); + run_loop.Run(); + } + + content::TestBrowserThreadBundle thread_bundle_; + crypto::ScopedTestNSSDB test_nssdb_; + std::unique_ptr<net::NSSCertDatabase> nss_cert_db_; + std::unique_ptr<FakeObserver> fake_observer_; + std::unique_ptr<CertificateManagerModel> certificate_manager_model_; + + private: + DISALLOW_COPY_AND_ASSIGN(CertificateManagerModelTest); +}; + +// CertificateManagerModel correctly lists CA certificates from the platform NSS +// Database. +// TODO(https://crbug.com/787602): Re-enable this test when it is identified why +// it was flaky. +TEST_F(CertificateManagerModelTest, DISABLED_ListsCertsFromPlatform) { + net::ScopedCERTCertificateList certs = CreateCERTCertificateListFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem", + net::X509Certificate::FORMAT_AUTO); + ASSERT_EQ(1U, certs.size()); + CERTCertificate* cert = certs[0].get(); + + ASSERT_EQ(SECSuccess, + PK11_ImportCert(test_nssdb_.slot(), cert, CK_INVALID_HANDLE, "cert", + PR_FALSE /* includeTrust (unused) */)); + RefreshAndWait(); + + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, cert); + ASSERT_TRUE(cert_info); + + EXPECT_EQ(net::CertType::CA_CERT, cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("pywebsocket"), cert_info->name()); + EXPECT_FALSE(cert_info->read_only()); + // This platform cert is untrusted because it is self-signed and has no + // trust bits. + EXPECT_TRUE(cert_info->untrusted()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPlatform, + cert_info->source()); + EXPECT_FALSE(cert_info->web_trust_anchor()); + EXPECT_FALSE(cert_info->hardware_backed()); + } + + certificate_manager_model_->SetCertTrust(cert, net::CertType::CA_CERT, + net::NSSCertDatabase::TRUSTED_SSL); + RefreshAndWait(); + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, cert); + ASSERT_TRUE(cert_info); + + EXPECT_FALSE(cert_info->untrusted()); + EXPECT_TRUE(cert_info->web_trust_anchor()); + } +} + +// CertificateManagerModel correctly lists client certificates from the platform +// NSS Database. +TEST_F(CertificateManagerModelTest, ListsClientCertsFromPlatform) { + net::ScopedCERTCertificate platform_client_cert; + net::ImportClientCertAndKeyFromFile( + net::GetTestCertsDirectory(), "client_1.pem", "client_1.pk8", + test_nssdb_.slot(), &platform_client_cert); + + RefreshAndWait(); + + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::USER_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* platform_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, + platform_client_cert.get()); + ASSERT_TRUE(platform_cert_info); + + EXPECT_EQ(net::CertType::USER_CERT, platform_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("Client Cert A"), platform_cert_info->name()); + EXPECT_FALSE(platform_cert_info->read_only()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPlatform, + platform_cert_info->source()); + EXPECT_FALSE(platform_cert_info->web_trust_anchor()); + EXPECT_FALSE(platform_cert_info->hardware_backed()); +} + +#if defined(OS_CHROMEOS) +namespace { + +class FakePolicyCertificateProvider : public policy::PolicyCertificateProvider { + public: + void AddPolicyProvidedCertsObserver(Observer* observer) override { + observer_list_.AddObserver(observer); + } + + void RemovePolicyProvidedCertsObserver(Observer* observer) override { + observer_list_.RemoveObserver(observer); + } + + net::CertificateList GetAllServerAndAuthorityCertificates() const override { + net::CertificateList merged; + merged.insert(merged.end(), web_trusted_certs_.begin(), + web_trusted_certs_.end()); + merged.insert(merged.end(), not_web_trusted_certs_.begin(), + not_web_trusted_certs_.end()); + return merged; + } + + net::CertificateList GetWebTrustedCertificates() const override { + return web_trusted_certs_; + } + + net::CertificateList GetCertificatesWithoutWebTrust() const override { + return not_web_trusted_certs_; + } + + void SetPolicyProvidedCertificates( + const net::CertificateList& web_trusted_certs, + const net::CertificateList& not_web_trusted_certs) { + web_trusted_certs_ = web_trusted_certs; + not_web_trusted_certs_ = not_web_trusted_certs; + } + + void NotifyObservers() { + net::CertificateList all_server_and_authority_certs = + GetAllServerAndAuthorityCertificates(); + net::CertificateList trust_anchors = GetWebTrustedCertificates(); + + for (auto& observer : observer_list_) { + observer.OnPolicyProvidedCertsChanged(all_server_and_authority_certs, + trust_anchors); + } + } + + private: + base::ObserverList<PolicyCertificateProvider::Observer, + true /* check_empty */>::Unchecked observer_list_; + net::CertificateList web_trusted_certs_; + net::CertificateList not_web_trusted_certs_; +}; + +class FakeExtensionCertificateProvider : public chromeos::CertificateProvider { + public: + FakeExtensionCertificateProvider( + const net::CertificateList* extension_client_certificates, + const bool* extensions_hang) + : extension_client_certificates_(extension_client_certificates), + extensions_hang_(extensions_hang) {} + + void GetCertificates( + const base::RepeatingCallback<void(net::ClientCertIdentityList)>& + callback) override { + if (*extensions_hang_) + return; + + callback.Run(FakeClientCertIdentityListFromCertificateList( + *extension_client_certificates_)); + } + + std::unique_ptr<CertificateProvider> Copy() override { + NOTREACHED(); + return nullptr; + } + + private: + const net::CertificateList* extension_client_certificates_; + + // If *|extensions_hang| is true, the |FakeExtensionCertificateProvider| hangs + // - it never calls the callbacks passed to |GetCertificates|. + const bool* extensions_hang_; +}; + +// Looks up a |CertInfo| in |org_grouping_map| corresponding to |cert|. Returns +// nullptr if no such |CertInfo| was found. +CertificateManagerModel::CertInfo* GetCertInfoFromOrgGroupingMap( + const CertificateManagerModel::OrgGroupingMap& org_grouping_map, + const net::X509Certificate* cert) { + for (const auto& org_and_cert_info_list : org_grouping_map) { + for (const auto& cert_info : org_and_cert_info_list.second) { + if (net::x509_util::IsSameCertificate(cert_info->cert(), cert)) + return cert_info.get(); + } + } + return nullptr; +} + +} // namespace + +class CertificateManagerModelChromeOSTest : public CertificateManagerModelTest { + protected: + std::unique_ptr<CertificateManagerModel::Params> + GetCertificateManagerModelParams() override { + auto params = std::make_unique<CertificateManagerModel::Params>(); + params->policy_certs_provider = &policy_certs_provider_; + params->extension_certificate_provider = + std::make_unique<FakeExtensionCertificateProvider>( + &extension_client_certs_, &extensions_hang_); + return params; + } + + void NotifyPolicyObserversAndWaitForRefresh() { + base::RunLoop run_loop; + fake_observer_->RunOnNextRefresh(run_loop.QuitClosure()); + policy_certs_provider_.NotifyObservers(); + run_loop.Run(); + } + + // Provider for policy certificates. In a non-test environment, this would + // usually be the UserNetworkConfigurationUpdater. + FakePolicyCertificateProvider policy_certs_provider_; + + // List of certificates that will be returned from the + // FakeExtensionCertificateProvider. + net::CertificateList extension_client_certs_; + // If true, the FakeExtensionCertificateProvider hangs. + bool extensions_hang_ = false; +}; + +// CertificateManagerModel correctly lists policy-provided certificates with web +// trust. +TEST_F(CertificateManagerModelChromeOSTest, ListsWebTrustedCertsFromPolicy) { + scoped_refptr<net::X509Certificate> cert = net::ImportCertFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem"); + ASSERT_TRUE(cert.get()); + policy_certs_provider_.SetPolicyProvidedCertificates({cert}, {}); + + NotifyPolicyObserversAndWaitForRefresh(); + + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, cert.get()); + ASSERT_TRUE(cert_info); + + EXPECT_EQ(net::CertType::CA_CERT, cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("pywebsocket"), cert_info->name()); + EXPECT_TRUE(cert_info->read_only()); + EXPECT_FALSE(cert_info->untrusted()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPolicy, + cert_info->source()); + EXPECT_TRUE(cert_info->web_trust_anchor()); + EXPECT_FALSE(cert_info->hardware_backed()); +} + +// CertificateManagerModel correctly lists policy-provided certificates without +// web trust. +TEST_F(CertificateManagerModelChromeOSTest, ListsNotWebTrustedCertsFromPolicy) { + scoped_refptr<net::X509Certificate> cert = net::ImportCertFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem"); + ASSERT_TRUE(cert.get()); + policy_certs_provider_.SetPolicyProvidedCertificates({}, {cert}); + + NotifyPolicyObserversAndWaitForRefresh(); + + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, cert.get()); + ASSERT_TRUE(cert_info); + + EXPECT_EQ(net::CertType::CA_CERT, cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("pywebsocket"), cert_info->name()); + EXPECT_TRUE(cert_info->read_only()); + EXPECT_FALSE(cert_info->untrusted()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPolicy, + cert_info->source()); + EXPECT_FALSE(cert_info->web_trust_anchor()); + EXPECT_FALSE(cert_info->hardware_backed()); +} + +// CertificateManagerModel correctly lists CA certificates that are in the +// platform NSS database and provided by policy with web trust. The +// policy-provided certificate hides the platform certificate in this case. +TEST_F(CertificateManagerModelChromeOSTest, + WebTrustedPolicyCertsWinOverPlatformCerts) { + net::ScopedCERTCertificateList certs = CreateCERTCertificateListFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem", + net::X509Certificate::FORMAT_AUTO); + ASSERT_EQ(1U, certs.size()); + CERTCertificate* platform_cert = certs[0].get(); + ASSERT_EQ(SECSuccess, PK11_ImportCert(test_nssdb_.slot(), platform_cert, + CK_INVALID_HANDLE, "cert", + PR_FALSE /* includeTrust (unused) */)); + + scoped_refptr<net::X509Certificate> policy_cert = net::ImportCertFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem"); + ASSERT_TRUE(policy_cert.get()); + policy_certs_provider_.SetPolicyProvidedCertificates({policy_cert}, {}); + + RefreshAndWait(); + + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* platform_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, platform_cert); + ASSERT_TRUE(platform_cert_info); + CertificateManagerModel::CertInfo* policy_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, policy_cert.get()); + ASSERT_TRUE(policy_cert_info); + + EXPECT_EQ(platform_cert_info, policy_cert_info); + + EXPECT_EQ(net::CertType::CA_CERT, policy_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("pywebsocket"), policy_cert_info->name()); + EXPECT_TRUE(policy_cert_info->read_only()); + EXPECT_FALSE(policy_cert_info->untrusted()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPolicy, + policy_cert_info->source()); + EXPECT_TRUE(policy_cert_info->web_trust_anchor()); + EXPECT_FALSE(policy_cert_info->hardware_backed()); + } + + // Remove the cert from policy-provided certs again. The platform certificate + // should be visible afterwards. + policy_certs_provider_.SetPolicyProvidedCertificates({}, {}); + NotifyPolicyObserversAndWaitForRefresh(); + + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* platform_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, platform_cert); + ASSERT_TRUE(platform_cert_info); + + EXPECT_EQ(net::CertType::CA_CERT, platform_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("pywebsocket"), platform_cert_info->name()); + EXPECT_FALSE(platform_cert_info->read_only()); + EXPECT_TRUE(platform_cert_info->untrusted()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPlatform, + platform_cert_info->source()); + EXPECT_FALSE(platform_cert_info->web_trust_anchor()); + EXPECT_FALSE(platform_cert_info->hardware_backed()); + } +} + +// CertificateManagerModel correctly lists CA certificates that are in the +// platform NSS database and provided by policy without web trust. The platform +// certificate hides the policy-provided certificate in this case. +TEST_F(CertificateManagerModelChromeOSTest, + PlatformCertsWinOverNotWebTrustedCerts) { + net::ScopedCERTCertificateList certs = CreateCERTCertificateListFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem", + net::X509Certificate::FORMAT_AUTO); + ASSERT_EQ(1U, certs.size()); + CERTCertificate* platform_cert = certs[0].get(); + ASSERT_EQ(SECSuccess, PK11_ImportCert(test_nssdb_.slot(), platform_cert, + CK_INVALID_HANDLE, "cert", + PR_FALSE /* includeTrust (unused) */)); + + scoped_refptr<net::X509Certificate> policy_cert = net::ImportCertFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem"); + ASSERT_TRUE(policy_cert.get()); + policy_certs_provider_.SetPolicyProvidedCertificates({}, {policy_cert}); + + RefreshAndWait(); + + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* platform_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, platform_cert); + ASSERT_TRUE(platform_cert_info); + CertificateManagerModel::CertInfo* policy_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, policy_cert.get()); + ASSERT_TRUE(policy_cert_info); + + EXPECT_EQ(platform_cert_info, policy_cert_info); + + EXPECT_EQ(net::CertType::CA_CERT, platform_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("pywebsocket"), platform_cert_info->name()); + EXPECT_FALSE(platform_cert_info->read_only()); + EXPECT_TRUE(platform_cert_info->untrusted()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPlatform, + platform_cert_info->source()); + EXPECT_FALSE(platform_cert_info->web_trust_anchor()); + EXPECT_FALSE(platform_cert_info->hardware_backed()); + } + + // Remove the certificate from the platform NSS database. The policy-provided + // certificate should be visible afterwards. + base::RunLoop run_loop; + fake_observer_->RunOnNextRefresh(run_loop.QuitClosure()); + certificate_manager_model_->Delete(platform_cert); + run_loop.Run(); + + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* policy_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, policy_cert.get()); + ASSERT_TRUE(policy_cert_info); + + EXPECT_EQ(net::CertType::CA_CERT, policy_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("pywebsocket"), policy_cert_info->name()); + EXPECT_TRUE(policy_cert_info->read_only()); + EXPECT_FALSE(policy_cert_info->untrusted()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPolicy, + policy_cert_info->source()); + EXPECT_FALSE(policy_cert_info->web_trust_anchor()); + EXPECT_FALSE(policy_cert_info->hardware_backed()); + } +} + +// When the Extension CertificateProvider hangs (e.g. because an extension is +// not responding), policy and platform certificates are still listed. +TEST_F(CertificateManagerModelChromeOSTest, + PlatformAndPolicyCertsListedWhenExtensionsHang) { + extensions_hang_ = true; + + net::ScopedCERTCertificateList certs = CreateCERTCertificateListFromFile( + net::GetTestCertsDirectory(), "websocket_cacert.pem", + net::X509Certificate::FORMAT_AUTO); + ASSERT_EQ(1U, certs.size()); + CERTCertificate* platform_cert = certs[0].get(); + ASSERT_EQ(SECSuccess, PK11_ImportCert(test_nssdb_.slot(), platform_cert, + CK_INVALID_HANDLE, "cert", + PR_FALSE /* includeTrust (unused) */)); + + scoped_refptr<net::X509Certificate> policy_cert = + net::ImportCertFromFile(net::GetTestCertsDirectory(), "root_ca_cert.pem"); + ASSERT_TRUE(policy_cert.get()); + policy_certs_provider_.SetPolicyProvidedCertificates({policy_cert}, {}); + + RefreshAndWait(); + + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::CA_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* platform_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, platform_cert); + ASSERT_TRUE(platform_cert_info); + CertificateManagerModel::CertInfo* policy_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, policy_cert.get()); + ASSERT_TRUE(policy_cert_info); + + EXPECT_NE(platform_cert_info, policy_cert_info); +} + +// CertificateManagerModel lists client certificates provided by extensions. +TEST_F(CertificateManagerModelChromeOSTest, ListsExtensionCerts) { + scoped_refptr<net::X509Certificate> extension_cert = + net::ImportCertFromFile(net::GetTestCertsDirectory(), "client_1.pem"); + ASSERT_TRUE(extension_cert.get()); + extension_client_certs_.push_back(extension_cert); + + RefreshAndWait(); + + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::USER_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* extension_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, extension_cert.get()); + ASSERT_TRUE(extension_cert_info); + + EXPECT_EQ(net::CertType::USER_CERT, extension_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("Client Cert A (extension provided)"), + extension_cert_info->name()); + EXPECT_TRUE(extension_cert_info->read_only()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kExtension, + extension_cert_info->source()); + EXPECT_FALSE(extension_cert_info->web_trust_anchor()); + EXPECT_FALSE(extension_cert_info->hardware_backed()); +} + +TEST_F(CertificateManagerModelChromeOSTest, + PlatformCertsWinOverExtensionCerts) { + net::ScopedCERTCertificate platform_client_cert; + net::ImportClientCertAndKeyFromFile( + net::GetTestCertsDirectory(), "client_1.pem", "client_1.pk8", + test_nssdb_.slot(), &platform_client_cert); + + scoped_refptr<net::X509Certificate> extension_cert = + net::ImportCertFromFile(net::GetTestCertsDirectory(), "client_1.pem"); + ASSERT_TRUE(extension_cert.get()); + extension_client_certs_.push_back(extension_cert); + + RefreshAndWait(); + + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::USER_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* platform_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, + platform_client_cert.get()); + ASSERT_TRUE(platform_cert_info); + CertificateManagerModel::CertInfo* extension_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, extension_cert.get()); + ASSERT_TRUE(extension_cert_info); + + EXPECT_EQ(platform_cert_info, extension_cert_info); + + EXPECT_EQ(net::CertType::USER_CERT, platform_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("Client Cert A"), platform_cert_info->name()); + EXPECT_FALSE(platform_cert_info->read_only()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kPlatform, + platform_cert_info->source()); + EXPECT_FALSE(platform_cert_info->web_trust_anchor()); + EXPECT_FALSE(platform_cert_info->hardware_backed()); + } + + // Remove the platform client certificate. The extension-provided client + // certificate should be visible afterwards. + base::RunLoop run_loop; + fake_observer_->RunOnNextRefresh(run_loop.QuitClosure()); + certificate_manager_model_->Delete(platform_client_cert.get()); + run_loop.Run(); + + { + CertificateManagerModel::OrgGroupingMap org_grouping_map; + certificate_manager_model_->FilterAndBuildOrgGroupingMap( + net::CertType::USER_CERT, &org_grouping_map); + CertificateManagerModel::CertInfo* extension_cert_info = + GetCertInfoFromOrgGroupingMap(org_grouping_map, extension_cert.get()); + ASSERT_TRUE(extension_cert_info); + + EXPECT_EQ(net::CertType::USER_CERT, extension_cert_info->type()); + EXPECT_EQ(base::UTF8ToUTF16("Client Cert A (extension provided)"), + extension_cert_info->name()); + EXPECT_TRUE(extension_cert_info->read_only()); + EXPECT_EQ(CertificateManagerModel::CertInfo::Source::kExtension, + extension_cert_info->source()); + EXPECT_FALSE(extension_cert_info->web_trust_anchor()); + EXPECT_FALSE(extension_cert_info->hardware_backed()); + } +} + +#endif // defined(OS_CHROMEOS)
diff --git a/chrome/browser/chrome_browser_main_browsertest.cc b/chrome/browser/chrome_browser_main_browsertest.cc index fe2676a..84eb5064 100644 --- a/chrome/browser/chrome_browser_main_browsertest.cc +++ b/chrome/browser/chrome_browser_main_browsertest.cc
@@ -14,15 +14,8 @@ #include "chrome/test/base/in_process_browser_test.h" #include "components/variations/service/variations_service.h" #include "components/variations/variations_switches.h" -#include "content/public/browser/network_service_instance.h" -#include "content/public/common/service_manager_connection.h" -#include "content/public/common/service_names.mojom.h" -#include "content/public/test/browser_test_utils.h" #include "net/base/mock_network_change_notifier.h" #include "net/base/network_change_notifier_factory.h" -#include "services/network/public/cpp/features.h" -#include "services/network/public/mojom/network_service_test.mojom.h" -#include "services/service_manager/public/cpp/connector.h" // Friend of ChromeBrowserMainPartsTestApi to poke at internal state. class ChromeBrowserMainPartsTestApi { @@ -43,50 +36,44 @@ namespace { -// Simulates a network connection change. -void SimulateNetworkChange(network::mojom::ConnectionType type) { - if (base::FeatureList::IsEnabled(network::features::kNetworkService) && - !content::IsNetworkServiceRunningInProcess()) { - network::mojom::NetworkServiceTestPtr network_service_test; - content::ServiceManagerConnection::GetForProcess() - ->GetConnector() - ->BindInterface(content::mojom::kNetworkServiceName, - &network_service_test); - base::RunLoop run_loop; - network_service_test->SimulateNetworkChange(type, run_loop.QuitClosure()); - run_loop.Run(); - return; - } - net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests( - net::NetworkChangeNotifier::ConnectionType(type)); -} - // ChromeBrowserMainExtraParts used to install a MockNetworkChangeNotifier. class ChromeBrowserMainExtraPartsNetFactoryInstaller : public ChromeBrowserMainExtraParts { public: ChromeBrowserMainExtraPartsNetFactoryInstaller() = default; + ~ChromeBrowserMainExtraPartsNetFactoryInstaller() override { + // |network_change_notifier_| needs to be destroyed before |net_installer_|. + network_change_notifier_.reset(); + } + + net::test::MockNetworkChangeNotifier* network_change_notifier() { + return network_change_notifier_.get(); + } // ChromeBrowserMainExtraParts: void PreEarlyInitialization() override {} - void ServiceManagerConnectionStarted( - content::ServiceManagerConnection* connection) override { - SimulateNetworkChange(network::mojom::ConnectionType::CONNECTION_NONE); + void PostMainMessageLoopStart() override { + ASSERT_TRUE(net::NetworkChangeNotifier::HasNetworkChangeNotifier()); + net_installer_ = + std::make_unique<net::NetworkChangeNotifier::DisableForTest>(); + network_change_notifier_ = + std::make_unique<net::test::MockNetworkChangeNotifier>(); + network_change_notifier_->SetConnectionType( + net::NetworkChangeNotifier::CONNECTION_NONE); } private: + std::unique_ptr<net::test::MockNetworkChangeNotifier> + network_change_notifier_; + std::unique_ptr<net::NetworkChangeNotifier::DisableForTest> net_installer_; + DISALLOW_COPY_AND_ASSIGN(ChromeBrowserMainExtraPartsNetFactoryInstaller); }; -class ChromeBrowserMainBrowserTest - : public InProcessBrowserTest, - network::NetworkConnectionTracker::NetworkConnectionObserver { +class ChromeBrowserMainBrowserTest : public InProcessBrowserTest { public: ChromeBrowserMainBrowserTest() = default; - ~ChromeBrowserMainBrowserTest() override { - content::GetNetworkConnectionTracker()->RemoveNetworkConnectionObserver( - this); - } + ~ChromeBrowserMainBrowserTest() override = default; protected: // InProcessBrowserTest: @@ -108,33 +95,8 @@ chrome_browser_main_parts->AddParts(extra_parts_); } - void SetUpOnMainThread() override { - content::GetNetworkConnectionTracker()->AddNetworkConnectionObserver(this); - } - - void WaitForConnectionType(network::mojom::ConnectionType type) { - if (connection_type_ == type) - return; - - expected_connection_type_ = type; - run_loop_ = std::make_unique<base::RunLoop>(); - run_loop_->Run(); - } - ChromeBrowserMainExtraPartsNetFactoryInstaller* extra_parts_ = nullptr; - private: - // network::NetworkConnectionTracker::NetworkConnectionObserver: - void OnConnectionChanged(network::mojom::ConnectionType type) override { - connection_type_ = type; - if (expected_connection_type_ == connection_type_ && run_loop_) - run_loop_->Quit(); - } - - network::mojom::ConnectionType expected_connection_type_; - network::mojom::ConnectionType connection_type_; - std::unique_ptr<base::RunLoop> run_loop_; - DISALLOW_COPY_AND_ASSIGN(ChromeBrowserMainBrowserTest); }; @@ -145,11 +107,14 @@ const int initial_request_count = g_browser_process->variations_service()->request_count(); ASSERT_TRUE(extra_parts_); - SimulateNetworkChange(network::mojom::ConnectionType::CONNECTION_WIFI); - WaitForConnectionType(network::mojom::ConnectionType::CONNECTION_WIFI); + extra_parts_->network_change_notifier()->SetConnectionType( + net::NetworkChangeNotifier::CONNECTION_WIFI); + net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests( + net::NetworkChangeNotifier::CONNECTION_WIFI); // NotifyObserversOfNetworkChangeForTests uses PostTask, so run the loop until // idle to ensure VariationsService processes the network change. - base::RunLoop().RunUntilIdle(); + base::RunLoop run_loop; + run_loop.RunUntilIdle(); const int final_request_count = g_browser_process->variations_service()->request_count(); EXPECT_EQ(initial_request_count + 1, final_request_count);
diff --git a/chrome/browser/chrome_content_browser_client.cc b/chrome/browser/chrome_content_browser_client.cc index 7be05e7d..7da42548 100644 --- a/chrome/browser/chrome_content_browser_client.cc +++ b/chrome/browser/chrome_content_browser_client.cc
@@ -2408,7 +2408,7 @@ void ChromeContentBrowserClient::AllowWorkerFileSystem( const GURL& url, content::ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback) { DCHECK_CURRENTLY_ON(BrowserThread::IO); ProfileIOData* io_data = ProfileIOData::FromResourceContext(context); @@ -2426,22 +2426,21 @@ #if BUILDFLAG(ENABLE_EXTENSIONS) void ChromeContentBrowserClient::GuestPermissionRequestHelper( const GURL& url, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback, bool allow) { DCHECK_CURRENTLY_ON(BrowserThread::IO); - std::vector<std::pair<int, int> >::const_iterator i; std::map<int, int> process_map; std::map<int, int>::const_iterator it; bool has_web_view_guest = false; // Record access to file system for potential display in UI. - for (i = render_frames.begin(); i != render_frames.end(); ++i) { - if (process_map.find(i->first) != process_map.end()) + for (const auto& it : render_frames) { + if (process_map.find(it.child_id) != process_map.end()) continue; - process_map.insert(std::pair<int, int>(i->first, i->second)); + process_map.insert(std::pair<int, int>(it.child_id, it.frame_routing_id)); - if (extensions::WebViewRendererState::GetInstance()->IsGuest(i->first)) + if (extensions::WebViewRendererState::GetInstance()->IsGuest(it.child_id)) has_web_view_guest = true; } if (!has_web_view_guest) { @@ -2480,16 +2479,15 @@ void ChromeContentBrowserClient::FileSystemAccessed( const GURL& url, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback, bool allow) { // Record access to file system for potential display in UI. - std::vector<std::pair<int, int> >::const_iterator i; - for (i = render_frames.begin(); i != render_frames.end(); ++i) { + for (const auto& it : render_frames) { BrowserThread::PostTask( BrowserThread::UI, FROM_HERE, base::BindOnce(&TabSpecificContentSettings::FileSystemAccessed, - i->first, i->second, url, !allow)); + it.child_id, it.frame_routing_id, url, !allow)); } callback.Run(allow); } @@ -2498,7 +2496,7 @@ const GURL& url, const base::string16& name, content::ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames) { + const std::vector<content::GlobalFrameRoutingId>& render_frames) { DCHECK_CURRENTLY_ON(BrowserThread::IO); ProfileIOData* io_data = ProfileIOData::FromResourceContext(context); content_settings::CookieSettings* cookie_settings = @@ -2506,12 +2504,11 @@ bool allow = cookie_settings->IsCookieAccessAllowed(url, url); // Record access to IndexedDB for potential display in UI. - std::vector<std::pair<int, int> >::const_iterator i; - for (i = render_frames.begin(); i != render_frames.end(); ++i) { + for (const auto& it : render_frames) { BrowserThread::PostTask( BrowserThread::UI, FROM_HERE, - base::BindOnce(&TabSpecificContentSettings::IndexedDBAccessed, i->first, - i->second, url, name, !allow)); + base::BindOnce(&TabSpecificContentSettings::IndexedDBAccessed, + it.child_id, it.frame_routing_id, url, name, !allow)); } return allow;
diff --git a/chrome/browser/chrome_content_browser_client.h b/chrome/browser/chrome_content_browser_client.h index d41a2a79..58cd542ac 100644 --- a/chrome/browser/chrome_content_browser_client.h +++ b/chrome/browser/chrome_content_browser_client.h
@@ -232,13 +232,13 @@ void AllowWorkerFileSystem( const GURL& url, content::ResourceContext* context, - const std::vector<std::pair<int, int>>& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback) override; bool AllowWorkerIndexedDB( const GURL& url, const base::string16& name, content::ResourceContext* context, - const std::vector<std::pair<int, int>>& render_frames) override; + const std::vector<content::GlobalFrameRoutingId>& render_frames) override; AllowWebBluetoothResult AllowWebBluetooth( content::BrowserContext* browser_context, const url::Origin& requesting_origin, @@ -516,14 +516,14 @@ void FileSystemAccessed( const GURL& url, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback, bool allow); #if BUILDFLAG(ENABLE_EXTENSIONS) void GuestPermissionRequestHelper( const GURL& url, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<content::GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback, bool allow);
diff --git a/chrome/browser/chromeos/BUILD.gn b/chrome/browser/chromeos/BUILD.gn index ea1d515a..dd643d7 100644 --- a/chrome/browser/chromeos/BUILD.gn +++ b/chrome/browser/chromeos/BUILD.gn
@@ -597,8 +597,6 @@ "dbus/chrome_features_service_provider.h", "dbus/chrome_proxy_resolution_service_provider_delegate.cc", "dbus/chrome_proxy_resolution_service_provider_delegate.h", - "dbus/chrome_virtual_file_request_service_provider_delegate.cc", - "dbus/chrome_virtual_file_request_service_provider_delegate.h", "dbus/component_updater_service_provider.cc", "dbus/component_updater_service_provider.h", "dbus/drive_file_stream_service_provider.cc", @@ -1485,6 +1483,7 @@ "policy/policy_cert_service_factory.h", "policy/policy_cert_verifier.cc", "policy/policy_cert_verifier.h", + "policy/policy_certificate_provider.h", "policy/policy_oauth2_token_fetcher.cc", "policy/policy_oauth2_token_fetcher.h", "policy/pre_signin_policy_fetcher.cc", @@ -2202,6 +2201,7 @@ "policy/device_cloud_policy_manager_chromeos_unittest.cc", "policy/device_cloud_policy_store_chromeos_unittest.cc", "policy/device_local_account_policy_service_unittest.cc", + "policy/device_policy_decoder_chromeos_unittest.cc", "policy/dm_token_storage_unittest.cc", "policy/extension_cache_unittest.cc", "policy/fake_affiliated_invalidation_service_provider.cc",
diff --git a/chrome/browser/chromeos/account_mapper_util.cc b/chrome/browser/chromeos/account_mapper_util.cc index 69aa2e7..f067280 100644 --- a/chrome/browser/chromeos/account_mapper_util.cc +++ b/chrome/browser/chromeos/account_mapper_util.cc
@@ -4,6 +4,8 @@ #include "chrome/browser/chromeos/account_mapper_util.h" +#include "components/account_id/account_id.h" +#include "components/signin/core/browser/account_info.h" #include "components/signin/core/browser/account_tracker_service.h" namespace chromeos { @@ -22,12 +24,9 @@ account_manager::AccountType::ACCOUNT_TYPE_GAIA) { return std::string(); } - - const std::string& account_id = - account_tracker_service_->FindAccountInfoByGaiaId(account_key.id) - .account_id; - DCHECK(!account_id.empty()) << "Can't find account id"; - return account_id; + const AccountInfo& account_info = AccountKeyToGaiaAccountInfo(account_key); + DCHECK(!account_info.account_id.empty()) << "Can't find account id"; + return account_info.account_id; } AccountManager::AccountKey AccountMapperUtil::OAuthAccountIdToAccountKey( @@ -42,4 +41,35 @@ account_info.gaia, account_manager::AccountType::ACCOUNT_TYPE_GAIA}; } +AccountInfo AccountMapperUtil::AccountKeyToGaiaAccountInfo( + const AccountManager::AccountKey& account_key) const { + AccountInfo account_info; + + DCHECK(account_key.IsValid()); + if (account_key.account_type != + account_manager::AccountType::ACCOUNT_TYPE_GAIA) { + return account_info; + } + account_info = + account_tracker_service_->FindAccountInfoByGaiaId(account_key.id); + DCHECK(!account_info.IsEmpty()) << "Can't find account info"; + + return account_info; +} + +// static +bool AccountMapperUtil::IsEqual(const AccountManager::AccountKey& account_key, + const AccountId& account_id) { + switch (account_key.account_type) { + case chromeos::account_manager::AccountType::ACCOUNT_TYPE_GAIA: + return (account_id.GetAccountType() == AccountType::GOOGLE) && + (account_id.GetGaiaId() == account_key.id); + case chromeos::account_manager::AccountType::ACCOUNT_TYPE_ACTIVE_DIRECTORY: + return (account_id.GetAccountType() == AccountType::ACTIVE_DIRECTORY) && + (account_id.GetObjGuid() == account_key.id); + case chromeos::account_manager::AccountType::ACCOUNT_TYPE_UNSPECIFIED: + return false; + } +} + } // namespace chromeos
diff --git a/chrome/browser/chromeos/account_mapper_util.h b/chrome/browser/chromeos/account_mapper_util.h index 14e5b82..d8f1989 100644 --- a/chrome/browser/chromeos/account_mapper_util.h +++ b/chrome/browser/chromeos/account_mapper_util.h
@@ -10,6 +10,8 @@ #include "base/macros.h" #include "chromeos/account_manager/account_manager.h" +class AccountId; +struct AccountInfo; class AccountTrackerService; namespace chromeos { @@ -30,6 +32,16 @@ AccountManager::AccountKey OAuthAccountIdToAccountKey( const std::string& account_id) const; + // A utility method to map an |account_key| representing a GAIA account to + // |AccountInfo|. Returns an empty |AccountInfo| for non-GAIA accounts. + AccountInfo AccountKeyToGaiaAccountInfo( + const AccountManager::AccountKey& account_key) const; + + // A utility method to check whether |account_key| and |account_id| represent + // the same account. + static bool IsEqual(const AccountManager::AccountKey& account_key, + const AccountId& account_id); + private: // A non-owning pointer to |AccountTrackerService|, which itself is a // |KeyedService|.
diff --git a/chrome/browser/chromeos/arc/arc_session_manager.cc b/chrome/browser/chromeos/arc/arc_session_manager.cc index 6b258d1..fa59819c 100644 --- a/chrome/browser/chromeos/arc/arc_session_manager.cc +++ b/chrome/browser/chromeos/arc/arc_session_manager.cc
@@ -4,6 +4,7 @@ #include "chrome/browser/chromeos/arc/arc_session_manager.h" +#include <string> #include <utility> #include "base/bind.h" @@ -18,7 +19,6 @@ #include "chrome/browser/chromeos/arc/arc_optin_uma.h" #include "chrome/browser/chromeos/arc/arc_support_host.h" #include "chrome/browser/chromeos/arc/arc_util.h" -#include "chrome/browser/chromeos/arc/auth/arc_auth_context.h" #include "chrome/browser/chromeos/arc/auth/arc_auth_service.h" #include "chrome/browser/chromeos/arc/optin/arc_terms_of_service_default_negotiator.h" #include "chrome/browser/chromeos/arc/optin/arc_terms_of_service_oobe_negotiator.h" @@ -456,8 +456,6 @@ cryptohome::Identification( multi_user_util::GetAccountIdFromProfile(profile_))); - context_ = std::make_unique<ArcAuthContext>(profile_); - if (g_enable_check_android_management_in_tests.value_or(g_ui_enabled)) ArcAndroidManagementChecker::StartClient(); @@ -488,7 +486,6 @@ support_host_->Close(); support_host_.reset(); } - context_.reset(); pai_starter_.reset(); fast_app_reinstall_starter_.reset(); profile_ = nullptr; @@ -876,8 +873,7 @@ return; android_management_checker_ = std::make_unique<ArcAndroidManagementChecker>( - profile_, context_->token_service(), context_->account_id(), - false /* retry_on_error */); + profile_, false /* retry_on_error */); android_management_checker_->StartCheck( base::Bind(&ArcSessionManager::OnAndroidManagementChecked, weak_ptr_factory_.GetWeakPtr())); @@ -931,8 +927,7 @@ } android_management_checker_ = std::make_unique<ArcAndroidManagementChecker>( - profile_, context_->token_service(), context_->account_id(), - true /* retry_on_error */); + profile_, true /* retry_on_error */); android_management_checker_->StartCheck( base::Bind(&ArcSessionManager::OnBackgroundAndroidManagementChecked, weak_ptr_factory_.GetWeakPtr())); @@ -975,8 +970,8 @@ provisioning_reported_ = false; std::string locale; - std::string preferred_lanaguages; - GetLocaleAndPreferredLanguages(profile_, &locale, &preferred_lanaguages); + std::string preferred_languages; + GetLocaleAndPreferredLanguages(profile_, &locale, &preferred_languages); ArcSession::UpgradeParams params; @@ -991,9 +986,9 @@ params.is_child = profile_->IsChild(); params.supervision_transition = GetSupervisionTransition(profile_); params.locale = locale; - // Empty |preferred_lanaguages| is converted to empty array. + // Empty |preferred_languages| is converted to empty array. params.preferred_languages = base::SplitString( - preferred_lanaguages, ",", base::TRIM_WHITESPACE, base::SPLIT_WANT_ALL); + preferred_languages, ",", base::TRIM_WHITESPACE, base::SPLIT_WANT_ALL); arc_session_runner_->RequestUpgrade(std::move(params)); } @@ -1056,7 +1051,7 @@ DCHECK_EQ(state_, State::STOPPED); if (!reenable_arc_) { - // Reenabling is not triggered. Do nothing. + // Re-enabling is not triggered. Do nothing. return; } DCHECK(enable_requested_);
diff --git a/chrome/browser/chromeos/arc/arc_session_manager.h b/chrome/browser/chromeos/arc/arc_session_manager.h index 328f60090..24f2167 100644 --- a/chrome/browser/chromeos/arc/arc_session_manager.h +++ b/chrome/browser/chromeos/arc/arc_session_manager.h
@@ -7,7 +7,6 @@ #include <memory> #include <ostream> -#include <string> #include "base/macros.h" #include "base/memory/weak_ptr.h" @@ -25,7 +24,6 @@ namespace arc { class ArcAndroidManagementChecker; -class ArcAuthContext; class ArcDataRemover; class ArcFastAppReinstallStarter; class ArcPaiStarter; @@ -219,10 +217,6 @@ ArcSupportHost* support_host() { return support_host_.get(); } - // TODO(hidehiko): Get rid of the getter by migration between ArcAuthContext - // and ArcAuthCodeFetcher. - ArcAuthContext* auth_context() { return context_.get(); } - // On provisioning completion (regardless of whether successfully done or // not), this is called with its status. On success, called with // ProvisioningResult::SUCCESS, otherwise |result| is the error reason. @@ -386,7 +380,6 @@ std::unique_ptr<ArcTermsOfServiceNegotiator> terms_of_service_negotiator_; - std::unique_ptr<ArcAuthContext> context_; std::unique_ptr<ArcAndroidManagementChecker> android_management_checker_; std::unique_ptr<ScopedOptInFlowTracker> scoped_opt_in_tracker_;
diff --git a/chrome/browser/chromeos/arc/auth/arc_auth_context.cc b/chrome/browser/chromeos/arc/auth/arc_auth_context.cc index 97470a7..bc76882 100644 --- a/chrome/browser/chromeos/arc/auth/arc_auth_context.cc +++ b/chrome/browser/chromeos/arc/auth/arc_auth_context.cc
@@ -6,16 +6,13 @@ #include <utility> +#include "base/stl_util.h" #include "base/strings/stringprintf.h" -#include "base/strings/utf_string_conversions.h" #include "chrome/browser/chromeos/arc/arc_support_host.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/signin/profile_oauth2_token_service_factory.h" -#include "chrome/browser/signin/signin_manager_factory.h" -#include "chrome/browser/signin/signin_ui_util.h" #include "chrome/browser/ui/app_list/arc/arc_app_utils.h" #include "components/signin/core/browser/profile_oauth2_token_service.h" -#include "components/signin/core/browser/signin_manager_base.h" #include "content/public/common/url_constants.h" #include "google_apis/gaia/gaia_auth_fetcher.h" #include "google_apis/gaia/gaia_constants.h" @@ -58,17 +55,12 @@ } // namespace -ArcAuthContext::ArcAuthContext(Profile* profile) - : profile_(profile), retry_backoff_(&kRetryBackoffPolicy) { - // Get token service and account ID to fetch auth tokens. - token_service_ = ProfileOAuth2TokenServiceFactory::GetForProfile(profile); - const SigninManagerBase* const signin_manager = - SigninManagerFactory::GetForProfile(profile); - CHECK(token_service_ && signin_manager); - account_id_ = signin_manager->GetAuthenticatedAccountId(); - - full_account_id_ = base::UTF16ToUTF8( - signin_ui_util::GetAuthenticatedUsername(signin_manager)); +ArcAuthContext::ArcAuthContext(Profile* profile, const std::string& account_id) + : profile_(profile), + account_id_(account_id), + token_service_(ProfileOAuth2TokenServiceFactory::GetForProfile(profile)), + retry_backoff_(&kRetryBackoffPolicy) { + DCHECK(base::ContainsValue(token_service_->GetAccounts(), account_id_)); } ArcAuthContext::~ArcAuthContext() {
diff --git a/chrome/browser/chromeos/arc/auth/arc_auth_context.h b/chrome/browser/chromeos/arc/auth/arc_auth_context.h index a9d5731..f4a9fbcb 100644 --- a/chrome/browser/chromeos/arc/auth/arc_auth_context.h +++ b/chrome/browser/chromeos/arc/auth/arc_auth_context.h
@@ -27,15 +27,17 @@ public GaiaAuthConsumer, public OAuth2TokenService::Observer { public: - explicit ArcAuthContext(Profile* profile); + // Creates an |ArcAuthContext| for the given |account_id|. This |account_id| + // must be the |account_id| used by the OAuth Token Service chain. + // Note: |account_id| can be the Device Account or a Secondary Account stored + // in Chrome OS Account Manager. + ArcAuthContext(Profile* profile, const std::string& account_id); ~ArcAuthContext() override; ProfileOAuth2TokenService* token_service() { return token_service_; } - const std::string& account_id() const { return account_id_; } - // Returns full account id, including dots that are removed in CrOS for - // the default account id. - const std::string& full_account_id() const { return full_account_id_; } + // TODO(sinhak): Check usages of |account_id()| and see if we can remove it. + const std::string& account_id() const { return account_id_; } // Prepares the context. Calling while an inflight operation exists will // cancel the inflight operation. @@ -70,10 +72,8 @@ // Unowned pointer. Profile* const profile_; - ProfileOAuth2TokenService* token_service_; - - std::string account_id_; - std::string full_account_id_; + const std::string account_id_; + ProfileOAuth2TokenService* const token_service_; // Whether the merge session should be skipped. Set to true only in testing. bool skip_merge_session_for_testing_ = false;
diff --git a/chrome/browser/chromeos/arc/auth/arc_auth_service.cc b/chrome/browser/chromeos/arc/auth/arc_auth_service.cc index 7c6f7c9..72c072c 100644 --- a/chrome/browser/chromeos/arc/auth/arc_auth_service.cc +++ b/chrome/browser/chromeos/arc/auth/arc_auth_service.cc
@@ -6,9 +6,12 @@ #include <utility> +#include "base/bind.h" #include "base/command_line.h" #include "base/memory/singleton.h" +#include "base/strings/utf_string_conversions.h" #include "base/time/time.h" +#include "chrome/browser/browser_process.h" #include "chrome/browser/chromeos/arc/arc_optin_uma.h" #include "chrome/browser/chromeos/arc/arc_session_manager.h" #include "chrome/browser/chromeos/arc/arc_util.h" @@ -16,9 +19,14 @@ #include "chrome/browser/chromeos/arc/auth/arc_robot_auth_code_fetcher.h" #include "chrome/browser/chromeos/arc/policy/arc_policy_util.h" #include "chrome/browser/chromeos/login/demo_mode/demo_session.h" +#include "chrome/browser/chromeos/profiles/profile_helper.h" #include "chrome/browser/lifetime/application_lifetime.h" #include "chrome/browser/profiles/profile.h" +#include "chrome/browser/signin/account_tracker_service_factory.h" +#include "chrome/browser/signin/signin_manager_factory.h" +#include "chrome/browser/signin/signin_ui_util.h" #include "chrome/browser/ui/app_list/arc/arc_data_removal_dialog.h" +#include "chromeos/account_manager/account_manager_factory.h" #include "chromeos/chromeos_switches.h" #include "components/arc/arc_bridge_service.h" #include "components/arc/arc_browser_context_keyed_service_factory_base.h" @@ -28,6 +36,8 @@ #include "components/arc/arc_supervision_transition.h" #include "components/arc/arc_util.h" #include "components/prefs/pref_service.h" +#include "components/signin/core/browser/account_tracker_service.h" +#include "components/signin/core/browser/signin_manager_base.h" #include "components/user_manager/user_manager.h" #include "content/public/browser/browser_context.h" #include "content/public/browser/browser_thread.h" @@ -121,7 +131,8 @@ const std::string& auth_info, const std::string& account_name, mojom::ChromeAccountType account_type, - bool is_managed) { + bool is_managed, + bool is_secondary_account) { mojom::AccountInfoPtr account_info = mojom::AccountInfo::New(); account_info->account_name = account_name; if (account_type == mojom::ChromeAccountType::ACTIVE_DIRECTORY_ACCOUNT) { @@ -134,6 +145,7 @@ } account_info->account_type = account_type; account_info->is_managed = is_managed; + account_info->is_secondary_account = is_secondary_account; return account_info; } @@ -151,22 +163,51 @@ ArcAuthService::ArcAuthService(content::BrowserContext* browser_context, ArcBridgeService* arc_bridge_service) : profile_(Profile::FromBrowserContext(browser_context)), + account_tracker_service_( + AccountTrackerServiceFactory::GetInstance()->GetForProfile(profile_)), arc_bridge_service_(arc_bridge_service), + account_mapper_util_(account_tracker_service_), url_loader_factory_( content::BrowserContext::GetDefaultStoragePartition(profile_) ->GetURLLoaderFactoryForBrowserProcess()), weak_ptr_factory_(this) { arc_bridge_service_->auth()->SetHost(this); arc_bridge_service_->auth()->AddObserver(this); + + if (chromeos::switches::IsAccountManagerEnabled()) { + // TODO(sinhak): This will need to be independent of Profile, when + // Multi-Profile on Chrome OS is launched. + chromeos::AccountManagerFactory* factory = + g_browser_process->platform_part()->GetAccountManagerFactory(); + account_manager_ = factory->GetAccountManager(profile_->GetPath().value()); + account_manager_->AddObserver(this); + } } ArcAuthService::~ArcAuthService() { + if (chromeos::switches::IsAccountManagerEnabled()) { + account_manager_->RemoveObserver(this); + } arc_bridge_service_->auth()->RemoveObserver(this); arc_bridge_service_->auth()->SetHost(nullptr); } +void ArcAuthService::OnConnectionReady() { + if (chromeos::switches::IsAccountManagerEnabled()) { + // The Mojo |OnSecondaryAccountUpserted| API is guaranteed to be called at + // least once for every account at startup. We need to get the list of + // accounts from |AccountManager|, just to be safe, since we may have missed + // the initial |AccountManager::Observer| notifications. We can safely call + // the Mojo |OnSecondaryAccountUpserted| API twice for every account since + // it is guaranteed to be idempotent. + account_manager_->GetAccounts(base::BindOnce( + &ArcAuthService::GetAccountsCallback, weak_ptr_factory_.GetWeakPtr())); + } +} + void ArcAuthService::OnConnectionClosed() { - fetcher_.reset(); + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + pending_token_requests_.clear(); } void ArcAuthService::OnAuthorizationComplete(mojom::ArcSignInStatus status, @@ -260,11 +301,32 @@ instance->OnAccountInfoReady(std::move(account_info), status); } -void ArcAuthService::RequestAccountInfo(bool initial_signin) { +void ArcAuthService::RequestAccountInfo( + bool initial_signin, + const base::Optional<std::string>& account_name) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); - // No other auth code-related operation may be in progress. - DCHECK(!fetcher_); + // Check if |account_name| points to a Secondary Account. + if (account_name.has_value()) { + DCHECK(!account_name.value().empty()); + + const std::string& gaia_id = + account_tracker_service_->FindAccountInfoByEmail(account_name.value()) + .gaia; + DCHECK(!gaia_id.empty()); + + if (!IsDeviceAccount(chromeos::AccountManager::AccountKey{ + gaia_id, + chromeos::account_manager::AccountType::ACCOUNT_TYPE_GAIA})) { + FetchSecondaryAccountInfo(account_name.value()); + return; + } + } + + FetchDeviceAccountInfo(initial_signin); +} + +void ArcAuthService::FetchDeviceAccountInfo(bool initial_signin) { const mojom::ChromeAccountType account_type = GetAccountType(profile_); if (IsArcOptInVerificationDisabled()) { @@ -272,7 +334,8 @@ CreateAccountInfo(false /* is_enforced */, std::string() /* auth_info */, std::string() /* auth_name */, account_type, - policy_util::IsAccountManaged(profile_)), + policy_util::IsAccountManaged(profile_), + false /* is_secondary_account */), mojom::ArcSignInStatus::SUCCESS); return; } @@ -283,10 +346,10 @@ auto enrollment_token_fetcher = std::make_unique<ArcActiveDirectoryEnrollmentTokenFetcher>( ArcSessionManager::Get()->support_host()); - enrollment_token_fetcher->Fetch( - base::BindOnce(&ArcAuthService::OnEnrollmentTokenFetched, - weak_ptr_factory_.GetWeakPtr())); - fetcher_ = std::move(enrollment_token_fetcher); + enrollment_token_fetcher->Fetch(base::BindOnce( + &ArcAuthService::OnActiveDirectoryEnrollmentTokenFetched, + weak_ptr_factory_.GetWeakPtr(), enrollment_token_fetcher.get())); + pending_token_requests_.emplace_back(std::move(enrollment_token_fetcher)); return; } @@ -295,7 +358,8 @@ OnAccountInfoReady( CreateAccountInfo(true /* is_enforced */, std::string() /* auth_info */, std::string() /* auth_name */, account_type, - true /* is_managed */), + true /* is_managed */, + false /* is_secondary_account */), mojom::ArcSignInStatus::SUCCESS); return; } @@ -308,21 +372,67 @@ auth_code_fetcher = std::make_unique<ArcRobotAuthCodeFetcher>(); } else { // Optionally retrieve auth code in silent mode. - auth_code_fetcher = std::make_unique<ArcBackgroundAuthCodeFetcher>( - url_loader_factory_, profile_, ArcSessionManager::Get()->auth_context(), - initial_signin); + const SigninManagerBase* const signin_manager = + SigninManagerFactory::GetForProfile(profile_); + auth_code_fetcher = CreateArcBackgroundAuthCodeFetcher( + signin_manager->GetAuthenticatedAccountId(), initial_signin); } - auth_code_fetcher->Fetch(base::Bind(&ArcAuthService::OnAuthCodeFetched, - weak_ptr_factory_.GetWeakPtr())); - fetcher_ = std::move(auth_code_fetcher); + auth_code_fetcher->Fetch( + base::Bind(&ArcAuthService::OnDeviceAccountAuthCodeFetched, + weak_ptr_factory_.GetWeakPtr(), auth_code_fetcher.get())); + pending_token_requests_.emplace_back(std::move(auth_code_fetcher)); } -void ArcAuthService::OnEnrollmentTokenFetched( +void ArcAuthService::OnTokenUpserted( + const chromeos::AccountManager::AccountKey& account_key) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + + // We send only Secondary Account update notifications to ARC++. ARC++ has a + // polling mechanism for the Device Account (See the Mojo APIs + // |RequestAccountInfo| and |OnAccountInfoReady|). + if (IsDeviceAccount(account_key)) { + return; + } + + auto* instance = ARC_GET_INSTANCE_FOR_METHOD(arc_bridge_service_->auth(), + OnSecondaryAccountUpserted); + if (!instance) { + LOG(ERROR) << "Auth instance is not available."; + return; + } + + const std::string& account_name = + account_mapper_util_.AccountKeyToGaiaAccountInfo(account_key).email; + DCHECK(!account_name.empty()); + instance->OnSecondaryAccountUpserted(account_name); +} + +void ArcAuthService::OnAccountRemoved( + const chromeos::AccountManager::AccountKey& account_key) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + DCHECK(!IsDeviceAccount(account_key)); + + auto* instance = ARC_GET_INSTANCE_FOR_METHOD(arc_bridge_service_->auth(), + OnSecondaryAccountRemoved); + if (!instance) { + LOG(ERROR) << "Auth instance is not available."; + return; + } + + const std::string& account_name = + account_mapper_util_.AccountKeyToGaiaAccountInfo(account_key).email; + DCHECK(!account_name.empty()); + instance->OnSecondaryAccountRemoved(account_name); +} + +void ArcAuthService::OnActiveDirectoryEnrollmentTokenFetched( + ArcActiveDirectoryEnrollmentTokenFetcher* fetcher, ArcActiveDirectoryEnrollmentTokenFetcher::Status status, const std::string& enrollment_token, const std::string& user_id) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); - fetcher_.reset(); + DeletePendingTokenRequest(fetcher); + fetcher = nullptr; switch (status) { case ArcActiveDirectoryEnrollmentTokenFetcher::Status::SUCCESS: { @@ -335,7 +445,8 @@ CreateAccountInfo(true /* is_enforced */, enrollment_token, std::string() /* account_name */, mojom::ChromeAccountType::ACTIVE_DIRECTORY_ACCOUNT, - true), + true /* is_managed */, + false /* is_secondary_account */), mojom::ArcSignInStatus::SUCCESS); break; } @@ -353,17 +464,24 @@ } } -void ArcAuthService::OnAuthCodeFetched(bool success, - const std::string& auth_code) { +void ArcAuthService::OnDeviceAccountAuthCodeFetched( + ArcAuthCodeFetcher* fetcher, + bool success, + const std::string& auth_code) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); - fetcher_.reset(); + DeletePendingTokenRequest(fetcher); + fetcher = nullptr; if (success) { + const SigninManagerBase* const signin_manager = + SigninManagerFactory::GetForProfile(profile_); + const std::string& full_account_id = base::UTF16ToUTF8( + signin_ui_util::GetAuthenticatedUsername(signin_manager)); OnAccountInfoReady( - CreateAccountInfo( - !IsArcOptInVerificationDisabled(), auth_code, - ArcSessionManager::Get()->auth_context()->full_account_id(), - GetAccountType(profile_), policy_util::IsAccountManaged(profile_)), + CreateAccountInfo(!IsArcOptInVerificationDisabled(), auth_code, + full_account_id, GetAccountType(profile_), + policy_util::IsAccountManaged(profile_), + false /* is_secondary_account */), mojom::ArcSignInStatus::SUCCESS); } else if (chromeos::DemoSession::Get() && chromeos::DemoSession::Get()->started()) { @@ -373,7 +491,8 @@ CreateAccountInfo(true /* is_enforced */, std::string() /* auth_info */, std::string() /* auth_name */, mojom::ChromeAccountType::OFFLINE_DEMO_ACCOUNT, - true /* is_managed */), + true /* is_managed */, + false /* is_secondary_account */), mojom::ArcSignInStatus::SUCCESS); } else { // Send error to ARC. @@ -382,6 +501,60 @@ } } +void ArcAuthService::FetchSecondaryAccountInfo( + const std::string& account_name) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + + const std::string& account_id = + account_tracker_service_->FindAccountInfoByEmail(account_name).account_id; + DCHECK(!account_id.empty()); + + std::unique_ptr<ArcBackgroundAuthCodeFetcher> fetcher = + CreateArcBackgroundAuthCodeFetcher(account_id, + false /* initial_signin */); + fetcher->Fetch(base::BindRepeating( + &ArcAuthService::OnSecondaryAccountAuthCodeFetched, + weak_ptr_factory_.GetWeakPtr(), account_name, fetcher.get())); + pending_token_requests_.emplace_back(std::move(fetcher)); +} + +void ArcAuthService::OnSecondaryAccountAuthCodeFetched( + const std::string& account_name, + ArcBackgroundAuthCodeFetcher* fetcher, + bool success, + const std::string& auth_code) { + DeletePendingTokenRequest(fetcher); + fetcher = nullptr; + + if (success) { + OnAccountInfoReady( + CreateAccountInfo(true /* is_enforced */, auth_code, account_name, + mojom::ChromeAccountType::USER_ACCOUNT, + false /* is_managed */, + true /* is_secondary_account */), + mojom::ArcSignInStatus::SUCCESS); + } else { + OnAccountInfoReady( + nullptr, mojom::ArcSignInStatus::CHROME_SERVER_COMMUNICATION_ERROR); + } +} + +void ArcAuthService::DeletePendingTokenRequest(ArcFetcherBase* fetcher) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + + for (auto it = pending_token_requests_.begin(); + it != pending_token_requests_.end(); ++it) { + if (it->get() == fetcher) { + pending_token_requests_.erase(it); + return; + } + } + + // We should not have received a call to delete a |fetcher| that was not in + // |pending_token_requests_|. + NOTREACHED(); +} + void ArcAuthService::SetURLLoaderFactoryForTesting( scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory) { url_loader_factory_ = std::move(url_loader_factory); @@ -398,4 +571,36 @@ ArcSessionManager::Get()->StopAndEnableArc(); } +void ArcAuthService::GetAccountsCallback( + std::vector<chromeos::AccountManager::AccountKey> accounts) { + for (const auto& account_key : accounts) { + OnTokenUpserted(account_key); + } +} + +bool ArcAuthService::IsDeviceAccount( + const chromeos::AccountManager::AccountKey& account_key) const { + const AccountId& device_account_id = chromeos::ProfileHelper::Get() + ->GetUserByProfile(profile_) + ->GetAccountId(); + + return account_mapper_util_.IsEqual(account_key, device_account_id); +} + +std::unique_ptr<ArcBackgroundAuthCodeFetcher> +ArcAuthService::CreateArcBackgroundAuthCodeFetcher( + const std::string& account_id, + bool initial_signin) { + auto fetcher = std::make_unique<ArcBackgroundAuthCodeFetcher>( + url_loader_factory_, profile_, account_id, initial_signin); + if (skip_merge_session_for_testing_) + fetcher->SkipMergeSessionForTesting(); + + return fetcher; +} + +void ArcAuthService::SkipMergeSessionForTesting() { + skip_merge_session_for_testing_ = true; +} + } // namespace arc
diff --git a/chrome/browser/chromeos/arc/auth/arc_auth_service.h b/chrome/browser/chromeos/arc/auth/arc_auth_service.h index ef73872..e59e814 100644 --- a/chrome/browser/chromeos/arc/auth/arc_auth_service.h +++ b/chrome/browser/chromeos/arc/auth/arc_auth_service.h
@@ -7,15 +7,20 @@ #include <memory> #include <string> +#include <vector> #include "base/macros.h" #include "base/memory/ref_counted.h" #include "base/memory/weak_ptr.h" +#include "base/optional.h" +#include "chrome/browser/chromeos/account_mapper_util.h" #include "chrome/browser/chromeos/arc/auth/arc_active_directory_enrollment_token_fetcher.h" +#include "chromeos/account_manager/account_manager.h" #include "components/arc/common/auth.mojom.h" #include "components/arc/connection_observer.h" #include "components/keyed_service/core/keyed_service.h" +class AccountTrackerService; class Profile; namespace content { @@ -28,13 +33,16 @@ namespace arc { -class ArcFetcherBase; +class ArcAuthCodeFetcher; +class ArcBackgroundAuthCodeFetcher; class ArcBridgeService; +class ArcFetcherBase; // Implementation of ARC authorization. class ArcAuthService : public KeyedService, public mojom::AuthHost, - public ConnectionObserver<mojom::AuthInstance> { + public ConnectionObserver<mojom::AuthInstance>, + public chromeos::AccountManager::Observer { public: // Returns singleton instance for the given BrowserContext, // or nullptr if the browser |context| is not allowed to use ARC. @@ -48,6 +56,7 @@ static const char kArcServiceName[]; // ConnectionObserver<mojom::AuthInstance>: + void OnConnectionReady() override; void OnConnectionClosed() override; // mojom::AuthHost: @@ -55,7 +64,9 @@ bool initial_signin) override; void OnSignInCompleteDeprecated() override; void OnSignInFailedDeprecated(mojom::ArcSignInStatus reason) override; - void RequestAccountInfo(bool initial_signin) override; + void RequestAccountInfo( + bool initial_signin, + const base::Optional<std::string>& account_name) override; void ReportMetrics(mojom::MetricsType metrics_type, int32_t value) override; void ReportAccountCheckStatus(mojom::AccountCheckStatus status) override; void ReportSupervisionChangeStatus( @@ -64,13 +75,51 @@ void SetURLLoaderFactoryForTesting( scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory); + // chromeos::AccountManager::Observer: + void OnTokenUpserted( + const chromeos::AccountManager::AccountKey& account_key) override; + void OnAccountRemoved( + const chromeos::AccountManager::AccountKey& account_key) override; + + void SkipMergeSessionForTesting(); + private: - // Callbacks when auth info is fetched. - void OnEnrollmentTokenFetched( + // Callback when Active Directory Enrollment Token is fetched. + void OnActiveDirectoryEnrollmentTokenFetched( + ArcActiveDirectoryEnrollmentTokenFetcher* fetcher, ArcActiveDirectoryEnrollmentTokenFetcher::Status status, const std::string& enrollment_token, const std::string& user_id); - void OnAuthCodeFetched(bool success, const std::string& auth_code); + + // Issues a request for fetching AccountInfo for the Device Account. + // |initial_signin| denotes whether this is the initial ARC++ provisioning + // flow or a subsequent sign-in. + void FetchDeviceAccountInfo(bool initial_signin); + + // Callback for |FetchDeviceAccountInfo|. + // |fetcher| is a pointer to the object that issues this callback. Used for + // deleting pending requests from |pending_token_requests_|. + // |success| and |auth_code| are the callback parameters passed by + // |ArcBackgroundAuthCodeFetcher::Fetch|. + void OnDeviceAccountAuthCodeFetched(ArcAuthCodeFetcher* fetcher, + bool success, + const std::string& auth_code); + + // Issues a request for fetching AccountInfo for a Secondary Account + // represented by |account_name|. |account_name| is the account identifier + // used by ARC++/Android. + void FetchSecondaryAccountInfo(const std::string& account_name); + + // Callback for |FetchSecondaryAccountInfo|, issued by + // |ArcBackgroundAuthCodeFetcher::Fetch|. |account_name| is the account + // identifier used by ARC++/Android. |fetcher| is used to identify the + // |ArcBackgroundAuthCodeFetcher| instance that completed the request. + // |success| and |auth_code| are arguments passed by + // |ArcBackgroundAuthCodeFetcher::Fetch| callback. + void OnSecondaryAccountAuthCodeFetched(const std::string& account_name, + ArcBackgroundAuthCodeFetcher* fetcher, + bool success, + const std::string& auth_code); // Called to let ARC container know the account info. void OnAccountInfoReady(mojom::AccountInfoPtr account_info, @@ -79,11 +128,40 @@ // Callback for data removal confirmation. void OnDataRemovalAccepted(bool accepted); + // |AccountManager::GetAccounts| callback. + void GetAccountsCallback( + std::vector<chromeos::AccountManager::AccountKey> accounts); + + // Checks whether |account_key| points to the Device Account. + bool IsDeviceAccount( + const chromeos::AccountManager::AccountKey& account_key) const; + + // Creates an |ArcBackgroundAuthCodeFetcher| for |account_id|. Can be used for + // Device Account and Secondary Accounts. |initial_signin| denotes whether the + // fetcher is being created for the initial ARC++ provisioning flow or for a + // subsequent sign-in. + std::unique_ptr<ArcBackgroundAuthCodeFetcher> + CreateArcBackgroundAuthCodeFetcher(const std::string& account_id, + bool initial_signin); + + // Deletes a completed enrollment token / auth code fetch request from + // |pending_token_requests_|. + void DeletePendingTokenRequest(ArcFetcherBase* fetcher); + + // Non-owning pointers. Profile* const profile_; + chromeos::AccountManager* account_manager_ = nullptr; + AccountTrackerService* const account_tracker_service_; ArcBridgeService* const arc_bridge_service_; + + chromeos::AccountMapperUtil account_mapper_util_; + scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory_; - std::unique_ptr<ArcFetcherBase> fetcher_; + // A list of pending enrollment token / auth code requests. + std::vector<std::unique_ptr<ArcFetcherBase>> pending_token_requests_; + + bool skip_merge_session_for_testing_ = false; base::WeakPtrFactory<ArcAuthService> weak_ptr_factory_;
diff --git a/chrome/browser/chromeos/arc/auth/arc_auth_service_browsertest.cc b/chrome/browser/chromeos/arc/auth/arc_auth_service_browsertest.cc index 96c5c2dc..560e10c 100644 --- a/chrome/browser/chromeos/arc/auth/arc_auth_service_browsertest.cc +++ b/chrome/browser/chromeos/arc/auth/arc_auth_service_browsertest.cc
@@ -11,6 +11,7 @@ #include "base/files/file_path.h" #include "base/files/scoped_temp_dir.h" #include "base/macros.h" +#include "base/optional.h" #include "base/run_loop.h" #include "base/test/scoped_feature_list.h" #include "chrome/browser/browser_process.h" @@ -26,6 +27,7 @@ #include "chrome/browser/chromeos/profiles/profile_helper.h" #include "chrome/browser/policy/cloud/test_request_interceptor.h" #include "chrome/browser/profiles/profile.h" +#include "chrome/browser/signin/account_tracker_service_factory.h" #include "chrome/browser/signin/chrome_device_id_helper.h" #include "chrome/browser/signin/fake_profile_oauth2_token_service_builder.h" #include "chrome/browser/signin/fake_signin_manager_builder.h" @@ -36,6 +38,8 @@ #include "chrome/browser/ui/ash/multi_user/multi_user_util.h" #include "chrome/test/base/in_process_browser_test.h" #include "chrome/test/base/testing_profile.h" +#include "chromeos/account_manager/account_manager.h" +#include "chromeos/account_manager/account_manager_factory.h" #include "chromeos/cryptohome/cryptohome_parameters.h" #include "components/account_id/account_id.h" #include "components/arc/arc_bridge_service.h" @@ -52,6 +56,7 @@ #include "components/policy/core/common/policy_switches.h" #include "components/prefs/pref_member.h" #include "components/prefs/pref_service.h" +#include "components/signin/core/browser/account_tracker_service.h" #include "components/signin/core/browser/fake_profile_oauth2_token_service.h" #include "components/user_manager/scoped_user_manager.h" #include "components/user_manager/user_manager.h" @@ -92,17 +97,38 @@ std::move(done_closure_).Run(); } - void RequestAccountInfo(base::Closure done_closure) { - done_closure_ = done_closure; - host_->RequestAccountInfo(true); + void RequestAccountInfo(base::OnceClosure done_closure) { + done_closure_ = std::move(done_closure); + host_->RequestAccountInfo(true /* initial_signin */, base::nullopt); + } + + void RequestSecondaryAccountInfo(base::OnceClosure done_closure, + const std::string& account_name) { + done_closure_ = std::move(done_closure); + host_->RequestAccountInfo(false /* initial_signin */, account_name); + } + + void OnSecondaryAccountUpserted(const std::string& account_name) override { + ++num_account_upserted_calls_; + upserted_account_name_ = account_name; + } + + void OnSecondaryAccountRemoved(const std::string& account_name) override { + ++num_account_removed_calls_; + removed_account_name_ = account_name; } mojom::AccountInfo* account_info() { return account_info_.get(); } + int num_account_upserted_calls_ = 0; + std::string upserted_account_name_; + int num_account_removed_calls_ = 0; + std::string removed_account_name_; + private: mojom::AuthHostPtr host_; mojom::AccountInfoPtr account_info_; - base::Closure done_closure_; + base::OnceClosure done_closure_; }; class ArcAuthServiceTest : public InProcessBrowserTest { @@ -195,6 +221,16 @@ profile_ = profile_builder.Build(); + chromeos::AccountManagerFactory* factory = + g_browser_process->platform_part()->GetAccountManagerFactory(); + chromeos::AccountManager* account_manager = + factory->GetAccountManager(profile_->GetPath().value()); + account_manager->Initialize( + temp_dir_.GetPath(), test_shared_loader_factory_, + base::BindRepeating([](const base::RepeatingClosure& closure) -> void { + closure.Run(); + })); + FakeProfileOAuth2TokenService* token_service = static_cast<FakeProfileOAuth2TokenService*>( ProfileOAuth2TokenServiceFactory::GetForProfile(profile())); @@ -211,11 +247,6 @@ ArcServiceLauncher::Get()->OnPrimaryUserProfilePrepared(profile()); - // It is non-trivial to navigate through the merge session in a testing - // context; currently we just skip it. - // TODO(blundell): Figure out how to enable this flow. - ArcSessionManager::Get()->auth_context()->SkipMergeSessionForTesting(); - auth_service_ = ArcAuthService::GetForBrowserContext(profile()); DCHECK(auth_service_); @@ -223,6 +254,10 @@ base::MakeRefCounted<network::WeakWrapperSharedURLLoaderFactory>( &test_url_loader_factory_); auth_service_->SetURLLoaderFactoryForTesting(test_shared_loader_factory_); + // It is non-trivial to navigate through the merge session in a testing + // context; currently we just skip it. + // TODO(blundell): Figure out how to enable this flow. + auth_service_->SkipMergeSessionForTesting(); arc_bridge_service_ = ArcServiceManager::Get()->arc_bridge_service(); DCHECK(arc_bridge_service_); @@ -230,6 +265,31 @@ WaitForInstanceReady(arc_bridge_service_->auth()); } + void SeedAccountInfo(const std::string& gaia_id, const std::string& email) { + AccountTrackerService* account_tracker_service = + AccountTrackerServiceFactory::GetInstance()->GetForProfile(profile()); + + AccountInfo account_info; + account_info.gaia = gaia_id; + account_info.email = email; + account_info.full_name = "name"; + account_info.given_name = "name"; + account_info.hosted_domain = "example.com"; + account_info.locale = "en"; + account_info.picture_url = "https://example.com"; + account_info.is_child_account = false; + account_info.account_id = account_tracker_service->PickAccountIdForAccount( + account_info.gaia, account_info.email); + + ASSERT_TRUE(account_info.IsValid()); + account_tracker_service->SeedAccountInfo(account_info); + + FakeProfileOAuth2TokenService* token_service = + static_cast<FakeProfileOAuth2TokenService*>( + ProfileOAuth2TokenServiceFactory::GetForProfile(profile())); + token_service->UpdateCredentials(account_info.account_id, kRefreshToken); + } + Profile* profile() { return profile_.get(); } void set_profile_name(const std::string& username) { @@ -262,7 +322,7 @@ SetAccountAndProfile(user_manager::USER_TYPE_REGULAR); test_url_loader_factory().AddResponse( arc::kAuthTokenExchangeEndPoint, - "{ \"token\" : \"" + std::string(kFakeAuthCode) + "\" }"); + R"({ "token" : ")" + std::string(kFakeAuthCode) + R"(" })"); base::RunLoop run_loop; auth_instance().RequestAccountInfo(run_loop.QuitClosure()); @@ -276,6 +336,83 @@ auth_instance().account_info()->account_type); EXPECT_FALSE(auth_instance().account_info()->enrollment_token); EXPECT_FALSE(auth_instance().account_info()->is_managed); + EXPECT_FALSE(auth_instance().account_info()->is_secondary_account); +} + +IN_PROC_BROWSER_TEST_F(ArcAuthServiceTest, + SecondaryAccountUpsertsArePropagated) { + const std::string gaia_id = "123999"; + const std::string email = "email.111@gmail.com"; + + SetAccountAndProfile(user_manager::USER_TYPE_REGULAR); + SeedAccountInfo(gaia_id, email); + + EXPECT_EQ(0, auth_instance().num_account_upserted_calls_); + + chromeos::AccountManager::AccountKey account_key{ + gaia_id, chromeos::account_manager::AccountType::ACCOUNT_TYPE_GAIA}; + auth_service().OnTokenUpserted(account_key); + base::RunLoop().RunUntilIdle(); + + EXPECT_EQ(1, auth_instance().num_account_upserted_calls_); + EXPECT_EQ(email, auth_instance().upserted_account_name_); +} + +IN_PROC_BROWSER_TEST_F(ArcAuthServiceTest, + SecondaryAccountRemovalsArePropagated) { + const std::string gaia_id = "123999"; + const std::string email = "email.111@gmail.com"; + + SetAccountAndProfile(user_manager::USER_TYPE_REGULAR); + SeedAccountInfo(gaia_id, email); + + EXPECT_EQ(0, auth_instance().num_account_removed_calls_); + + chromeos::AccountManager::AccountKey account_key{ + gaia_id, chromeos::account_manager::AccountType::ACCOUNT_TYPE_GAIA}; + auth_service().OnAccountRemoved(account_key); + base::RunLoop().RunUntilIdle(); + + EXPECT_EQ(1, auth_instance().num_account_removed_calls_); + EXPECT_EQ(email, auth_instance().removed_account_name_); +} + +IN_PROC_BROWSER_TEST_F(ArcAuthServiceTest, + DeviceAccountUpsertsAreNotPropagated) { + SetAccountAndProfile(user_manager::USER_TYPE_REGULAR); + + EXPECT_EQ(0, auth_instance().num_account_upserted_calls_); + + chromeos::AccountManager::AccountKey account_key{ + kFakeGaiaId, chromeos::account_manager::AccountType::ACCOUNT_TYPE_GAIA}; + auth_service().OnTokenUpserted(account_key); + base::RunLoop().RunUntilIdle(); + + EXPECT_EQ(0, auth_instance().num_account_upserted_calls_); +} + +IN_PROC_BROWSER_TEST_F(ArcAuthServiceTest, FetchSecondaryAccountInfoSucceeds) { + const std::string gaia_id = "123999"; + const std::string email = "email.111@gmail.com"; + + SetAccountAndProfile(user_manager::USER_TYPE_REGULAR); + SeedAccountInfo(gaia_id, email); + test_url_loader_factory().AddResponse( + arc::kAuthTokenExchangeEndPoint, + R"({ "token" : ")" + std::string(kFakeAuthCode) + R"(" })"); + + base::RunLoop run_loop; + auth_instance().RequestSecondaryAccountInfo(run_loop.QuitClosure(), email); + run_loop.Run(); + + ASSERT_TRUE(auth_instance().account_info()); + EXPECT_EQ(email, auth_instance().account_info()->account_name.value()); + EXPECT_EQ(kFakeAuthCode, auth_instance().account_info()->auth_code.value()); + EXPECT_EQ(mojom::ChromeAccountType::USER_ACCOUNT, + auth_instance().account_info()->account_type); + EXPECT_FALSE(auth_instance().account_info()->enrollment_token); + EXPECT_FALSE(auth_instance().account_info()->is_managed); + EXPECT_TRUE(auth_instance().account_info()->is_secondary_account); } class ArcRobotAccountAuthServiceTest : public ArcAuthServiceTest { @@ -441,7 +578,7 @@ EXPECT_TRUE(profile()->IsChild()); test_url_loader_factory().AddResponse( arc::kAuthTokenExchangeEndPoint, - "{ \"token\" : \"" + std::string(kFakeAuthCode) + "\" }"); + R"({ "token" : ")" + std::string(kFakeAuthCode) + R"(" })"); base::RunLoop run_loop; auth_instance().RequestAccountInfo(run_loop.QuitClosure());
diff --git a/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.cc b/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.cc index 8ba6be43..0d9ea4b 100644 --- a/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.cc +++ b/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.cc
@@ -51,12 +51,12 @@ ArcBackgroundAuthCodeFetcher::ArcBackgroundAuthCodeFetcher( scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, Profile* profile, - ArcAuthContext* context, + const std::string& account_id, bool initial_signin) : OAuth2TokenService::Consumer(kConsumerName), url_loader_factory_(std::move(url_loader_factory)), profile_(profile), - context_(context), + context_(profile_, account_id), initial_signin_(initial_signin), weak_ptr_factory_(this) {} @@ -65,8 +65,8 @@ void ArcBackgroundAuthCodeFetcher::Fetch(const FetchCallback& callback) { DCHECK(callback_.is_null()); callback_ = callback; - context_->Prepare(base::Bind(&ArcBackgroundAuthCodeFetcher::OnPrepared, - weak_ptr_factory_.GetWeakPtr())); + context_.Prepare(base::Bind(&ArcBackgroundAuthCodeFetcher::OnPrepared, + weak_ptr_factory_.GetWeakPtr())); } void ArcBackgroundAuthCodeFetcher::OnPrepared( @@ -77,13 +77,13 @@ } // Get token service and account ID to fetch auth tokens. - ProfileOAuth2TokenService* const token_service = context_->token_service(); - const std::string& account_id = context_->account_id(); - DCHECK(token_service->RefreshTokenIsAvailable(account_id)); + ProfileOAuth2TokenService* const token_service = context_.token_service(); + DCHECK(token_service->RefreshTokenIsAvailable(context_.account_id())); OAuth2TokenService::ScopeSet scopes; scopes.insert(GaiaConstants::kOAuth1LoginScope); - login_token_request_ = token_service->StartRequest(account_id, scopes, this); + login_token_request_ = + token_service->StartRequest(context_.account_id(), scopes, this); } void ArcBackgroundAuthCodeFetcher::OnGetTokenSuccess( @@ -230,11 +230,17 @@ void ArcBackgroundAuthCodeFetcher::ReportResult( const std::string& auth_code, OptInSilentAuthCode uma_status) { - if (initial_signin_) + if (initial_signin_) { UpdateSilentAuthCodeUMA(uma_status); - else + } else { + // TODO(sinhak): Check if we need to migrate this / create a new metric. UpdateReauthorizationSilentAuthCodeUMA(uma_status); + } std::move(callback_).Run(!auth_code.empty(), auth_code); } +void ArcBackgroundAuthCodeFetcher::SkipMergeSessionForTesting() { + context_.SkipMergeSessionForTesting(); +} + } // namespace arc
diff --git a/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.h b/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.h index 8622bcc..9ad9c09 100644 --- a/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.h +++ b/chrome/browser/chromeos/arc/auth/arc_background_auth_code_fetcher.h
@@ -38,16 +38,19 @@ class ArcBackgroundAuthCodeFetcher : public ArcAuthCodeFetcher, public OAuth2TokenService::Consumer { public: + // |account_id| is the id used by the OAuth Token Service chain. ArcBackgroundAuthCodeFetcher( scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, Profile* profile, - ArcAuthContext* context, + const std::string& account_id, bool initial_signin); ~ArcBackgroundAuthCodeFetcher() override; // ArcAuthCodeFetcher: void Fetch(const FetchCallback& callback) override; + void SkipMergeSessionForTesting(); + private: void ResetFetchers(); void OnPrepared(net::URLRequestContextGetter* request_context_getter); @@ -65,9 +68,9 @@ OptInSilentAuthCode uma_status); scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory_; - // Unowned pointers. + // Unowned pointer. Profile* const profile_; - ArcAuthContext* const context_; + ArcAuthContext context_; FetchCallback callback_; std::unique_ptr<OAuth2TokenService::Request> login_token_request_;
diff --git a/chrome/browser/chromeos/arc/policy/arc_android_management_checker.cc b/chrome/browser/chromeos/arc/policy/arc_android_management_checker.cc index a369091..4ead23e7 100644 --- a/chrome/browser/chromeos/arc/policy/arc_android_management_checker.cc +++ b/chrome/browser/chromeos/arc/policy/arc_android_management_checker.cc
@@ -15,9 +15,12 @@ #include "chrome/browser/chromeos/policy/browser_policy_connector_chromeos.h" #include "chrome/browser/net/system_network_context_manager.h" #include "chrome/browser/profiles/profile.h" +#include "chrome/browser/signin/profile_oauth2_token_service_factory.h" +#include "chrome/browser/signin/signin_manager_factory.h" #include "components/policy/core/browser/browser_policy_connector.h" #include "components/policy/core/common/cloud/device_management_service.h" #include "components/signin/core/browser/profile_oauth2_token_service.h" +#include "components/signin/core/browser/signin_manager_base.h" #include "services/network/public/cpp/shared_url_loader_factory.h" namespace arc { @@ -33,24 +36,30 @@ return connector->device_management_service(); } +// Returns the Device Account Id. Assumes that |profile| is the only Profile +// on Chrome OS. +std::string GetDeviceAccountId(Profile* profile) { + const SigninManagerBase* const signin_manager = + SigninManagerFactory::GetForProfile(profile); + + return signin_manager->GetAuthenticatedAccountId(); +} + } // namespace -ArcAndroidManagementChecker::ArcAndroidManagementChecker( - Profile* profile, - ProfileOAuth2TokenService* token_service, - const std::string& account_id, - bool retry_on_error) +ArcAndroidManagementChecker::ArcAndroidManagementChecker(Profile* profile, + bool retry_on_error) : profile_(profile), - token_service_(token_service), - account_id_(account_id), + token_service_(ProfileOAuth2TokenServiceFactory::GetForProfile(profile_)), + device_account_id_(GetDeviceAccountId(profile_)), retry_on_error_(retry_on_error), retry_delay_(kRetryDelayMin), android_management_client_( GetDeviceManagementService(), g_browser_process->system_network_context_manager() ->GetSharedURLLoaderFactory(), - account_id, - token_service), + device_account_id_, + token_service_), weak_ptr_factory_(this) {} ArcAndroidManagementChecker::~ArcAndroidManagementChecker() { @@ -79,7 +88,7 @@ } void ArcAndroidManagementChecker::EnsureRefreshTokenLoaded() { - if (token_service_->RefreshTokenIsAvailable(account_id_)) { + if (token_service_->RefreshTokenIsAvailable(device_account_id_)) { // If the refresh token is already available, just start the management // check immediately. StartCheckInternal(); @@ -93,7 +102,7 @@ void ArcAndroidManagementChecker::OnRefreshTokenAvailable( const std::string& account_id) { - if (account_id != account_id_) + if (account_id != device_account_id_) return; OnRefreshTokensLoaded(); } @@ -106,7 +115,7 @@ void ArcAndroidManagementChecker::StartCheckInternal() { DCHECK(!callback_.is_null()); - if (!token_service_->RefreshTokenIsAvailable(account_id_)) { + if (!token_service_->RefreshTokenIsAvailable(device_account_id_)) { VLOG(2) << "No refresh token is available for android management check."; std::move(callback_).Run(policy::AndroidManagementClient::Result::ERROR); return;
diff --git a/chrome/browser/chromeos/arc/policy/arc_android_management_checker.h b/chrome/browser/chromeos/arc/policy/arc_android_management_checker.h index 54b0de6..e1abc36 100644 --- a/chrome/browser/chromeos/arc/policy/arc_android_management_checker.h +++ b/chrome/browser/chromeos/arc/policy/arc_android_management_checker.h
@@ -21,10 +21,7 @@ class ArcAndroidManagementChecker : public OAuth2TokenService::Observer { public: - ArcAndroidManagementChecker(Profile* profile, - ProfileOAuth2TokenService* token_service, - const std::string& account_id, - bool retry_on_error); + ArcAndroidManagementChecker(Profile* profile, bool retry_on_error); ~ArcAndroidManagementChecker() override; static void StartClient(); @@ -54,7 +51,7 @@ Profile* profile_; ProfileOAuth2TokenService* const token_service_; - const std::string account_id_; + const std::string device_account_id_; // If true, on error, instead of reporting the error to the caller, schedule // the retry with delay.
diff --git a/chrome/browser/chromeos/chrome_browser_main_chromeos.cc b/chrome/browser/chromeos/chrome_browser_main_chromeos.cc index 93698f8b..c04f681 100644 --- a/chrome/browser/chromeos/chrome_browser_main_chromeos.cc +++ b/chrome/browser/chromeos/chrome_browser_main_chromeos.cc
@@ -47,7 +47,6 @@ #include "chrome/browser/chromeos/boot_times_recorder.h" #include "chrome/browser/chromeos/dbus/chrome_features_service_provider.h" #include "chrome/browser/chromeos/dbus/chrome_proxy_resolution_service_provider_delegate.h" -#include "chrome/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.h" #include "chrome/browser/chromeos/dbus/component_updater_service_provider.h" #include "chrome/browser/chromeos/dbus/drive_file_stream_service_provider.h" #include "chrome/browser/chromeos/dbus/kiosk_info_service_provider.h" @@ -347,9 +346,7 @@ kVirtualFileRequestServiceName, dbus::ObjectPath(kVirtualFileRequestServicePath), CrosDBusService::CreateServiceProviderList( - std::make_unique<VirtualFileRequestServiceProvider>( - std::make_unique< - ChromeVirtualFileRequestServiceProviderDelegate>()))); + std::make_unique<VirtualFileRequestServiceProvider>())); component_updater_service_ = CrosDBusService::Create( kComponentUpdaterServiceName,
diff --git a/chrome/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.cc b/chrome/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.cc deleted file mode 100644 index 352e22fb..0000000 --- a/chrome/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.cc +++ /dev/null
@@ -1,52 +0,0 @@ -// 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/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.h" - -#include "chrome/browser/chromeos/arc/arc_session_manager.h" -#include "chrome/browser/chromeos/arc/fileapi/arc_file_system_bridge.h" -#include "chrome/browser/profiles/profile.h" - -namespace chromeos { - -namespace { - -arc::ArcFileSystemBridge* GetArcFileSystemBridge() { - arc::ArcSessionManager* session_manager = arc::ArcSessionManager::Get(); - if (!session_manager) - return nullptr; - Profile* profile = session_manager->profile(); - if (!profile) - return nullptr; - return arc::ArcFileSystemBridge::GetForBrowserContext(profile); -} - -} // namespace - -ChromeVirtualFileRequestServiceProviderDelegate:: - ChromeVirtualFileRequestServiceProviderDelegate() = default; - -ChromeVirtualFileRequestServiceProviderDelegate:: - ~ChromeVirtualFileRequestServiceProviderDelegate() = default; - -bool ChromeVirtualFileRequestServiceProviderDelegate::HandleReadRequest( - const std::string& id, - int64_t offset, - int64_t size, - base::ScopedFD pipe_write_end) { - arc::ArcFileSystemBridge* bridge = GetArcFileSystemBridge(); - if (!bridge) - return false; - return bridge->HandleReadRequest(id, offset, size, std::move(pipe_write_end)); -} - -bool ChromeVirtualFileRequestServiceProviderDelegate::HandleIdReleased( - const std::string& id) { - arc::ArcFileSystemBridge* bridge = GetArcFileSystemBridge(); - if (!bridge) - return false; - return bridge->HandleIdReleased(id); -} - -} // namespace chromeos
diff --git a/chrome/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.h b/chrome/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.h deleted file mode 100644 index d00f428..0000000 --- a/chrome/browser/chromeos/dbus/chrome_virtual_file_request_service_provider_delegate.h +++ /dev/null
@@ -1,38 +0,0 @@ -// 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_BROWSER_CHROMEOS_DBUS_CHROME_VIRTUAL_FILE_REQUEST_SERVICE_PROVIDER_DELEGATE_H_ -#define CHROME_BROWSER_CHROMEOS_DBUS_CHROME_VIRTUAL_FILE_REQUEST_SERVICE_PROVIDER_DELEGATE_H_ - -#include <string> - -#include "base/compiler_specific.h" -#include "base/macros.h" -#include "base/memory/ref_counted.h" -#include "base/memory/weak_ptr.h" -#include "chrome/browser/chromeos/dbus/virtual_file_request_service_provider.h" - -namespace chromeos { - -// Chrome's VirtualFileRequestServiceProvider::Delegate implementation. -class ChromeVirtualFileRequestServiceProviderDelegate - : public VirtualFileRequestServiceProvider::Delegate { - public: - ChromeVirtualFileRequestServiceProviderDelegate(); - ~ChromeVirtualFileRequestServiceProviderDelegate() override; - - // VirtualFileRequestServiceProvider::Delegate overrides: - bool HandleReadRequest(const std::string& id, - int64_t offset, - int64_t size, - base::ScopedFD pipe_write_end) override; - bool HandleIdReleased(const std::string& id) override; - - private: - DISALLOW_COPY_AND_ASSIGN(ChromeVirtualFileRequestServiceProviderDelegate); -}; - -} // namespace chromeos - -#endif // CHROME_BROWSER_CHROMEOS_DBUS_CHROME_VIRTUAL_FILE_REQUEST_SERVICE_PROVIDER_DELEGATE_H_
diff --git a/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.cc b/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.cc index 39b76e0..05fc138 100644 --- a/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.cc +++ b/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.cc
@@ -4,17 +4,37 @@ #include "chrome/browser/chromeos/dbus/virtual_file_request_service_provider.h" +#include <stdint.h> + +#include <memory> +#include <string> #include <utility> #include "base/bind.h" +#include "base/files/scoped_file.h" +#include "chrome/browser/chromeos/arc/arc_session_manager.h" +#include "chrome/browser/chromeos/arc/fileapi/arc_file_system_bridge.h" +#include "chrome/browser/profiles/profile.h" #include "dbus/message.h" #include "third_party/cros_system_api/dbus/service_constants.h" namespace chromeos { +namespace { -VirtualFileRequestServiceProvider::VirtualFileRequestServiceProvider( - std::unique_ptr<Delegate> delegate) - : delegate_(std::move(delegate)), weak_ptr_factory_(this) {} +arc::ArcFileSystemBridge* GetArcFileSystemBridge() { + arc::ArcSessionManager* session_manager = arc::ArcSessionManager::Get(); + if (!session_manager) + return nullptr; + Profile* profile = session_manager->profile(); + if (!profile) + return nullptr; + return arc::ArcFileSystemBridge::GetForBrowserContext(profile); +} + +} // namespace + +VirtualFileRequestServiceProvider::VirtualFileRequestServiceProvider() + : weak_ptr_factory_(this) {} VirtualFileRequestServiceProvider::~VirtualFileRequestServiceProvider() = default; @@ -57,13 +77,15 @@ method_call, DBUS_ERROR_INVALID_ARGS, std::string())); return; } - if (!delegate_->HandleReadRequest(id, offset, size, - std::move(pipe_write_end))) { + + arc::ArcFileSystemBridge* bridge = GetArcFileSystemBridge(); + if (bridge && + bridge->HandleReadRequest(id, offset, size, std::move(pipe_write_end))) { + response_sender.Run(dbus::Response::FromMethodCall(method_call)); + } else { response_sender.Run(dbus::ErrorResponse::FromMethodCall( method_call, DBUS_ERROR_FAILED, std::string())); - return; } - response_sender.Run(dbus::Response::FromMethodCall(method_call)); } void VirtualFileRequestServiceProvider::HandleIdReleased( @@ -76,12 +98,14 @@ method_call, DBUS_ERROR_INVALID_ARGS, std::string())); return; } - if (!delegate_->HandleIdReleased(id)) { + + arc::ArcFileSystemBridge* bridge = GetArcFileSystemBridge(); + if (bridge && bridge->HandleIdReleased(id)) { + response_sender.Run(dbus::Response::FromMethodCall(method_call)); + } else { response_sender.Run(dbus::ErrorResponse::FromMethodCall( method_call, DBUS_ERROR_FAILED, std::string())); - return; } - response_sender.Run(dbus::Response::FromMethodCall(method_call)); } } // namespace chromeos
diff --git a/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.h b/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.h index b589fc05..244740ad 100644 --- a/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.h +++ b/chrome/browser/chromeos/dbus/virtual_file_request_service_provider.h
@@ -5,13 +5,6 @@ #ifndef CHROME_BROWSER_CHROMEOS_DBUS_VIRTUAL_FILE_REQUEST_SERVICE_PROVIDER_H_ #define CHROME_BROWSER_CHROMEOS_DBUS_VIRTUAL_FILE_REQUEST_SERVICE_PROVIDER_H_ -#include <stdint.h> - -#include <memory> -#include <string> - -#include "base/compiler_specific.h" -#include "base/files/scoped_file.h" #include "base/macros.h" #include "base/memory/ref_counted.h" #include "base/memory/weak_ptr.h" @@ -29,23 +22,7 @@ class VirtualFileRequestServiceProvider : public CrosDBusService::ServiceProviderInterface { public: - // TODO(derat): Move the delegate into this class. - class Delegate { - public: - virtual ~Delegate() {} - - // Writes the requested data to the given pipe write end. - virtual bool HandleReadRequest(const std::string& id, - int64_t offset, - int64_t size, - base::ScopedFD pipe_write_end) = 0; - - // Releases resources associated with the ID. - virtual bool HandleIdReleased(const std::string& id) = 0; - }; - - explicit VirtualFileRequestServiceProvider( - std::unique_ptr<Delegate> delegate); + VirtualFileRequestServiceProvider(); ~VirtualFileRequestServiceProvider() override; // CrosDBusService::ServiceProviderInterface overrides: @@ -58,8 +35,6 @@ void HandleIdReleased(dbus::MethodCall* method_call, dbus::ExportedObject::ResponseSender response_sender); - std::unique_ptr<Delegate> delegate_; - // Keep this last so that all weak pointers will be invalidated at the // beginning of destruction. base::WeakPtrFactory<VirtualFileRequestServiceProvider> weak_ptr_factory_;
diff --git a/chrome/browser/chromeos/extensions/file_manager/file_manager_private_apitest.cc b/chrome/browser/chromeos/extensions/file_manager/file_manager_private_apitest.cc index 6b3d9b38..c2e25b0 100644 --- a/chrome/browser/chromeos/extensions/file_manager/file_manager_private_apitest.cc +++ b/chrome/browser/chromeos/extensions/file_manager/file_manager_private_apitest.cc
@@ -375,11 +375,19 @@ // check that UnmountPath is really called with the same value. EXPECT_CALL(*disk_mount_manager_mock_, UnmountPath(_, _, _)) .Times(0); + EXPECT_CALL( + *disk_mount_manager_mock_, + UnmountPath(chromeos::CrosDisksClient::GetRemovableDiskMountPoint() + .AppendASCII("mount_path1") + .AsUTF8Unsafe(), + chromeos::UNMOUNT_OPTIONS_NONE, _)) + .Times(1); EXPECT_CALL(*disk_mount_manager_mock_, - UnmountPath( - chromeos::CrosDisksClient::GetArchiveMountPoint().AppendASCII( - "archive_mount_path").AsUTF8Unsafe(), - chromeos::UNMOUNT_OPTIONS_NONE, _)).Times(1); + UnmountPath(chromeos::CrosDisksClient::GetArchiveMountPoint() + .AppendASCII("archive_mount_path") + .AsUTF8Unsafe(), + chromeos::UNMOUNT_OPTIONS_LAZY, _)) + .Times(1); ASSERT_TRUE(RunComponentExtensionTest("file_browser/mount_test")) << message_;
diff --git a/chrome/browser/chromeos/extensions/file_manager/private_api_mount.cc b/chrome/browser/chromeos/extensions/file_manager/private_api_mount.cc index 99d8f18..8a8ecdb 100644 --- a/chrome/browser/chromeos/extensions/file_manager/private_api_mount.cc +++ b/chrome/browser/chromeos/extensions/file_manager/private_api_mount.cc
@@ -225,8 +225,12 @@ switch (volume->type()) { case file_manager::VOLUME_TYPE_REMOVABLE_DISK_PARTITION: case file_manager::VOLUME_TYPE_MOUNTED_ARCHIVE_FILE: { + chromeos::UnmountOptions unmount_options = chromeos::UNMOUNT_OPTIONS_NONE; + if (volume->is_read_only()) + unmount_options = chromeos::UNMOUNT_OPTIONS_LAZY; + DiskMountManager::GetInstance()->UnmountPath( - volume->mount_path().value(), chromeos::UNMOUNT_OPTIONS_NONE, + volume->mount_path().value(), unmount_options, DiskMountManager::UnmountPathCallback()); break; }
diff --git a/chrome/browser/chromeos/file_manager/filesystem_api_util.cc b/chrome/browser/chromeos/file_manager/filesystem_api_util.cc index 61731e9..b6bbf7a3 100644 --- a/chrome/browser/chromeos/file_manager/filesystem_api_util.cc +++ b/chrome/browser/chromeos/file_manager/filesystem_api_util.cc
@@ -129,6 +129,7 @@ switch (type) { case storage::kFileSystemTypeNativeLocal: case storage::kFileSystemTypeRestrictedNativeLocal: + case storage::kFileSystemTypeDriveFs: return false; default: // The path indeed corresponds to a mount point not associated with a
diff --git a/chrome/browser/chromeos/input_method/input_method_manager_impl.cc b/chrome/browser/chromeos/input_method/input_method_manager_impl.cc index cc8aa16..7121a46 100644 --- a/chrome/browser/chromeos/input_method/input_method_manager_impl.cc +++ b/chrome/browser/chromeos/input_method/input_method_manager_impl.cc
@@ -1389,7 +1389,8 @@ InputMethodManagerImpl::GetInputMethodKeyboardController() { // Callers expect a nullptr when the keyboard is disabled. See // https://crbug.com/850020. - return keyboard::KeyboardController::Get()->enabled() + return keyboard::KeyboardController::HasInstance() && + keyboard::KeyboardController::Get()->enabled() ? keyboard::KeyboardController::Get() : nullptr; }
diff --git a/chrome/browser/chromeos/login/screens/demo_preferences_screen.cc b/chrome/browser/chromeos/login/screens/demo_preferences_screen.cc index 3867f6d5..de5e676 100644 --- a/chrome/browser/chromeos/login/screens/demo_preferences_screen.cc +++ b/chrome/browser/chromeos/login/screens/demo_preferences_screen.cc
@@ -4,37 +4,80 @@ #include "chrome/browser/chromeos/login/screens/demo_preferences_screen.h" -#include "base/logging.h" #include "chrome/browser/chromeos/login/screens/base_screen_delegate.h" #include "chrome/browser/chromeos/login/screens/demo_preferences_screen_view.h" #include "chrome/browser/chromeos/login/screens/screen_exit_code.h" +#include "chrome/browser/chromeos/login/screens/welcome_screen.h" +#include "chrome/browser/chromeos/login/wizard_controller.h" +#include "ui/base/ime/chromeos/input_method_descriptor.h" namespace chromeos { +namespace { + constexpr char kUserActionContinue[] = "continue-setup"; constexpr char kUserActionClose[] = "close-setup"; +constexpr char kContextKeyLocale[] = "locale"; +constexpr char kContextKeyInputMethod[] = "input-method"; + +WelcomeScreen* GetWelcomeScreen() { + const WizardController* wizard_controller = + WizardController::default_controller(); + DCHECK(wizard_controller); + return WelcomeScreen::Get(wizard_controller->screen_manager()); +} + +// Sets locale and input method. If |locale| or |input_method| is empty then +// they will not be changed. +void SetApplicationLocaleAndInputMethod(const std::string& locale, + const std::string& input_method) { + WelcomeScreen* welcome_screen = GetWelcomeScreen(); + DCHECK(welcome_screen); + welcome_screen->SetApplicationLocaleAndInputMethod(locale, input_method); +} + +} // namespace + DemoPreferencesScreen::DemoPreferencesScreen( BaseScreenDelegate* base_screen_delegate, DemoPreferencesScreenView* view) : BaseScreen(base_screen_delegate, OobeScreen::SCREEN_OOBE_DEMO_PREFERENCES), + input_manager_observer_(this), view_(view) { DCHECK(view_); view_->Bind(this); + + // TODO(agawronska): Add tests for locale and input changes. + input_method::InputMethodManager* input_manager = + input_method::InputMethodManager::Get(); + UpdateInputMethod(input_manager); + input_manager_observer_.Add(input_manager); } DemoPreferencesScreen::~DemoPreferencesScreen() { + input_method::InputMethodManager::Get()->RemoveObserver(this); + if (view_) view_->Bind(nullptr); } void DemoPreferencesScreen::Show() { + WelcomeScreen* welcome_screen = GetWelcomeScreen(); + if (welcome_screen) { + initial_locale_ = welcome_screen->GetApplicationLocale(); + initial_input_method_ = welcome_screen->GetInputMethod(); + } + if (view_) view_->Show(); } void DemoPreferencesScreen::Hide() { + initial_locale_.clear(); + initial_input_method_.clear(); + if (view_) view_->Hide(); } @@ -43,15 +86,44 @@ if (action_id == kUserActionContinue) { Finish(ScreenExitCode::DEMO_MODE_PREFERENCES_CONTINUED); } else if (action_id == kUserActionClose) { + // Restore initial locale and input method if the user pressed back button. + SetApplicationLocaleAndInputMethod(initial_locale_, initial_input_method_); Finish(ScreenExitCode::DEMO_MODE_PREFERENCES_CANCELED); } else { BaseScreen::OnUserAction(action_id); } } +void DemoPreferencesScreen::OnContextKeyUpdated( + const ::login::ScreenContext::KeyType& key) { + if (key == kContextKeyLocale) { + SetApplicationLocaleAndInputMethod(context_.GetString(kContextKeyLocale), + std::string()); + } else if (key == kContextKeyInputMethod) { + SetApplicationLocaleAndInputMethod( + std::string(), context_.GetString(kContextKeyInputMethod)); + } else { + BaseScreen::OnContextKeyUpdated(key); + } +} + void DemoPreferencesScreen::OnViewDestroyed(DemoPreferencesScreenView* view) { if (view_ == view) view_ = nullptr; } +void DemoPreferencesScreen::InputMethodChanged( + input_method::InputMethodManager* manager, + Profile* profile, + bool show_message) { + UpdateInputMethod(manager); +} + +void DemoPreferencesScreen::UpdateInputMethod( + input_method::InputMethodManager* input_manager) { + const input_method::InputMethodDescriptor input_method = + input_manager->GetActiveIMEState()->GetCurrentInputMethod(); + GetContextEditor().SetString(kContextKeyInputMethod, input_method.id()); +} + } // namespace chromeos
diff --git a/chrome/browser/chromeos/login/screens/demo_preferences_screen.h b/chrome/browser/chromeos/login/screens/demo_preferences_screen.h index e4826ea..4aab7a9 100644 --- a/chrome/browser/chromeos/login/screens/demo_preferences_screen.h +++ b/chrome/browser/chromeos/login/screens/demo_preferences_screen.h
@@ -5,8 +5,13 @@ #ifndef CHROME_BROWSER_CHROMEOS_LOGIN_SCREENS_DEMO_PREFERENCES_SCREEN_H_ #define CHROME_BROWSER_CHROMEOS_LOGIN_SCREENS_DEMO_PREFERENCES_SCREEN_H_ +#include <string> + #include "base/macros.h" +#include "base/scoped_observer.h" #include "chrome/browser/chromeos/login/screens/base_screen.h" +#include "components/login/screens/screen_context.h" +#include "ui/base/ime/chromeos/input_method_manager.h" namespace chromeos { @@ -15,7 +20,9 @@ // Controls demo mode preferences. The screen can be shown during OOBE. It // allows user to choose preferences for retail demo mode. -class DemoPreferencesScreen : public BaseScreen { +class DemoPreferencesScreen + : public BaseScreen, + public input_method::InputMethodManager::Observer { public: DemoPreferencesScreen(BaseScreenDelegate* base_screen_delegate, DemoPreferencesScreenView* view); @@ -25,12 +32,32 @@ void Show() override; void Hide() override; void OnUserAction(const std::string& action_id) override; + void OnContextKeyUpdated(const ::login::ScreenContext::KeyType& key) override; // Called when view is being destroyed. If Screen is destroyed earlier // then it has to call Bind(nullptr). void OnViewDestroyed(DemoPreferencesScreenView* view); private: + // InputMethodManager::Observer: + void InputMethodChanged(input_method::InputMethodManager* manager, + Profile* profile, + bool show_message) override; + + // Passes current input method to the context, so it can be shown in the UI. + void UpdateInputMethod(input_method::InputMethodManager* input_manager); + + // Initial locale that was set when the screen was shown. It will be restored + // if user presses back button. + std::string initial_locale_; + + // Initial input method that was set when the screen was shown. It will be + // restored if user presses back button. + std::string initial_input_method_; + + ScopedObserver<input_method::InputMethodManager, DemoPreferencesScreen> + input_manager_observer_; + DemoPreferencesScreenView* view_; DISALLOW_COPY_AND_ASSIGN(DemoPreferencesScreen);
diff --git a/chrome/browser/chromeos/login/wizard_controller.h b/chrome/browser/chromeos/login/wizard_controller.h index cffe2e4..f734b34 100644 --- a/chrome/browser/chromeos/login/wizard_controller.h +++ b/chrome/browser/chromeos/login/wizard_controller.h
@@ -148,7 +148,7 @@ BaseScreen* GetScreen(OobeScreen screen); // Returns the current ScreenManager instance. - ScreenManager* screen_manager() { return screen_manager_.get(); } + ScreenManager* screen_manager() const { return screen_manager_.get(); } // Volume percent at which spoken feedback is still audible. static const int kMinAudibleOutputVolumePercent;
diff --git a/chrome/browser/chromeos/oauth2_token_service_delegate_unittest.cc b/chrome/browser/chromeos/oauth2_token_service_delegate_unittest.cc index 62573c8..c02771c7 100644 --- a/chrome/browser/chromeos/oauth2_token_service_delegate_unittest.cc +++ b/chrome/browser/chromeos/oauth2_token_service_delegate_unittest.cc
@@ -105,7 +105,7 @@ AccountTrackerService::MIGRATION_NOT_STARTED); client_ = std::make_unique<TestSigninClient>(&pref_service_); - account_tracker_service_.Initialize(client_.get()); + account_tracker_service_.Initialize(&pref_service_, base::FilePath()); account_info_ = CreateAccountInfoTestFixture("111" /* gaia_id */, "user@gmail.com" /* email */);
diff --git a/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.cc b/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.cc index 50a9d17..bc54873 100644 --- a/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.cc +++ b/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.cc
@@ -15,7 +15,6 @@ #include "base/strings/stringprintf.h" #include "base/syslog_logging.h" #include "base/values.h" -#include "chrome/browser/browser_process.h" #include "chrome/browser/chromeos/policy/device_local_account.h" #include "chrome/browser/chromeos/policy/off_hours/off_hours_proto_parser.h" #include "chrome/browser/chromeos/tpm_firmware_update.h" @@ -23,6 +22,7 @@ #include "chromeos/dbus/dbus_thread_manager.h" #include "chromeos/dbus/update_engine_client.h" #include "chromeos/settings/cros_settings_names.h" +#include "components/policy/core/common/chrome_schema.h" #include "components/policy/core/common/external_data_fetcher.h" #include "components/policy/core/common/policy_map.h" #include "components/policy/core/common/policy_types.h" @@ -40,6 +40,26 @@ namespace { +// If the |json_string| can be decoded and validated against the schema +// identified by |policy_name| in policy_templates.json, the policy +// |policy_name| in |policies| will be set to the decoded base::Value. +// Otherwise, the policy will be set to a base::Value of the original +// |json_string|. This way, the faulty value can still be seen in +// chrome://policy along with any errors/warnings. +void SetJsonDevicePolicy(const std::string& policy_name, + const std::string& json_string, + PolicyMap* policies) { + std::string error; + std::unique_ptr<base::Value> decoded_json = + DecodeJsonStringAndNormalize(json_string, policy_name, &error); + auto value_to_set = decoded_json ? std::move(decoded_json) + : std::make_unique<base::Value>(json_string); + policies->Set(policy_name, POLICY_LEVEL_MANDATORY, POLICY_SCOPE_MACHINE, + POLICY_SOURCE_CLOUD, std::move(value_to_set), nullptr); + if (!error.empty()) + policies->SetError(policy_name, error); +} + // Decodes a protobuf integer to an IntegerValue. Returns NULL in case the input // value is out of bounds. std::unique_ptr<base::Value> DecodeIntegerValue(google::protobuf::int64 value) { @@ -53,50 +73,6 @@ return std::unique_ptr<base::Value>(new base::Value(static_cast<int>(value))); } -// Decodes a JSON string to a base::Value, and drops unknown properties -// according to a policy schema. |policy_name| is the name of a policy schema -// defined in policy_templates.json. Returns NULL in case the input is not a -// valid JSON string. -std::unique_ptr<base::Value> DecodeJsonStringAndDropUnknownBySchema( - const std::string& json_string, - const std::string& policy_name) { - std::string error; - std::unique_ptr<base::Value> root = base::JSONReader::ReadAndReturnError( - json_string, base::JSON_ALLOW_TRAILING_COMMAS, NULL, &error); - - if (!root) { - LOG(WARNING) << "Invalid JSON string: " << error << ", ignoring."; - return std::unique_ptr<base::Value>(); - } - - const Schema& schema = g_browser_process->browser_policy_connector() - ->GetChromeSchema() - .GetKnownProperty(policy_name); - - if (schema.valid()) { - std::string error_path; - bool changed = false; - - if (!schema.Normalize(root.get(), SCHEMA_ALLOW_UNKNOWN, &error_path, &error, - &changed)) { - LOG(WARNING) << "Invalid policy value for " << policy_name << ": " - << error << " at " << error_path << "."; - return std::unique_ptr<base::Value>(); - } - - if (changed) { - LOG(WARNING) << "Some properties in " << policy_name - << " were dropped: " << error << " at " << error_path << "."; - } - } else { - LOG(WARNING) << "Unknown or invalid policy schema for " << policy_name - << "."; - return std::unique_ptr<base::Value>(); - } - - return root; -} - std::unique_ptr<base::Value> DecodeConnectionType(int value) { static const char* const kConnectionTypes[] = { shill::kTypeEthernet, shill::kTypeWifi, shill::kTypeWimax, @@ -335,15 +311,8 @@ const em::LoginScreenPowerManagementProto& container( policy.login_screen_power_management()); if (container.has_login_screen_power_management()) { - std::unique_ptr<base::Value> decoded_json; - decoded_json = DecodeJsonStringAndDropUnknownBySchema( - container.login_screen_power_management(), - key::kDeviceLoginScreenPowerManagement); - if (decoded_json) { - policies->Set(key::kDeviceLoginScreenPowerManagement, - POLICY_LEVEL_MANDATORY, POLICY_SCOPE_MACHINE, - POLICY_SOURCE_CLOUD, std::move(decoded_json), nullptr); - } + SetJsonDevicePolicy(key::kDeviceLoginScreenPowerManagement, + container.login_screen_power_management(), policies); } } @@ -674,28 +643,13 @@ } if (container.has_disallowed_time_intervals()) { - std::unique_ptr<base::Value> decoded_json = - DecodeJsonStringAndDropUnknownBySchema( - container.disallowed_time_intervals(), - key::kDeviceAutoUpdateTimeRestrictions); - if (decoded_json && !decoded_json->is_none()) { - policies->Set(key::kDeviceAutoUpdateTimeRestrictions, - POLICY_LEVEL_MANDATORY, POLICY_SCOPE_MACHINE, - POLICY_SOURCE_CLOUD, std::move(decoded_json), nullptr); - } + SetJsonDevicePolicy(key::kDeviceAutoUpdateTimeRestrictions, + container.disallowed_time_intervals(), policies); } if (container.has_staging_schedule()) { - std::unique_ptr<base::Value> staging_percent_of_fleet_per_week_policy = - DecodeJsonStringAndDropUnknownBySchema( - container.staging_schedule(), key::kDeviceUpdateStagingSchedule); - - if (staging_percent_of_fleet_per_week_policy) { - policies->Set(key::kDeviceUpdateStagingSchedule, POLICY_LEVEL_MANDATORY, - POLICY_SCOPE_MACHINE, POLICY_SOURCE_CLOUD, - std::move(staging_percent_of_fleet_per_week_policy), - nullptr); - } + SetJsonDevicePolicy(key::kDeviceUpdateStagingSchedule, + container.staging_schedule(), policies); } } @@ -933,17 +887,8 @@ const em::DeviceWallpaperImageProto& container( policy.device_wallpaper_image()); if (container.has_device_wallpaper_image()) { - std::unique_ptr<base::DictionaryValue> dict_val = - base::DictionaryValue::From( - base::JSONReader::Read(container.device_wallpaper_image())); - if (dict_val) { - policies->Set(key::kDeviceWallpaperImage, POLICY_LEVEL_MANDATORY, - POLICY_SCOPE_MACHINE, POLICY_SOURCE_CLOUD, - std::move(dict_val), nullptr); - } else { - SYSLOG(ERROR) << "Value of wallpaper policy has invalid format: " - << container.device_wallpaper_image(); - } + SetJsonDevicePolicy(key::kDeviceWallpaperImage, + container.device_wallpaper_image(), policies); } } @@ -977,12 +922,8 @@ const em::DeviceNativePrintersProto& container( policy.native_device_printers()); if (container.has_external_policy()) { - std::unique_ptr<base::DictionaryValue> dict_val = - base::DictionaryValue::From( - base::JSONReader::Read(container.external_policy())); - policies->Set(key::kDeviceNativePrinters, POLICY_LEVEL_MANDATORY, - POLICY_SCOPE_MACHINE, POLICY_SOURCE_CLOUD, - std::move(dict_val), nullptr); + SetJsonDevicePolicy(key::kDeviceNativePrinters, + container.external_policy(), policies); } } @@ -1112,6 +1053,43 @@ } // namespace +std::unique_ptr<base::Value> DecodeJsonStringAndNormalize( + const std::string& json_string, + const std::string& policy_name, + std::string* error) { + std::string json_error; + std::unique_ptr<base::Value> root = base::JSONReader::ReadAndReturnError( + json_string, base::JSON_ALLOW_TRAILING_COMMAS, NULL, &json_error); + if (!root) { + *error = "Invalid JSON string: " + json_error; + return nullptr; + } + + const Schema& schema = + policy::GetChromeSchema().GetKnownProperty(policy_name); + CHECK(schema.valid()); + + std::string schema_error; + std::string error_path; + bool changed = false; + if (!schema.Normalize(root.get(), SCHEMA_ALLOW_UNKNOWN, &error_path, + &schema_error, &changed)) { + std::ostringstream msg; + msg << "Invalid policy value: " << schema_error << " (at " + << (error_path.empty() ? "toplevel" : error_path) << ")"; + *error = msg.str(); + return nullptr; + } + if (changed) { + std::ostringstream msg; + msg << "Dropped unknown properties: " << schema_error << " (at " + << (error_path.empty() ? "toplevel" : error_path) << ")"; + *error = msg.str(); + } + + return root; +} + void DecodeDevicePolicy(const em::ChromeDeviceSettingsProto& policy, PolicyMap* policies) { // Decode the various groups of policies.
diff --git a/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.h b/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.h index bc9fc63..edc4f7f7 100644 --- a/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.h +++ b/chrome/browser/chromeos/policy/device_policy_decoder_chromeos.h
@@ -5,14 +5,32 @@ #ifndef CHROME_BROWSER_CHROMEOS_POLICY_DEVICE_POLICY_DECODER_CHROMEOS_H_ #define CHROME_BROWSER_CHROMEOS_POLICY_DEVICE_POLICY_DECODER_CHROMEOS_H_ +#include <memory> +#include <string> + namespace enterprise_management { class ChromeDeviceSettingsProto; } +namespace base { +class Value; +} + namespace policy { class PolicyMap; +// Decodes a JSON string to a base::Value and validates it against the schema +// defined in policy_templates.json for the policy named |policy_name|. Unknown +// properties are dropped. Returns nullptr if the input cannot be parsed as +// valid JSON string or doesn't comply with the declared schema (e.g. mismatched +// type, missing required field, etc.). Any warning or error messages from the +// decoding and schema validation process are stored in |error|. +std::unique_ptr<base::Value> DecodeJsonStringAndNormalize( + const std::string& json_string, + const std::string& policy_name, + std::string* error); + // Decodes device policy in ChromeDeviceSettingsProto representation into the a // PolicyMap. void DecodeDevicePolicy(
diff --git a/chrome/browser/chromeos/policy/device_policy_decoder_chromeos_unittest.cc b/chrome/browser/chromeos/policy/device_policy_decoder_chromeos_unittest.cc new file mode 100644 index 0000000..6482e49 --- /dev/null +++ b/chrome/browser/chromeos/policy/device_policy_decoder_chromeos_unittest.cc
@@ -0,0 +1,114 @@ +// Copyright 2018 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/browser/chromeos/policy/device_policy_decoder_chromeos.h" +#include "components/policy/policy_constants.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace policy { + +namespace { + +constexpr char kInvalidJson[] = R"({"foo": "bar")"; + +constexpr char kInvalidPolicyName[] = "invalid-policy-name"; + +constexpr char kWallpaperJson[] = R"({ + "url": "https://example.com/device_wallpaper.jpg", + "hash": "examplewallpaperhash" + })"; + +constexpr char kWallpaperJsonInvalidValue[] = R"({ + "url": 123, + "hash": "examplewallpaperhash" + })"; + +constexpr char kWallpaperJsonUnknownProperty[] = R"({ + "url": "https://example.com/device_wallpaper.jpg", + "hash": "examplewallpaperhash", + "unknown-field": "random-value" + })"; + +constexpr char kWallpaperUrlPropertyName[] = "url"; +constexpr char kWallpaperUrlPropertyValue[] = + "https://example.com/device_wallpaper.jpg"; +constexpr char kWallpaperHashPropertyName[] = "hash"; +constexpr char kWallpaperHashPropertyValue[] = "examplewallpaperhash"; + +} // namespace + +class DevicePolicyDecoderChromeOSTest : public testing::Test { + public: + DevicePolicyDecoderChromeOSTest() = default; + ~DevicePolicyDecoderChromeOSTest() override = default; + + protected: + std::unique_ptr<base::Value> GetWallpaperDict() const; + + private: + DISALLOW_COPY_AND_ASSIGN(DevicePolicyDecoderChromeOSTest); +}; + +std::unique_ptr<base::Value> DevicePolicyDecoderChromeOSTest::GetWallpaperDict() + const { + auto dict = std::make_unique<base::DictionaryValue>(); + dict->SetKey(kWallpaperUrlPropertyName, + base::Value(kWallpaperUrlPropertyValue)); + dict->SetKey(kWallpaperHashPropertyName, + base::Value(kWallpaperHashPropertyValue)); + return dict; +} + +TEST_F(DevicePolicyDecoderChromeOSTest, + DecodeJsonStringAndNormalizeJSONParseError) { + std::string error; + std::unique_ptr<base::Value> decoded_json = DecodeJsonStringAndNormalize( + kInvalidJson, key::kDeviceWallpaperImage, &error); + EXPECT_FALSE(decoded_json); + EXPECT_EQ("Invalid JSON string: Line: 1, column: 13, Syntax error.", error); +} + +#if GTEST_HAS_DEATH_TEST +TEST_F(DevicePolicyDecoderChromeOSTest, + DecodeJsonStringAndNormalizeInvalidSchema) { + std::string error; + EXPECT_DEATH( + DecodeJsonStringAndNormalize(kWallpaperJson, kInvalidPolicyName, &error), + ""); +} +#endif + +TEST_F(DevicePolicyDecoderChromeOSTest, + DecodeJsonStringAndNormalizeInvalidValue) { + std::string error; + std::unique_ptr<base::Value> decoded_json = DecodeJsonStringAndNormalize( + kWallpaperJsonInvalidValue, key::kDeviceWallpaperImage, &error); + EXPECT_FALSE(decoded_json); + EXPECT_EQ( + "Invalid policy value: The value type doesn't match the schema type. (at " + "url)", + error); +} + +TEST_F(DevicePolicyDecoderChromeOSTest, + DecodeJsonStringAndNormalizeUnknownProperty) { + std::string error; + std::unique_ptr<base::Value> decoded_json = DecodeJsonStringAndNormalize( + kWallpaperJsonUnknownProperty, key::kDeviceWallpaperImage, &error); + EXPECT_EQ(*GetWallpaperDict(), *decoded_json); + EXPECT_EQ( + "Dropped unknown properties: Unknown property: unknown-field (at " + "toplevel)", + error); +} + +TEST_F(DevicePolicyDecoderChromeOSTest, DecodeJsonStringAndNormalizeSuccess) { + std::string error; + std::unique_ptr<base::Value> decoded_json = DecodeJsonStringAndNormalize( + kWallpaperJson, key::kDeviceWallpaperImage, &error); + EXPECT_EQ(*GetWallpaperDict(), *decoded_json); + EXPECT_TRUE(error.empty()); +} + +} // namespace policy
diff --git a/chrome/browser/chromeos/policy/network_configuration_updater_unittest.cc b/chrome/browser/chromeos/policy/network_configuration_updater_unittest.cc index 8dcf37f..f2c0ddb0 100644 --- a/chrome/browser/chromeos/policy/network_configuration_updater_unittest.cc +++ b/chrome/browser/chromeos/policy/network_configuration_updater_unittest.cc
@@ -15,6 +15,7 @@ #include "base/run_loop.h" #include "base/values.h" #include "chrome/browser/chromeos/policy/device_network_configuration_updater.h" +#include "chrome/browser/chromeos/policy/policy_certificate_provider.h" #include "chrome/browser/chromeos/policy/user_network_configuration_updater.h" #include "chrome/browser/chromeos/settings/cros_settings.h" #include "chrome/browser/chromeos/settings/scoped_cros_settings_test_helper.h" @@ -81,7 +82,7 @@ }; class FakePolicyProvidedCertsObserver - : public UserNetworkConfigurationUpdater::PolicyProvidedCertsObserver { + : public PolicyCertificateProvider::Observer { public: FakePolicyProvidedCertsObserver() {} @@ -517,7 +518,8 @@ TEST_F(NetworkConfigurationUpdaterTest, DoNotAllowTrustedCertificatesFromPolicy) { EXPECT_CALL(network_config_handler_, - SetPolicy(onc::ONC_SOURCE_USER_POLICY, _, _, _)); + SetPolicy(onc::ONC_SOURCE_USER_POLICY, _, _, _)) + .Times(AnyNumber()); UserNetworkConfigurationUpdater* updater = CreateNetworkConfigurationUpdaterForUserPolicy( @@ -529,10 +531,17 @@ FakePolicyProvidedCertsObserver observer; updater->AddPolicyProvidedCertsObserver(&observer); + PolicyMap policy; + policy.Set(key::kOpenNetworkConfiguration, POLICY_LEVEL_MANDATORY, + POLICY_SCOPE_USER, POLICY_SOURCE_CLOUD, + std::make_unique<base::Value>(kFakeONC), nullptr); + UpdateProviderPolicy(policy); MarkPolicyProviderInitialized(); base::RunLoop().RunUntilIdle(); EXPECT_TRUE(updater->GetWebTrustedCertificates().empty()); + EXPECT_EQ(2u, updater->GetCertificatesWithoutWebTrust().size()); + EXPECT_EQ(2u, updater->GetAllServerAndAuthorityCertificates().size()); EXPECT_TRUE(observer.trust_anchors_.empty()); updater->RemovePolicyProvidedCertsObserver(&observer); @@ -564,6 +573,8 @@ // Certificates with the "Web" trust flag set will be returned. EXPECT_EQ(1u, updater->GetWebTrustedCertificates().size()); + EXPECT_EQ(1u, updater->GetCertificatesWithoutWebTrust().size()); + EXPECT_EQ(2u, updater->GetAllServerAndAuthorityCertificates().size()); EXPECT_EQ(1u, observer.trust_anchors_.size()); updater->RemovePolicyProvidedCertsObserver(&observer); @@ -589,6 +600,8 @@ // Verify that the returned certificate list is empty. EXPECT_TRUE(updater->GetWebTrustedCertificates().empty()); EXPECT_TRUE(observer.trust_anchors_.empty()); + EXPECT_TRUE(updater->GetCertificatesWithoutWebTrust().empty()); + EXPECT_TRUE(updater->GetAllServerAndAuthorityCertificates().empty()); // Change to ONC policy with web trust certs. PolicyMap policy; @@ -602,6 +615,8 @@ // to observers. EXPECT_EQ(1u, updater->GetWebTrustedCertificates().size()); EXPECT_EQ(1u, observer.trust_anchors_.size()); + EXPECT_EQ(1u, updater->GetCertificatesWithoutWebTrust().size()); + EXPECT_EQ(2u, updater->GetAllServerAndAuthorityCertificates().size()); updater->RemovePolicyProvidedCertsObserver(&observer); }
diff --git a/chrome/browser/chromeos/policy/policy_cert_service.h b/chrome/browser/chromeos/policy/policy_cert_service.h index 1d436dd5..4ff69a0 100644 --- a/chrome/browser/chromeos/policy/policy_cert_service.h +++ b/chrome/browser/chromeos/policy/policy_cert_service.h
@@ -13,6 +13,7 @@ #include "base/macros.h" #include "base/memory/ref_counted.h" #include "base/memory/weak_ptr.h" +#include "chrome/browser/chromeos/policy/policy_certificate_provider.h" #include "chrome/browser/chromeos/policy/user_network_configuration_updater.h" #include "components/keyed_service/core/keyed_service.h" @@ -34,9 +35,8 @@ // and marking the profile's prefs if any of the trust anchors was used. // Except for unit tests, PolicyCertVerifier should only be created through this // class. -class PolicyCertService - : public KeyedService, - public UserNetworkConfigurationUpdater::PolicyProvidedCertsObserver { +class PolicyCertService : public KeyedService, + public PolicyCertificateProvider::Observer { public: PolicyCertService(const std::string& user_id, UserNetworkConfigurationUpdater* net_conf_updater,
diff --git a/chrome/browser/chromeos/policy/policy_cert_service_factory.cc b/chrome/browser/chromeos/policy/policy_cert_service_factory.cc index 8c86647f..a60b2ba00 100644 --- a/chrome/browser/chromeos/policy/policy_cert_service_factory.cc +++ b/chrome/browser/chromeos/policy/policy_cert_service_factory.cc
@@ -99,7 +99,7 @@ return NULL; UserNetworkConfigurationUpdater* net_conf_updater = - UserNetworkConfigurationUpdaterFactory::GetForProfile(profile); + UserNetworkConfigurationUpdaterFactory::GetForBrowserContext(profile); if (!net_conf_updater) return NULL;
diff --git a/chrome/browser/chromeos/policy/policy_certificate_provider.h b/chrome/browser/chromeos/policy/policy_certificate_provider.h new file mode 100644 index 0000000..ae1654ec --- /dev/null +++ b/chrome/browser/chromeos/policy/policy_certificate_provider.h
@@ -0,0 +1,60 @@ +// Copyright 2018 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_BROWSER_CHROMEOS_POLICY_POLICY_CERTIFICATE_PROVIDER_H_ +#define CHROME_BROWSER_CHROMEOS_POLICY_POLICY_CERTIFICATE_PROVIDER_H_ + +#include <memory> +#include <vector> + +#include "base/macros.h" +#include "base/memory/ref_counted.h" + +namespace net { +class X509Certificate; +using CertificateList = std::vector<scoped_refptr<X509Certificate>>; +} // namespace net + +namespace policy { + +class PolicyCertificateProvider { + public: + virtual ~PolicyCertificateProvider() {} + + class Observer { + public: + virtual ~Observer() = default; + + // Is called every time the list of policy-set server and authority + // certificates changes. + virtual void OnPolicyProvidedCertsChanged( + const net::CertificateList& all_server_and_authority_certs, + const net::CertificateList& trust_anchors) = 0; + }; + + virtual void AddPolicyProvidedCertsObserver(Observer* observer) = 0; + virtual void RemovePolicyProvidedCertsObserver(Observer* observer) = 0; + + // Returns all server and authority certificates successfully parsed from ONC, + // independent of their trust bits. + virtual net::CertificateList GetAllServerAndAuthorityCertificates() const = 0; + + // Returns the server and authority certificates which were successfully + // parsed from ONC and were granted web trust. This means that the + // certificates had the "Web" trust bit set, and this + // UserNetworkConfigurationUpdater instance was created with + // |allow_trusted_certs_from_policy| = true. + virtual net::CertificateList GetWebTrustedCertificates() const = 0; + + // Returns the server and authority certificates which were successfully + // parsed from ONC and did not request or were not granted web trust. + // This is equivalent to calling |GetAllServerAndAuthorityCertificates| and + // then removing all certificates returned by |GetWebTrustedCertificates| from + // the result. + virtual net::CertificateList GetCertificatesWithoutWebTrust() const = 0; +}; + +} // namespace policy + +#endif // CHROME_BROWSER_CHROMEOS_POLICY_POLICY_CERTIFICATE_PROVIDER_H_
diff --git a/chrome/browser/chromeos/policy/user_network_configuration_updater.cc b/chrome/browser/chromeos/policy/user_network_configuration_updater.cc index 2d4d7b7..b15c2f49 100644 --- a/chrome/browser/chromeos/policy/user_network_configuration_updater.cc +++ b/chrome/browser/chromeos/policy/user_network_configuration_updater.cc
@@ -25,6 +25,8 @@ #include "net/cert/x509_certificate.h" #include "net/cert/x509_util_nss.h" +using chromeos::onc::OncParsedCertificates; + namespace policy { UserNetworkConfigurationUpdater::~UserNetworkConfigurationUpdater() {} @@ -52,13 +54,13 @@ } void UserNetworkConfigurationUpdater::AddPolicyProvidedCertsObserver( - PolicyProvidedCertsObserver* observer) { + PolicyCertificateProvider::Observer* observer) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); observer_list_.AddObserver(observer); } void UserNetworkConfigurationUpdater::RemovePolicyProvidedCertsObserver( - PolicyProvidedCertsObserver* observer) { + PolicyCertificateProvider::Observer* observer) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); observer_list_.RemoveObserver(observer); } @@ -75,7 +77,7 @@ network_config_handler), allow_trusted_certificates_from_policy_(allow_trusted_certs_from_policy), user_(&user), - certs_(std::make_unique<chromeos::onc::OncParsedCertificates>()), + certs_(std::make_unique<OncParsedCertificates>()), weak_factory_(this) { // The updater is created with |client_certificate_importer_| unset and is // responsible for creating it. This requires |GetNSSCertDatabaseForProfile| @@ -89,44 +91,40 @@ net::CertificateList UserNetworkConfigurationUpdater::GetAllServerAndAuthorityCertificates() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - - net::CertificateList all_server_and_authority_certs; - - for (const chromeos::onc::OncParsedCertificates::ServerOrAuthorityCertificate& - server_or_authority_cert : - certs_->server_or_authority_certificates()) { - all_server_and_authority_certs.push_back( - server_or_authority_cert.certificate()); - } - - return all_server_and_authority_certs; + return GetServerAndAuthorityCertificates(base::BindRepeating( + [](const OncParsedCertificates::ServerOrAuthorityCertificate& cert) { + return true; + })); } net::CertificateList UserNetworkConfigurationUpdater::GetWebTrustedCertificates() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - if (!allow_trusted_certificates_from_policy_) return net::CertificateList(); - net::CertificateList trust_anchors; - for (const chromeos::onc::OncParsedCertificates::ServerOrAuthorityCertificate& - server_or_authority_cert : - certs_->server_or_authority_certificates()) { - if (server_or_authority_cert.web_trust_requested()) - trust_anchors.push_back(server_or_authority_cert.certificate()); - } + return GetServerAndAuthorityCertificates(base::BindRepeating( + [](const OncParsedCertificates::ServerOrAuthorityCertificate& cert) { + return cert.web_trust_requested(); + })); +} - return trust_anchors; +net::CertificateList +UserNetworkConfigurationUpdater::GetCertificatesWithoutWebTrust() const { + if (!allow_trusted_certificates_from_policy_) + return GetAllServerAndAuthorityCertificates(); + + return GetServerAndAuthorityCertificates(base::BindRepeating( + [](const OncParsedCertificates::ServerOrAuthorityCertificate& cert) { + return !cert.web_trust_requested(); + })); } void UserNetworkConfigurationUpdater::ImportCertificates( const base::ListValue& certificates_onc) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - std::unique_ptr<chromeos::onc::OncParsedCertificates> incoming_certs = - std::make_unique<chromeos::onc::OncParsedCertificates>(certificates_onc); + std::unique_ptr<OncParsedCertificates> incoming_certs = + std::make_unique<OncParsedCertificates>(certificates_onc); bool server_or_authority_certs_changed = certs_->server_or_authority_certificates() != @@ -221,4 +219,20 @@ } } +net::CertificateList +UserNetworkConfigurationUpdater::GetServerAndAuthorityCertificates( + ServerOrAuthorityCertPredicate predicate) const { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + + net::CertificateList certificates; + + for (const OncParsedCertificates::ServerOrAuthorityCertificate& + server_or_authority_cert : + certs_->server_or_authority_certificates()) { + if (predicate.Run(server_or_authority_cert)) + certificates.push_back(server_or_authority_cert.certificate()); + } + + return certificates; +} } // namespace policy
diff --git a/chrome/browser/chromeos/policy/user_network_configuration_updater.h b/chrome/browser/chromeos/policy/user_network_configuration_updater.h index 07edd6f..d37e9f7 100644 --- a/chrome/browser/chromeos/policy/user_network_configuration_updater.h +++ b/chrome/browser/chromeos/policy/user_network_configuration_updater.h
@@ -15,6 +15,7 @@ #include "base/observer_list.h" #include "base/sequence_checker.h" #include "chrome/browser/chromeos/policy/network_configuration_updater.h" +#include "chrome/browser/chromeos/policy/policy_certificate_provider.h" #include "chromeos/network/onc/onc_parsed_certificates.h" #include "components/keyed_service/core/keyed_service.h" #include "content/public/browser/notification_observer.h" @@ -52,18 +53,10 @@ // expansion with the user's name (or email address, etc.) and handling of "Web" // trust of certificates. class UserNetworkConfigurationUpdater : public NetworkConfigurationUpdater, + public PolicyCertificateProvider, public KeyedService, public content::NotificationObserver { public: - class PolicyProvidedCertsObserver { - public: - // Is called every time the list of policy-set server and authority - // certificates changes. - virtual void OnPolicyProvidedCertsChanged( - const net::CertificateList& all_server_and_authority_certs, - const net::CertificateList& trust_anchors) = 0; - }; - ~UserNetworkConfigurationUpdater() override; // Creates an updater that applies the ONC user policy from |policy_service| @@ -79,19 +72,14 @@ PolicyService* policy_service, chromeos::ManagedNetworkConfigurationHandler* network_config_handler); - void AddPolicyProvidedCertsObserver(PolicyProvidedCertsObserver* observer); - void RemovePolicyProvidedCertsObserver(PolicyProvidedCertsObserver* observer); - - // Returns all server and authority certificates successfully parsed from ONC, - // independent of their trust bits. - net::CertificateList GetAllServerAndAuthorityCertificates() const; - - // Returns the server and authority certificates which were successfully - // parsed from ONC and were granted web trust. This means that the - // certificates had the "Web" trust bit set, and this - // UserNetworkConfigurationUpdater instance was created with - // |allow_trusted_certs_from_policy| = true. - net::CertificateList GetWebTrustedCertificates() const; + // PolicyCertificateProvider: + void AddPolicyProvidedCertsObserver( + PolicyCertificateProvider::Observer* observer) override; + void RemovePolicyProvidedCertsObserver( + PolicyCertificateProvider::Observer* observer) override; + net::CertificateList GetAllServerAndAuthorityCertificates() const override; + net::CertificateList GetWebTrustedCertificates() const override; + net::CertificateList GetCertificatesWithoutWebTrust() const override; // Helper method to expose |SetClientCertificateImporter| for usage in tests. // Note that the CertificateImporter is only used for importing client @@ -102,6 +90,11 @@ private: class CrosTrustAnchorProvider; + // A predicate used for filtering server or authority certificates. + using ServerOrAuthorityCertPredicate = base::RepeatingCallback<bool( + const chromeos::onc::OncParsedCertificates::ServerOrAuthorityCertificate& + cert)>; + UserNetworkConfigurationUpdater( Profile* profile, bool allow_trusted_certs_from_policy, @@ -132,13 +125,18 @@ void NotifyPolicyProvidedCertsChanged(); + // Returns all server and authority certificates successfully parsed from ONC + // for which |predicate| returns true. + net::CertificateList GetServerAndAuthorityCertificates( + ServerOrAuthorityCertPredicate predicate) const; + // Whether Web trust is allowed or not. bool allow_trusted_certificates_from_policy_; // The user for whom the user policy will be applied. const user_manager::User* user_; - base::ObserverList<PolicyProvidedCertsObserver, true>::Unchecked + base::ObserverList<PolicyCertificateProvider::Observer, true>::Unchecked observer_list_; // Holds certificates from the last parsed ONC policy.
diff --git a/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.cc b/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.cc index 680c8171..b503ed2 100644 --- a/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.cc +++ b/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.cc
@@ -21,9 +21,10 @@ // static UserNetworkConfigurationUpdater* -UserNetworkConfigurationUpdaterFactory::GetForProfile(Profile* profile) { +UserNetworkConfigurationUpdaterFactory::GetForBrowserContext( + content::BrowserContext* browser_context) { return static_cast<UserNetworkConfigurationUpdater*>( - GetInstance()->GetServiceForBrowserContext(profile, true)); + GetInstance()->GetServiceForBrowserContext(browser_context, true)); } // static
diff --git a/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.h b/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.h index 946721c..e250989 100644 --- a/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.h +++ b/chrome/browser/chromeos/policy/user_network_configuration_updater_factory.h
@@ -14,7 +14,9 @@ struct DefaultSingletonTraits; } // namespace base -class Profile; +namespace content { +class BrowserContext; +} namespace policy { @@ -25,9 +27,11 @@ : public BrowserContextKeyedServiceFactory { public: // Returns an existing or creates a new UserNetworkConfigurationUpdater for - // |profile|. Will return NULL if this service isn't allowed for |profile|, - // i.e. for all but the primary user's profile. - static UserNetworkConfigurationUpdater* GetForProfile(Profile* profile); + // |browser_context|. Will return nullptr if this service isn't allowed for + // |browser_context|, i.e. for all but the BrowserContext which refers to the + // primary user's profile. + static UserNetworkConfigurationUpdater* GetForBrowserContext( + content::BrowserContext* browser_context); static UserNetworkConfigurationUpdaterFactory* GetInstance();
diff --git a/chrome/browser/chromeos/policy/user_network_configuration_updater_factory_browsertest.cc b/chrome/browser/chromeos/policy/user_network_configuration_updater_factory_browsertest.cc index 544a7ae..838d51e 100644 --- a/chrome/browser/chromeos/policy/user_network_configuration_updater_factory_browsertest.cc +++ b/chrome/browser/chromeos/policy/user_network_configuration_updater_factory_browsertest.cc
@@ -18,6 +18,7 @@ #include "chrome/browser/chromeos/login/wizard_controller.h" #include "chrome/browser/chromeos/policy/device_policy_cros_browser_test.h" #include "chrome/browser/chromeos/policy/login_policy_test_base.h" +#include "chrome/browser/chromeos/policy/policy_certificate_provider.h" #include "chrome/browser/chromeos/policy/user_network_configuration_updater.h" #include "chrome/browser/chromeos/policy/user_network_configuration_updater_factory.h" #include "chrome/browser/chromeos/profiles/profile_helper.h" @@ -74,11 +75,11 @@ // Allows waiting until the list of policy-pushed web-trusted certificates // changes. class WebTrustedCertsChangedObserver - : public UserNetworkConfigurationUpdater::PolicyProvidedCertsObserver { + : public PolicyCertificateProvider::Observer { public: WebTrustedCertsChangedObserver() {} - // UserNetworkConfigurationUpdater:PolicyProvidedCertsObserver + // PolicyCertificateProvider::Observer void OnPolicyProvidedCertsChanged( const net::CertificateList& all_server_and_authority_certs, const net::CertificateList& trust_anchors) override { @@ -255,7 +256,7 @@ // |profile|'s UserNetworkConfigurationUpdater. void SetRootCertONCPolicy(Profile* profile) { UserNetworkConfigurationUpdater* user_network_configuration_updater = - UserNetworkConfigurationUpdaterFactory::GetForProfile(profile); + UserNetworkConfigurationUpdaterFactory::GetForBrowserContext(profile); WebTrustedCertsChangedObserver trust_roots_changed_observer; user_network_configuration_updater->AddPolicyProvidedCertsObserver( &trust_roots_changed_observer);
diff --git a/chrome/browser/chromeos/printing/synced_printers_manager.cc b/chrome/browser/chromeos/printing/synced_printers_manager.cc index 73fcfd17..860f0f26 100644 --- a/chrome/browser/chromeos/printing/synced_printers_manager.cc +++ b/chrome/browser/chromeos/printing/synced_printers_manager.cc
@@ -354,8 +354,6 @@ // static void SyncedPrintersManager::RegisterProfilePrefs( user_prefs::PrefRegistrySyncable* registry) { - registry->RegisterListPref(prefs::kPrintingDevices, - user_prefs::PrefRegistrySyncable::SYNCABLE_PREF); registry->RegisterListPref(prefs::kRecommendedNativePrinters); ExternalPrintersPrefBridge::RegisterProfilePrefs(registry, UserPolicyNames());
diff --git a/chrome/browser/chromeos/settings/device_settings_provider.cc b/chrome/browser/chromeos/settings/device_settings_provider.cc index 4904303..cc9a253 100644 --- a/chrome/browser/chromeos/settings/device_settings_provider.cc +++ b/chrome/browser/chromeos/settings/device_settings_provider.cc
@@ -22,6 +22,7 @@ #include "chrome/browser/browser_process.h" #include "chrome/browser/chromeos/ownership/owner_settings_service_chromeos.h" #include "chrome/browser/chromeos/policy/device_local_account.h" +#include "chrome/browser/chromeos/policy/device_policy_decoder_chromeos.h" #include "chrome/browser/chromeos/policy/off_hours/off_hours_proto_parser.h" #include "chrome/browser/chromeos/settings/cros_settings.h" #include "chrome/browser/chromeos/settings/device_settings_cache.h" @@ -35,6 +36,7 @@ #include "components/policy/core/common/chrome_schema.h" #include "components/policy/core/common/cloud/cloud_policy_constants.h" #include "components/policy/core/common/schema.h" +#include "components/policy/policy_constants.h" #include "components/policy/proto/device_management_backend.pb.h" #include "components/prefs/pref_service.h" @@ -121,49 +123,23 @@ kDeviceAutoUpdateTimeRestrictions, }; -// Decodes a JSON string to a base::Value, and drops unknown properties -// according to a policy schema. |policy_name| is the name of a policy schema -// defined in policy_templates.json. Returns null in case the input is not a -// valid JSON string. -std::unique_ptr<base::Value> DecodeJsonStringAndDropUnknownBySchema( - const std::string& json_string, - const std::string& policy_name) { +// Re-use the DecodeJsonStringAndNormalize from device_policy_decoder_chromeos.h +// here to decode the json string and validate it against |policy_name|'s +// schema. If the json string is valid, the decoded base::Value will be stored +// as |setting_name| in |pref_value_map|. The error can be ignored here since it +// is already reported during decoding in device_policy_decoder_chromeos.cc. +void SetJsonDeviceSetting(const std::string& setting_name, + const std::string& policy_name, + const std::string& json_string, + PrefValueMap* pref_value_map) { std::string error; - std::unique_ptr<base::Value> root = base::JSONReader::ReadAndReturnError( - json_string, base::JSON_ALLOW_TRAILING_COMMAS, nullptr, &error); - - if (!root) { - LOG(WARNING) << "Invalid JSON string: " << error << ", ignoring."; - return nullptr; - } - - const policy::Schema& schema = - policy::GetChromeSchema().GetKnownProperty(policy_name); - - if (!schema.valid()) { - LOG(WARNING) << "Unknown or invalid policy schema for " << policy_name - << "."; - return nullptr; - } - - std::string error_path; - bool changed = false; - if (!schema.Normalize(root.get(), policy::SCHEMA_ALLOW_UNKNOWN, &error_path, - &error, &changed)) { - LOG(WARNING) << "Invalid policy value for " << policy_name << ": " << error - << " at " << error_path << "."; - return nullptr; - } - if (changed) { - LOG(WARNING) << "Some properties in " << policy_name - << " were dropped: " << error << " at " << error_path << "."; - } - - return root; + std::unique_ptr<base::Value> decoded_json = + policy::DecodeJsonStringAndNormalize(json_string, policy_name, &error); + if (decoded_json) + pref_value_map->SetValue(setting_name, std::move(decoded_json)); } void DecodeLoginPolicies(const em::ChromeDeviceSettingsProto& policy, - bool is_enterprise_managed, PrefValueMap* new_values_cache) { // For all our boolean settings the following is applicable: // true is default permissive value and false is safe prohibitive value. @@ -202,7 +178,7 @@ policy.guest_mode_enabled().guest_mode_enabled()); bool supervised_users_enabled = false; - if (is_enterprise_managed) { + if (InstallAttributes::Get()->IsEnterpriseManaged()) { supervised_users_enabled = policy.has_supervised_users_settings() && policy.supervised_users_settings().has_supervised_users_enabled() && @@ -444,14 +420,10 @@ } if (au_settings_proto.has_disallowed_time_intervals()) { - std::unique_ptr<base::Value> decoded_intervals = - DecodeJsonStringAndDropUnknownBySchema( - au_settings_proto.disallowed_time_intervals(), - "DeviceAutoUpdateTimeRestrictions"); - if (decoded_intervals) { - new_values_cache->SetValue(kDeviceAutoUpdateTimeRestrictions, - std::move(decoded_intervals)); - } + SetJsonDeviceSetting(kDeviceAutoUpdateTimeRestrictions, + policy::key::kDeviceAutoUpdateTimeRestrictions, + au_settings_proto.disallowed_time_intervals(), + new_values_cache); } } } @@ -534,7 +506,6 @@ } void DecodeGenericPolicies(const em::ChromeDeviceSettingsProto& policy, - bool is_enterprise_managed, PrefValueMap* new_values_cache) { if (policy.has_metrics_enabled() && policy.metrics_enabled().has_metrics_enabled()) { @@ -543,7 +514,8 @@ } else { // If the policy is missing, default to reporting enabled on enterprise- // enrolled devices, c.f. crbug/456186. - new_values_cache->SetBoolean(kStatsReportingPref, is_enterprise_managed); + new_values_cache->SetBoolean( + kStatsReportingPref, InstallAttributes::Get()->IsEnterpriseManaged()); } if (!policy.has_release_channel() || @@ -637,16 +609,10 @@ if (policy.has_device_wallpaper_image() && policy.device_wallpaper_image().has_device_wallpaper_image()) { - const std::string& wallpaper_policy( - policy.device_wallpaper_image().device_wallpaper_image()); - std::unique_ptr<base::DictionaryValue> dict_val = - base::DictionaryValue::From(base::JSONReader::Read(wallpaper_policy)); - if (dict_val) { - new_values_cache->SetValue(kDeviceWallpaperImage, std::move(dict_val)); - } else { - SYSLOG(ERROR) << "Value of wallpaper policy has invalid format: " - << wallpaper_policy; - } + SetJsonDeviceSetting( + kDeviceWallpaperImage, policy::key::kDeviceWallpaperImage, + policy.device_wallpaper_image().device_wallpaper_image(), + new_values_cache); } if (policy.has_device_off_hours()) { @@ -704,7 +670,7 @@ } else { // If the policy is missing, default to false on enterprise-enrolled // devices. - if (is_enterprise_managed) { + if (InstallAttributes::Get()->IsEnterpriseManaged()) { new_values_cache->SetBoolean(kVirtualMachinesAllowed, false); } } @@ -772,14 +738,12 @@ void DeviceSettingsProvider::DecodePolicies( const em::ChromeDeviceSettingsProto& policy, PrefValueMap* new_values_cache) { - bool is_enterprise_managed = InstallAttributes::Get()->IsEnterpriseManaged(); - - DecodeLoginPolicies(policy, is_enterprise_managed, new_values_cache); + DecodeLoginPolicies(policy, new_values_cache); DecodeNetworkPolicies(policy, new_values_cache); DecodeAutoUpdatePolicies(policy, new_values_cache); DecodeReportingPolicies(policy, new_values_cache); DecodeHeartbeatPolicies(policy, new_values_cache); - DecodeGenericPolicies(policy, is_enterprise_managed, new_values_cache); + DecodeGenericPolicies(policy, new_values_cache); DecodeLogUploadPolicies(policy, new_values_cache); }
diff --git a/chrome/browser/chromeos/settings/device_settings_provider_unittest.cc b/chrome/browser/chromeos/settings/device_settings_provider_unittest.cc index 535ecd3..098f9f1 100644 --- a/chrome/browser/chromeos/settings/device_settings_provider_unittest.cc +++ b/chrome/browser/chromeos/settings/device_settings_provider_unittest.cc
@@ -604,7 +604,7 @@ EXPECT_EQ(nullptr, provider_->Get(kDeviceWallpaperImage)); // Set with valid json format. - const std::string valid_format("{\"type\":\"object\"}"); + const std::string valid_format(R"({"url":"foo", "hash": "bar"})"); SetWallpaperSettings(valid_format); std::unique_ptr<base::DictionaryValue> expected_value = base::DictionaryValue::From(base::JSONReader::Read(valid_format));
diff --git a/chrome/browser/chromeos/smb_client/smb_service.cc b/chrome/browser/chromeos/smb_client/smb_service.cc index d5f209b..0ab7555 100644 --- a/chrome/browser/chromeos/smb_client/smb_service.cc +++ b/chrome/browser/chromeos/smb_client/smb_service.cc
@@ -320,7 +320,11 @@ void SmbService::RegisterHostLocators() { SetUpMdnsHostLocator(); - SetUpNetBiosHostLocator(); + if (IsNetBiosDiscoveryEnabled()) { + SetUpNetBiosHostLocator(); + } else { + LOG(WARNING) << "SmbService: NetBios discovery disabled."; + } } void SmbService::SetUpMdnsHostLocator() { @@ -342,6 +346,10 @@ return profile_->GetPrefs()->GetBoolean(prefs::kNetworkFileSharesAllowed); } +bool SmbService::IsNetBiosDiscoveryEnabled() const { + return profile_->GetPrefs()->GetBoolean(prefs::kNetBiosShareDiscoveryEnabled); +} + void SmbService::RecordMountCount() const { const std::vector<ProvidedFileSystemInfo> file_systems = GetProviderService()->GetProvidedFileSystemInfoList(provider_id_);
diff --git a/chrome/browser/chromeos/smb_client/smb_service.h b/chrome/browser/chromeos/smb_client/smb_service.h index 0691864..b671801 100644 --- a/chrome/browser/chromeos/smb_client/smb_service.h +++ b/chrome/browser/chromeos/smb_client/smb_service.h
@@ -138,6 +138,9 @@ // Whether Network File Shares are allowed to be used. Controlled via policy. bool IsAllowedByPolicy() const; + // Whether NetBios discovery should be used. Controlled via policy. + bool IsNetBiosDiscoveryEnabled() const; + // Records metrics on the number of SMB mounts a user has. void RecordMountCount() const;
diff --git a/chrome/browser/data_use_measurement/chrome_data_use_ascriber.cc b/chrome/browser/data_use_measurement/chrome_data_use_ascriber.cc index e204cf6d..c145260 100644 --- a/chrome/browser/data_use_measurement/chrome_data_use_ascriber.cc +++ b/chrome/browser/data_use_measurement/chrome_data_use_ascriber.cc
@@ -152,7 +152,7 @@ // render frames don't have a record. However, this can also be caused by // URLRequests racing the frame create events. // TODO(kundaji): Add UMA. - RenderFrameHostID frame_key(render_process_id, render_frame_id); + content::GlobalFrameRoutingId frame_key(render_process_id, render_frame_id); const auto main_frame_key_iter = subframe_to_mainframe_map_.find(frame_key); if (main_frame_key_iter == subframe_to_mainframe_map_.end()) { return data_use_recorders_.end(); @@ -307,14 +307,14 @@ return; const auto render_frame = - RenderFrameHostID(render_process_id, render_frame_id); + content::GlobalFrameRoutingId(render_process_id, render_frame_id); if (main_render_process_id != -1 && main_render_frame_id != -1) { // Create an entry in |subframe_to_mainframe_map_| for this frame mapped to // it's parent frame. subframe_to_mainframe_map_.insert(std::make_pair( - render_frame, - RenderFrameHostID(main_render_process_id, main_render_frame_id))); + render_frame, content::GlobalFrameRoutingId(main_render_process_id, + main_render_frame_id))); } else { subframe_to_mainframe_map_.insert( std::make_pair(render_frame, render_frame)); @@ -338,7 +338,7 @@ if (IsDisabled()) return; - RenderFrameHostID key(render_process_id, render_frame_id); + content::GlobalFrameRoutingId key(render_process_id, render_frame_id); if (main_render_process_id == -1 && main_render_frame_id == -1) { auto main_frame_it = main_render_frame_entry_map_.find(key); @@ -396,7 +396,7 @@ return; main_render_frame_entry_map_ - .find(RenderFrameHostID(render_process_id, render_frame_id)) + .find(content::GlobalFrameRoutingId(render_process_id, render_frame_id)) ->second.pending_navigation_global_request_id = global_request_id; } @@ -411,7 +411,7 @@ if (IsDisabled()) return; - RenderFrameHostID main_frame(render_process_id, render_frame_id); + content::GlobalFrameRoutingId main_frame(render_process_id, render_frame_id); auto main_frame_it = main_render_frame_entry_map_.find(main_frame); if (main_frame_it == main_render_frame_entry_map_.end()) @@ -547,7 +547,7 @@ if (!validated_url.SchemeIsHTTPOrHTTPS()) return; - RenderFrameHostID main_frame(render_process_id, render_frame_id); + content::GlobalFrameRoutingId main_frame(render_process_id, render_frame_id); auto main_frame_it = main_render_frame_entry_map_.find(main_frame); if (main_frame_it == main_render_frame_entry_map_.end()) @@ -609,8 +609,9 @@ if (IsDisabled()) return; - auto main_frame_it = main_render_frame_entry_map_.find( - RenderFrameHostID(main_render_process_id, main_render_frame_id)); + auto main_frame_it = + main_render_frame_entry_map_.find(content::GlobalFrameRoutingId( + main_render_process_id, main_render_frame_id)); if (main_frame_it != main_render_frame_entry_map_.end()) { main_frame_it->second.is_visible = visible; if (main_frame_it->second.data_use_recorder != data_use_recorders_.end()) @@ -626,8 +627,9 @@ if (IsDisabled()) return; - auto old_frame_iter = main_render_frame_entry_map_.find( - RenderFrameHostID(old_render_process_id, old_render_frame_id)); + auto old_frame_iter = + main_render_frame_entry_map_.find(content::GlobalFrameRoutingId( + old_render_process_id, old_render_frame_id)); if (old_frame_iter != main_render_frame_entry_map_.end()) { WasShownOrHidden(new_render_process_id, new_render_frame_id, true); @@ -636,7 +638,8 @@ // Transfer the pending navigation global request ID from old to new main // frame. main_render_frame_entry_map_ - .find(RenderFrameHostID(new_render_process_id, new_render_frame_id)) + .find(content::GlobalFrameRoutingId(new_render_process_id, + new_render_frame_id)) ->second.pending_navigation_global_request_id = old_frame_iter->second.pending_navigation_global_request_id; old_frame_iter->second.pending_navigation_global_request_id =
diff --git a/chrome/browser/data_use_measurement/chrome_data_use_ascriber.h b/chrome/browser/data_use_measurement/chrome_data_use_ascriber.h index f9ef712..23db643 100644 --- a/chrome/browser/data_use_measurement/chrome_data_use_ascriber.h +++ b/chrome/browser/data_use_measurement/chrome_data_use_ascriber.h
@@ -21,6 +21,7 @@ #include "chrome/browser/data_use_measurement/chrome_data_use_recorder.h" #include "components/data_use_measurement/core/data_use_ascriber.h" #include "content/public/browser/global_request_id.h" +#include "content/public/browser/global_routing_id.h" #include "url/gurl.h" namespace content { @@ -205,13 +206,14 @@ // Map from RenderFrameHost to the MainRenderFrameEntry which contains all // details of the main frame. New entry is added on main render frame creation // and removed on its deletion. - std::map<RenderFrameHostID, MainRenderFrameEntry> + std::map<content::GlobalFrameRoutingId, MainRenderFrameEntry> main_render_frame_entry_map_; // Maps subframe IDs to the mainframe ID, so the mainframe lifetime can have // ownership over the lifetime of entries in |data_use_recorders_|. Mainframes // are mapped to themselves. - std::map<RenderFrameHostID, RenderFrameHostID> subframe_to_mainframe_map_; + std::map<content::GlobalFrameRoutingId, content::GlobalFrameRoutingId> + subframe_to_mainframe_map_; // Map from pending navigations to the DataUseRecorderEntry in // |data_use_recorders_| that the navigation ascribes data use to.
diff --git a/chrome/browser/data_use_measurement/chrome_data_use_ascriber_unittest.cc b/chrome/browser/data_use_measurement/chrome_data_use_ascriber_unittest.cc index cb793cb..fa2b530 100644 --- a/chrome/browser/data_use_measurement/chrome_data_use_ascriber_unittest.cc +++ b/chrome/browser/data_use_measurement/chrome_data_use_ascriber_unittest.cc
@@ -243,7 +243,7 @@ // Navigation commit should merge the two data use recorder entries. EXPECT_EQ(1u, recorders().size()); auto& recorder_entry = recorders().front(); - EXPECT_EQ(RenderFrameHostID(kRenderProcessId, kRenderFrameId), + EXPECT_EQ(content::GlobalFrameRoutingId(kRenderProcessId, kRenderFrameId), recorder_entry.main_frame_id()); EXPECT_EQ(content::GlobalRequestID(kRenderProcessId, 0), recorder_entry.main_frame_request_id()); @@ -305,7 +305,7 @@ EXPECT_EQ(1u, recorders().size()); auto& recorder_entry = recorders().front(); - EXPECT_EQ(RenderFrameHostID(kRenderProcessId, kRenderFrameId), + EXPECT_EQ(content::GlobalFrameRoutingId(kRenderProcessId, kRenderFrameId), recorder_entry.main_frame_id()); EXPECT_EQ(content::GlobalRequestID(kRenderProcessId, 0), recorder_entry.main_frame_request_id()); @@ -351,7 +351,7 @@ EXPECT_EQ(1u, recorders().size()); auto& page_load_a_recorder = recorders().front(); - EXPECT_EQ(RenderFrameHostID(kRenderProcessId, kRenderFrameId), + EXPECT_EQ(content::GlobalFrameRoutingId(kRenderProcessId, kRenderFrameId), page_load_a_recorder.main_frame_id()); EXPECT_EQ(content::GlobalRequestID(kRenderProcessId, 0), page_load_a_recorder.main_frame_request_id()); @@ -384,7 +384,7 @@ // Previous page recorder is gone. EXPECT_EQ(1u, recorders().size()); auto& page_load_b_recorder = recorders().back(); - EXPECT_EQ(RenderFrameHostID(kRenderProcessId, kRenderFrameId), + EXPECT_EQ(content::GlobalFrameRoutingId(kRenderProcessId, kRenderFrameId), page_load_b_recorder.main_frame_id()); EXPECT_EQ(content::GlobalRequestID(kRenderProcessId, 0), page_load_b_recorder.main_frame_request_id()); @@ -491,7 +491,7 @@ EXPECT_EQ(1u, recorders().size()); auto& recorder_entry = recorders().front(); - EXPECT_EQ(RenderFrameHostID(kRenderProcessId, kRenderFrameId), + EXPECT_EQ(content::GlobalFrameRoutingId(kRenderProcessId, kRenderFrameId), recorder_entry.main_frame_id()); EXPECT_EQ(content::GlobalRequestID(kRenderProcessId, 0), recorder_entry.main_frame_request_id()); @@ -548,7 +548,7 @@ EXPECT_EQ(1u, recorders().size()); auto& recorder_entry = recorders().front(); - EXPECT_EQ(RenderFrameHostID(kRenderProcessId, kRenderFrameId), + EXPECT_EQ(content::GlobalFrameRoutingId(kRenderProcessId, kRenderFrameId), recorder_entry.main_frame_id()); EXPECT_EQ(content::GlobalRequestID(kRenderProcessId, 0), recorder_entry.main_frame_request_id());
diff --git a/chrome/browser/data_use_measurement/chrome_data_use_recorder.h b/chrome/browser/data_use_measurement/chrome_data_use_recorder.h index 9ca8b49..88bce23 100644 --- a/chrome/browser/data_use_measurement/chrome_data_use_recorder.h +++ b/chrome/browser/data_use_measurement/chrome_data_use_recorder.h
@@ -10,19 +10,18 @@ #include "base/macros.h" #include "components/data_use_measurement/core/data_use_recorder.h" #include "content/public/browser/global_request_id.h" +#include "content/public/browser/global_routing_id.h" namespace data_use_measurement { -typedef std::pair<int, int> RenderFrameHostID; - class ChromeDataUseRecorder : public DataUseRecorder { public: explicit ChromeDataUseRecorder(DataUse::TrafficType traffic_type); ~ChromeDataUseRecorder() override; - RenderFrameHostID main_frame_id() const { return main_frame_id_; } + content::GlobalFrameRoutingId main_frame_id() const { return main_frame_id_; } - void set_main_frame_id(RenderFrameHostID frame_id) { + void set_main_frame_id(content::GlobalFrameRoutingId frame_id) { main_frame_id_ = frame_id; } @@ -37,7 +36,7 @@ private: // Identifier for the main frame for the page load this recorder is tracking. // Only valid if the data use is associated with a page load. - RenderFrameHostID main_frame_id_; + content::GlobalFrameRoutingId main_frame_id_; // Identifier for the MAIN_FRAME request for this page load. Only valid if // the data use is associated with a page load.
diff --git a/chrome/browser/download/download_request_limiter.h b/chrome/browser/download/download_request_limiter.h index 1ac98258..577b77ee 100644 --- a/chrome/browser/download/download_request_limiter.h +++ b/chrome/browser/download/download_request_limiter.h
@@ -239,6 +239,7 @@ FRIEND_TEST_ALL_PREFIXES(ContentSettingImageModelBrowserTest, CreateBubbleModel); friend class base::RefCountedThreadSafe<DownloadRequestLimiter>; + friend class BackgroundFetchBrowserTest; friend class ContentSettingBubbleDialogTest; friend class DownloadRequestLimiterTest; friend class TabDownloadState;
diff --git a/chrome/browser/download/download_target_determiner_unittest.cc b/chrome/browser/download/download_target_determiner_unittest.cc index 4ca3d5e9..e169701 100644 --- a/chrome/browser/download/download_target_determiner_unittest.cc +++ b/chrome/browser/download/download_target_determiner_unittest.cc
@@ -592,7 +592,14 @@ callback.Run(new_path, DownloadPathReservationTracker::UNIQUIFY); } -TEST_F(DownloadTargetDeterminerTest, Basic) { +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_Basic DISABLED_Basic +#else +#define MAYBE_Basic Basic +#endif + +TEST_F(DownloadTargetDeterminerTest, MAYBE_Basic) { const DownloadTestCase kBasicTestCases[] = { {// Automatic Safe AUTOMATIC, download::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS, @@ -728,9 +735,16 @@ arraysize(kSafeBrowsingTestCases)); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_MaybeDangerousContent DISABLED_MaybeDangerousContent +#else +#define MAYBE_MaybeDangerousContent MaybeDangerousContent +#endif + // The SafeBrowsing check is performed early. Make sure that a download item // that has been marked as MAYBE_DANGEROUS_CONTENT behaves correctly. -TEST_F(DownloadTargetDeterminerTest, MaybeDangerousContent) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_MaybeDangerousContent) { const DownloadTestCase kSafeBrowsingTestCases[] = { {// 0: Automatic Maybe dangerous content AUTOMATIC, download::DOWNLOAD_DANGER_TYPE_MAYBE_DANGEROUS_CONTENT, @@ -784,8 +798,15 @@ arraysize(kSafeBrowsingTestCases)); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_LastSavePath DISABLED_LastSavePath +#else +#define MAYBE_LastSavePath LastSavePath +#endif + // Test whether the last saved directory is used for 'Save As' downloads. -TEST_F(DownloadTargetDeterminerTest, LastSavePath) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_LastSavePath) { const DownloadTestCase kLastSavePathTestCasesPre[] = { {// 0: If the last save path is empty, then the default download directory // should be used. @@ -972,6 +993,13 @@ } } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_InactiveDownload DISABLED_InactiveDownload +#else +#define MAYBE_InactiveDownload InactiveDownload +#endif + // Test that an inactive download will still get a virtual or local download // path. TEST_F(DownloadTargetDeterminerTest, InactiveDownload) { @@ -1092,10 +1120,17 @@ arraysize(kLocalPathFailedCases)); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_VisitedReferrer DISABLED_VisitedReferrer +#else +#define MAYBE_VisitedReferrer VisitedReferrer +#endif + // Downloads that have a danger level of ALLOW_ON_USER_GESTURE should be marked // as safe depending on whether there was a user gesture associated with the // download and whether the referrer was visited prior to today. -TEST_F(DownloadTargetDeterminerTest, VisitedReferrer) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_VisitedReferrer) { const DownloadTestCase kVisitedReferrerCases[] = { // http://visited.example.com/ is added to the history as a visit that // happened prior to today. @@ -1287,9 +1322,16 @@ } } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_PromptAlways_SafeAutomatic DISABLED_PromptAlways_SafeAutomatic +#else +#define MAYBE_PromptAlways_SafeAutomatic PromptAlways_SafeAutomatic +#endif + // These test cases are run with "Prompt for download" user preference set to // true. -TEST_F(DownloadTargetDeterminerTest, PromptAlways_SafeAutomatic) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_PromptAlways_SafeAutomatic) { const DownloadTestCase kSafeAutomatic = { // 0: Safe Automatic - Should prompt because of "Prompt for download" // preference setting. @@ -1313,7 +1355,14 @@ RunTestCasesWithActiveItem(&kSafeAutomatic, 1); } -TEST_F(DownloadTargetDeterminerTest, PromptAlways_SafeSaveAs) { +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_PromptAlways_SafeSaveAs DISABLED_PromptAlways_SafeSaveAs +#else +#define MAYBE_PromptAlways_SafeSaveAs PromptAlways_SafeSaveAs +#endif + +TEST_F(DownloadTargetDeterminerTest, MAYBE_PromptAlways_SafeSaveAs) { const DownloadTestCase kSafeSaveAs = { // 1: Safe Save As - Should prompt because of "Save as" invocation. SAVE_AS, @@ -1355,7 +1404,14 @@ RunTestCasesWithActiveItem(&kSafeForced, 1); } -TEST_F(DownloadTargetDeterminerTest, PromptAlways_AutoOpen) { +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_PromptAlways_AutoOpen DISABLED_PromptAlways_AutoOpen +#else +#define MAYBE_PromptAlways_AutoOpen PromptAlways_AutoOpen +#endif + +TEST_F(DownloadTargetDeterminerTest, MAYBE_PromptAlways_AutoOpen) { const DownloadTestCase kAutoOpen = { // 3: Automatic - The filename extension is marked as one that we will // open automatically. Shouldn't prompt. @@ -1376,9 +1432,18 @@ RunTestCasesWithActiveItem(&kAutoOpen, 1); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_ContinueWithoutConfirmation_SaveAs \ + DISABLED_ContinueWithoutConfirmation_SaveAs +#else +#define MAYBE_ContinueWithoutConfirmation_SaveAs \ + ContinueWithoutConfirmation_SaveAs +#endif + // If an embedder responds to a RequestConfirmation with a new path and a // CONTINUE_WITHOUT_CONFIRMATION, then we shouldn't consider the file as safe. -TEST_F(DownloadTargetDeterminerTest, ContinueWithoutConfirmation_SaveAs) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_ContinueWithoutConfirmation_SaveAs) { const DownloadTestCase kTestCase = { SAVE_AS, download::DOWNLOAD_DANGER_TYPE_DANGEROUS_FILE, @@ -1497,9 +1562,16 @@ arraysize(kManagedPathTestCases)); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_NotifyExtensionsSafe DISABLED_NotifyExtensionsSafe +#else +#define MAYBE_NotifyExtensionsSafe NotifyExtensionsSafe +#endif + // Test basic functionality supporting extensions that want to override download // filenames. -TEST_F(DownloadTargetDeterminerTest, NotifyExtensionsSafe) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_NotifyExtensionsSafe) { const DownloadTestCase kNotifyExtensionsTestCases[] = { {// 0: Automatic Safe AUTOMATIC, download::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS, @@ -1587,9 +1659,16 @@ RunTestCasesWithActiveItem(&kHandledBySafeBrowsing, 1); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_NotifyExtensionsConflict DISABLED_NotifyExtensionsConflict +#else +#define MAYBE_NotifyExtensionsConflict NotifyExtensionsConflict +#endif + // Test that conflict actions set by extensions are passed correctly into // ReserveVirtualPath. -TEST_F(DownloadTargetDeterminerTest, NotifyExtensionsConflict) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_NotifyExtensionsConflict) { const DownloadTestCase kNotifyExtensionsTestCase = { AUTOMATIC, download::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS, @@ -1636,9 +1715,16 @@ RunTestCase(test_case, base::FilePath(), item.get()); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_NotifyExtensionsDefaultPath DISABLED_NotifyExtensionsDefaultPath +#else +#define MAYBE_NotifyExtensionsDefaultPath NotifyExtensionsDefaultPath +#endif + // Test that relative paths returned by extensions are always relative to the // default downloads path. -TEST_F(DownloadTargetDeterminerTest, NotifyExtensionsDefaultPath) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_NotifyExtensionsDefaultPath) { const DownloadTestCase kNotifyExtensionsTestCase = { AUTOMATIC, download::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS, @@ -1700,12 +1786,19 @@ RunTestCase(test_case, GetPathInDownloadDir(kInitialPath), item.get()); } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_ResumedNoPrompt DISABLED_ResumedNoPrompt +#else +#define MAYBE_ResumedNoPrompt ResumedNoPrompt +#endif + // Prompting behavior for resumed downloads is based on the last interrupt // reason. If the reason indicates that the target path may not be suitable for // the download (ACCESS_DENIED, NO_SPACE, etc..), then the user should be // prompted, and not otherwise. These test cases shouldn't result in prompting // since the error is set to NETWORK_FAILED. -TEST_F(DownloadTargetDeterminerTest, ResumedNoPrompt) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_ResumedNoPrompt) { // All test cases run with GetPathInDownloadDir(kInitialPath) as the inital // path. const base::FilePath::CharType* kInitialPath = @@ -1891,8 +1984,15 @@ } } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_IntermediateNameForResumed DISABLED_IntermediateNameForResumed +#else +#define MAYBE_IntermediateNameForResumed IntermediateNameForResumed +#endif + // Test intermediate filename generation for resumed downloads. -TEST_F(DownloadTargetDeterminerTest, IntermediateNameForResumed) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_IntermediateNameForResumed) { // All test cases run with GetPathInDownloadDir(kInitialPath) as the inital // path. const base::FilePath::CharType kInitialPath[] = @@ -2006,8 +2106,15 @@ } } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_MIMETypeDetermination DISABLED_MIMETypeDetermination +#else +#define MAYBE_MIMETypeDetermination MIMETypeDetermination +#endif + // Test MIME type determination based on the target filename. -TEST_F(DownloadTargetDeterminerTest, MIMETypeDetermination) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_MIMETypeDetermination) { // All test cases run with GetPathInDownloadDir(kInitialPath) as the inital // path. const base::FilePath::CharType kInitialPath[] = @@ -2099,8 +2206,16 @@ } } +// Flaky on Nexus 5x. http://crbug.com/877026 +#if defined(OS_ANDROID) +#define MAYBE_ResumedWithUserValidatedDownload \ + DISABLED_ResumedWithUserValidatedDownload +#else +#define MAYBE_ResumedWithUserValidatedDownload ResumedWithUserValidatedDownload +#endif + // Test that a user validated download won't be treated as dangerous. -TEST_F(DownloadTargetDeterminerTest, ResumedWithUserValidatedDownload) { +TEST_F(DownloadTargetDeterminerTest, MAYBE_ResumedWithUserValidatedDownload) { const base::FilePath::CharType kInitialPath[] = FILE_PATH_LITERAL("some_path/bar.txt"); const base::FilePath::CharType* kIntermediatePath =
diff --git a/chrome/browser/extensions/api/declarative_net_request/declarative_net_request_browsertest.cc b/chrome/browser/extensions/api/declarative_net_request/declarative_net_request_browsertest.cc index a56f2d27..090b3a16 100644 --- a/chrome/browser/extensions/api/declarative_net_request/declarative_net_request_browsertest.cc +++ b/chrome/browser/extensions/api/declarative_net_request/declarative_net_request_browsertest.cc
@@ -52,6 +52,7 @@ #include "extensions/browser/api/declarative_net_request/ruleset_manager.h" #include "extensions/browser/api/declarative_net_request/ruleset_matcher.h" #include "extensions/browser/api/declarative_net_request/test_utils.h" +#include "extensions/browser/api/declarative_net_request/utils.h" #include "extensions/browser/api/web_request/web_request_info.h" #include "extensions/browser/extension_prefs.h" #include "extensions/browser/extension_registry.h" @@ -1808,10 +1809,11 @@ verify_page_load(false); } - // Overwrite the indexed ruleset file with arbitrary data to mimic corruption. + // Overwrite the indexed ruleset file with arbitrary data to mimic corruption, + // while maintaining the correct version header. { base::ScopedAllowBlockingForTesting scoped_allow_blocking; - std::string corrupted_data = "data"; + std::string corrupted_data = GetVersionHeaderForTesting() + "data"; ASSERT_EQ(static_cast<int>(corrupted_data.size()), base::WriteFile(file_util::GetIndexedRulesetPath(extension_path), corrupted_data.c_str(), corrupted_data.size())); @@ -1869,7 +1871,7 @@ // Mimic extension prefs corruption by overwriting the indexed ruleset // checksum. const int kInvalidRulesetChecksum = -1; - ExtensionPrefs::Get(profile())->SetDNRRulesetChecksumForTesting( + ExtensionPrefs::Get(profile())->SetDNRRulesetChecksum( extension_id, kInvalidRulesetChecksum); TestExtensionRegistryObserver registry_observer( @@ -1904,6 +1906,60 @@ false /*sample*/, 1 /*count*/); } +// Tests that we reindex the extension ruleset in case its ruleset format +// version is not the same as one used by Chrome. +IN_PROC_BROWSER_TEST_P(DeclarativeNetRequestBrowserTest_Packed, + ReindexOnRulesetVersionMismatch) { + // Set up an observer for RulesetMatcher to monitor the number of extension + // rulesets. + RulesetCountWaiter ruleset_count_waiter; + ScopedRulesetManagerTestObserver scoped_observer( + &ruleset_count_waiter, + base::WrapRefCounted(ExtensionSystem::Get(profile())->info_map())); + + TestRule rule = CreateGenericRule(); + rule.condition->url_filter = std::string("*"); + ASSERT_NO_FATAL_FAILURE(LoadExtensionWithRules({rule})); + ruleset_count_waiter.WaitForRulesetCount(1); + + const ExtensionId extension_id = last_loaded_extension_id(); + const auto* rules_monitor_service = BrowserContextKeyedAPIFactory< + declarative_net_request::RulesMonitorService>::Get(profile()); + EXPECT_TRUE(rules_monitor_service->HasRegisteredRuleset(extension_id)); + + DisableExtension(extension_id); + ruleset_count_waiter.WaitForRulesetCount(0); + EXPECT_FALSE(rules_monitor_service->HasRegisteredRuleset(extension_id)); + + // Now change the current indexed ruleset format version. This should cause a + // version mismatch when the extension is loaded again, but reindexing should + // still succeed. + const int kIndexedRulesetFormatVersion = 100; + std::string old_version_header = GetVersionHeaderForTesting(); + SetIndexedRulesetFormatVersionForTesting(kIndexedRulesetFormatVersion); + ASSERT_NE(old_version_header, GetVersionHeaderForTesting()); + + base::HistogramTester tester; + EnableExtension(extension_id); + ruleset_count_waiter.WaitForRulesetCount(1); + EXPECT_TRUE(rules_monitor_service->HasRegisteredRuleset(extension_id)); + + // Verify that loading the ruleset would have failed initially due to + // version header mismatch and later succeeded. + EXPECT_EQ(1, tester.GetBucketCount( + "Extensions.DeclarativeNetRequest.LoadRulesetResult", + RulesetMatcher::LoadRulesetResult:: + kLoadErrorVersionMismatch /*sample*/)); + EXPECT_EQ(1, tester.GetBucketCount( + "Extensions.DeclarativeNetRequest.LoadRulesetResult", + RulesetMatcher::LoadRulesetResult::kLoadSuccess /*sample*/)); + + // Verify that reindexing succeeded. + tester.ExpectUniqueSample( + "Extensions.DeclarativeNetRequest.RulesetReindexSuccessful", + true /*sample*/, 1 /*count*/); +} + // Test fixture to verify that host permissions for the request url and the // request initiator are properly checked. Loads an example.com url with four // sub-frames named frame_[1..4] from hosts frame_[1..4].com. The initiator for
diff --git a/chrome/browser/extensions/api/declarative_net_request/ruleset_matcher_unittest.cc b/chrome/browser/extensions/api/declarative_net_request/ruleset_matcher_unittest.cc index 9020986..4e6f395 100644 --- a/chrome/browser/extensions/api/declarative_net_request/ruleset_matcher_unittest.cc +++ b/chrome/browser/extensions/api/declarative_net_request/ruleset_matcher_unittest.cc
@@ -14,6 +14,7 @@ #include "chrome/browser/profiles/profile.h" #include "components/url_pattern_index/flat/url_pattern_index_generated.h" #include "extensions/browser/api/declarative_net_request/test_utils.h" +#include "extensions/browser/api/declarative_net_request/utils.h" #include "extensions/browser/extension_prefs.h" #include "extensions/common/api/declarative_net_request/constants.h" #include "extensions/common/api/declarative_net_request/test_utils.h" @@ -123,7 +124,8 @@ base::FilePath indexed_ruleset_path = file_util::GetIndexedRulesetPath(extension()->path()); - // Persist invalid data to the ruleset file. + // Persist invalid data to the ruleset file and ensure that a version mismatch + // occurs. std::string data = "invalid data"; ASSERT_EQ(static_cast<int>(data.size()), base::WriteFile(indexed_ruleset_path, data.c_str(), data.size())); @@ -134,6 +136,16 @@ ->GetDNRRulesetChecksum(extension()->id(), &expected_checksum)); std::unique_ptr<RulesetMatcher> matcher; + EXPECT_EQ(RulesetMatcher::kLoadErrorVersionMismatch, + RulesetMatcher::CreateVerifiedMatcher(indexed_ruleset_path, + expected_checksum, &matcher)); + + // Now, persist invalid data to the ruleset file, while maintaining the + // correct version header. Ensure that it fails verification due to checksum + // mismatch. + data = GetVersionHeaderForTesting() + "invalid data"; + ASSERT_EQ(static_cast<int>(data.size()), + base::WriteFile(indexed_ruleset_path, data.c_str(), data.size())); EXPECT_EQ(RulesetMatcher::kLoadErrorRulesetVerification, RulesetMatcher::CreateVerifiedMatcher(indexed_ruleset_path, expected_checksum, &matcher));
diff --git a/chrome/browser/media/router/BUILD.gn b/chrome/browser/media/router/BUILD.gn index 62caf98..4774e72 100644 --- a/chrome/browser/media/router/BUILD.gn +++ b/chrome/browser/media/router/BUILD.gn
@@ -55,7 +55,6 @@ "presentation/presentation_service_delegate_observers.h", "presentation/receiver_presentation_service_delegate_impl.cc", "presentation/receiver_presentation_service_delegate_impl.h", - "presentation/render_frame_host_id.h", "route_message_observer.cc", "route_message_observer.h", "route_message_util.cc",
diff --git a/chrome/browser/media/router/presentation/local_presentation_manager.cc b/chrome/browser/media/router/presentation/local_presentation_manager.cc index 21a75f3..a578750 100644 --- a/chrome/browser/media/router/presentation/local_presentation_manager.cc +++ b/chrome/browser/media/router/presentation/local_presentation_manager.cc
@@ -36,12 +36,13 @@ void LocalPresentationManager::RegisterLocalPresentationController( const PresentationInfo& presentation_info, - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, content::PresentationConnectionPtr controller_connection_ptr, content::PresentationConnectionRequest receiver_connection_request, const MediaRoute& route) { DVLOG(2) << __func__ << " [presentation_id]: " << presentation_info.id - << ", [render_frame_host_id]: " << render_frame_host_id.second; + << ", [render_frame_host_id]: " + << render_frame_host_id.frame_routing_id; DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); auto* presentation = GetOrCreateLocalPresentation(presentation_info); @@ -52,9 +53,10 @@ void LocalPresentationManager::UnregisterLocalPresentationController( const std::string& presentation_id, - const RenderFrameHostId& render_frame_host_id) { + const content::GlobalFrameRoutingId& render_frame_host_id) { DVLOG(2) << __func__ << " [presentation_id]: " << presentation_id - << ", [render_frame_host_id]: " << render_frame_host_id.second; + << ", [render_frame_host_id]: " + << render_frame_host_id.frame_routing_id; DCHECK_CALLED_ON_VALID_THREAD(thread_checker_); auto it = local_presentations_.find(presentation_id); @@ -108,7 +110,7 @@ LocalPresentationManager::LocalPresentation::~LocalPresentation() {} void LocalPresentationManager::LocalPresentation::RegisterController( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, content::PresentationConnectionPtr controller_connection_ptr, content::PresentationConnectionRequest receiver_connection_request, const MediaRoute& route) { @@ -127,7 +129,7 @@ } void LocalPresentationManager::LocalPresentation::UnregisterController( - const RenderFrameHostId& render_frame_host_id) { + const content::GlobalFrameRoutingId& render_frame_host_id) { pending_controllers_.erase(render_frame_host_id); }
diff --git a/chrome/browser/media/router/presentation/local_presentation_manager.h b/chrome/browser/media/router/presentation/local_presentation_manager.h index 820aa7d..bcddd4f 100644 --- a/chrome/browser/media/router/presentation/local_presentation_manager.h +++ b/chrome/browser/media/router/presentation/local_presentation_manager.h
@@ -13,9 +13,9 @@ #include "base/macros.h" #include "base/optional.h" #include "base/threading/thread_checker.h" -#include "chrome/browser/media/router/presentation/render_frame_host_id.h" #include "chrome/common/media_router/media_route.h" #include "components/keyed_service/core/keyed_service.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/presentation_service_delegate.h" #include "third_party/blink/public/mojom/presentation/presentation.mojom.h" @@ -114,7 +114,7 @@ // |receiver_callback| passed below. virtual void RegisterLocalPresentationController( const blink::mojom::PresentationInfo& presentation_info, - const RenderFrameHostId& render_frame_id, + const content::GlobalFrameRoutingId& render_frame_id, content::PresentationConnectionPtr controller_connection_ptr, content::PresentationConnectionRequest receiver_connection_request, const MediaRoute& route); @@ -126,7 +126,7 @@ // and any other pending controller. virtual void UnregisterLocalPresentationController( const std::string& presentation_id, - const RenderFrameHostId& render_frame_id); + const content::GlobalFrameRoutingId& render_frame_id); // Registers |receiver_callback| to presentation with |presentation_info|. virtual void OnLocalPresentationReceiverCreated( @@ -165,14 +165,15 @@ // |receiver_connection_request|, and store it in |pending_controllers_| // map. void RegisterController( - const RenderFrameHostId& render_frame_id, + const content::GlobalFrameRoutingId& render_frame_id, content::PresentationConnectionPtr controller_connection_ptr, content::PresentationConnectionRequest receiver_connection_request, const MediaRoute& route); // Unregister controller with |render_frame_id|. Do nothing if there is no // pending controller with |render_frame_id|. - void UnregisterController(const RenderFrameHostId& render_frame_id); + void UnregisterController( + const content::GlobalFrameRoutingId& render_frame_id); // Register |receiver_callback| to current local_presentation object. // For each controller in |pending_controllers_| map, invoke @@ -213,9 +214,9 @@ // Contains ControllerConnection objects registered via // |RegisterController()| before |receiver_callback_| is set. - std::unordered_map<RenderFrameHostId, + std::unordered_map<content::GlobalFrameRoutingId, std::unique_ptr<ControllerConnection>, - RenderFrameHostIdHasher> + content::GlobalFrameRoutingIdHasher> pending_controllers_; DISALLOW_COPY_AND_ASSIGN(LocalPresentation);
diff --git a/chrome/browser/media/router/presentation/local_presentation_manager_unittest.cc b/chrome/browser/media/router/presentation/local_presentation_manager_unittest.cc index e999f38..bf63bba 100644 --- a/chrome/browser/media/router/presentation/local_presentation_manager_unittest.cc +++ b/chrome/browser/media/router/presentation/local_presentation_manager_unittest.cc
@@ -2,6 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. +#include <utility> #include <vector> #include "base/bind.h" @@ -67,7 +68,7 @@ render_frame_host_id_, std::move(controller)); } - void RegisterController(const RenderFrameHostId& render_frame_id, + void RegisterController(const content::GlobalFrameRoutingId& render_frame_id, content::PresentationConnectionPtr controller) { RegisterController(presentation_info_, render_frame_id, std::move(controller)); @@ -79,7 +80,7 @@ } void RegisterController(const PresentationInfo& presentation_info, - const RenderFrameHostId& render_frame_id, + const content::GlobalFrameRoutingId& render_frame_id, content::PresentationConnectionPtr controller) { content::PresentationConnectionRequest receiver_conn_request; manager()->RegisterLocalPresentationController( @@ -102,7 +103,8 @@ base::Unretained(&receiver_callback))); } - void UnregisterController(const RenderFrameHostId& render_frame_id) { + void UnregisterController( + const content::GlobalFrameRoutingId& render_frame_id) { manager()->UnregisterLocalPresentationController(kPresentationId, render_frame_id); } @@ -117,7 +119,7 @@ } private: - const RenderFrameHostId render_frame_host_id_; + const content::GlobalFrameRoutingId render_frame_host_id_; const PresentationInfo presentation_info_; LocalPresentationManager manager_; MediaRoute route_; @@ -152,9 +154,11 @@ TEST_F(LocalPresentationManagerTest, RegisterMultipleControllersSamePresentation) { content::PresentationConnectionPtr controller1; - RegisterController(RenderFrameHostId(1, 1), std::move(controller1)); + RegisterController(content::GlobalFrameRoutingId(1, 1), + std::move(controller1)); content::PresentationConnectionPtr controller2; - RegisterController(RenderFrameHostId(1, 2), std::move(controller2)); + RegisterController(content::GlobalFrameRoutingId(1, 2), + std::move(controller2)); VerifyPresentationsSize(1); } @@ -244,9 +248,11 @@ TEST_F(LocalPresentationManagerTest, RegisterTwoControllersThenReceiverInvokesCallbackTwice) { content::PresentationConnectionPtr controller1; - RegisterController(RenderFrameHostId(1, 1), std::move(controller1)); + RegisterController(content::GlobalFrameRoutingId(1, 1), + std::move(controller1)); content::PresentationConnectionPtr controller2; - RegisterController(RenderFrameHostId(1, 2), std::move(controller2)); + RegisterController(content::GlobalFrameRoutingId(1, 2), + std::move(controller2)); MockReceiverConnectionAvailableCallback receiver_callback; EXPECT_CALL(receiver_callback, OnReceiverConnectionAvailableRaw(_, _)) @@ -257,7 +263,8 @@ TEST_F(LocalPresentationManagerTest, RegisterControllerReceiverConontrollerInvokesCallbackTwice) { content::PresentationConnectionPtr controller1; - RegisterController(RenderFrameHostId(1, 1), std::move(controller1)); + RegisterController(content::GlobalFrameRoutingId(1, 1), + std::move(controller1)); MockReceiverConnectionAvailableCallback receiver_callback; EXPECT_CALL(receiver_callback, OnReceiverConnectionAvailableRaw(_, _)) @@ -265,22 +272,25 @@ RegisterReceiver(receiver_callback); content::PresentationConnectionPtr controller2; - RegisterController(RenderFrameHostId(1, 2), std::move(controller2)); + RegisterController(content::GlobalFrameRoutingId(1, 2), + std::move(controller2)); } TEST_F(LocalPresentationManagerTest, UnregisterFirstControllerFromeConnectedPresentation) { content::PresentationConnectionPtr controller1; - RegisterController(RenderFrameHostId(1, 1), std::move(controller1)); + RegisterController(content::GlobalFrameRoutingId(1, 1), + std::move(controller1)); content::PresentationConnectionPtr controller2; - RegisterController(RenderFrameHostId(1, 2), std::move(controller2)); + RegisterController(content::GlobalFrameRoutingId(1, 2), + std::move(controller2)); MockReceiverConnectionAvailableCallback receiver_callback; EXPECT_CALL(receiver_callback, OnReceiverConnectionAvailableRaw(_, _)) .Times(2); RegisterReceiver(receiver_callback); - UnregisterController(RenderFrameHostId(1, 1)); - UnregisterController(RenderFrameHostId(1, 1)); + UnregisterController(content::GlobalFrameRoutingId(1, 1)); + UnregisterController(content::GlobalFrameRoutingId(1, 1)); VerifyPresentationsSize(1); }
diff --git a/chrome/browser/media/router/presentation/presentation_service_delegate_impl.cc b/chrome/browser/media/router/presentation/presentation_service_delegate_impl.cc index f8b7743b..6aa8a4cd 100644 --- a/chrome/browser/media/router/presentation/presentation_service_delegate_impl.cc +++ b/chrome/browser/media/router/presentation/presentation_service_delegate_impl.cc
@@ -53,9 +53,9 @@ // Gets the last committed URL for the render frame specified by // |render_frame_host_id|. url::Origin GetLastCommittedURLForFrame( - RenderFrameHostId render_frame_host_id) { + content::GlobalFrameRoutingId render_frame_host_id) { RenderFrameHost* render_frame_host = RenderFrameHost::FromID( - render_frame_host_id.first, render_frame_host_id.second); + render_frame_host_id.child_id, render_frame_host_id.frame_routing_id); DCHECK(render_frame_host); return render_frame_host->GetLastCommittedOrigin(); } @@ -80,7 +80,7 @@ // is destroyed. class PresentationFrame { public: - PresentationFrame(const RenderFrameHostId& render_frame_host_id, + PresentationFrame(const content::GlobalFrameRoutingId& render_frame_host_id, content::WebContents* web_contents, MediaRouter* router); ~PresentationFrame(); @@ -121,7 +121,7 @@ std::unique_ptr<BrowserPresentationConnectionProxy>> browser_connection_proxies_; - RenderFrameHostId render_frame_host_id_; + content::GlobalFrameRoutingId render_frame_host_id_; // References to the owning WebContents, and the corresponding MediaRouter. content::WebContents* web_contents_; @@ -129,7 +129,7 @@ }; PresentationFrame::PresentationFrame( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, content::WebContents* web_contents, MediaRouter* router) : render_frame_host_id_(render_frame_host_id), @@ -333,7 +333,8 @@ int render_frame_id, content::PresentationScreenAvailabilityListener* listener) { DCHECK(listener); - RenderFrameHostId render_frame_host_id(render_process_id, render_frame_id); + content::GlobalFrameRoutingId render_frame_host_id(render_process_id, + render_frame_id); auto* presentation_frame = GetOrAddPresentationFrame(render_frame_host_id); return presentation_frame->SetScreenAvailabilityListener(listener); } @@ -343,7 +344,8 @@ int render_frame_id, content::PresentationScreenAvailabilityListener* listener) { DCHECK(listener); - RenderFrameHostId render_frame_host_id(render_process_id, render_frame_id); + content::GlobalFrameRoutingId render_frame_host_id(render_process_id, + render_frame_id); const auto it = presentation_frames_.find(render_frame_host_id); if (it != presentation_frames_.end()) it->second->RemoveScreenAvailabilityListener(listener); @@ -351,7 +353,8 @@ void PresentationServiceDelegateImpl::Reset(int render_process_id, int render_frame_id) { - RenderFrameHostId render_frame_host_id(render_process_id, render_frame_id); + content::GlobalFrameRoutingId render_frame_host_id(render_process_id, + render_frame_id); const auto it = presentation_frames_.find(render_frame_host_id); if (it != presentation_frames_.end()) { it->second->Reset(); @@ -366,7 +369,7 @@ } PresentationFrame* PresentationServiceDelegateImpl::GetOrAddPresentationFrame( - const RenderFrameHostId& render_frame_host_id) { + const content::GlobalFrameRoutingId& render_frame_host_id) { auto& presentation_frame = presentation_frames_[render_frame_host_id]; if (!presentation_frame) { presentation_frame.reset( @@ -391,7 +394,7 @@ } void PresentationServiceDelegateImpl::OnJoinRouteResponse( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, const GURL& presentation_url, const std::string& presentation_id, content::PresentationConnectionCallback success_cb, @@ -414,7 +417,7 @@ } void PresentationServiceDelegateImpl::OnStartPresentationSucceeded( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, content::PresentationConnectionCallback success_cb, const PresentationInfo& new_presentation_info, const MediaRoute& route) { @@ -427,7 +430,7 @@ } void PresentationServiceDelegateImpl::AddPresentation( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, const PresentationInfo& presentation_info, const MediaRoute& route) { auto* presentation_frame = GetOrAddPresentationFrame(render_frame_host_id); @@ -435,7 +438,7 @@ } void PresentationServiceDelegateImpl::RemovePresentation( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, const std::string& presentation_id) { const auto it = presentation_frames_.find(render_frame_host_id); if (it != presentation_frames_.end()) @@ -544,7 +547,8 @@ int render_process_id, int render_frame_id, const std::string& presentation_id) { - const RenderFrameHostId rfh_id(render_process_id, render_frame_id); + const content::GlobalFrameRoutingId rfh_id(render_process_id, + render_frame_id); auto route_id = GetRouteId(rfh_id, presentation_id); if (route_id.empty()) { DVLOG(1) << "No active route for: " << presentation_id; @@ -570,7 +574,8 @@ int render_process_id, int render_frame_id, const std::string& presentation_id) { - const RenderFrameHostId rfh_id(render_process_id, render_frame_id); + const content::GlobalFrameRoutingId rfh_id(render_process_id, + render_frame_id); auto route_id = GetRouteId(rfh_id, presentation_id); if (route_id.empty()) { DVLOG(1) << "No active route for: " << presentation_id; @@ -586,7 +591,8 @@ const PresentationInfo& connection, const content::PresentationConnectionStateChangedCallback& state_changed_cb) { - RenderFrameHostId render_frame_host_id(render_process_id, render_frame_id); + content::GlobalFrameRoutingId render_frame_host_id(render_process_id, + render_frame_id); const auto it = presentation_frames_.find(render_frame_host_id); if (it != presentation_frames_.end()) it->second->ListenForConnectionStateChange(connection, state_changed_cb); @@ -598,7 +604,8 @@ const PresentationInfo& presentation_info, content::PresentationConnectionPtr controller_connection_ptr, content::PresentationConnectionRequest receiver_connection_request) { - RenderFrameHostId render_frame_host_id(render_process_id, render_frame_id); + content::GlobalFrameRoutingId render_frame_host_id(render_process_id, + render_frame_id); auto* presentation_frame = GetOrAddPresentationFrame(render_frame_host_id); presentation_frame->ConnectToPresentation( presentation_info, std::move(controller_connection_ptr), @@ -654,7 +661,8 @@ int render_process_id, int render_frame_id, const MediaSource::Id& source_id) const { - RenderFrameHostId render_frame_host_id(render_process_id, render_frame_id); + content::GlobalFrameRoutingId render_frame_host_id(render_process_id, + render_frame_id); const auto it = presentation_frames_.find(render_frame_host_id); return it != presentation_frames_.end() && it->second->HasScreenAvailabilityListenerForTest(source_id); @@ -675,7 +683,8 @@ int render_process_id, int render_frame_id, const std::string& presentation_id) { - const RenderFrameHostId rfh_id(render_process_id, render_frame_id); + const content::GlobalFrameRoutingId rfh_id(render_process_id, + render_frame_id); MediaRoute::Id route_id = GetRouteId(rfh_id, presentation_id); if (route_id.empty()) @@ -685,7 +694,7 @@ } MediaRoute::Id PresentationServiceDelegateImpl::GetRouteId( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, const std::string& presentation_id) const { const auto it = presentation_frames_.find(render_frame_host_id); return it != presentation_frames_.end()
diff --git a/chrome/browser/media/router/presentation/presentation_service_delegate_impl.h b/chrome/browser/media/router/presentation/presentation_service_delegate_impl.h index 287b241a..2f10f532 100644 --- a/chrome/browser/media/router/presentation/presentation_service_delegate_impl.h +++ b/chrome/browser/media/router/presentation/presentation_service_delegate_impl.h
@@ -5,9 +5,9 @@ #ifndef CHROME_BROWSER_MEDIA_ROUTER_PRESENTATION_PRESENTATION_SERVICE_DELEGATE_IMPL_H_ #define CHROME_BROWSER_MEDIA_ROUTER_PRESENTATION_PRESENTATION_SERVICE_DELEGATE_IMPL_H_ -#include <map> #include <memory> #include <string> +#include <unordered_map> #include <utility> #include <vector> @@ -19,7 +19,6 @@ #include "build/build_config.h" #include "chrome/browser/media/router/media_router.h" #include "chrome/browser/media/router/presentation/presentation_service_delegate_observers.h" -#include "chrome/browser/media/router/presentation/render_frame_host_id.h" #include "chrome/common/media_router/media_source.h" #include "content/public/browser/presentation_request.h" #include "content/public/browser/presentation_service_delegate.h" @@ -179,10 +178,10 @@ explicit PresentationServiceDelegateImpl(content::WebContents* web_contents); PresentationFrame* GetOrAddPresentationFrame( - const RenderFrameHostId& render_frame_host_id); + const content::GlobalFrameRoutingId& render_frame_host_id); void OnJoinRouteResponse( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, const GURL& presentation_url, const std::string& presentation_id, content::PresentationConnectionCallback success_cb, @@ -190,7 +189,7 @@ const RouteRequestResult& result); void OnStartPresentationSucceeded( - const RenderFrameHostId& render_frame_host_id, + const content::GlobalFrameRoutingId& render_frame_host_id, content::PresentationConnectionCallback success_cb, const blink::mojom::PresentationInfo& new_presentation_info, const MediaRoute& route); @@ -199,14 +198,16 @@ // presentation and its corresponding MediaRoute has been created. // The PresentationFrame will be created if it does not already exist. // This must be called before |ConnectToPresentation()|. - void AddPresentation(const RenderFrameHostId& render_frame_host_id, - const blink::mojom::PresentationInfo& presentation_info, - const MediaRoute& route); + void AddPresentation( + const content::GlobalFrameRoutingId& render_frame_host_id, + const blink::mojom::PresentationInfo& presentation_info, + const MediaRoute& route); // Notifies the PresentationFrame of |render_frame_host_id| that a // presentation and its corresponding MediaRoute has been removed. - void RemovePresentation(const RenderFrameHostId& render_frame_host_id, - const std::string& presentation_id); + void RemovePresentation( + const content::GlobalFrameRoutingId& render_frame_host_id, + const std::string& presentation_id); // Clears the default presentation request for the owning WebContents and // notifies observers of changes. Also resets @@ -215,8 +216,9 @@ // Returns the ID of the route corresponding to |presentation_id| in the given // frame, or empty if no such route exist. - MediaRoute::Id GetRouteId(const RenderFrameHostId& render_frame_host_id, - const std::string& presentation_id) const; + MediaRoute::Id GetRouteId( + const content::GlobalFrameRoutingId& render_frame_host_id, + const std::string& presentation_id) const; #if !defined(OS_ANDROID) // Returns true if auto-join requests should be cancelled for |origin|. @@ -242,9 +244,9 @@ // Maps a frame identifier to a PresentationFrame object for frames // that are using Presentation API. - std::unordered_map<RenderFrameHostId, + std::unordered_map<content::GlobalFrameRoutingId, std::unique_ptr<PresentationFrame>, - RenderFrameHostIdHasher> + content::GlobalFrameRoutingIdHasher> presentation_frames_; PresentationServiceDelegateObservers observers_;
diff --git a/chrome/browser/media/router/presentation/presentation_service_delegate_impl_unittest.cc b/chrome/browser/media/router/presentation/presentation_service_delegate_impl_unittest.cc index 187ab7d..9f8479a 100644 --- a/chrome/browser/media/router/presentation/presentation_service_delegate_impl_unittest.cc +++ b/chrome/browser/media/router/presentation/presentation_service_delegate_impl_unittest.cc
@@ -82,7 +82,7 @@ public: void RegisterLocalPresentationController( const PresentationInfo& presentation_info, - const RenderFrameHostId& render_frame_id, + const content::GlobalFrameRoutingId& render_frame_id, content::PresentationConnectionPtr controller, content::PresentationConnectionRequest, const MediaRoute& route) override { @@ -92,11 +92,11 @@ MOCK_METHOD3(RegisterLocalPresentationController, void(const PresentationInfo& presentation_info, - const RenderFrameHostId& render_frame_id, + const content::GlobalFrameRoutingId& render_frame_id, const MediaRoute& route)); MOCK_METHOD2(UnregisterLocalPresentationController, void(const std::string& presentation_id, - const RenderFrameHostId& render_frame_id)); + const content::GlobalFrameRoutingId& render_frame_id)); MOCK_METHOD2(OnLocalPresentationReceiverCreated, void(const PresentationInfo& presentation_info, const content::ReceiverConnectionAvailableCallback& @@ -139,7 +139,8 @@ delegate_impl_ = PresentationServiceDelegateImpl::FromWebContents(wc); SetMainFrame(); presentation_request_ = std::make_unique<content::PresentationRequest>( - RenderFrameHostId(main_frame_process_id_, main_frame_routing_id_), + content::GlobalFrameRoutingId(main_frame_process_id_, + main_frame_routing_id_), presentation_urls_, frame_origin_); SetMockLocalPresentationManager(); } @@ -173,7 +174,8 @@ // Should not trigger callback since request doesn't match. content::PresentationRequest different_request( - RenderFrameHostId(100, 200), {presentation_url2_}, frame_origin_); + content::GlobalFrameRoutingId(100, 200), {presentation_url2_}, + frame_origin_); MediaRoute media_route("differentRouteId", source2_, "mediaSinkId", "", true, true); media_route.set_incognito(incognito); @@ -494,7 +496,8 @@ TestCloseConnectionForLocalPresentation) { GURL presentation_url = GURL("http://www.example.com/presentation.html"); PresentationInfo presentation_info(presentation_url, kPresentationId); - RenderFrameHostId rfh_id(main_frame_process_id_, main_frame_routing_id_); + content::GlobalFrameRoutingId rfh_id(main_frame_process_id_, + main_frame_routing_id_); MediaRoute media_route("route_id", MediaSourceForPresentationUrl(presentation_url), "mediaSinkId", "", true, true); @@ -537,8 +540,9 @@ EXPECT_CALL(success_cb, Run(_)); EXPECT_CALL(mock_local_manager, UnregisterLocalPresentationController( - kPresentationId, RenderFrameHostId(main_frame_process_id_, - main_frame_routing_id_))); + kPresentationId, + content::GlobalFrameRoutingId(main_frame_process_id_, + main_frame_routing_id_))); delegate_impl_->ReconnectPresentation(*presentation_request_, kPresentationId, success_cb.Get(), error_cb.Get()); @@ -546,7 +550,8 @@ } TEST_F(PresentationServiceDelegateImplTest, ConnectToLocalPresentation) { - RenderFrameHostId rfh_id(main_frame_process_id_, main_frame_routing_id_); + content::GlobalFrameRoutingId rfh_id(main_frame_process_id_, + main_frame_routing_id_); PresentationInfo presentation_info(presentation_url1_, kPresentationId); MediaRoute media_route("route_id", @@ -578,7 +583,8 @@ } TEST_F(PresentationServiceDelegateImplTest, ConnectToPresentation) { - RenderFrameHostId rfh_id(main_frame_process_id_, main_frame_routing_id_); + content::GlobalFrameRoutingId rfh_id(main_frame_process_id_, + main_frame_routing_id_); PresentationInfo presentation_info(presentation_url1_, kPresentationId); MediaRoute media_route("route_id",
diff --git a/chrome/browser/media/router/presentation/presentation_service_delegate_observers.cc b/chrome/browser/media/router/presentation/presentation_service_delegate_observers.cc index 8c6c0e4..4d8f90d4 100644 --- a/chrome/browser/media/router/presentation/presentation_service_delegate_observers.cc +++ b/chrome/browser/media/router/presentation/presentation_service_delegate_observers.cc
@@ -21,14 +21,15 @@ content::PresentationServiceDelegate::Observer* observer) { DCHECK(observer); - RenderFrameHostId rfh_id(render_process_id, render_frame_id); + content::GlobalFrameRoutingId rfh_id(render_process_id, render_frame_id); DCHECK(!base::ContainsKey(observers_, rfh_id)); observers_[rfh_id] = observer; } void PresentationServiceDelegateObservers::RemoveObserver(int render_process_id, int render_frame_id) { - observers_.erase(RenderFrameHostId(render_process_id, render_frame_id)); + observers_.erase( + content::GlobalFrameRoutingId(render_process_id, render_frame_id)); } } // namespace media_router
diff --git a/chrome/browser/media/router/presentation/presentation_service_delegate_observers.h b/chrome/browser/media/router/presentation/presentation_service_delegate_observers.h index 1491176..3c30c15 100644 --- a/chrome/browser/media/router/presentation/presentation_service_delegate_observers.h +++ b/chrome/browser/media/router/presentation/presentation_service_delegate_observers.h
@@ -7,7 +7,7 @@ #include <map> -#include "chrome/browser/media/router/presentation/render_frame_host_id.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/presentation_service_delegate.h" namespace media_router { @@ -33,7 +33,8 @@ virtual void RemoveObserver(int render_process_id, int render_frame_id); private: - std::map<RenderFrameHostId, content::PresentationServiceDelegate::Observer*> + std::map<content::GlobalFrameRoutingId, + content::PresentationServiceDelegate::Observer*> observers_; };
diff --git a/chrome/browser/media/router/presentation/render_frame_host_id.h b/chrome/browser/media/router/presentation/render_frame_host_id.h deleted file mode 100644 index f139d5d..0000000 --- a/chrome/browser/media/router/presentation/render_frame_host_id.h +++ /dev/null
@@ -1,24 +0,0 @@ -// Copyright 2015 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CHROME_BROWSER_MEDIA_ROUTER_PRESENTATION_RENDER_FRAME_HOST_ID_H_ -#define CHROME_BROWSER_MEDIA_ROUTER_PRESENTATION_RENDER_FRAME_HOST_ID_H_ - -#include <utility> - -#include "base/hash.h" - -namespace media_router { - -using RenderFrameHostId = std::pair<int, int>; - -struct RenderFrameHostIdHasher { - std::size_t operator()(const RenderFrameHostId id) const { - return base::HashInts(id.first, id.second); - } -}; - -} // namespace media_router - -#endif // CHROME_BROWSER_MEDIA_ROUTER_PRESENTATION_RENDER_FRAME_HOST_ID_H_
diff --git a/chrome/browser/metrics/chrome_metrics_services_manager_client.cc b/chrome/browser/metrics/chrome_metrics_services_manager_client.cc index 38cae30..714c4f2 100644 --- a/chrome/browser/metrics/chrome_metrics_services_manager_client.cc +++ b/chrome/browser/metrics/chrome_metrics_services_manager_client.cc
@@ -28,7 +28,6 @@ #include "components/variations/variations_associated_data.h" #include "components/version_info/version_info.h" #include "content/public/browser/browser_thread.h" -#include "content/public/browser/network_service_instance.h" #include "services/network/public/cpp/shared_url_loader_factory.h" #if defined(OS_ANDROID) @@ -241,8 +240,7 @@ return variations::VariationsService::Create( std::make_unique<ChromeVariationsServiceClient>(), local_state_, GetMetricsStateManager(), switches::kDisableBackgroundNetworking, - chrome_variations::CreateUIStringOverrider(), - base::BindOnce(&content::GetNetworkConnectionTracker)); + chrome_variations::CreateUIStringOverrider()); } std::unique_ptr<metrics::MetricsServiceClient>
diff --git a/chrome/browser/password_manager/chrome_password_manager_client.cc b/chrome/browser/password_manager/chrome_password_manager_client.cc index 5e0398d..239321e 100644 --- a/chrome/browser/password_manager/chrome_password_manager_client.cc +++ b/chrome/browser/password_manager/chrome_password_manager_client.cc
@@ -777,7 +777,9 @@ auto* driver = driver_factory_->GetDriverForFrame( password_manager_client_bindings_.GetCurrentTargetFrame()); DCHECK(driver); - gfx::RectF element_bounds_in_screen_space = GetBoundsInScreenSpace(bounds); + gfx::RectF element_bounds_in_screen_space = + GetBoundsInScreenSpace(TransformToRootCoordinates( + password_manager_driver_bindings_.GetCurrentTargetFrame(), bounds)); popup_controller_ = PasswordGenerationPopupControllerImpl::GetOrCreate( popup_controller_, element_bounds_in_screen_space, form, base::string16(), // No generation_element needed for editing. @@ -1065,17 +1067,18 @@ auto* driver = driver_factory_->GetDriverForFrame( password_manager_client_bindings_.GetCurrentTargetFrame()); DCHECK(driver); - // Autofill drop-down and password generation use different coordinates. - gfx::RectF element_bounds_in_screen_space = TransformToRootCoordinates( + gfx::RectF element_bounds_in_top_frame_space = TransformToRootCoordinates( password_manager_client_bindings_.GetCurrentTargetFrame(), ui_data.bounds); if (!is_manually_triggered && driver->GetPasswordAutofillManager() ->MaybeShowPasswordSuggestionsWithGeneration( - element_bounds_in_screen_space, ui_data.text_direction)) + element_bounds_in_top_frame_space, ui_data.text_direction)) { return; + } - element_bounds_in_screen_space = GetBoundsInScreenSpace(ui_data.bounds); + gfx::RectF element_bounds_in_screen_space = + GetBoundsInScreenSpace(element_bounds_in_top_frame_space); password_manager_.SetGenerationElementAndReasonForForm( driver, ui_data.password_form, ui_data.generation_element, is_manually_triggered);
diff --git a/chrome/browser/password_manager/password_accessory_controller.cc b/chrome/browser/password_manager/password_accessory_controller.cc index c4866e05..cd3ae17 100644 --- a/chrome/browser/password_manager/password_accessory_controller.cc +++ b/chrome/browser/password_manager/password_accessory_controller.cc
@@ -173,7 +173,7 @@ autofill::FillingStatus status) { if (status != autofill::FillingStatus::SUCCESS) return; // TODO(crbug/853766): Record success rate. - view_->OpenKeyboard(); // Bring up the keyboard for the still focused field. + view_->SwapSheetWithKeyboard(); } void PasswordAccessoryController::RefreshSuggestionsForField( @@ -184,7 +184,7 @@ current_origin_ = origin; view_->OnItemsAvailable(CreateViewItems(origin, origin_suggestions_[origin], is_password_field)); - view_->OpenKeyboard(); // Should happen automatically. + view_->SwapSheetWithKeyboard(); } else { // For unfillable fields, reset the origin and send the empty state message. current_origin_ = url::Origin();
diff --git a/chrome/browser/password_manager/password_accessory_controller_unittest.cc b/chrome/browser/password_manager/password_accessory_controller_unittest.cc index 9f2ffb3..df23aec 100644 --- a/chrome/browser/password_manager/password_accessory_controller_unittest.cc +++ b/chrome/browser/password_manager/password_accessory_controller_unittest.cc
@@ -65,7 +65,7 @@ MOCK_METHOD0(OnViewDestroyed, void()); MOCK_METHOD1(OnAutomaticGenerationStatusChanged, void(bool)); MOCK_METHOD0(CloseAccessorySheet, void()); - MOCK_METHOD0(OpenKeyboard, void()); + MOCK_METHOD0(SwapSheetWithKeyboard, void()); private: DISALLOW_COPY_AND_ASSIGN(MockPasswordAccessoryView); @@ -259,7 +259,7 @@ mock_dialog_factory_.Get(), favicon_service()); NavigateAndCommit(GURL(kExampleSite)); EXPECT_CALL(*view(), CloseAccessorySheet()).Times(AnyNumber()); - EXPECT_CALL(*view(), OpenKeyboard()).Times(AnyNumber()); + EXPECT_CALL(*view(), SwapSheetWithKeyboard()).Times(AnyNumber()); } PasswordAccessoryController* controller() { @@ -406,12 +406,12 @@ TEST_F(PasswordAccessoryControllerTest, ClosesViewOnSuccessfullFillingOnly) { // If the filling wasn't successful, no call is expected. EXPECT_CALL(*view(), CloseAccessorySheet()).Times(0); - EXPECT_CALL(*view(), OpenKeyboard()).Times(0); + EXPECT_CALL(*view(), SwapSheetWithKeyboard()).Times(0); controller()->OnFilledIntoFocusedField(FillingStatus::ERROR_NOT_ALLOWED); controller()->OnFilledIntoFocusedField(FillingStatus::ERROR_NO_VALID_FIELD); // If the filling completed successfully, let the view know. - EXPECT_CALL(*view(), OpenKeyboard()); + EXPECT_CALL(*view(), SwapSheetWithKeyboard()); controller()->OnFilledIntoFocusedField(FillingStatus::SUCCESS); } @@ -421,7 +421,8 @@ EXPECT_CALL(*view(), OnItemsAvailable(_)).Times(AnyNumber()); EXPECT_CALL(*view(), CloseAccessorySheet()); - EXPECT_CALL(*view(), OpenKeyboard()).Times(0); // Don't touch the keyboard! + EXPECT_CALL(*view(), SwapSheetWithKeyboard()) + .Times(0); // Don't touch the keyboard! controller()->RefreshSuggestionsForField( url::Origin::Create(GURL(kExampleSite)), /*is_fillable=*/false,
diff --git a/chrome/browser/password_manager/password_accessory_view_interface.h b/chrome/browser/password_manager/password_accessory_view_interface.h index 6bc3fd8f..77c3e09 100644 --- a/chrome/browser/password_manager/password_accessory_view_interface.h +++ b/chrome/browser/password_manager/password_accessory_view_interface.h
@@ -74,8 +74,8 @@ // Called to inform the view that the accessory sheet should be closed now. virtual void CloseAccessorySheet() = 0; - // Called to inform the view that the accessory sheet should be closed now. - virtual void OpenKeyboard() = 0; + // Opens a keyboard which dismisses the sheet. NoOp without open sheet. + virtual void SwapSheetWithKeyboard() = 0; private: friend class PasswordAccessoryController;
diff --git a/chrome/browser/plugins/plugins_resource_service.cc b/chrome/browser/plugins/plugins_resource_service.cc index 8223414..b553264 100644 --- a/chrome/browser/plugins/plugins_resource_service.cc +++ b/chrome/browser/plugins/plugins_resource_service.cc
@@ -14,7 +14,6 @@ #include "chrome/common/pref_names.h" #include "components/prefs/pref_registry_simple.h" #include "components/prefs/pref_service.h" -#include "content/public/browser/network_service_instance.h" #include "content/public/common/service_manager_connection.h" #include "services/data_decoder/public/cpp/safe_json_parser.h" #include "services/network/public/cpp/shared_url_loader_factory.h" @@ -90,8 +89,7 @@ base::Bind(data_decoder::SafeJsonParser::Parse, content::ServiceManagerConnection::GetForProcess() ->GetConnector()), - kPluginResourceServiceTrafficAnnotation, - base::BindOnce(&content::GetNetworkConnectionTracker)) {} + kPluginResourceServiceTrafficAnnotation) {} void PluginsResourceService::Init() { const base::DictionaryValue* metadata =
diff --git a/chrome/browser/policy/configuration_policy_handler_list_factory.cc b/chrome/browser/policy/configuration_policy_handler_list_factory.cc index e87e5e8..bb8db7b 100644 --- a/chrome/browser/policy/configuration_policy_handler_list_factory.cc +++ b/chrome/browser/policy/configuration_policy_handler_list_factory.cc
@@ -1000,6 +1000,11 @@ handlers->AddHandler( std::make_unique<extensions::ExtensionSettingsPolicyHandler>( chrome_schema)); + handlers->AddHandler(std::make_unique<SimpleSchemaValidatingPolicyHandler>( + key::kWebAppInstallForceList, prefs::kWebAppInstallForceList, + chrome_schema, SCHEMA_STRICT, + SimpleSchemaValidatingPolicyHandler::RECOMMENDED_PROHIBITED, + SimpleSchemaValidatingPolicyHandler::MANDATORY_ALLOWED)); #endif #if !defined(OS_CHROMEOS) && !defined(OS_ANDROID)
diff --git a/chrome/browser/policy/policy_browsertest.cc b/chrome/browser/policy/policy_browsertest.cc index aadab97..6963d95 100644 --- a/chrome/browser/policy/policy_browsertest.cc +++ b/chrome/browser/policy/policy_browsertest.cc
@@ -114,6 +114,7 @@ #include "chrome/common/chrome_switches.h" #include "chrome/common/extensions/extension_constants.h" #include "chrome/common/extensions/extension_test_util.h" +#include "chrome/common/extensions/manifest_handlers/app_launch_info.h" #include "chrome/common/net/safe_search_util.h" #include "chrome/common/pref_names.h" #include "chrome/common/url_constants.h" @@ -6284,6 +6285,54 @@ EXPECT_TRUE(context->CanRequestObjectPermission(kTestUrl, kTestUrl)); } +// Similar to PolicyTest but sets the WebAppInstallForceList policy before the +// browser is started. +class WebAppInstallForceListPolicyTest : public PolicyTest { + public: + WebAppInstallForceListPolicyTest() {} + ~WebAppInstallForceListPolicyTest() override {} + + void SetUpInProcessBrowserTestFixture() override { + PolicyTest::SetUpInProcessBrowserTestFixture(); + ASSERT_TRUE(embedded_test_server()->Start()); + + policy_app_url_ = + embedded_test_server()->GetURL("/banners/manifest_test_page.html"); + base::Value url(policy_app_url_.spec()); + base::Value launch_container("window"); + + base::Value item(base::Value::Type::DICTIONARY); + item.SetKey("url", std::move(url)); + item.SetKey("launch_container", std::move(launch_container)); + + base::Value list(base::Value::Type::LIST); + list.GetList().push_back(std::move(item)); + + PolicyMap policies; + SetPolicy(&policies, key::kWebAppInstallForceList, + base::Value::ToUniquePtrValue(std::move(list))); + provider_.UpdateChromePolicy(policies); + } + + protected: + GURL policy_app_url_; + + private: + DISALLOW_COPY_AND_ASSIGN(WebAppInstallForceListPolicyTest); +}; + +IN_PROC_BROWSER_TEST_F(WebAppInstallForceListPolicyTest, StartUpInstallation) { + extensions::TestExtensionRegistryObserver observer( + extensions::ExtensionRegistry::Get(browser()->profile())); + const extensions::Extension* installed_extension = + observer.WaitForExtensionWillBeInstalled(); + + ASSERT_TRUE(installed_extension); + const GURL installed_app_url = + extensions::AppLaunchInfo::GetFullLaunchURL(installed_extension); + EXPECT_EQ(policy_app_url_, installed_app_url); +} + #if !defined(OS_CHROMEOS) && !defined(OS_ANDROID) // The possibilities for a boolean policy.
diff --git a/chrome/browser/prefs/pref_service_incognito_whitelist.cc b/chrome/browser/prefs/pref_service_incognito_whitelist.cc index 9413624..61b3980 100644 --- a/chrome/browser/prefs/pref_service_incognito_whitelist.cc +++ b/chrome/browser/prefs/pref_service_incognito_whitelist.cc
@@ -131,6 +131,9 @@ // they need to be persisted. rappor::prefs::kRapporCohortSeed, rappor::prefs::kRapporSecret, + // Reading list preferences are common between incognito and regular mode. + reading_list::prefs::kReadingListHasUnseenEntries, + // Although UKMs are not collected in incognito, theses preferences may be // changed by UMA/Sync/Unity consent, and need to be the same between // incognito and regular modes. @@ -297,22 +300,6 @@ prefs::kInvertNotificationShown, - prefs::kPrintingEnabled, prefs::kPrintPreviewDisabled, - prefs::kPrintPreviewDefaultDestinationSelectionRules, - -#if !defined(OS_CHROMEOS) && !defined(OS_ANDROID) - prefs::kPrintPreviewUseSystemDefaultPrinter, -#endif - -#if defined(OS_CHROMEOS) - prefs::kPrintingDevices, prefs::kRecommendedNativePrinters, - prefs::kRecommendedNativePrintersFile, - prefs::kRecommendedNativePrintersAccessMode, - prefs::kRecommendedNativePrintersBlacklist, - prefs::kRecommendedNativePrintersWhitelist, - prefs::kUserNativePrintersAllowed, -#endif // OS_CHROMEOS - prefs::kMessageCenterDisabledExtensionIds, prefs::kMessageCenterDisabledSystemComponentIds, @@ -418,8 +405,6 @@ prefs::kDefaultAudioCaptureDevice, prefs::kDefaultVideoCaptureDevice, prefs::kMediaDeviceIdSalt, prefs::kMediaStorageIdSalt, - prefs::kPrintPreviewStickySettings, - prefs::kMaxConnectionsPerProxy, prefs::kAudioCaptureAllowed, prefs::kAudioCaptureAllowedUrls, @@ -608,9 +593,6 @@ onc::prefs::kDeviceOpenNetworkConfiguration, onc::prefs::kOpenNetworkConfiguration, - // components/reading_list/core/reading_list_pref_names.h - reading_list::prefs::kReadingListHasUnseenEntries, - // components/search_engines/search_engines_pref_names.h prefs::kSyncedDefaultSearchProviderGUID, prefs::kDefaultSearchProviderEnabled, prefs::kSearchProviderOverrides,
diff --git a/chrome/browser/prerender/OWNERS b/chrome/browser/prerender/OWNERS index 03f1a3b..61337163 100644 --- a/chrome/browser/prerender/OWNERS +++ b/chrome/browser/prerender/OWNERS
@@ -1,7 +1,5 @@ -davidben@chromium.org droger@chromium.org mattcary@chromium.org -mmenke@chromium.org pasko@chromium.org # COMPONENT: Internals>Preload
diff --git a/chrome/browser/prerender/prerender_browsertest.cc b/chrome/browser/prerender/prerender_browsertest.cc index dfb91c5..83fb836 100644 --- a/chrome/browser/prerender/prerender_browsertest.cc +++ b/chrome/browser/prerender/prerender_browsertest.cc
@@ -428,21 +428,27 @@ } // TabStripModelObserver implementation: - void TabReplacedAt(TabStripModel* tab_strip_model, - WebContents* old_contents, - WebContents* new_contents, - int index) override { - if (old_contents != web_contents()) + void OnTabStripModelChanged( + TabStripModel* tab_strip_model, + const TabStripModelChange& change, + const TabStripSelectionChange& selection) override { + if (change.type() != TabStripModelChange::kReplaced) return; - // Switch to observing the new WebContents. - Observe(new_contents); - if (new_contents->IsLoading()) { - // If the new WebContents is still loading, wait for it to complete. Only - // one load post-swap is supported. - did_start_loading_ = true; - number_of_loads_ = 1; - } else { - loop_.Quit(); + + for (const auto& delta : change.deltas()) { + if (delta.replace.old_contents != web_contents()) + continue; + + // Switch to observing the new WebContents. + Observe(delta.replace.new_contents); + if (delta.replace.new_contents->IsLoading()) { + // If the new WebContents is still loading, wait for it to complete. + // Only one load post-swap is supported. + did_start_loading_ = true; + number_of_loads_ = 1; + } else { + loop_.Quit(); + } } } @@ -1430,8 +1436,9 @@ // http://crbug.com/100514 #define MAYBE_PrerenderIframeDelayLoadPlugin \ DISABLED_PrerenderIframeDelayLoadPlugin -#elif defined(OS_WIN) && defined(ARCH_CPU_X86_64) -// TODO(jschuh): Failing plugin tests. crbug.com/244653 +#elif defined(OS_WIN) +// TODO(jschuh): Failing plugin tests. https://crbug.com/244653, +// https://crbug.com/876872 #define MAYBE_PrerenderIframeDelayLoadPlugin \ DISABLED_PrerenderIframeDelayLoadPlugin #else
diff --git a/chrome/browser/previews/previews_service_unittest.cc b/chrome/browser/previews/previews_service_unittest.cc index e5c1e3c..244ccf2 100644 --- a/chrome/browser/previews/previews_service_unittest.cc +++ b/chrome/browser/previews/previews_service_unittest.cc
@@ -16,6 +16,7 @@ #include "base/single_thread_task_runner.h" #include "base/test/scoped_feature_list.h" #include "base/time/default_clock.h" +#include "build/build_config.h" #include "components/blacklist/opt_out_blacklist/opt_out_blacklist_data.h" #include "components/data_reduction_proxy/core/common/data_reduction_proxy_features.h" #include "components/previews/content/previews_decider_impl.h" @@ -187,8 +188,12 @@ } TEST_F(PreviewsServiceTest, TestNoScriptPreviewsEnabledByFeature) { +#if !defined(OS_ANDROID) + // For non-android, default is disabled. EXPECT_FALSE(previews_decider_impl()->IsPreviewEnabled( previews::PreviewsType::NOSCRIPT)); +#endif // defined(OS_ANDROID) + base::test::ScopedFeatureList scoped_feature_list; scoped_feature_list.InitAndEnableFeature( previews::features::kNoScriptPreviews);
diff --git a/chrome/browser/resources/chromeos/login/demo_preferences.js b/chrome/browser/resources/chromeos/login/demo_preferences.js index ca1b2809..5952902 100644 --- a/chrome/browser/resources/chromeos/login/demo_preferences.js +++ b/chrome/browser/resources/chromeos/login/demo_preferences.js
@@ -8,25 +8,12 @@ behaviors: [I18nBehavior, OobeDialogHostBehavior], properties: { - /** Currently selected system language (display name). */ - currentLanguage: { - type: String, - value: '', - }, - - /** Currently selected input method (display name). */ - currentKeyboard: { - type: String, - value: '', - }, - /** * List of languages for language selector dropdown. * @type {!Array<!OobeTypes.LanguageDsc>} */ languages: { type: Array, - observer: 'onLanguagesChanged_', }, /** @@ -35,25 +22,40 @@ */ keyboards: { type: Array, - observer: 'onKeyboardsChanged_', }, }, - /** @override */ - ready: function() { - this.i18nUpdateLocale(); - + /** Called after resources are updated. */ + updateLocalizedContent: function() { assert(loadTimeData); var languageList = loadTimeData.getValue('languageList'); this.setLanguageList_(languageList); var inputMethodsList = loadTimeData.getValue('inputMethodsList'); this.setInputMethods_(inputMethodsList); + + this.i18nUpdateLocale(); }, - /** Called after resources are updated. */ - updateLocalizedContent: function() { - this.i18nUpdateLocale(); + /** + * Sets selected keyboard. + * @param {string} keyboardId + */ + setSelectedKeyboard: function(keyboardId) { + var found = false; + for (var keyboard of this.keyboards) { + if (keyboard.value != keyboardId) { + keyboard.selected = false; + continue; + } + keyboard.selected = true; + found = true; + } + if (!found) + return; + + // Force i18n-dropdown to refresh. + this.keyboards = this.keyboards.slice(); }, /** @@ -75,29 +77,6 @@ }, /** - * Sets selected keyboard. - * @param {string} keyboardId - * @private - */ - setSelectedKeyboard_: function(keyboardId) { - var found = false; - for (var keyboard of this.keyboards) { - if (keyboard.value != keyboardId) { - keyboard.selected = false; - continue; - } - keyboard.selected = true; - found = true; - } - if (!found) - return; - - // Force i18n-dropdown to refresh. - this.keyboards = this.keyboards.slice(); - this.onKeyboardsChanged_(); - }, - - /** * Handle language selection. * @param {!{detail: {!OobeTypes.LanguageDsc}}} event * @private @@ -105,7 +84,6 @@ onLanguageSelected_: function(event) { var item = event.detail; var languageId = item.value; - this.currentLanguage = item.title; this.screen.onLanguageSelected_(languageId); }, @@ -117,27 +95,10 @@ onKeyboardSelected_: function(event) { var item = event.detail; var inputMethodId = item.value; - this.currentKeyboard = item.title; this.screen.onKeyboardSelected_(inputMethodId); }, /** - * Language changes handler. - * @private - */ - onLanguagesChanged_: function() { - this.currentLanguage = getSelectedTitle(this.languages); - }, - - /** - * Keyboard changes handler. - * @private - */ - onKeyboardsChanged_: function() { - this.currentKeyboard = getSelectedTitle(this.keyboards); - }, - - /** * Back button click handler. * @private */
diff --git a/chrome/browser/resources/chromeos/login/oobe_screen_demo_preferences.js b/chrome/browser/resources/chromeos/login/oobe_screen_demo_preferences.js index 005f1bdc..2f984ff 100644 --- a/chrome/browser/resources/chromeos/login/oobe_screen_demo_preferences.js +++ b/chrome/browser/resources/chromeos/login/oobe_screen_demo_preferences.js
@@ -10,26 +10,30 @@ var CONTEXT_KEY_LOCALE = 'locale'; var CONTEXT_KEY_INPUT_METHOD = 'input-method'; + var demoPreferencesModule = null; + return { + /** @override */ decorate: function() { - var demoPreferences = $('demo-preferences-content'); - demoPreferences.screen = this; + demoPreferencesModule = $('demo-preferences-content'); + demoPreferencesModule.screen = this; this.context.addObserver( CONTEXT_KEY_INPUT_METHOD, function(inputMethodId) { $('demo-preferences-content').setSelectedKeyboard(inputMethodId); }); + this.updateLocalizedContent(); }, /** Returns a control which should receive an initial focus. */ get defaultControl() { - return $('demo-preferences-content'); + return demoPreferencesModule; }, /** Called after resources are updated. */ updateLocalizedContent: function() { - $('demo-preferences-content').updateLocalizedContent(); + demoPreferencesModule.updateLocalizedContent(); }, /**
diff --git a/chrome/browser/resources/webauthn/2x/error_timeout.png b/chrome/browser/resources/webauthn/2x/error.png similarity index 100% rename from chrome/browser/resources/webauthn/2x/error_timeout.png rename to chrome/browser/resources/webauthn/2x/error.png Binary files differ
diff --git a/chrome/browser/resources/webauthn/error_timeout.png b/chrome/browser/resources/webauthn/error.png similarity index 100% rename from chrome/browser/resources/webauthn/error_timeout.png rename to chrome/browser/resources/webauthn/error.png Binary files differ
diff --git a/chrome/browser/signin/account_tracker_service_factory.cc b/chrome/browser/signin/account_tracker_service_factory.cc index 75a061e..6551c56 100644 --- a/chrome/browser/signin/account_tracker_service_factory.cc +++ b/chrome/browser/signin/account_tracker_service_factory.cc
@@ -7,7 +7,6 @@ #include <memory> #include "chrome/browser/profiles/profile.h" -#include "chrome/browser/signin/chrome_signin_client_factory.h" #include "components/keyed_service/content/browser_context_dependency_manager.h" #include "components/signin/core/browser/account_tracker_service.h" @@ -15,7 +14,6 @@ : BrowserContextKeyedServiceFactory( "AccountTrackerServiceFactory", BrowserContextDependencyManager::GetInstance()) { - DependsOn(ChromeSigninClientFactory::GetInstance()); } AccountTrackerServiceFactory::~AccountTrackerServiceFactory() { @@ -42,7 +40,6 @@ content::BrowserContext* context) const { Profile* profile = static_cast<Profile*>(context); AccountTrackerService* service = new AccountTrackerService(); - service->Initialize(ChromeSigninClientFactory::GetForProfile(profile), - profile->GetPath()); + service->Initialize(profile->GetPrefs(), profile->GetPath()); return service; }
diff --git a/chrome/browser/signin/dice_response_handler_unittest.cc b/chrome/browser/signin/dice_response_handler_unittest.cc index 9e1ef9be..9ea632c1 100644 --- a/chrome/browser/signin/dice_response_handler_unittest.cc +++ b/chrome/browser/signin/dice_response_handler_unittest.cc
@@ -153,7 +153,7 @@ &token_service_, &signin_manager_, &signin_client_, nullptr, std::move(account_reconcilor_delegate)); about_signin_internals_.Initialize(&signin_client_); - account_tracker_service_.Initialize(&signin_client_); + account_tracker_service_.Initialize(&pref_service_, base::FilePath()); account_reconcilor_->AddObserver(this); }
diff --git a/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate.h b/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate.h index 7043b02c..82da56e9 100644 --- a/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate.h +++ b/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate.h
@@ -22,6 +22,7 @@ #include "net/base/backoff_entry.h" #include "services/network/public/cpp/network_connection_tracker.h" +class SigninClient; namespace user_prefs { class PrefRegistrySyncable; }
diff --git a/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate_unittest.cc b/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate_unittest.cc index eada98a..555797e 100644 --- a/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate_unittest.cc +++ b/chrome/browser/signin/mutable_profile_oauth2_token_service_delegate_unittest.cc
@@ -110,7 +110,7 @@ client_->test_url_loader_factory()->AddResponse( GaiaUrls::GetInstance()->oauth2_revoke_url().spec(), ""); LoadTokenDatabase(); - account_tracker_service_.Initialize(client_.get()); + account_tracker_service_.Initialize(&pref_service_, base::FilePath()); } void TearDown() override { @@ -1045,7 +1045,7 @@ dict->SetString("gaia", base::UTF8ToUTF16(gaia_id)); update->Append(std::move(dict)); account_tracker_service_.Shutdown(); - account_tracker_service_.Initialize(client_.get()); + account_tracker_service_.Initialize(&pref_service_, base::FilePath()); AddAuthTokenManually("AccountId-" + email, "refresh_token"); oauth2_service_delegate_->LoadCredentials(gaia_id); @@ -1108,7 +1108,7 @@ dict->SetString("gaia", base::UTF8ToUTF16(gaia_id2)); update->Append(std::move(dict)); account_tracker_service_.Shutdown(); - account_tracker_service_.Initialize(client_.get()); + account_tracker_service_.Initialize(&pref_service_, base::FilePath()); AddAuthTokenManually("AccountId-" + email1, "refresh_token"); AddAuthTokenManually("AccountId-" + email2, "refresh_token");
diff --git a/chrome/browser/signin/process_dice_header_delegate_impl_unittest.cc b/chrome/browser/signin/process_dice_header_delegate_impl_unittest.cc index cc15bc3..fd1f8aa 100644 --- a/chrome/browser/signin/process_dice_header_delegate_impl_unittest.cc +++ b/chrome/browser/signin/process_dice_header_delegate_impl_unittest.cc
@@ -48,7 +48,7 @@ auth_error_(GoogleServiceAuthError::INVALID_GAIA_CREDENTIALS) { AccountTrackerService::RegisterPrefs(pref_service_.registry()); SigninManager::RegisterProfilePrefs(pref_service_.registry()); - account_tracker_service_.Initialize(&signin_client_); + account_tracker_service_.Initialize(&pref_service_, base::FilePath()); } ~ProcessDiceHeaderDelegateImplTest() override {
diff --git a/chrome/browser/sync/test/integration/quiesce_status_change_checker.cc b/chrome/browser/sync/test/integration/quiesce_status_change_checker.cc index 4c9896d..cc3550f8 100644 --- a/chrome/browser/sync/test/integration/quiesce_status_change_checker.cc +++ b/chrome/browser/sync/test/integration/quiesce_status_change_checker.cc
@@ -16,6 +16,21 @@ namespace { +// Compares two serialized progress markers for equivalence to determine client +// side progress. Some aspects of the progress markers like +// GarbageCollectionDirectives are irrelevant for this, as they can vary between +// requests -- for example a version_watermark could be based on request time. +bool AreProgressMarkersEquivalent(const std::string& serialized1, + const std::string& serialized2) { + sync_pb::DataTypeProgressMarker marker1; + sync_pb::DataTypeProgressMarker marker2; + CHECK(marker1.ParseFromString(serialized1)); + CHECK(marker2.ParseFromString(serialized2)); + marker1.clear_gc_directive(); + marker2.clear_gc_directive(); + return marker1.SerializeAsString() == marker2.SerializeAsString(); +} + // Returns true if these services have matching progress markers. bool ProgressMarkersMatch(const browser_sync::ProfileSyncService* service1, const browser_sync::ProfileSyncService* service2) { @@ -50,7 +65,7 @@ } // Fail if any of them don't match. - if (pm_it1->second != pm_it2->second) { + if (!AreProgressMarkersEquivalent(pm_it1->second, pm_it2->second)) { return false; } }
diff --git a/chrome/browser/sync/test/integration/single_client_wallet_sync_test.cc b/chrome/browser/sync/test/integration/single_client_wallet_sync_test.cc index e624001..bfffa42 100644 --- a/chrome/browser/sync/test/integration/single_client_wallet_sync_test.cc +++ b/chrome/browser/sync/test/integration/single_client_wallet_sync_test.cc
@@ -32,9 +32,9 @@ using autofill::AutofillProfile; using autofill::CreditCard; using autofill::data_util::TruncateUTF8; +using autofill_helper::GetAccountWebDataService; using autofill_helper::GetPersonalDataManager; using autofill_helper::GetProfileWebDataService; -using autofill_helper::GetAccountWebDataService; using base::ASCIIToUTF16; namespace { @@ -121,10 +121,15 @@ return std::move(consumer.result()); } -void AddDefaultCard(fake_server::FakeServer* server) { - sync_pb::EntitySpecifics specifics; +sync_pb::SyncEntity CreateDefaultSyncWalletCard() { + sync_pb::SyncEntity entity; + entity.set_name(kDefaultCardID); + entity.set_id_string(kDefaultCardID); + entity.set_version(0); // Will be overridden by the fake server. + entity.set_ctime(12345); + entity.set_mtime(12345); sync_pb::AutofillWalletSpecifics* wallet_specifics = - specifics.mutable_autofill_wallet(); + entity.mutable_specifics()->mutable_autofill_wallet(); wallet_specifics->set_type( sync_pb::AutofillWalletSpecifics::MASKED_CREDIT_CARD); @@ -138,10 +143,7 @@ credit_card->set_status(sync_pb::WalletMaskedCreditCard::VALID); credit_card->set_type(kDefaultCardType); credit_card->set_billing_address_id(kDefaultBillingAddressId); - - server->InjectEntity( - syncer::PersistentUniqueClientEntity::CreateFromEntitySpecifics( - kDefaultCardID, specifics, 12345, 12345)); + return entity; } CreditCard GetDefaultCreditCard() { @@ -158,10 +160,16 @@ return card; } -void AddDefaultProfile(fake_server::FakeServer* server) { - sync_pb::EntitySpecifics specifics; +sync_pb::SyncEntity CreateDefaultSyncWalletAddress() { + sync_pb::SyncEntity entity; + entity.set_name(kDefaultAddressID); + entity.set_id_string(kDefaultAddressID); + entity.set_version(0); // Will be overridden by the fake server. + entity.set_ctime(12345); + entity.set_mtime(12345); + sync_pb::AutofillWalletSpecifics* wallet_specifics = - specifics.mutable_autofill_wallet(); + entity.mutable_specifics()->mutable_autofill_wallet(); wallet_specifics->set_type(sync_pb::AutofillWalletSpecifics::POSTAL_ADDRESS); sync_pb::WalletPostalAddress* wallet_address = @@ -179,9 +187,7 @@ wallet_address->set_sorting_code(kDefaultSortingCode); wallet_address->set_language_code(kDefaultLanguageCode); - server->InjectEntity( - syncer::PersistentUniqueClientEntity::CreateFromEntitySpecifics( - kDefaultAddressID, specifics, 12345, 12345)); + return entity; } // TODO(sebsg): Instead add a function to create a card, and one to inject in @@ -279,7 +285,7 @@ : public UssSwitchToggler, public SingleClientWalletSyncTest { public: - SingleClientWalletSyncTestIncludingUssTests(){}; + SingleClientWalletSyncTestIncludingUssTests() {} ~SingleClientWalletSyncTestIncludingUssTests() override {} private: @@ -304,8 +310,8 @@ {}, // Disabled. {autofill::features::kAutofillEnableAccountWalletStorage}); - AddDefaultProfile(GetFakeServer()); - AddDefaultCard(GetFakeServer()); + GetFakeServer()->SetWalletData( + {CreateDefaultSyncWalletAddress(), CreateDefaultSyncWalletCard()}); ASSERT_TRUE(SetupSync()); auto profile_data = GetProfileWebDataService(0); @@ -345,8 +351,9 @@ {}); ASSERT_TRUE(SetupClients()); - AddDefaultCard(GetFakeServer()); - AddDefaultProfile(GetFakeServer()); + + GetFakeServer()->SetWalletData( + {CreateDefaultSyncWalletAddress(), CreateDefaultSyncWalletCard()}); ASSERT_TRUE(GetClient(0)->SignIn()); ASSERT_TRUE(GetClient(0)->AwaitEngineInitialization( @@ -384,8 +391,8 @@ // Wallet data should get cleared from the database when sync is disabled. IN_PROC_BROWSER_TEST_F(SingleClientWalletSyncTest, ClearOnDisableSync) { - AddDefaultCard(GetFakeServer()); - AddDefaultProfile(GetFakeServer()); + GetFakeServer()->SetWalletData( + {CreateDefaultSyncWalletAddress(), CreateDefaultSyncWalletCard()}); ASSERT_TRUE(SetupSync()); // Make sure the card is in the DB. @@ -403,8 +410,8 @@ // Wallet data should get cleared from the database when the wallet sync type // flag is disabled. IN_PROC_BROWSER_TEST_F(SingleClientWalletSyncTest, ClearOnDisableWalletSync) { - AddDefaultCard(GetFakeServer()); - AddDefaultProfile(GetFakeServer()); + GetFakeServer()->SetWalletData( + {CreateDefaultSyncWalletAddress(), CreateDefaultSyncWalletCard()}); ASSERT_TRUE(SetupSync()); // Make sure the card is in the DB. @@ -423,8 +430,8 @@ // integration flag is disabled. IN_PROC_BROWSER_TEST_F(SingleClientWalletSyncTest, ClearOnDisableWalletAutofill) { - AddDefaultCard(GetFakeServer()); - AddDefaultProfile(GetFakeServer()); + GetFakeServer()->SetWalletData( + {CreateDefaultSyncWalletAddress(), CreateDefaultSyncWalletCard()}); ASSERT_TRUE(SetupSync()); // Make sure the card is in the DB. @@ -475,7 +482,7 @@ profiles[0]->GetRawInfo(autofill::COMPANY_NAME)))); // Add a new card from the server and sync it down. - AddDefaultCard(GetFakeServer()); + GetFakeServer()->SetWalletData({CreateDefaultSyncWalletCard()}); ASSERT_TRUE(SetupSync()); // The only card present on the client should be the one from the server. @@ -522,7 +529,7 @@ EXPECT_EQ("a123", cards[0]->server_id()); // Add a new profile from the server and sync it down. - AddDefaultProfile(GetFakeServer()); + GetFakeServer()->SetWalletData({CreateDefaultSyncWalletAddress()}); ASSERT_TRUE(SetupSync()); // The only profile present on the client should be the one from the server. @@ -562,7 +569,7 @@ // Sync the same card from the server, except with a default billing address // id. - AddDefaultCard(GetFakeServer()); + GetFakeServer()->SetWalletData({CreateDefaultSyncWalletCard()}); ASSERT_TRUE(SetupSync()); // The billing address is should still refer to the local profile. @@ -597,7 +604,7 @@ // Sync the same card from the server, except with a default billing address // id. - AddDefaultCard(GetFakeServer()); + GetFakeServer()->SetWalletData({CreateDefaultSyncWalletCard()}); ASSERT_TRUE(SetupSync()); // The billing address should be the one from the server card.
diff --git a/chrome/browser/translate/translate_manager_render_view_host_unittest.cc b/chrome/browser/translate/translate_manager_render_view_host_unittest.cc index 24ba4a2..d56e4c1 100644 --- a/chrome/browser/translate/translate_manager_render_view_host_unittest.cc +++ b/chrome/browser/translate/translate_manager_render_view_host_unittest.cc
@@ -474,8 +474,7 @@ // Clears the translate script so it is fetched every time and sets the // expiration delay to a large value by default (in case it was zeroed in a // previous test). - TranslateService::InitializeForTesting( - network::mojom::ConnectionType::CONNECTION_WIFI); + TranslateService::InitializeForTesting(); translate::TranslateDownloadManager* download_manager = translate::TranslateDownloadManager::GetInstance(); download_manager->ClearTranslateScriptForTesting();
diff --git a/chrome/browser/translate/translate_service.cc b/chrome/browser/translate/translate_service.cc index 14be91b..aa44331 100644 --- a/chrome/browser/translate/translate_service.cc +++ b/chrome/browser/translate/translate_service.cc
@@ -19,7 +19,6 @@ #include "components/prefs/pref_service.h" #include "components/translate/core/browser/translate_download_manager.h" #include "components/translate/core/browser/translate_manager.h" -#include "content/public/browser/network_service_instance.h" #include "content/public/common/url_constants.h" #include "url/gurl.h" @@ -30,15 +29,14 @@ namespace { // The singleton instance of TranslateService. -TranslateService* g_translate_service = nullptr; +TranslateService* g_translate_service = NULL; } TranslateService::TranslateService() : resource_request_allowed_notifier_( g_browser_process->local_state(), - switches::kDisableBackgroundNetworking, - base::BindOnce(&content::GetNetworkConnectionTracker)) { - resource_request_allowed_notifier_.Init(this, true /* leaky */); + switches::kDisableBackgroundNetworking) { + resource_request_allowed_notifier_.Init(this); } TranslateService::~TranslateService() {} @@ -77,18 +75,14 @@ } // static -void TranslateService::InitializeForTesting( - network::mojom::ConnectionType type) { +void TranslateService::InitializeForTesting() { if (!g_translate_service) { TranslateService::Initialize(); translate::TranslateManager::SetIgnoreMissingKeyForTesting(true); } else { translate::TranslateDownloadManager::GetInstance()->ResetForTesting(); + g_translate_service->OnResourceRequestsAllowed(); } - - g_translate_service->resource_request_allowed_notifier_ - .SetConnectionTypeForTesting(type); - g_translate_service->OnResourceRequestsAllowed(); } // static
diff --git a/chrome/browser/translate/translate_service.h b/chrome/browser/translate/translate_service.h index 8cd6b36..8b8901d 100644 --- a/chrome/browser/translate/translate_service.h +++ b/chrome/browser/translate/translate_service.h
@@ -27,7 +27,7 @@ // Initializes the TranslateService in a way that it can be initialized // multiple times in a unit test suite (once for each test). Should be paired // with ShutdownForTesting at the end of the test. - static void InitializeForTesting(network::mojom::ConnectionType type); + static void InitializeForTesting(); // Shuts down the TranslateService at the end of a test in a way that the next // test can initialize and use the service.
diff --git a/chrome/browser/translate/translate_service_unittest.cc b/chrome/browser/translate/translate_service_unittest.cc index 99c79b5..5e925d16 100644 --- a/chrome/browser/translate/translate_service_unittest.cc +++ b/chrome/browser/translate/translate_service_unittest.cc
@@ -10,7 +10,6 @@ #include "components/prefs/testing_pref_service.h" #include "components/translate/core/browser/translate_download_manager.h" #include "content/public/common/url_constants.h" -#include "content/public/test/test_browser_thread_bundle.h" #include "testing/gtest/include/gtest/gtest.h" #include "url/gurl.h" @@ -50,9 +49,7 @@ // Tests that download and history URLs are not translatable. TEST(TranslateServiceTest, DownloadsAndHistoryNotTranslated) { - content::TestBrowserThreadBundle thread_bundle; - TranslateService::InitializeForTesting( - network::mojom::ConnectionType::CONNECTION_WIFI); + TranslateService::InitializeForTesting(); EXPECT_FALSE( TranslateService::IsTranslatableURL(GURL(chrome::kChromeUIDownloadsURL))); EXPECT_FALSE(
diff --git a/chrome/browser/ui/ash/launcher/chrome_launcher_controller_unittest.cc b/chrome/browser/ui/ash/launcher/chrome_launcher_controller_unittest.cc index 45631b6d..d2dd126d 100644 --- a/chrome/browser/ui/ash/launcher/chrome_launcher_controller_unittest.cc +++ b/chrome/browser/ui/ash/launcher/chrome_launcher_controller_unittest.cc
@@ -107,6 +107,7 @@ #include "extensions/browser/app_window/native_app_window.h" #include "extensions/common/extension.h" #include "extensions/common/manifest_constants.h" +#include "extensions/grit/extensions_browser_resources.h" #include "testing/gtest/include/gtest/gtest.h" #include "ui/aura/client/window_parenting_client.h" #include "ui/aura/window.h" @@ -116,6 +117,7 @@ #include "ui/display/screen.h" #include "ui/events/base_event_utils.h" #include "ui/events/event_constants.h" +#include "ui/gfx/image/image_skia_operations.h" #include "ui/gfx/image/image_unittest_util.h" #include "ui/views/widget/widget.h" @@ -313,6 +315,35 @@ set_delegate_count_++; } + // Helper that waits for idle and extracts the non-default bitmap from the + // last updated item in shelf controller. + SkBitmap GetLastItemImage() { + if (default_app_image_.isNull()) { + default_app_image_ = + *gfx::ImageSkiaOperations::CreateResizedImage( + *ui::ResourceBundle::GetSharedInstance().GetImageSkiaNamed( + IDR_APP_DEFAULT_ICON), + skia::ImageOperations::RESIZE_BEST, + gfx::Size(extension_misc::EXTENSION_ICON_SMALL, + extension_misc::EXTENSION_ICON_SMALL)) + .bitmap(); + } + + // Loading icon is multistep process. At first step default app icon is + // loaded while real icon is requested and decoded. + // base::RunLoop().RunUntilIdle() hides these steps and in most cases real + // icon is returned afterward. However in rare cases default icon is left + // after base::RunLoop().RunUntilIdle(). So make sure we don't return + // default icon that may fail test expectations. + while (true) { + base::RunLoop().RunUntilIdle(); + const SkBitmap* bitmap = last_item().image.bitmap(); + CHECK(bitmap); + if (!gfx::test::AreBitmapsEqual(default_app_image_, *bitmap)) + return *bitmap; + } + } + private: size_t added_count_ = 0; size_t removed_count_ = 0; @@ -323,6 +354,9 @@ ash::mojom::ShelfObserverAssociatedPtr observer_; mojo::Binding<ash::mojom::ShelfController> binding_; + // Used to cache default app image. + SkBitmap default_app_image_; + DISALLOW_COPY_AND_ASSIGN(TestShelfController); }; @@ -335,15 +369,6 @@ ash::LAUNCH_FROM_UNKNOWN, base::DoNothing()); } -// Helper that waits for idle and extracts the bitmap from the last updated item -// in shelf controller. -SkBitmap GetLastItemImage(TestShelfController* shelf_controller) { - base::RunLoop().RunUntilIdle(); - const SkBitmap* bitmap = shelf_controller->last_item().image.bitmap(); - CHECK(bitmap); - return *bitmap; -} - // Creates a window with TYPE_APP shelf item type and the given app_id. views::Widget* CreateShelfAppWindow(const std::string& app_id) { views::Widget::InitParams params(views::Widget::InitParams::TYPE_WINDOW); @@ -2409,7 +2434,7 @@ GetPinnedAppStatus()); } -TEST_P(ChromeLauncherControllerWithArcTest, DISABLED_ArcCustomAppIcon) { +TEST_P(ChromeLauncherControllerWithArcTest, ArcCustomAppIcon) { InitLauncherController(); TestShelfController* shelf_controller = @@ -2450,55 +2475,55 @@ model_->GetShelfItemDelegate(ash::ShelfID(arc_app_id)); ASSERT_TRUE(item_delegate); base::RunLoop().RunUntilIdle(); - const SkBitmap default_icon = GetLastItemImage(shelf_controller); + const SkBitmap default_icon = shelf_controller->GetLastItemImage(); // No custom icon set. Acitivating windows should not change icon. window1->Activate(); EXPECT_TRUE(gfx::test::AreBitmapsEqual(default_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); window2->Activate(); EXPECT_TRUE(gfx::test::AreBitmapsEqual(default_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); // Set custom icon on active item. Icon should change to custom. arc_test_.app_instance()->SendTaskDescription(2, std::string(), png_data); - const SkBitmap custom_icon = GetLastItemImage(shelf_controller); + const SkBitmap custom_icon = shelf_controller->GetLastItemImage(); EXPECT_FALSE(gfx::test::AreBitmapsEqual(default_icon, custom_icon)); // Switch back to the item without custom icon. Icon should be changed to // default. window1->Activate(); EXPECT_TRUE(gfx::test::AreBitmapsEqual(default_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); // Test that setting an invalid icon should not change custom icon. arc_test_.app_instance()->SendTaskDescription(1, std::string(), png_data); EXPECT_TRUE(gfx::test::AreBitmapsEqual(custom_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); arc_test_.app_instance()->SendTaskDescription(1, std::string(), invalid_png_data); EXPECT_TRUE(gfx::test::AreBitmapsEqual(custom_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); // Check window removing with active custom icon. Reseting custom icon of // inactive window doesn't reset shelf icon. arc_test_.app_instance()->SendTaskDescription(2, std::string(), std::string()); EXPECT_TRUE(gfx::test::AreBitmapsEqual(custom_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); // Set custom icon back to validate closing active window later. arc_test_.app_instance()->SendTaskDescription(2, std::string(), png_data); EXPECT_TRUE(gfx::test::AreBitmapsEqual(custom_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); // Reseting custom icon of active window resets shelf icon. arc_test_.app_instance()->SendTaskDescription(1, std::string(), std::string()); EXPECT_TRUE(gfx::test::AreBitmapsEqual(default_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); window1->CloseNow(); EXPECT_TRUE(gfx::test::AreBitmapsEqual(custom_icon, - GetLastItemImage(shelf_controller))); + shelf_controller->GetLastItemImage())); } // Check that with multi profile V1 apps are properly added / removed from the
diff --git a/chrome/browser/ui/media_router/presentation_receiver_window_controller_browsertest.cc b/chrome/browser/ui/media_router/presentation_receiver_window_controller_browsertest.cc index 52bd8f6..f57076e6e 100644 --- a/chrome/browser/ui/media_router/presentation_receiver_window_controller_browsertest.cc +++ b/chrome/browser/ui/media_router/presentation_receiver_window_controller_browsertest.cc
@@ -40,8 +40,6 @@ namespace { -using RenderFrameHostId = std::pair<int, int>; - constexpr char kPresentationId[] = "test_id"; const base::FilePath::StringPieceType kResourcePath = FILE_PATH_LITERAL("media/router/"); @@ -294,7 +292,7 @@ browser()->profile()) ->RegisterLocalPresentationController( blink::mojom::PresentationInfo(presentation_url, kPresentationId), - RenderFrameHostId(0, 0), std::move(controller_ptr), + content::GlobalFrameRoutingId(0, 0), std::move(controller_ptr), controller_connection.MakeConnectionRequest(), media_router::MediaRoute("route", media_router::MediaSource(presentation_url),
diff --git a/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.cc b/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.cc index 19258bf..982cb16 100644 --- a/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.cc +++ b/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.cc
@@ -70,3 +70,8 @@ if (IsActiveInputContextHandler(input_method_chromeos_.get())) input_method_chromeos_->CancelComposition(client_.get()); } + +void InputMethodBridge::ShowVirtualKeyboardIfEnabled() { + if (IsActiveInputContextHandler(input_method_chromeos_.get())) + input_method_chromeos_->ShowVirtualKeyboardIfEnabled(); +}
diff --git a/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.h b/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.h index 0d99164..90610b6 100644 --- a/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.h +++ b/chrome/browser/ui/views/ime_driver/input_method_bridge_chromeos.h
@@ -32,6 +32,7 @@ void ProcessKeyEvent(std::unique_ptr<ui::Event> key_event, ProcessKeyEventCallback callback) override; void CancelComposition() override; + void ShowVirtualKeyboardIfEnabled() override; private: std::unique_ptr<RemoteTextInputClient> client_;
diff --git a/chrome/browser/ui/views/ime_driver/simple_input_method.cc b/chrome/browser/ui/views/ime_driver/simple_input_method.cc index 0dd51a3..dcde6e6 100644 --- a/chrome/browser/ui/views/ime_driver/simple_input_method.cc +++ b/chrome/browser/ui/views/ime_driver/simple_input_method.cc
@@ -11,13 +11,24 @@ SimpleInputMethod::~SimpleInputMethod() {} void SimpleInputMethod::OnTextInputTypeChanged( - ui::TextInputType text_input_type) {} + ui::TextInputType text_input_type) { + NOTIMPLEMENTED_LOG_ONCE(); +} -void SimpleInputMethod::OnCaretBoundsChanged(const gfx::Rect& caret_bounds) {} +void SimpleInputMethod::OnCaretBoundsChanged(const gfx::Rect& caret_bounds) { + NOTIMPLEMENTED_LOG_ONCE(); +} void SimpleInputMethod::ProcessKeyEvent(std::unique_ptr<ui::Event> key_event, ProcessKeyEventCallback callback) { + NOTIMPLEMENTED_LOG_ONCE(); std::move(callback).Run(false); } -void SimpleInputMethod::CancelComposition() {} +void SimpleInputMethod::CancelComposition() { + NOTIMPLEMENTED_LOG_ONCE(); +} + +void SimpleInputMethod::ShowVirtualKeyboardIfEnabled() { + NOTIMPLEMENTED_LOG_ONCE(); +}
diff --git a/chrome/browser/ui/views/ime_driver/simple_input_method.h b/chrome/browser/ui/views/ime_driver/simple_input_method.h index f262c21..4b9f33e 100644 --- a/chrome/browser/ui/views/ime_driver/simple_input_method.h +++ b/chrome/browser/ui/views/ime_driver/simple_input_method.h
@@ -22,6 +22,7 @@ void ProcessKeyEvent(std::unique_ptr<ui::Event> key_event, ProcessKeyEventCallback callback) override; void CancelComposition() override; + void ShowVirtualKeyboardIfEnabled() override; private: DISALLOW_COPY_AND_ASSIGN(SimpleInputMethod);
diff --git a/chrome/browser/ui/views/payments/payment_request_dialog_view.cc b/chrome/browser/ui/views/payments/payment_request_dialog_view.cc index 5d4f784a..6668837 100644 --- a/chrome/browser/ui/views/payments/payment_request_dialog_view.cc +++ b/chrome/browser/ui/views/payments/payment_request_dialog_view.cc
@@ -146,19 +146,6 @@ constrained_window::ShowWebModalDialogViews(this, request_->web_contents()); } -void PaymentRequestDialogView::ShowDialogAtPaymentHandlerSheet( - const GURL& url, - PaymentHandlerOpenWindowCallback callback) { - view_stack_->Push(CreateViewAndInstallController( - std::make_unique<PaymentHandlerWebFlowViewController>( - request_->spec(), request_->state(), this, - GetProfile(), url, std::move(callback)), - &controller_map_), - /* animate = */ false); - HideProcessingSpinner(); - ShowDialog(); -} - void PaymentRequestDialogView::CloseDialog() { // This calls PaymentRequestDialogView::Cancel() before closing. // ViewHierarchyChanged() also gets called after Cancel(). @@ -235,6 +222,14 @@ } void PaymentRequestDialogView::GoBack() { + // If payment request UI is skipped when calling PaymentRequest.show, then + // abort payment request when back button is clicked. This only happens for + // service worker based payment handler under circumstance. + if (request_->skipped_payment_request_ui()) { + CloseDialog(); + return; + } + view_stack_->Pop(); if (observer_for_testing_)
diff --git a/chrome/browser/ui/views/payments/payment_request_dialog_view.h b/chrome/browser/ui/views/payments/payment_request_dialog_view.h index 6037b176..652570d 100644 --- a/chrome/browser/ui/views/payments/payment_request_dialog_view.h +++ b/chrome/browser/ui/views/payments/payment_request_dialog_view.h
@@ -106,9 +106,6 @@ // payments::PaymentRequestDialog: void ShowDialog() override; - void ShowDialogAtPaymentHandlerSheet( - const GURL& url, - PaymentHandlerOpenWindowCallback callback) override; void CloseDialog() override; void ShowErrorMessage() override; void ShowProcessingSpinner() override;
diff --git a/chrome/browser/ui/views/webauthn/sheet_view_factory.cc b/chrome/browser/ui/views/webauthn/sheet_view_factory.cc index 8056592..0af22da 100644 --- a/chrome/browser/ui/views/webauthn/sheet_view_factory.cc +++ b/chrome/browser/ui/views/webauthn/sheet_view_factory.cc
@@ -57,6 +57,15 @@ std::make_unique<AuthenticatorNoAvailableTransportsErrorModel>( dialog_model)); break; + case Step::kErrorKeyNotRegistered: + sheet_view = std::make_unique<AuthenticatorRequestSheetView>( + std::make_unique<AuthenticatorNotRegisteredErrorModel>(dialog_model)); + break; + case Step::kErrorKeyAlreadyRegistered: + sheet_view = std::make_unique<AuthenticatorRequestSheetView>( + std::make_unique<AuthenticatorAlreadyRegisteredErrorModel>( + dialog_model)); + break; case Step::kBlePowerOnManual: sheet_view = std::make_unique<AuthenticatorRequestSheetView>( std::make_unique<AuthenticatorBlePowerOnManualSheetModel>(
diff --git a/chrome/browser/ui/webauthn/authenticator_dialog_browsertest.cc b/chrome/browser/ui/webauthn/authenticator_dialog_browsertest.cc index 3eb7696..ebdfd3e 100644 --- a/chrome/browser/ui/webauthn/authenticator_dialog_browsertest.cc +++ b/chrome/browser/ui/webauthn/authenticator_dialog_browsertest.cc
@@ -42,12 +42,18 @@ } else if (name == "activate_usb") { model->SetCurrentStep( AuthenticatorRequestDialogModel::Step::kUsbInsertAndActivate); - } else if (name == "no_available_transports") { - model->SetCurrentStep( - AuthenticatorRequestDialogModel::Step::kErrorNoAvailableTransports); } else if (name == "timeout") { model->SetCurrentStep( AuthenticatorRequestDialogModel::Step::kErrorTimedOut); + } else if (name == "no_available_transports") { + model->SetCurrentStep( + AuthenticatorRequestDialogModel::Step::kErrorNoAvailableTransports); + } else if (name == "key_not_registered") { + model->SetCurrentStep( + AuthenticatorRequestDialogModel::Step::kErrorKeyNotRegistered); + } else if (name == "key_already_registered") { + model->SetCurrentStep( + AuthenticatorRequestDialogModel::Step::kErrorKeyAlreadyRegistered); } else if (name == "ble_power_on_manual") { model->SetCurrentStep( AuthenticatorRequestDialogModel::Step::kBlePowerOnManual); @@ -112,6 +118,15 @@ ShowAndVerifyUi(); } +IN_PROC_BROWSER_TEST_F(AuthenticatorDialogTest, InvokeUi_key_not_registered) { + ShowAndVerifyUi(); +} + +IN_PROC_BROWSER_TEST_F(AuthenticatorDialogTest, + InvokeUi_key_already_registered) { + ShowAndVerifyUi(); +} + IN_PROC_BROWSER_TEST_F(AuthenticatorDialogTest, InvokeUi_ble_power_on_manual) { ShowAndVerifyUi(); }
diff --git a/chrome/browser/ui/webauthn/sheet_models.cc b/chrome/browser/ui/webauthn/sheet_models.cc index 78a9090..815616f 100644 --- a/chrome/browser/ui/webauthn/sheet_models.cc +++ b/chrome/browser/ui/webauthn/sheet_models.cc
@@ -170,7 +170,7 @@ // AuthenticatorTimeoutErrorModel --------------------------------------------- gfx::ImageSkia* AuthenticatorTimeoutErrorModel::GetStepIllustration() const { - return GetImage(IDR_WEBAUTHN_ILLUSTRATION_ERROR_TIMEOUT_1X); + return GetImage(IDR_WEBAUTHN_ILLUSTRATION_ERROR_1X); } base::string16 AuthenticatorTimeoutErrorModel::GetStepTitle() const { @@ -194,7 +194,7 @@ gfx::ImageSkia* AuthenticatorNoAvailableTransportsErrorModel::GetStepIllustration() const { - return GetImage(IDR_WEBAUTHN_ILLUSTRATION_ERROR_TIMEOUT_1X); + return GetImage(IDR_WEBAUTHN_ILLUSTRATION_ERROR_1X); } base::string16 AuthenticatorNoAvailableTransportsErrorModel::GetStepTitle() @@ -208,6 +208,72 @@ IDS_WEBAUTHN_ERROR_NO_TRANSPORTS_DESCRIPTION); } +// AuthenticatorNotRegisteredErrorModel --------------------------------------- + +gfx::ImageSkia* AuthenticatorNotRegisteredErrorModel::GetStepIllustration() + const { + return GetImage(IDR_WEBAUTHN_ILLUSTRATION_ERROR_1X); +} + +base::string16 AuthenticatorNotRegisteredErrorModel::GetStepTitle() const { + return l10n_util::GetStringUTF16(IDS_WEBAUTHN_ERROR_WRONG_KEY_SIGN_TITLE); +} + +base::string16 AuthenticatorNotRegisteredErrorModel::GetStepDescription() + const { + return l10n_util::GetStringUTF16( + IDS_WEBAUTHN_ERROR_WRONG_KEY_SIGN_DESCRIPTION); +} + +bool AuthenticatorNotRegisteredErrorModel::IsAcceptButtonVisible() const { + return true; +} + +bool AuthenticatorNotRegisteredErrorModel::IsAcceptButtonEnabled() const { + return true; +} + +base::string16 AuthenticatorNotRegisteredErrorModel::GetAcceptButtonLabel() + const { + // TODO(engedy): This should use a separate string resource. + return l10n_util::GetStringUTF16(IDS_WEBAUTHN_BLUETOOTH_POWER_ON_MANUAL_NEXT); +} + +void AuthenticatorNotRegisteredErrorModel::OnAccept() {} + +// AuthenticatorAlreadyRegisteredErrorModel ----------------------------------- + +gfx::ImageSkia* AuthenticatorAlreadyRegisteredErrorModel::GetStepIllustration() + const { + return GetImage(IDR_WEBAUTHN_ILLUSTRATION_ERROR_1X); +} + +base::string16 AuthenticatorAlreadyRegisteredErrorModel::GetStepTitle() const { + return l10n_util::GetStringUTF16(IDS_WEBAUTHN_ERROR_WRONG_KEY_REGISTER_TITLE); +} + +base::string16 AuthenticatorAlreadyRegisteredErrorModel::GetStepDescription() + const { + return l10n_util::GetStringUTF16( + IDS_WEBAUTHN_ERROR_WRONG_KEY_REGISTER_DESCRIPTION); +} + +bool AuthenticatorAlreadyRegisteredErrorModel::IsAcceptButtonVisible() const { + return true; +} + +bool AuthenticatorAlreadyRegisteredErrorModel::IsAcceptButtonEnabled() const { + return true; +} + +base::string16 AuthenticatorAlreadyRegisteredErrorModel::GetAcceptButtonLabel() + const { + // TODO(engedy): This should use a separate string resource. + return l10n_util::GetStringUTF16(IDS_WEBAUTHN_BLUETOOTH_POWER_ON_MANUAL_NEXT); +} + +void AuthenticatorAlreadyRegisteredErrorModel::OnAccept() {} + // AuthenticatorBlePowerOnManualSheetModel ------------------------------------ gfx::ImageSkia* AuthenticatorBlePowerOnManualSheetModel::GetStepIllustration()
diff --git a/chrome/browser/ui/webauthn/sheet_models.h b/chrome/browser/ui/webauthn/sheet_models.h index 315b103..2d9b3835 100644 --- a/chrome/browser/ui/webauthn/sheet_models.h +++ b/chrome/browser/ui/webauthn/sheet_models.h
@@ -125,6 +125,38 @@ base::string16 GetStepDescription() const override; }; +class AuthenticatorNotRegisteredErrorModel + : public AuthenticatorSheetModelBase { + public: + using AuthenticatorSheetModelBase::AuthenticatorSheetModelBase; + + private: + // AuthenticatorSheetModelBase: + gfx::ImageSkia* GetStepIllustration() const override; + base::string16 GetStepTitle() const override; + base::string16 GetStepDescription() const override; + bool IsAcceptButtonVisible() const override; + bool IsAcceptButtonEnabled() const override; + base::string16 GetAcceptButtonLabel() const override; + void OnAccept() override; +}; + +class AuthenticatorAlreadyRegisteredErrorModel + : public AuthenticatorSheetModelBase { + public: + using AuthenticatorSheetModelBase::AuthenticatorSheetModelBase; + + private: + // AuthenticatorSheetModelBase: + gfx::ImageSkia* GetStepIllustration() const override; + base::string16 GetStepTitle() const override; + base::string16 GetStepDescription() const override; + bool IsAcceptButtonVisible() const override; + bool IsAcceptButtonEnabled() const override; + base::string16 GetAcceptButtonLabel() const override; + void OnAccept() override; +}; + class AuthenticatorBlePowerOnManualSheetModel : public AuthenticatorSheetModelBase { public:
diff --git a/chrome/browser/ui/webui/certificates_handler.cc b/chrome/browser/ui/webui/certificates_handler.cc index 655fcbe..57ccbca 100644 --- a/chrome/browser/ui/webui/certificates_handler.cc +++ b/chrome/browser/ui/webui/certificates_handler.cc
@@ -42,11 +42,6 @@ #include "net/der/parser.h" #include "ui/base/l10n/l10n_util.h" -#if defined(OS_CHROMEOS) -#include "chrome/browser/chromeos/policy/user_network_configuration_updater.h" -#include "chrome/browser/chromeos/policy/user_network_configuration_updater_factory.h" -#endif - using base::UTF8ToUTF16; namespace { @@ -57,10 +52,13 @@ static const char kCertificatesHandlerKeyField[] = "id"; static const char kCertificatesHandlerNameField[] = "name"; static const char kCertificatesHandlerObjSignField[] = "objSign"; -static const char kCertificatesHandlerPolicyField[] = "policy"; +static const char kCertificatesHandlerPolicyInstalledField[] = "policy"; +static const char kCertificatesHandlerWebTrustAnchorField[] = "webTrustAnchor"; static const char kCertificatesHandlerReadonlyField[] = "readonly"; static const char kCertificatesHandlerSslField[] = "ssl"; static const char kCertificatesHandlerSubnodesField[] = "subnodes"; +static const char kCertificatesHandlerContainsPolicyCertsField[] = + "containsPolicyCerts"; static const char kCertificatesHandlerUntrustedField[] = "untrusted"; // Field names for communicating erros to JS. @@ -70,7 +68,7 @@ static const char kCertificatesHandlerErrorTitle[] = "title"; // Enumeration of different callers of SelectFile. (Start counting at 1 so -// if SelectFile is accidentally called with params=NULL it won't match any.) +// if SelectFile is accidentally called with params=nullptr it won't match any.) enum { EXPORT_PERSONAL_FILE_SELECTED = 1, IMPORT_PERSONAL_FILE_SELECTED, @@ -99,7 +97,7 @@ base::string16 b_str; a_dict->GetString(kCertificatesHandlerNameField, &a_str); b_dict->GetString(kCertificatesHandlerNameField, &b_str); - if (collator_ == NULL) + if (collator_ == nullptr) return a_str < b_str; return base::i18n::CompareString16WithCollator(*collator_, a_str, b_str) == UCOL_LESS; @@ -132,13 +130,6 @@ CERTCertificate* cert_; }; -// Determine whether a certificate was stored with web trust by a policy. -bool IsPolicyInstalledWithWebTrust(const net::CertificateList& web_trust_certs, - CERTCertificate* cert) { - return std::find_if(web_trust_certs.begin(), web_trust_certs.end(), - CertEquals(cert)) != web_trust_certs.end(); -} - // Determine if |data| could be a PFX Protocol Data Unit. // This only does the minimum parsing necessary to distinguish a PFX file from a // DER encoded Certificate. @@ -226,12 +217,12 @@ CERTCertificate* CertIdMap::CallbackArgsToCert(const base::ListValue* args) { std::string node_id; if (!args->GetString(0, &node_id)) - return NULL; + return nullptr; CERTCertificate* cert = IdToCert(node_id); if (!cert) { NOTREACHED(); - return NULL; + return nullptr; } return cert; @@ -414,18 +405,10 @@ } void CertificatesHandler::CertificatesRefreshed() { - net::CertificateList web_trusted_certs; -#if defined(OS_CHROMEOS) - policy::UserNetworkConfigurationUpdater* service = - policy::UserNetworkConfigurationUpdaterFactory::GetForProfile( - Profile::FromWebUI(web_ui())); - if (service) - web_trusted_certs = service->GetWebTrustedCertificates(); -#endif - PopulateTree("personalCerts", net::USER_CERT, web_trusted_certs); - PopulateTree("serverCerts", net::SERVER_CERT, web_trusted_certs); - PopulateTree("caCerts", net::CA_CERT, web_trusted_certs); - PopulateTree("otherCerts", net::OTHER_CERT, web_trusted_certs); + PopulateTree("personalCerts", net::USER_CERT); + PopulateTree("serverCerts", net::SERVER_CERT); + PopulateTree("caCerts", net::CA_CERT); + PopulateTree("otherCerts", net::OTHER_CERT); } void CertificatesHandler::FileSelected(const base::FilePath& path, @@ -785,7 +768,7 @@ // away so they don't try and call back to us. if (select_file_dialog_.get()) select_file_dialog_->ListenerDestroyed(); - select_file_dialog_ = NULL; + select_file_dialog_ = nullptr; } void CertificatesHandler::HandleImportServer(const base::ListValue* args) { @@ -1023,74 +1006,72 @@ // to do anything. } -void CertificatesHandler::PopulateTree( - const std::string& tab_name, - net::CertType type, - const net::CertificateList& web_trust_certs) { +void CertificatesHandler::PopulateTree(const std::string& tab_name, + net::CertType type) { std::unique_ptr<icu::Collator> collator; UErrorCode error = U_ZERO_ERROR; collator.reset(icu::Collator::createInstance( icu::Locale(g_browser_process->GetApplicationLocale().c_str()), error)); if (U_FAILURE(error)) - collator.reset(NULL); + collator.reset(); DictionaryIdComparator comparator(collator.get()); - CertificateManagerModel::OrgGroupingMap map; + CertificateManagerModel::OrgGroupingMap org_grouping_map; - certificate_manager_model_->FilterAndBuildOrgGroupingMap(type, &map); + certificate_manager_model_->FilterAndBuildOrgGroupingMap(type, + &org_grouping_map); - { - std::unique_ptr<base::ListValue> nodes = - std::make_unique<base::ListValue>(); - for (CertificateManagerModel::OrgGroupingMap::iterator i = map.begin(); - i != map.end(); ++i) { - // Populate first level (org name). - std::unique_ptr<base::DictionaryValue> dict(new base::DictionaryValue); - dict->SetString(kCertificatesHandlerKeyField, OrgNameToId(i->first)); - dict->SetString(kCertificatesHandlerNameField, i->first); + base::ListValue nodes; + for (const auto& org_grouping_map_entry : org_grouping_map) { + // Populate first level (org name). + base::DictionaryValue org_dict; + org_dict.SetKey(kCertificatesHandlerKeyField, + base::Value(OrgNameToId(org_grouping_map_entry.first))); + org_dict.SetKey(kCertificatesHandlerNameField, + base::Value(org_grouping_map_entry.first)); - // Populate second level (certs). - auto subnodes = std::make_unique<base::ListValue>(); - for (net::ScopedCERTCertificateList::const_iterator org_cert_it = - i->second.begin(); - org_cert_it != i->second.end(); ++org_cert_it) { - std::unique_ptr<base::DictionaryValue> cert_dict( - new base::DictionaryValue); - CERTCertificate* cert = org_cert_it->get(); - cert_dict->SetString(kCertificatesHandlerKeyField, - cert_id_map_->CertToId(cert)); - cert_dict->SetString( - kCertificatesHandlerNameField, - certificate_manager_model_->GetColumnText( - cert, CertificateManagerModel::COL_SUBJECT_NAME)); - cert_dict->SetBoolean( - kCertificatesHandlerReadonlyField, - certificate_manager_model_->cert_db()->IsReadOnly(cert)); - // Policy-installed certificates with web trust are trusted. - bool policy_trusted = - IsPolicyInstalledWithWebTrust(web_trust_certs, cert); - cert_dict->SetBoolean( - kCertificatesHandlerUntrustedField, - !policy_trusted && - certificate_manager_model_->cert_db()->IsUntrusted(cert)); - cert_dict->SetBoolean(kCertificatesHandlerPolicyField, policy_trusted); - // TODO(hshi): This should be determined by testing for PKCS #11 - // CKA_EXTRACTABLE attribute. We may need to use the NSS function - // PK11_ReadRawAttribute to do that. - cert_dict->SetBoolean( - kCertificatesHandlerExtractableField, - !certificate_manager_model_->IsHardwareBacked(cert)); - // TODO(mattm): Other columns. - subnodes->Append(std::move(cert_dict)); - } - std::sort(subnodes->begin(), subnodes->end(), comparator); + // Populate second level (certs). + base::ListValue subnodes; + bool contains_policy_certs = false; + for (const auto& org_cert : org_grouping_map_entry.second) { + base::DictionaryValue cert_dict; + CERTCertificate* cert = org_cert->cert(); + cert_dict.SetKey(kCertificatesHandlerKeyField, + base::Value(cert_id_map_->CertToId(cert))); + cert_dict.SetKey(kCertificatesHandlerNameField, + base::Value(org_cert->name())); + cert_dict.SetKey(kCertificatesHandlerReadonlyField, + base::Value(org_cert->read_only())); + cert_dict.SetKey(kCertificatesHandlerUntrustedField, + base::Value(org_cert->untrusted())); + cert_dict.SetKey( + kCertificatesHandlerPolicyInstalledField, + base::Value(org_cert->source() == + CertificateManagerModel::CertInfo::Source::kPolicy)); + cert_dict.SetKey(kCertificatesHandlerWebTrustAnchorField, + base::Value(org_cert->web_trust_anchor())); + // TODO(hshi): This should be determined by testing for PKCS #11 + // CKA_EXTRACTABLE attribute. We may need to use the NSS function + // PK11_ReadRawAttribute to do that. + cert_dict.SetKey(kCertificatesHandlerExtractableField, + base::Value(!org_cert->hardware_backed())); + // TODO(mattm): Other columns. + subnodes.GetList().push_back(std::move(cert_dict)); - dict->Set(kCertificatesHandlerSubnodesField, std::move(subnodes)); - nodes->Append(std::move(dict)); + contains_policy_certs |= + org_cert->source() == + CertificateManagerModel::CertInfo::Source::kPolicy; } - std::sort(nodes->begin(), nodes->end(), comparator); + std::sort(subnodes.GetList().begin(), subnodes.GetList().end(), comparator); - FireWebUIListener("certificates-changed", base::Value(tab_name), *nodes); + org_dict.SetKey(kCertificatesHandlerContainsPolicyCertsField, + base::Value(contains_policy_certs)); + org_dict.SetKey(kCertificatesHandlerSubnodesField, std::move(subnodes)); + nodes.GetList().push_back(std::move(org_dict)); } + std::sort(nodes.GetList().begin(), nodes.GetList().end(), comparator); + + FireWebUIListener("certificates-changed", base::Value(tab_name), + std::move(nodes)); } void CertificatesHandler::ResolveCallback(const base::Value& response) {
diff --git a/chrome/browser/ui/webui/certificates_handler.h b/chrome/browser/ui/webui/certificates_handler.h index fa60476..3e69636 100644 --- a/chrome/browser/ui/webui/certificates_handler.h +++ b/chrome/browser/ui/webui/certificates_handler.h
@@ -136,14 +136,7 @@ void HandleRefreshCertificates(const base::ListValue* args); // Populate the given tab's tree. - void PopulateTree(const std::string& tab_name, - net::CertType type, - const net::CertificateList& web_trust_certs); - - // Populate the tree after retrieving the list of policy-installed - // web-trusted certificates. - void OnPolicyWebTrustCertsRetrieved( - const net::CertificateList& web_trust_certs); + void PopulateTree(const std::string& tab_name, net::CertType type); void ResolveCallback(const base::Value& response); void RejectCallback(const base::Value& response);
diff --git a/chrome/browser/vr/OWNERS b/chrome/browser/vr/OWNERS index a89c9964..5a930f06 100644 --- a/chrome/browser/vr/OWNERS +++ b/chrome/browser/vr/OWNERS
@@ -1,4 +1,3 @@ -asimjour@chromium.org cjgrant@chromium.org mthiesse@chromium.org tiborg@chromium.org
diff --git a/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.cc b/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.cc index 0109c0b..9d01827 100644 --- a/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.cc +++ b/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.cc
@@ -8,6 +8,8 @@ #include "base/bind.h" #include "base/values.h" +#include "build/build_config.h" +#include "chrome/browser/profiles/profile.h" #include "chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_constants.h" #include "chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h" #include "chrome/common/pref_names.h" @@ -15,6 +17,10 @@ #include "components/prefs/pref_service.h" #include "content/public/browser/browser_thread.h" +#if defined(OS_CHROMEOS) +#include "chrome/browser/chromeos/profiles/profile_helper.h" +#endif // OS_CHROMEOS + namespace web_app { WebAppPolicyManager::WebAppPolicyManager(PrefService* pref_service, @@ -36,6 +42,22 @@ registry->RegisterListPref(prefs::kWebAppInstallForceList); } +// static +bool WebAppPolicyManager::ShouldEnableForProfile(Profile* profile) { +// PolicyBrowserTests applies test policies to all profiles, including the +// sign-in profile. This causes tests to become flaky since the tests could +// finish before, during, or after the policy apps fail to install in the +// sign-in profile. So we temporarily add a guard to ignore the policy for the +// sign-in profile. +// TODO(crbug.com/876705): Remove once the policy no longer applies to the +// sign-in profile during tests. +#if defined(OS_CHROMEOS) + return !chromeos::ProfileHelper::IsSigninProfile(profile); +#else // !OS_CHROMEOS + return true; +#endif +} + void WebAppPolicyManager::RefreshPolicyInstalledApps() { const base::Value* web_apps = pref_service_->GetList(prefs::kWebAppInstallForceList); @@ -43,16 +65,24 @@ std::vector<PendingAppManager::AppInfo> apps_to_install; for (const base::Value& info : web_apps->GetList()) { const base::Value& url = *info.FindKey(kUrlKey); - const base::Value& launch_container = *info.FindKey(kLaunchContainerKey); + const base::Value* launch_container = info.FindKey(kLaunchContainerKey); - DCHECK(launch_container.GetString() == kLaunchContainerWindowValue || - launch_container.GetString() == kLaunchContainerTabValue); + DCHECK(!launch_container || + launch_container->GetString() == kLaunchContainerWindowValue || + launch_container->GetString() == kLaunchContainerTabValue); - apps_to_install.emplace_back( - GURL(url.GetString()), - launch_container.GetString() == kLaunchContainerWindowValue - ? PendingAppManager::LaunchContainer::kWindow - : PendingAppManager::LaunchContainer::kTab); + PendingAppManager::LaunchContainer container; + + // TODO(crbug.com/864904): Remove this default once PendingAppManager + // supports not setting the launch container. + if (!launch_container) + container = PendingAppManager::LaunchContainer::kTab; + else if (launch_container->GetString() == kLaunchContainerWindowValue) + container = PendingAppManager::LaunchContainer::kWindow; + else + container = PendingAppManager::LaunchContainer::kTab; + + apps_to_install.emplace_back(GURL(url.GetString()), container); } pending_app_manager_->InstallApps(std::move(apps_to_install), base::DoNothing());
diff --git a/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.h b/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.h index ec83957..7e6ce3b 100644 --- a/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.h +++ b/chrome/browser/web_applications/bookmark_apps/policy/web_app_policy_manager.h
@@ -13,6 +13,7 @@ #include "url/gurl.h" class PrefService; +class Profile; namespace user_prefs { class PrefRegistrySyncable; @@ -34,6 +35,8 @@ static void RegisterProfilePrefs(user_prefs::PrefRegistrySyncable* registry); + static bool ShouldEnableForProfile(Profile* profile); + private: void RefreshPolicyInstalledApps();
diff --git a/chrome/browser/web_applications/extensions/bookmark_app_installation_task.cc b/chrome/browser/web_applications/extensions/bookmark_app_installation_task.cc index c8441209..fa4f87bd 100644 --- a/chrome/browser/web_applications/extensions/bookmark_app_installation_task.cc +++ b/chrome/browser/web_applications/extensions/bookmark_app_installation_task.cc
@@ -52,8 +52,11 @@ favicon::CreateContentFaviconDriverForWebContents(web_contents); } -BookmarkAppInstallationTask::BookmarkAppInstallationTask(Profile* profile) +BookmarkAppInstallationTask::BookmarkAppInstallationTask( + Profile* profile, + web_app::PendingAppManager::AppInfo app_info) : profile_(profile), + app_info_(std::move(app_info)), helper_factory_(base::BindRepeating(&BookmarkAppHelperCreateWrapper)), data_retriever_(std::make_unique<BookmarkAppDataRetriever>()), installer_(std::make_unique<BookmarkAppInstaller>(profile)) {}
diff --git a/chrome/browser/web_applications/extensions/bookmark_app_installation_task.h b/chrome/browser/web_applications/extensions/bookmark_app_installation_task.h index 20f7a22..eb745d4 100644 --- a/chrome/browser/web_applications/extensions/bookmark_app_installation_task.h +++ b/chrome/browser/web_applications/extensions/bookmark_app_installation_task.h
@@ -11,6 +11,7 @@ #include "base/callback.h" #include "base/macros.h" #include "base/memory/weak_ptr.h" +#include "chrome/browser/web_applications/components/pending_app_manager.h" class Profile; enum class WebappInstallSource; @@ -60,7 +61,13 @@ // Ensures the tab helpers necessary for installing an app are present. static void CreateTabHelpers(content::WebContents* web_contents); - explicit BookmarkAppInstallationTask(Profile* profile); + // Constructs a task that will install a BookmarkApp-based Shortcut or Web App + // for |profile|. |app_info| will be used to decide some of the + // properties of the installed app e.g. open in a tab vs. window, installed by + // policy, etc. + explicit BookmarkAppInstallationTask( + Profile* profile, + web_app::PendingAppManager::AppInfo app_info); virtual ~BookmarkAppInstallationTask(); @@ -68,6 +75,8 @@ content::WebContents* web_contents, ResultCallback callback); + const web_app::PendingAppManager::AppInfo& app_info() { return app_info_; } + void SetBookmarkAppHelperFactoryForTesting( BookmarkAppHelperFactory helper_factory); void SetDataRetrieverForTesting( @@ -89,6 +98,8 @@ Profile* profile_; + const web_app::PendingAppManager::AppInfo app_info_; + // We temporarily use a BookmarkAppHelper until the WebApp and WebShortcut // installation tasks reach feature parity with BookmarkAppHelper. std::unique_ptr<BookmarkAppHelper> helper_;
diff --git a/chrome/browser/web_applications/extensions/bookmark_app_installation_task_unittest.cc b/chrome/browser/web_applications/extensions/bookmark_app_installation_task_unittest.cc index 26e90e92..dc6eb1bd 100644 --- a/chrome/browser/web_applications/extensions/bookmark_app_installation_task_unittest.cc +++ b/chrome/browser/web_applications/extensions/bookmark_app_installation_task_unittest.cc
@@ -278,9 +278,15 @@ TEST_F(BookmarkAppInstallationTaskTest, WebAppOrShortcutFromContents_InstallationSucceeds) { - auto task = std::make_unique<BookmarkAppInstallationTask>(profile()); + const GURL app_url(kWebAppUrl); + + auto task = std::make_unique<BookmarkAppInstallationTask>( + profile(), + web_app::PendingAppManager::AppInfo( + app_url, web_app::PendingAppManager::LaunchContainer::kWindow)); + WebApplicationInfo info; - info.app_url = GURL(kWebAppUrl); + info.app_url = app_url; info.title = base::UTF8ToUTF16(kWebAppTitle); task->SetDataRetrieverForTesting(std::make_unique<TestDataRetriever>( std::make_unique<WebApplicationInfo>(std::move(info)))); @@ -303,9 +309,15 @@ TEST_F(BookmarkAppInstallationTaskTest, WebAppOrShortcutFromContents_InstallationFails) { - auto task = std::make_unique<BookmarkAppInstallationTask>(profile()); + const GURL app_url(kWebAppUrl); + + auto task = std::make_unique<BookmarkAppInstallationTask>( + profile(), + web_app::PendingAppManager::AppInfo( + app_url, web_app::PendingAppManager::LaunchContainer::kWindow)); + WebApplicationInfo info; - info.app_url = GURL(kWebAppUrl); + info.app_url = app_url; info.title = base::UTF8ToUTF16(kWebAppTitle); task->SetDataRetrieverForTesting(std::make_unique<TestDataRetriever>( std::make_unique<WebApplicationInfo>(std::move(info))));
diff --git a/chrome/browser/web_applications/extensions/bookmark_app_shortcut_installation_task.cc b/chrome/browser/web_applications/extensions/bookmark_app_shortcut_installation_task.cc index e2f117b6..30e31ae 100644 --- a/chrome/browser/web_applications/extensions/bookmark_app_shortcut_installation_task.cc +++ b/chrome/browser/web_applications/extensions/bookmark_app_shortcut_installation_task.cc
@@ -20,7 +20,15 @@ BookmarkAppShortcutInstallationTask::BookmarkAppShortcutInstallationTask( Profile* profile) - : BookmarkAppInstallationTask(profile) {} + : BookmarkAppInstallationTask( + profile, + // Pass an empty AppInfo since it doesn't influence the installation + // right now. + // TODO(crbug.com/864904): Take an AppInfo object once the installer + // can use the information. + web_app::PendingAppManager::AppInfo( + GURL(), + web_app::PendingAppManager::LaunchContainer::kTab)) {} BookmarkAppShortcutInstallationTask::~BookmarkAppShortcutInstallationTask() = default;
diff --git a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc index f6961d4f..a561939 100644 --- a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc +++ b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.cc
@@ -28,18 +28,21 @@ } std::unique_ptr<BookmarkAppInstallationTask> InstallationTaskCreateWrapper( - Profile* profile) { - return std::make_unique<BookmarkAppInstallationTask>(profile); + Profile* profile, + web_app::PendingAppManager::AppInfo app_info) { + return std::make_unique<BookmarkAppInstallationTask>(profile, + std::move(app_info)); } } // namespace -struct PendingBookmarkAppManager::Installation { - Installation(AppInfo info, OnceInstallCallback callback) - : info(std::move(info)), callback(std::move(callback)) {} - ~Installation() = default; +struct PendingBookmarkAppManager::TaskAndCallback { + TaskAndCallback(std::unique_ptr<BookmarkAppInstallationTask> task, + OnceInstallCallback callback) + : task(std::move(task)), callback(std::move(callback)) {} + ~TaskAndCallback() = default; - AppInfo info; + std::unique_ptr<BookmarkAppInstallationTask> task; OnceInstallCallback callback; }; @@ -54,19 +57,21 @@ void PendingBookmarkAppManager::Install(AppInfo app_to_install, OnceInstallCallback callback) { // Check that we are not already installing the same app. - if (current_installation_ && current_installation_->info == app_to_install) { + if (current_task_and_callback_ && + current_task_and_callback_->task->app_info() == app_to_install) { std::move(callback).Run(app_to_install.url, std::string()); return; } - for (const auto& installation : installation_queue_) { - if (installation->info == app_to_install) { + for (const auto& installation : pending_tasks_and_callbacks_) { + if (installation->task->app_info() == app_to_install) { std::move(callback).Run(app_to_install.url, std::string()); return; } } - installation_queue_.push_front(std::make_unique<Installation>( - std::move(app_to_install), std::move(callback))); + pending_tasks_and_callbacks_.push_front(std::make_unique<TaskAndCallback>( + task_factory_.Run(profile_, std::move(app_to_install)), + std::move(callback))); base::ThreadTaskRunnerHandle::Get()->PostTask( FROM_HERE, @@ -78,8 +83,8 @@ std::vector<AppInfo> apps_to_install, const RepeatingInstallCallback& callback) { for (auto& app_to_install : apps_to_install) { - installation_queue_.push_back( - std::make_unique<Installation>(std::move(app_to_install), callback)); + pending_tasks_and_callbacks_.push_back(std::make_unique<TaskAndCallback>( + task_factory_.Run(profile_, std::move(app_to_install)), callback)); } base::ThreadTaskRunnerHandle::Get()->PostTask( @@ -101,22 +106,22 @@ } void PendingBookmarkAppManager::MaybeStartNextInstallation() { - if (current_installation_) + if (current_task_and_callback_) return; - if (installation_queue_.empty()) { + if (pending_tasks_and_callbacks_.empty()) { web_contents_.reset(); return; } - current_installation_ = std::move(installation_queue_.front()); - installation_queue_.pop_front(); + current_task_and_callback_ = std::move(pending_tasks_and_callbacks_.front()); + pending_tasks_and_callbacks_.pop_front(); CreateWebContentsIfNecessary(); Observe(web_contents_.get()); content::NavigationController::LoadURLParams load_params( - current_installation_->info.url); + current_task_and_callback_->task->app_info().url); load_params.transition_type = ui::PAGE_TRANSITION_GENERATED; web_contents_->GetController().LoadURLWithParams(load_params); timer_->Start( @@ -155,9 +160,10 @@ base::BindOnce(&PendingBookmarkAppManager::MaybeStartNextInstallation, weak_ptr_factory_.GetWeakPtr())); - std::unique_ptr<Installation> installation; - installation.swap(current_installation_); - std::move(installation->callback).Run(installation->info.url, app_id); + std::unique_ptr<TaskAndCallback> task_and_callback; + task_and_callback.swap(current_task_and_callback_); + std::move(task_and_callback->callback) + .Run(task_and_callback->task->app_info().url, app_id); } void PendingBookmarkAppManager::DidFinishLoad( @@ -168,14 +174,13 @@ return; } - if (validated_url != current_installation_->info.url) { + if (validated_url != current_task_and_callback_->task->app_info().url) { CurrentInstallationFinished(std::string()); return; } Observe(nullptr); - current_installation_task_ = task_factory_.Run(profile_); - current_installation_task_->InstallWebAppOrShortcutFromWebContents( + current_task_and_callback_->task->InstallWebAppOrShortcutFromWebContents( web_contents_.get(), base::BindOnce(&PendingBookmarkAppManager::OnInstalled, // Safe because the installation task will not run its
diff --git a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h index d52a857..1c48cec 100644 --- a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h +++ b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager.h
@@ -38,9 +38,8 @@ public: using WebContentsFactory = base::RepeatingCallback<std::unique_ptr<content::WebContents>(Profile*)>; - using TaskFactory = - base::RepeatingCallback<std::unique_ptr<BookmarkAppInstallationTask>( - Profile*)>; + using TaskFactory = base::RepeatingCallback< + std::unique_ptr<BookmarkAppInstallationTask>(Profile*, AppInfo)>; explicit PendingBookmarkAppManager(Profile* profile); ~PendingBookmarkAppManager() override; @@ -56,7 +55,7 @@ void SetTimerForTesting(std::unique_ptr<base::OneShotTimer> timer); private: - struct Installation; + struct TaskAndCallback; void MaybeStartNextInstallation(); @@ -84,10 +83,9 @@ std::unique_ptr<content::WebContents> web_contents_; std::unique_ptr<base::OneShotTimer> timer_; - std::unique_ptr<Installation> current_installation_; - std::unique_ptr<BookmarkAppInstallationTask> current_installation_task_; + std::unique_ptr<TaskAndCallback> current_task_and_callback_; - std::deque<std::unique_ptr<Installation>> installation_queue_; + std::deque<std::unique_ptr<TaskAndCallback>> pending_tasks_and_callbacks_; base::WeakPtrFactory<PendingBookmarkAppManager> weak_ptr_factory_{this};
diff --git a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc index 92098340..5e88dda5 100644 --- a/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc +++ b/chrome/browser/web_applications/extensions/pending_bookmark_app_manager_unittest.cc
@@ -53,8 +53,11 @@ class TestBookmarkAppInstallationTask : public BookmarkAppInstallationTask { public: - TestBookmarkAppInstallationTask(Profile* profile, bool succeeds) - : BookmarkAppInstallationTask(profile), succeeds_(succeeds) {} + TestBookmarkAppInstallationTask(Profile* profile, + web_app::PendingAppManager::AppInfo app_info, + bool succeeds) + : BookmarkAppInstallationTask(profile, std::move(app_info)), + succeeds_(succeeds) {} ~TestBookmarkAppInstallationTask() override = default; void InstallWebAppOrShortcutFromWebContents( @@ -110,13 +113,17 @@ } std::unique_ptr<BookmarkAppInstallationTask> CreateSuccessfulInstallationTask( - Profile* profile) { - return std::make_unique<TestBookmarkAppInstallationTask>(profile, true); + Profile* profile, + web_app::PendingAppManager::AppInfo app_info) { + return std::make_unique<TestBookmarkAppInstallationTask>( + profile, std::move(app_info), true); } std::unique_ptr<BookmarkAppInstallationTask> CreateFailingInstallationTask( - Profile* profile) { - return std::make_unique<TestBookmarkAppInstallationTask>(profile, false); + Profile* profile, + web_app::PendingAppManager::AppInfo app_info) { + return std::make_unique<TestBookmarkAppInstallationTask>( + profile, std::move(app_info), false); } void InstallCallback(const GURL& url, const std::string& app_id) {
diff --git a/chrome/browser/web_applications/web_app_provider.cc b/chrome/browser/web_applications/web_app_provider.cc index 596e7d83..61e6e60 100644 --- a/chrome/browser/web_applications/web_app_provider.cc +++ b/chrome/browser/web_applications/web_app_provider.cc
@@ -22,10 +22,12 @@ WebAppProvider::WebAppProvider(Profile* profile) : pending_app_manager_( - std::make_unique<extensions::PendingBookmarkAppManager>(profile)), - web_app_policy_manager_( - std::make_unique<WebAppPolicyManager>(profile->GetPrefs(), - pending_app_manager_.get())) { + std::make_unique<extensions::PendingBookmarkAppManager>(profile)) { + if (WebAppPolicyManager::ShouldEnableForProfile(profile)) { + web_app_policy_manager_ = std::make_unique<WebAppPolicyManager>( + profile->GetPrefs(), pending_app_manager_.get()); + } + web_app::ScanForExternalWebApps( profile, base::BindOnce(&WebAppProvider::OnScanForExternalWebApps, weak_ptr_factory_.GetWeakPtr()));
diff --git a/chrome/browser/webauthn/authenticator_request_dialog_model.cc b/chrome/browser/webauthn/authenticator_request_dialog_model.cc index b9a8cc0..8890c703 100644 --- a/chrome/browser/webauthn/authenticator_request_dialog_model.cc +++ b/chrome/browser/webauthn/authenticator_request_dialog_model.cc
@@ -6,7 +6,9 @@ #include <utility> +#include "base/bind.h" #include "base/stl_util.h" +#include "base/threading/sequenced_task_runner_handle.h" namespace { @@ -120,6 +122,7 @@ SetCurrentStep(Step::kTransportSelection); break; case AuthenticatorTransport::kInternal: + SetCurrentStep(Step::kTouchId); TryTouchId(); break; case AuthenticatorTransport::kBluetoothLowEnergy: @@ -160,7 +163,6 @@ } void AuthenticatorRequestDialogModel::TryTouchId() { - SetCurrentStep(Step::kTouchId); if (!request_callback_) return; @@ -174,7 +176,14 @@ if (touch_id_authenticator == saved_authenticators_.end()) return; - request_callback_.Run(touch_id_authenticator->authenticator_id); + static base::TimeDelta kTouchIdDispatchDelay = + base::TimeDelta::FromMilliseconds(1000); + + base::SequencedTaskRunnerHandle::Get()->PostDelayedTask( + FROM_HERE, + base::BindOnce(request_callback_, + touch_id_authenticator->authenticator_id), + kTouchIdDispatchDelay); } void AuthenticatorRequestDialogModel::Cancel() {
diff --git a/chrome/browser/webauthn/authenticator_request_dialog_model.h b/chrome/browser/webauthn/authenticator_request_dialog_model.h index 9f95091..12d4c894 100644 --- a/chrome/browser/webauthn/authenticator_request_dialog_model.h +++ b/chrome/browser/webauthn/authenticator_request_dialog_model.h
@@ -36,6 +36,8 @@ kTransportSelection, kErrorTimedOut, kErrorNoAvailableTransports, + kErrorKeyNotRegistered, + kErrorKeyAlreadyRegistered, kCompleted, // Universal Serial Bus (USB).
diff --git a/chrome/chrome_cleaner/BUILD.gn b/chrome/chrome_cleaner/BUILD.gn index b688db9..ede274ae 100644 --- a/chrome/chrome_cleaner/BUILD.gn +++ b/chrome/chrome_cleaner/BUILD.gn
@@ -36,6 +36,7 @@ "//chrome/chrome_cleaner/logging:unittest_sources", "//chrome/chrome_cleaner/os:unittest_sources", "//chrome/chrome_cleaner/pup_data:unittest_sources", + "//chrome/chrome_cleaner/scanner:unittest_sources", "//chrome/chrome_cleaner/settings:unittest_sources", "//chrome/chrome_cleaner/strings:unittest_sources", "//chrome/chrome_cleaner/test:unittest_sources",
diff --git a/chrome/chrome_cleaner/interfaces/BUILD.gn b/chrome/chrome_cleaner/interfaces/BUILD.gn deleted file mode 100644 index 7f48e4ca..0000000 --- a/chrome/chrome_cleaner/interfaces/BUILD.gn +++ /dev/null
@@ -1,21 +0,0 @@ -# Copyright 2018 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. - -import("//mojo/public/tools/bindings/mojom.gni") - -mojom("engine_sandbox_interface") { - sources = [ - "cleaner_engine_requests.mojom", - "engine_file_requests.mojom", - "engine_requests.mojom", - "engine_sandbox.mojom", - "pup.mojom", - "string16_embedded_nulls.mojom", - "windows_handle.mojom", - ] - deps = [ - "//components/chrome_cleaner/public/interfaces:interfaces", - "//mojo/public/mojom/base", - ] -}
diff --git a/chrome/chrome_cleaner/interfaces/OWNERS b/chrome/chrome_cleaner/interfaces/OWNERS deleted file mode 100644 index 08850f4..0000000 --- a/chrome/chrome_cleaner/interfaces/OWNERS +++ /dev/null
@@ -1,2 +0,0 @@ -per-file *.mojom=set noparent -per-file *.mojom=file://ipc/SECURITY_OWNERS
diff --git a/chrome/chrome_cleaner/interfaces/cleaner_engine_requests.mojom b/chrome/chrome_cleaner/interfaces/cleaner_engine_requests.mojom deleted file mode 100644 index 7eb77f1..0000000 --- a/chrome/chrome_cleaner/interfaces/cleaner_engine_requests.mojom +++ /dev/null
@@ -1,53 +0,0 @@ -// Copyright 2018 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. - -module chrome_cleaner.mojom; - -import "chrome/chrome_cleaner/interfaces/string16_embedded_nulls.mojom"; -import "components/chrome_cleaner/public/interfaces/chrome_prompt.mojom"; -import "mojo/public/mojom/base/string16.mojom"; - -// Passes requests that can mutate the system from the low-privilege sandbox -// target process to the high-privilege broker process. It is implemented in -// CleanerEngineRequestsImpl in engines/broker. -// -// This interface is only used when in cleaning mode, in which case the broker -// process runs with administrator privileges, so the parameters of each method -// must be carefully validated to ensure that the requests are safe. -interface CleanerEngineRequests { - // Attempts to deletes the given file, applying some basic checks to ensure - // the file is safe to delete. - SandboxDeleteFile(FilePath file_name) => (bool result); - - // Schedules the given file for post-reboot removal, applying some basic - // checks to ensure the file is safe to delete. - SandboxDeleteFilePostReboot(FilePath file_name) => (bool result); - - // Deletes the given registry key. |key| may contain null characters. - SandboxNtDeleteRegistryKey(String16EmbeddedNulls key) => (bool result); - - // Deletes the given value for the given registry key. |key| and |key_name| - // may contain null characters. - SandboxNtDeleteRegistryValue(String16EmbeddedNulls key, - String16EmbeddedNulls value_name) - => (bool result); - - // Updates the value of the given key's value to |new_value|. - // |new_value| must be a subset of the existing value. This is intended to be - // used to delete parts of a value, not to set a new value. - SandboxNtChangeRegistryValue(String16EmbeddedNulls key, - String16EmbeddedNulls value_name, - String16EmbeddedNulls new_value) - => (bool result); - - // Deletes the given service. - SandboxDeleteService(mojo_base.mojom.String16 name) => (bool result); - - // Deletes the given task. - SandboxDeleteTask(mojo_base.mojom.String16 name) => (bool result); - - // Terminates the given process. - // The broker process can't be terminated. - SandboxTerminateProcess(uint32 process_id) => (bool result); -};
diff --git a/chrome/chrome_cleaner/interfaces/engine_file_requests.mojom b/chrome/chrome_cleaner/interfaces/engine_file_requests.mojom deleted file mode 100644 index beba962e..0000000 --- a/chrome/chrome_cleaner/interfaces/engine_file_requests.mojom +++ /dev/null
@@ -1,46 +0,0 @@ -// Copyright 2018 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. - -module chrome_cleaner.mojom; - -import "components/chrome_cleaner/public/interfaces/chrome_prompt.mojom"; - -// Handles returned by FindFirstFile aren't real handles, so we can't pass them -// through mojo as handles, since they can't be duplicated. -struct FindHandle { - int64 find_handle; -}; - -struct FindFileData { - array<uint8> data; -}; - -// Passes file handling requests from the low-privilege sandbox target process -// to the high-privilege broker process. It is implemented in -// EngineFileRequestsImpl in engines/broker. -// -// This interface is used in scanning and cleaning mode, and when initializing -// the engine (which may need to load auxiliary file resources.) -interface EngineFileRequests { - // Calls ::FindFirstFile for the given path, returning the results from - // ::FindFirstFile. - SandboxFindFirstFile(FilePath file_name) => - (uint32 result, FindFileData win32_find_data, FindHandle find_handle); - - // Calls ::FindNextFile for the given handle, returning the results from - // ::FindNextFile. - SandboxFindNextFile(FindHandle find_handle) => - (uint32 result, FindFileData win32_find_data); - - // Calls ::FindClose on the given handle, returning the results from - // ::FindClose. - SandboxFindClose(FindHandle find_handle) => (uint32 result); - - // Returns a read-only file handle for the given file. The only acceptable - // values for |dwFlagsAndAttributes| are FILE_FLAG_NO_BUFFERING, - // FILE_FLAG_SEQUENTIAL_SCAN, FILE_FLAG_RANDOM_ACCESS, and - // FILE_FLAG_OPEN_REPARSE_POINT. - SandboxOpenReadOnlyFile(FilePath file_name, uint32 dwFlagsAndAttributes) => - (handle result); -};
diff --git a/chrome/chrome_cleaner/interfaces/engine_requests.mojom b/chrome/chrome_cleaner/interfaces/engine_requests.mojom deleted file mode 100644 index a816495..0000000 --- a/chrome/chrome_cleaner/interfaces/engine_requests.mojom +++ /dev/null
@@ -1,90 +0,0 @@ -// Copyright 2018 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. -module chrome_cleaner.mojom; - -import "chrome/chrome_cleaner/interfaces/string16_embedded_nulls.mojom"; -import "chrome/chrome_cleaner/interfaces/windows_handle.mojom"; -import "components/chrome_cleaner/public/interfaces/chrome_prompt.mojom"; -import "mojo/public/mojom/base/process_id.mojom"; -import "mojo/public/mojom/base/string16.mojom"; - -enum KnownFolder { - kWindows = 0, - kProgramFiles = 1, - kProgramFilesX86 = 2, - kAppData = 3, -}; - -struct StringSid { - mojo_base.mojom.String16 value; -}; - -struct ScheduledTaskAction { - FilePath path; - FilePath working_dir; - mojo_base.mojom.String16 arguments; -}; - -struct ScheduledTask { - mojo_base.mojom.String16 name; - mojo_base.mojom.String16 description; - array<ScheduledTaskAction> actions; -}; - -struct UserInformation { - mojo_base.mojom.String16 name; - mojo_base.mojom.String16 domain; - // User account type (SID_NAME_USE). See - // https://msdn.microsoft.com/en-us/library/windows/desktop/aa379601(v=vs.85).aspx - uint32 account_type; -}; - -// Passes requests that do not mutate the system from the low-privilege sandbox -// target process to the high-privilege broker process. It is implemented in -// EngineRequestsImpl in engines/broker. -// -// This interface is used in scanning and cleaning mode. -interface EngineRequests { - // Converts the given KnownFolder Id to its folder path. - SandboxGetKnownFolderPath(KnownFolder folder_id) => - (bool result, FilePath folder_path); - - // Gets all of the processes currently running on the machine. - SandboxGetProcesses() => - (bool result, array<mojo_base.mojom.ProcessId> processes); - - // Gets all the tasks on the system. - SandboxGetTasks() => (bool result, array<ScheduledTask> tasks); - - // Returns the path to the executable of the given process. - SandboxGetProcessImagePath(mojo_base.mojom.ProcessId pid) => - (bool result, FilePath image_path); - - // Gets all of the modules loaded into memory for the given process. - SandboxGetLoadedModules(mojo_base.mojom.ProcessId pid) => - (bool result, array<mojo_base.mojom.String16> modules); - - // Gets the command line for the given process. - SandboxGetProcessCommandLine(mojo_base.mojom.ProcessId pid) => - (bool result, mojo_base.mojom.String16 command_line); - - // Gets the given UserInformation values for |sid|. - SandboxGetUserInfoFromSID(StringSid sid) => (bool result, - UserInformation user_info); - - // Gets a read-only registry key handle to the given key. - // |dw_access| may specify KEY_WOW64_32KEY or KEY_WOW64_64KEY. |root_key| must - // be non-null, and |sub_key| can't have any null characters. - SandboxOpenReadOnlyRegistry(WindowsHandle root_key, - mojo_base.mojom.String16 sub_key, uint32 dw_access) => - (uint32 result, WindowsHandle reg_handle); - - // Gets a read-only registry key handle to the given key. - // |dw_access| may not specify KEY_WOW64_32KEY or KEY_WOW64_64KEY. - // ||root_key| may be null, and |sub_key| may have null characters. - SandboxNtOpenReadOnlyRegistry(WindowsHandle root_key, - String16EmbeddedNulls sub_key, - uint32 dw_access) => - (uint32 result, WindowsHandle reg_handle); -};
diff --git a/chrome/chrome_cleaner/interfaces/engine_sandbox.mojom b/chrome/chrome_cleaner/interfaces/engine_sandbox.mojom deleted file mode 100644 index 78f33be..0000000 --- a/chrome/chrome_cleaner/interfaces/engine_sandbox.mojom +++ /dev/null
@@ -1,79 +0,0 @@ -// Copyright 2018 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. - -module chrome_cleaner.mojom; - -import "chrome/chrome_cleaner/interfaces/cleaner_engine_requests.mojom"; -import "chrome/chrome_cleaner/interfaces/engine_requests.mojom"; -import "chrome/chrome_cleaner/interfaces/engine_file_requests.mojom"; -import "chrome/chrome_cleaner/interfaces/pup.mojom"; -import "components/chrome_cleaner/public/interfaces/chrome_prompt.mojom"; - -// All result_code parameters and return values in these interfaces correspond -// to ESETResultCode values for the ESET engine, and to -// EngineOperationStatus::ResultCode values the Urza engine. - -// This interface passes scan results back from the target process to the -// broker process. -interface EngineScanResults { - // Called zero or more times with details of UwS. - FoundUwS(uint32 pup_id, PUP pup); - - // Called exactly once, after any calls to FoundUwS. - Done(uint32 result_code); -}; - -// This interface passes cleanup results back from the target process to the -// broker process. -interface EngineCleanupResults { - // Called once the cleaner has finished cleaning. - Done(uint32 result_code); -}; - -// This interface connects the sandbox broker process to the sandbox target -// process, which implements the interface using functions declared in -// third_party/eset_lib/src/api/eset_cleaner.h. -interface EngineCommands { - // Runs the engine's initialization routine. - Initialize(associated EngineFileRequests file_requests, - FilePath log_directory) => (uint32 result_code); - - // Starts scanning the user's system. - // |enabled_uws| contains a list of UwS IDs to scan for. - // |enabled_trace_locations| is a list of trace locations, to which scanning - // should be limited. - // |include_details| is true if the results should include full details of - // each UwS found, false if the results should include only the ID. - // |results| is an interface which will be used to return results: - // FoundUwS will be called 0 or more times with details of the UwS found, - // followed by exactly one call to Done. - // - // If the scan request returns an error immediately, that error is returned - // and |results| is not used. Otherwise a success result code is returned and - // any further errors will be reported by calling Done on the |results| - // interface. - StartScan(array<uint32> enabled_uws, - array<TraceLocation> enabled_trace_locations, - bool include_details, - associated EngineFileRequests file_requests, - associated EngineRequests sandboxed_engine_requests, - associated EngineScanResults results) => (uint32 result_code); - - // Starts cleaning up the user's system. |enabled_uws| contains a list of UwS - // IDs to cleanup. - // - // If the cleanup request returns an error immediately, that error is returned - // and |results| is not used. Otherwise a success result code is returned and - // any further errors will be reported by calling Done on the |results| - // interface. - StartCleanup(array<uint32> enabled_uws, - associated EngineFileRequests file_requests, - associated EngineRequests sandboxed_engine_requests, - associated CleanerEngineRequests - sandboxed_cleaner_engine_requests, - associated EngineCleanupResults results) => (uint32 result_code); - - // Runs the engine's finalization routine. - Finalize() => (uint32 result_code); -};
diff --git a/chrome/chrome_cleaner/interfaces/pup.mojom b/chrome/chrome_cleaner/interfaces/pup.mojom deleted file mode 100644 index 3b871c8..0000000 --- a/chrome/chrome_cleaner/interfaces/pup.mojom +++ /dev/null
@@ -1,61 +0,0 @@ -// Copyright 2018 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. - -module chrome_cleaner.mojom; - -import "chrome/chrome_cleaner/interfaces/string16_embedded_nulls.mojom"; -import "chrome/chrome_cleaner/interfaces/windows_handle.mojom"; -import "components/chrome_cleaner/public/interfaces/chrome_prompt.mojom"; -import "mojo/public/mojom/base/string16.mojom"; - -// Source: -// https://msdn.microsoft.com/en-us/library/windows/desktop/aa384129.aspx -enum Wow64Access { - kNone = 0, - // KEY_WOW64_64KEY - k64Key = 0x0100, - // KEY_WOW64_32KEY - k32Key = 0x0200, -}; - -// Typemapped to chrome_cleaner::RegKeyPath. -struct RegKeyPath { - WindowsHandle rootkey; - // This is only sent by URZA, which currently doesn't support registry paths - // with embedded nulls. - mojo_base.mojom.String16 subkey; - Wow64Access wow64access; -}; - -// Used for reporting detected registry footprints. -// Typemapped to chrome_cleaner::PUPData::RegistryFootprint. -struct RegistryFootprint { - RegKeyPath key_path; - String16EmbeddedNulls value_name; - String16EmbeddedNulls value_substring; - // An enumerator of chrome_cleaner::RegistryMatchRule. - uint32 rule; -}; - -// Typemapped to chrome_cleaner::UwS::TraceLocation enumeration from -// chrome_cleaner/logging/proto/shared_data.proto. -// The struct is used here as a work-around to make Mojo check passed values -// without having to duplicate the enum definition. -struct TraceLocation { - int32 value; -}; - -// Typemapped to chrome_cleaner::PUPData::FileInfo. -struct FileInfo { - array<TraceLocation> found_in; -}; - -// Partially typemapped to chrome_cleaner::PUPData::PUP. -// UwS signatures are not included. -struct PUP { - array<FilePath> expanded_disk_footprints; - array<RegistryFootprint> expanded_registry_footprints; - array<mojo_base.mojom.String16> expanded_scheduled_tasks; - map<FilePath, FileInfo> disk_footprints_info; -};
diff --git a/chrome/chrome_cleaner/interfaces/string16_embedded_nulls.mojom b/chrome/chrome_cleaner/interfaces/string16_embedded_nulls.mojom deleted file mode 100644 index a8aa080e..0000000 --- a/chrome/chrome_cleaner/interfaces/string16_embedded_nulls.mojom +++ /dev/null
@@ -1,24 +0,0 @@ -// Copyright 2018 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. - -module chrome_cleaner.mojom; - -// Typemapped to chrome_cleaner::String16EmbeddedNulls. -// -// Note: Mojo doesn't allow sending null arrays over the wire, and the strings -// represented by this type can be empty (without a null at the end). -// Because of that, represented as a union of either something that is -// always empty (NullValue) or a non-empty array of uint16. -union String16EmbeddedNulls { - // The underlying string is a null array (not the same as an empty string, - // which has at least one character '\0'). - NullValue? null_value; - - // The underlying string is either a null-terminated empty string (size is 1), - // or a non-empty string that can be either null-terminated or not. - array<uint16> value; -}; - -struct NullValue { -};
diff --git a/chrome/chrome_cleaner/interfaces/windows_handle.mojom b/chrome/chrome_cleaner/interfaces/windows_handle.mojom deleted file mode 100644 index 5fb1f61..0000000 --- a/chrome/chrome_cleaner/interfaces/windows_handle.mojom +++ /dev/null
@@ -1,31 +0,0 @@ -// Copyright 2018 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. - -module chrome_cleaner.mojom; - -enum SpecialWindowsHandle { - NULL_HANDLE, - INVALID_HANDLE, - CLASSES_ROOT, - CURRENT_CONFIG, - CURRENT_USER, - LOCAL_MACHINE, - USERS, -}; - -// Mojo's |handle| type passes handles with DUPLICATE_CLOSE_SOURCE. The special -// handles above can't be closed, so they can't be passed as |handle|. Use a -// wrapper that puts these in |special_handle| and plain handles in -// |raw_handle|. Typemapped to HANDLE. -union WindowsHandle { - handle raw_handle; - SpecialWindowsHandle special_handle; -}; - -interface TestWindowsHandle { - EchoHandle(WindowsHandle in_WindowsHandle) => - (WindowsHandle out_WindowsHandle); - - EchoRawHandle(handle in_handle) => (handle out_handle); -};
diff --git a/chrome/chrome_cleaner/logging/cleaner_logging_service_unittest.cc b/chrome/chrome_cleaner/logging/cleaner_logging_service_unittest.cc index 7232959..3b5125a5 100644 --- a/chrome/chrome_cleaner/logging/cleaner_logging_service_unittest.cc +++ b/chrome/chrome_cleaner/logging/cleaner_logging_service_unittest.cc
@@ -1363,8 +1363,8 @@ TEST_P(CleanerLoggingServiceTest, AllExpectedRemovalsConfirmed) { const base::FilePath kFile1(L"C:\\Program Files\\uws.exe"); - const base::FilePath kFile2(L"C:\\Program Files\\virus.exe"); - const base::FilePath kFile3(L"C:\\Program Files\\malware.exe"); + const base::FilePath kFile2(L"C:\\Program Files\\persistant.exe"); + const base::FilePath kFile3(L"C:\\Program Files\\another_uws.exe"); const base::FilePath kFile4(L"C:\\Program Files\\inactive.txt"); logging_service_->EnableUploads(true, registry_logger_.get());
diff --git a/chrome/chrome_cleaner/scanner/BUILD.gn b/chrome/chrome_cleaner/scanner/BUILD.gn new file mode 100644 index 0000000..d472c85 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/BUILD.gn
@@ -0,0 +1,143 @@ +# Copyright 2018 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. + +source_set("signature_matcher_api") { + sources = [ + "signature_matcher_api.h", + ] + + deps = [ + "//base:base", + ] +} + +source_set("matcher_util") { + sources = [ + "matcher_util.cc", + "matcher_util.h", + ] + + deps = [ + "//base:base", + "//chrome/chrome_cleaner/constants:common_strings", + "//chrome/chrome_cleaner/os:common_os", + "//chrome/chrome_cleaner/scanner:signature_matcher_api", + "//chrome/chrome_cleaner/settings:settings", + "//chrome/chrome_cleaner/strings", + ] + + public_deps = [ + "//chrome/chrome_cleaner/pup_data:pup_data_base", + ] +} + +source_set("signature_matcher") { + sources = [ + "signature_matcher.cc", + "signature_matcher.h", + ] + + deps = [ + ":matcher_util", + ":signature_matcher_api", + "//base", + "//chrome/chrome_cleaner/os:common_os", + ] +} + +source_set("scanner_api") { + sources = [ + "scanner.h", + ] + + deps = [ + "//base", + "//chrome/chrome_cleaner/constants:uws_id", + "//components/chrome_cleaner/public/constants", + ] +} + +source_set("scanner") { + sources = [ + "urza_scanner_impl.cc", + "urza_scanner_impl.h", + ] + + deps = [ + ":matcher_util", + ":scanner_api", + ":signature_matcher_api", + "//base:base", + "//chrome/chrome_cleaner/chrome_utils:chrome_util_lib", + "//chrome/chrome_cleaner/constants:common_strings", + "//chrome/chrome_cleaner/logging:common", + "//chrome/chrome_cleaner/logging:logging_definitions", + "//chrome/chrome_cleaner/logging:scoped_timed_task_logger", + "//chrome/chrome_cleaner/os:common_os", + "//chrome/chrome_cleaner/proto:shared_pup_enums_proto", + "//chrome/chrome_cleaner/pup_data:pup_data_base", + "//chrome/chrome_cleaner/settings", + "//chrome/chrome_cleaner/settings:settings_definitions", + "//chrome/chrome_cleaner/strings", + "//components/chrome_cleaner/public/interfaces", + ] +} + +source_set("reporter_scanner") { + sources = [ + "scanner_controller.cc", + "scanner_controller.h", + "urza_scanner_controller.cc", + "urza_scanner_controller.h", + ] + + deps = [ + ":scanner", + ":signature_matcher", + "//base", + "//chrome/chrome_cleaner/crash:crash_keys", + "//chrome/chrome_cleaner/ipc:sandbox", + "//chrome/chrome_cleaner/logging:common", + "//chrome/chrome_cleaner/os:common_os", + "//chrome/chrome_cleaner/pup_data:pup_data_base", + "//chrome/chrome_cleaner/scanner:signature_matcher_api", + "//chrome/chrome_cleaner/settings:settings", + "//components/chrome_cleaner/public/constants:constants", + "//third_party/crashpad/crashpad/client", + "//third_party/crashpad/crashpad/util", + ] +} + +source_set("unittest_sources") { + testonly = true + + sources = [ + "matcher_util_unittest.cc", + "signature_matcher_unittest.cc", + "urza_scanner_impl_unittest.cc", + ] + + deps = [ + ":matcher_util", + ":scanner", + ":signature_matcher", + "//base:base", + "//base/test:test_support", + "//chrome/chrome_cleaner/chrome_utils:chrome_util_lib", + "//chrome/chrome_cleaner/constants:common_strings", + "//chrome/chrome_cleaner/logging:common", + "//chrome/chrome_cleaner/logging:mock_logging_service", + "//chrome/chrome_cleaner/logging/proto:shared_data_proto", + "//chrome/chrome_cleaner/os:common_os", + "//chrome/chrome_cleaner/proto:shared_pup_enums_proto", + "//chrome/chrome_cleaner/strings", + "//chrome/chrome_cleaner/test:test_pup_data", + "//chrome/chrome_cleaner/test:test_strings", + "//chrome/chrome_cleaner/test:test_util", + "//chrome/chrome_cleaner/test/resources:test_resources", + "//sandbox/win:sandbox", + "//testing/gmock", + "//testing/gtest", + ] +}
diff --git a/chrome/chrome_cleaner/scanner/matcher_util.cc b/chrome/chrome_cleaner/scanner/matcher_util.cc new file mode 100644 index 0000000..5897d3d --- /dev/null +++ b/chrome/chrome_cleaner/scanner/matcher_util.cc
@@ -0,0 +1,275 @@ +// Copyright 2018 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/chrome_cleaner/scanner/matcher_util.h" + +#include <stdint.h> + +#include <cctype> +#include <memory> +#include <set> +#include <vector> + +#include "base/command_line.h" +#include "base/file_version_info.h" +#include "base/files/file_enumerator.h" +#include "base/files/file_util.h" +#include "base/path_service.h" +#include "base/strings/string_util.h" +#include "base/strings/utf_string_conversions.h" +#include "base/win/registry.h" +#include "chrome/chrome_cleaner/constants/chrome_cleaner_switches.h" +#include "chrome/chrome_cleaner/os/disk_util.h" +#include "chrome/chrome_cleaner/os/file_path_sanitization.h" +#include "chrome/chrome_cleaner/os/registry_util.h" +#include "chrome/chrome_cleaner/os/task_scheduler.h" +#include "chrome/chrome_cleaner/pup_data/pup_disk_util.h" +#include "chrome/chrome_cleaner/scanner/signature_matcher_api.h" +#include "chrome/chrome_cleaner/strings/string_util.h" + +namespace chrome_cleaner { + +namespace { +// The maximum file size for computing the digest of listed files. +const size_t kMaxFileSizeToLog = 2 * kMegaByte; + +void LogFile(const base::FilePath& file_path) { + if (IsFileSizeLessThan(file_path, kMaxFileSizeToLog)) { + std::string digest; + if (ComputeSHA256DigestOfPath(file_path, &digest)) { + LOG(INFO) << " -- '" << SanitizePath(file_path) + << "' digest = " << digest; + } else { + LOG(ERROR) << "Failed to get digest for : '" << SanitizePath(file_path) + << "'."; + } + } else { + LOG(INFO) << " -- '" << SanitizePath(file_path) << "'"; + } +} + +} // namespace + +const size_t kKiloByte = 1024; // File size in bytes. +const size_t kMegaByte = 1024 * 1024; // File size in bytes. +// The maximum number of files to log when listing the content of a folder. +const size_t kMaxFilesInFolderToLog = 10; + +bool IsFileSizeLessThan(const base::FilePath& path, size_t size) { + int64_t file_size = 0; + return (base::GetFileSize(path, &file_size) && + static_cast<size_t>(file_size) < size); +} + +bool MatchSingleFileWithPattern(const base::FilePath& root_path, + const base::string16& pattern, + bool include_folders, + base::FilePath* match) { + DCHECK(match); + + base::FilePath match_found; + bool found_one = false; + + int file_type = base::FileEnumerator::FILES; + if (include_folders) + file_type |= base::FileEnumerator::DIRECTORIES; + + if (NameContainsWildcards(pattern)) { + base::FileEnumerator file_enum(root_path, false, file_type, pattern); + for (base::FilePath file = file_enum.Next(); !file.empty(); + file = file_enum.Next()) { + if (NameMatchesPattern(file.BaseName().value(), pattern, 0)) { + if (found_one) { + return false; + } else { + match_found = file; + found_one = true; + } + } + } + } else { + match_found = root_path.Append(pattern); + if (base::PathExists(match_found)) + found_one = true; + } + + if (found_one) + *match = match_found; + return found_one; +} + +void DeleteSoftwareRegistryKeys(const base::string16& software_key_path, + PUPData::PUP* pup) { + DCHECK(pup); + PUPData::DeleteRegistryKeyIfPresent( + RegKeyPath(HKEY_CURRENT_USER, software_key_path.c_str(), KEY_WOW64_32KEY), + pup); + PUPData::DeleteRegistryKeyIfPresent( + RegKeyPath(HKEY_LOCAL_MACHINE, software_key_path.c_str(), + KEY_WOW64_32KEY), + pup); + PUPData::DeleteRegistryKeyIfPresent( + RegKeyPath(HKEY_CURRENT_USER, software_key_path.c_str(), KEY_WOW64_64KEY), + pup); + PUPData::DeleteRegistryKeyIfPresent( + RegKeyPath(HKEY_LOCAL_MACHINE, software_key_path.c_str(), + KEY_WOW64_64KEY), + pup); +} + +void CollectPathRecursively(const base::FilePath& path, PUPData::PUP* pup) { + DCHECK(pup); + if (base::PathExists(path)) + CollectPathsRecursively(path, pup); +} + +void CollectSinglePath(const base::FilePath& path, PUPData::PUP* pup) { + DCHECK(pup); + if (base::PathExists(path) && !base::DirectoryExists(path)) + pup->AddDiskFootprint(path); +} + +void CollectDiskFootprintRecursively(int csidl, + const base::char16* path, + PUPData::PUP* pup) { + DCHECK_NE(csidl, PUPData::kInvalidCsidl); + DCHECK(path); + + base::FilePath expanded_path( + ExpandSpecialFolderPath(csidl, base::FilePath(path))); + if (expanded_path.empty()) + return; + CollectPathRecursively(expanded_path, pup); +} + +bool IsKnownFileByDigest(const base::FilePath& path, + const SignatureMatcherAPI* signature_matcher, + const char* const digests[], + size_t digests_length) { + DCHECK(signature_matcher); + if (base::DirectoryExists(path) || !base::PathExists(path)) + return false; + + std::string path_digest; + if (!signature_matcher->ComputeSHA256DigestOfPath(path, &path_digest)) { + PLOG(ERROR) << "Can't compute file digest: '" << SanitizePath(path) << "'."; + return false; + } + + for (size_t index = 0; index < digests_length; ++index) { + const char* expected_digest = digests[index]; + DCHECK(expected_digest); + DCHECK_EQ(expected_digest, base::ToUpperASCII(expected_digest)); + DCHECK_EQ(64UL, strlen(expected_digest)); + if (path_digest.compare(expected_digest) == 0) + return true; + } + + return false; +} + +bool IsKnownFileByDigestInfo(const base::FilePath& fullpath, + const SignatureMatcherAPI* signature_matcher, + const FileDigestInfo* digests, + size_t digests_length) { + DCHECK(signature_matcher); + DCHECK(digests); + + if (base::DirectoryExists(fullpath) || !base::PathExists(fullpath)) + return false; + + size_t filesize = 0; + std::string digest; + for (size_t index = 0; index < digests_length; ++index) { + if (signature_matcher->MatchFileDigestInfo(fullpath, &filesize, &digest, + digests[index])) { + return true; + } + } + return false; +} + +bool IsKnownFileByOriginalFilename(const base::FilePath& path, + const SignatureMatcherAPI* signature_matcher, + const base::char16* const names[], + size_t names_length) { + DCHECK(signature_matcher); + DCHECK(names); + VersionInformation version_information; + if (base::DirectoryExists(path) || !base::PathExists(path) || + !signature_matcher->RetrieveVersionInformation(path, + &version_information)) { + return false; + } + + for (size_t i = 0; i < names_length; ++i) { + if (String16EqualsCaseInsensitive(version_information.original_filename, + names[i])) { + return true; + } + } + return false; +} + +bool IsKnownFileByCompanyName(const base::FilePath& path, + const SignatureMatcherAPI* signature_matcher, + const base::char16* const names[], + size_t names_length) { + DCHECK(signature_matcher); + DCHECK(names); + VersionInformation version_information; + if (base::DirectoryExists(path) || !base::PathExists(path) || + !signature_matcher->RetrieveVersionInformation(path, + &version_information)) { + return false; + } + + for (size_t i = 0; i < names_length; ++i) { + if (String16EqualsCaseInsensitive(version_information.company_name, + names[i])) { + return true; + } + } + return false; +} + +void LogFoundDigest(const base::FilePath file_path, + const char* prefix, + PUPData::PUP* pup) { + DCHECK(prefix); + std::string digest; + int64_t size = -1; + if (!base::GetFileSize(file_path, &size)) + PLOG(ERROR) << "Failed to get size for: '" << SanitizePath(file_path) + << "'."; + + if (ComputeSHA256DigestOfPath(file_path, &digest)) { + LOG(INFO) << "Found digest for " << prefix << ", path: '" + << SanitizePath(file_path) << "', digest: '" << digest + << "', size: '" << size << "'."; + } else { + LOG(INFO) << "Failed to get digest for " << prefix << ", path: '" + << SanitizePath(file_path) << "', size: '" << size << "'."; + } +} + +void LogFoundDigest(const base::FilePath file_path, const char* prefix) { + LogFoundDigest(file_path, prefix, nullptr); +} + +void LogFolderContent(const base::FilePath& folder_path) { + base::FileEnumerator file_enum(folder_path, true, + base::FileEnumerator::FILES); + size_t nb_files = 0; + for (base::FilePath file_path = file_enum.Next(); !file_path.empty(); + file_path = file_enum.Next()) { + LogFile(file_path); + if (++nb_files > kMaxFilesInFolderToLog) { + LOG(INFO) << "The folder contains too many files."; + return; + } + } +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/scanner/matcher_util.h b/chrome/chrome_cleaner/scanner/matcher_util.h new file mode 100644 index 0000000..c792c14 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/matcher_util.h
@@ -0,0 +1,93 @@ +// Copyright 2018 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_CHROME_CLEANER_SCANNER_MATCHER_UTIL_H_ +#define CHROME_CHROME_CLEANER_SCANNER_MATCHER_UTIL_H_ + +#include <set> +#include <string> +#include <vector> + +#include "base/strings/string16.h" +#include "chrome/chrome_cleaner/pup_data/pup_data.h" +#include "chrome/chrome_cleaner/settings/matching_options.h" + +namespace base { +class FilePath; +} // namespace base + +namespace chrome_cleaner { + +class SignatureMatcherAPI; + +extern const size_t kKiloByte; +extern const size_t kMegaByte; +extern const size_t kMaxFilesInFolderToLog; // Exposed for unittests. + +// Return whether the file |path| has a smaller size than |size|. +bool IsFileSizeLessThan(const base::FilePath& path, size_t size); + +// Find a single matching file for |pattern| located in |root_path|. Wild-cards +// are allowed in |pattern| only. |include_folders| flag controls whether or not +// the folders should be taken into account. |match| is set to the matching file +// path. If none or more than one file are found, the function returns false. +bool MatchSingleFileWithPattern(const base::FilePath& root_path, + const base::string16& pattern, + bool include_folders, + base::FilePath* match); + +void DeleteSoftwareRegistryKeys(const base::string16& software_key_path, + PUPData::PUP* pup); + +void CollectSinglePath(const base::FilePath& path, PUPData::PUP* pup); + +void CollectPathRecursively(const base::FilePath& path, PUPData::PUP* pup); + +void CollectDiskFootprintRecursively(int csidl, + const base::char16* path, + PUPData::PUP* pup); + +bool IsKnownFileByDigest(const base::FilePath& path, + const SignatureMatcherAPI* signature_matcher, + const char* const digests[], + size_t digests_length); + +// A pair of filesize and digest. The filesize is used to avoid computing the +// digest of a file. +struct FileDigestInfo { + const char* const digest; + size_t filesize; +}; + +// Check whether the checksum (sha256) of a given file is part of a sorted +// array of |FileDigestInfo|. +bool IsKnownFileByDigestInfo(const base::FilePath& path, + const SignatureMatcherAPI* signature_matcher, + const FileDigestInfo* digests, + size_t digests_length); + +bool IsKnownFileByOriginalFilename(const base::FilePath& path, + const SignatureMatcherAPI* signature_matcher, + const base::char16* const names[], + size_t names_length); + +bool IsKnownFileByCompanyName(const base::FilePath& path, + const SignatureMatcherAPI* signature_matcher, + const base::char16* const names[], + size_t names_length); + +// Log the found digest of |file_path| described by |prefix|. +void LogFoundDigest(const base::FilePath file_path, + const char* prefix, + PUPData::PUP* pup); + +// This is equivalent to the above LogFoundDigest(file_path, prefix, nullptr). +void LogFoundDigest(const base::FilePath file_path, const char* prefix); + +// This is equivalent to the above LogFolderContent(folder_path, nullptr). +void LogFolderContent(const base::FilePath& folder_path); + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_SCANNER_MATCHER_UTIL_H_
diff --git a/chrome/chrome_cleaner/scanner/matcher_util_unittest.cc b/chrome/chrome_cleaner/scanner/matcher_util_unittest.cc new file mode 100644 index 0000000..3dc353b9 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/matcher_util_unittest.cc
@@ -0,0 +1,448 @@ +// Copyright 2018 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/chrome_cleaner/scanner/matcher_util.h" + +#include <shlobj.h> + +#include <memory> +#include <string> + +#include "base/command_line.h" +#include "base/path_service.h" +#include "base/strings/strcat.h" +#include "base/strings/string_number_conversions.h" +#include "base/test/scoped_path_override.h" +#include "base/test/test_reg_util_win.h" +#include "base/win/registry.h" +#include "chrome/chrome_cleaner/os/file_path_sanitization.h" +#include "chrome/chrome_cleaner/scanner/signature_matcher.h" +#include "chrome/chrome_cleaner/test/resources/grit/test_resources.h" +#include "chrome/chrome_cleaner/test/test_file_util.h" +#include "chrome/chrome_cleaner/test/test_pup_data.h" +#include "chrome/chrome_cleaner/test/test_signature_matcher.h" +#include "chrome/chrome_cleaner/test/test_task_scheduler.h" +#include "chrome/chrome_cleaner/test/test_util.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace chrome_cleaner { + +namespace { + +constexpr base::char16 kFileName1[] = L"File1"; +constexpr base::char16 kFileName2[] = L"File2"; +constexpr base::char16 kFileName3[] = L"File3"; +constexpr base::char16 kFileName4[] = L"File4"; + +constexpr char kFileContent1[] = "This is the file content."; +constexpr char kFileContent2[] = "Hi!"; +constexpr char kFileContent3[] = "Hello World!"; +constexpr char kFileContent4[] = "Ho!"; + +constexpr char kFileContent[] = "This is the file content."; + +const char* const kKnownContentDigests[] = { + "00D2BB3E285BA62224888A9AD874AC2787D4CF681F30A2FD8EE2873859ECE1DC", + // Hash for content: |kFileContent|. + "BD283E41A3672B6BDAA574F8BD7176F8BCA95BD81383CDE32AA6D78B1DB0E371", +}; + +constexpr base::char16 kKnownOriginalFilename[] = L"uws.exe"; +constexpr base::char16 kUnknownOriginalFilename[] = L"knowngood.exe"; +const base::char16* const kKnownOriginalFilenames[] = { + L"dummy entry", L"uws.exe", L"zombie uws.exe", +}; + +constexpr base::char16 kKnownCompanyName[] = L"uws vendor inc"; +constexpr base::char16 kUnknownCompanyName[] = L"paradise"; +const base::char16* const kKnownCompanyNames[] = { + L"dummy entry", L"uws vendor inc", L"ACME", +}; + +constexpr FileDigestInfo kFileContentDigestInfos[] = { + {"02544E052F29BBA79C81243EC63B43B6CD85B185461928E65BFF501346C62A75", 33}, + {"04614470DDF4939091F5EC4A13C92A9EAAACF07CA5C3F713E792E2D21CD24075", 21}, + // Hash for content: |kFileContent2|. + {"82E0B92772BC0DA59AAB0B9231AA006FB37B4F99EC3E853C5A62786A1C7215BD", 4}, + {"9000000000000000000000000000000000000000000000000000000000000009", 4}, + {"94F7BDF53CDFDE7AA5E5C90BCDA6793B7377CE39E2591ABC758EBAE8072A275C", 12}, + // Hash for content: |kFileContent1|. + {"BD283E41A3672B6BDAA574F8BD7176F8BCA95BD81383CDE32AA6D78B1DB0E371", 26}, +}; + +// Messages are logged to a vector for testing. +class LoggingTest : public testing::Test { + public: + LoggingOverride logger_; +}; + +} // namespace + +TEST(MatcherUtilTest, IsKnownFileByDigest) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + base::FilePath file_path1(temp_dir.GetPath().Append(kFileName1)); + base::FilePath file_path2(temp_dir.GetPath().Append(kFileName2)); + base::FilePath file_path3(temp_dir.GetPath().Append(kFileName3)); + + CreateFileWithContent(file_path1, kFileContent, sizeof(kFileContent)); + CreateFileWithRepeatedContent(file_path2, kFileContent, sizeof(kFileContent), + 2); + + std::unique_ptr<SignatureMatcher> signature_matcher = + std::make_unique<SignatureMatcher>(); + ASSERT_TRUE(signature_matcher); + + // Hash: BD283E41A3672B6BDAA574F8BD7176F8BCA95BD81383CDE32AA6D78B1DB0E371. + EXPECT_TRUE(IsKnownFileByDigest(file_path1, signature_matcher.get(), + kKnownContentDigests, + base::size(kKnownContentDigests))); + // Hash: not present. + EXPECT_FALSE(IsKnownFileByDigest(file_path2, signature_matcher.get(), + kKnownContentDigests, + base::size(kKnownContentDigests))); + // The file doesn't exist. + EXPECT_FALSE(IsKnownFileByDigest(file_path3, signature_matcher.get(), + kKnownContentDigests, + base::size(kKnownContentDigests))); +} + +TEST(MatcherUtilTest, IsKnownFileByDigestInfo) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + base::FilePath file_path1(temp_dir.GetPath().Append(kFileName1)); + base::FilePath file_path2(temp_dir.GetPath().Append(kFileName2)); + base::FilePath file_path3(temp_dir.GetPath().Append(kFileName3)); + base::FilePath file_path4(temp_dir.GetPath().Append(kFileName4)); + + CreateFileWithContent(file_path1, kFileContent1, sizeof(kFileContent1)); + CreateFileWithContent(file_path2, kFileContent2, sizeof(kFileContent2)); + CreateFileWithContent(file_path3, kFileContent3, sizeof(kFileContent3)); + + std::unique_ptr<SignatureMatcher> signature_matcher = + std::make_unique<SignatureMatcher>(); + + // Search BD283E41A3672B6BDAA574F8BD7176F8BCA95BD81383CDE32AA6D78B1DB0E371. + EXPECT_TRUE(IsKnownFileByDigestInfo(file_path1, signature_matcher.get(), + kFileContentDigestInfos, + base::size(kFileContentDigestInfos))); + // Search 82E0B92772BC0DA59AAB0B9231AA006FB37B4F99EC3E853C5A62786A1C7215BD. + EXPECT_TRUE(IsKnownFileByDigestInfo(file_path2, signature_matcher.get(), + kFileContentDigestInfos, + base::size(kFileContentDigestInfos))); + + // Replace the content of file_path2 with a content of the same size, it + // must no longer match. + ASSERT_EQ(sizeof(kFileContent2), sizeof(kFileContent4)); + CreateFileWithContent(file_path2, kFileContent4, sizeof(kFileContent4)); + EXPECT_FALSE(IsKnownFileByDigestInfo(file_path2, signature_matcher.get(), + kFileContentDigestInfos, + base::size(kFileContentDigestInfos))); + + // The digest of |file_path3| is not in the array. + EXPECT_FALSE(IsKnownFileByDigestInfo(file_path3, signature_matcher.get(), + kFileContentDigestInfos, + base::size(kFileContentDigestInfos))); + // The |file_path4| doesn't exist. + EXPECT_FALSE(IsKnownFileByDigestInfo(file_path4, signature_matcher.get(), + kFileContentDigestInfos, + base::size(kFileContentDigestInfos))); +} + +TEST(MatcherUtilTest, IsKnownFileByOriginalFilename) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + + TestSignatureMatcher signature_matcher; + + const base::FilePath normalized_temp_dir_path = + NormalizePath(temp_dir.GetPath()); + + // A non-existing file should not be recognized. + base::FilePath nonexistent_file_path( + normalized_temp_dir_path.Append(kFileName1)); + EXPECT_FALSE(IsKnownFileByOriginalFilename( + nonexistent_file_path, &signature_matcher, kKnownOriginalFilenames, + base::size(kKnownOriginalFilenames))); + + // An existing file without version information should not be recognized. + base::FilePath file_path2(normalized_temp_dir_path.Append(kFileName2)); + CreateFileWithContent(file_path2, kFileContent, sizeof(kFileContent)); + EXPECT_FALSE(IsKnownFileByOriginalFilename( + file_path2, &signature_matcher, kKnownOriginalFilenames, + base::size(kKnownOriginalFilenames))); + + // A file with version information but not in the array should not be + // recognized. + base::FilePath file_path3(normalized_temp_dir_path.Append(kFileName3)); + + VersionInformation goodware_information = {}; + goodware_information.original_filename = kUnknownOriginalFilename; + signature_matcher.MatchVersionInformation(file_path3, goodware_information); + + CreateFileWithContent(file_path3, kFileContent, sizeof(kFileContent)); + EXPECT_FALSE(IsKnownFileByOriginalFilename( + file_path3, &signature_matcher, kKnownOriginalFilenames, + base::size(kKnownOriginalFilenames))); + + // A file with version information present in the array should be recognized. + base::FilePath file_path4(normalized_temp_dir_path.Append(kFileName4)); + + VersionInformation badware_information = {}; + badware_information.original_filename = kKnownOriginalFilename; + signature_matcher.MatchVersionInformation(file_path4, badware_information); + + CreateFileWithContent(file_path4, kFileContent, sizeof(kFileContent)); + EXPECT_TRUE(IsKnownFileByOriginalFilename( + file_path4, &signature_matcher, kKnownOriginalFilenames, + base::size(kKnownOriginalFilenames))); +} + +TEST(MatcherUtilTest, IsKnownFileByCompanyName) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + + const base::FilePath normalized_temp_dir_path = + NormalizePath(temp_dir.GetPath()); + + TestSignatureMatcher signature_matcher; + + // A non-existing file should not be recognized. + base::FilePath nonexistent_file_path( + normalized_temp_dir_path.Append(kFileName1)); + EXPECT_FALSE(IsKnownFileByCompanyName(nonexistent_file_path, + &signature_matcher, kKnownCompanyNames, + base::size(kKnownCompanyNames))); + + // An existing file without version information should not be recognized. + base::FilePath file_path2(normalized_temp_dir_path.Append(kFileName2)); + CreateFileWithContent(file_path2, kFileContent, sizeof(kFileContent)); + EXPECT_FALSE(IsKnownFileByCompanyName(file_path2, &signature_matcher, + kKnownCompanyNames, + base::size(kKnownCompanyNames))); + + // A file with version information but not in the array should not be + // recognized. + base::FilePath file_path3(normalized_temp_dir_path.Append(kFileName3)); + + VersionInformation goodware_information = {}; + goodware_information.company_name = kUnknownCompanyName; + signature_matcher.MatchVersionInformation(file_path3, goodware_information); + + CreateFileWithContent(file_path3, kFileContent, sizeof(kFileContent)); + EXPECT_FALSE(IsKnownFileByCompanyName(file_path3, &signature_matcher, + kKnownCompanyNames, + base::size(kKnownCompanyNames))); + + // A file with version information present in the array should be recognized. + base::FilePath file_path4(normalized_temp_dir_path.Append(kFileName4)); + + VersionInformation badware_information = {}; + badware_information.company_name = kKnownCompanyName; + signature_matcher.MatchVersionInformation(file_path4, badware_information); + + CreateFileWithContent(file_path4, kFileContent, sizeof(kFileContent)); + EXPECT_TRUE(IsKnownFileByCompanyName(file_path4, &signature_matcher, + kKnownCompanyNames, + base::size(kKnownCompanyNames))); +} + +TEST(MatcherUtilTest, MatchSingleFileWithPattern) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + base::FilePath match; + + // Collect no path. + EXPECT_FALSE( + MatchSingleFileWithPattern(temp_dir.GetPath(), L"*", false, &match)); + + // Collect exactly one path matching the pattern. + base::FilePath file_path1(temp_dir.GetPath().Append(L"dummy.1.tar.gz")); + base::FilePath file_path2(temp_dir.GetPath().Append(L"uws-name.exe")); + CreateFileWithContent(file_path1, kFileContent, sizeof(kFileContent)); + CreateFileWithContent(file_path2, kFileContent, sizeof(kFileContent)); + match.clear(); + EXPECT_TRUE(MatchSingleFileWithPattern(temp_dir.GetPath(), L"*.*.*.*", false, + &match)); + EXPECT_EQ(file_path1, match); + match.clear(); + EXPECT_TRUE(MatchSingleFileWithPattern(temp_dir.GetPath(), L"uws*.exe", false, + &match)); + EXPECT_EQ(file_path2, match); + match.clear(); + EXPECT_TRUE(MatchSingleFileWithPattern(temp_dir.GetPath(), LR"(uws-????.exe)", + false, &match)); + EXPECT_EQ(file_path2, match); + + // Collecting multiple paths should fail. + base::FilePath file_path3(temp_dir.GetPath().Append(L"dummy.2.tar.gz")); + CreateFileWithContent(file_path3, kFileContent, sizeof(kFileContent)); + EXPECT_FALSE(MatchSingleFileWithPattern(temp_dir.GetPath(), L"*.*.*.*", false, + &match)); +} + +TEST(MatcherUtilTest, MatchSingleFileWithPatternWithFolders) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + base::FilePath match; + + // Collect no path. + EXPECT_FALSE( + MatchSingleFileWithPattern(temp_dir.GetPath(), L"*", true, &match)); + + // Add a folder to the main folder. + base::FilePath folder = temp_dir.GetPath().Append(L"folder"); + ASSERT_TRUE(base::CreateDirectory(folder)); + + // Collect exactly one path matching the pattern. + base::FilePath file_path(temp_dir.GetPath().Append(L"dummy.1.tar.gz")); + CreateFileWithContent(file_path, kFileContent, sizeof(kFileContent)); + + match.clear(); + EXPECT_TRUE(MatchSingleFileWithPattern(temp_dir.GetPath(), L"*.*.*.*", false, + &match)); + EXPECT_EQ(file_path, match); + + match.clear(); + EXPECT_TRUE( + MatchSingleFileWithPattern(temp_dir.GetPath(), L"*.*.*.*", true, &match)); + EXPECT_EQ(file_path, match); + + // Collect with a wild-card matching everything. + match.clear(); + EXPECT_TRUE( + MatchSingleFileWithPattern(temp_dir.GetPath(), L"*", false, &match)); + EXPECT_EQ(file_path, match); + + match.clear(); + EXPECT_FALSE( + MatchSingleFileWithPattern(temp_dir.GetPath(), L"*", true, &match)); + EXPECT_TRUE(match.empty()); + + // Collecting the folder. + EXPECT_FALSE( + MatchSingleFileWithPattern(temp_dir.GetPath(), L"fold?r", false, &match)); + EXPECT_TRUE(match.empty()); + + EXPECT_TRUE( + MatchSingleFileWithPattern(temp_dir.GetPath(), L"fold?r", true, &match)); + EXPECT_EQ(folder, match); +} + +TEST(MatcherUtilTest, CollectPathRecursively) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + + // Add a folder to the main folder. + base::FilePath folder = temp_dir.GetPath().Append(L"folder"); + ASSERT_TRUE(base::CreateDirectory(folder)); + base::FilePath subfolder = folder.Append(L"subfolder"); + ASSERT_TRUE(base::CreateDirectory(subfolder)); + + base::FilePath file_path1(folder.Append(kFileName1)); + CreateFileWithContent(file_path1, kFileContent, sizeof(kFileContent)); + base::FilePath file_path2(subfolder.Append(kFileName2)); + CreateFileWithContent(file_path2, kFileContent, sizeof(kFileContent)); + + base::FilePath nonexistent_path = temp_dir.GetPath().Append(L"nonexistent"); + + SimpleTestPUP pup; + CollectPathRecursively(nonexistent_path, &pup); + EXPECT_TRUE(pup.expanded_disk_footprints.empty()); + + CollectPathRecursively(folder, &pup); + EXPECT_FALSE(pup.expanded_disk_footprints.empty()); + + ExpectDiskFootprint(pup, folder); + ExpectDiskFootprint(pup, subfolder); + ExpectDiskFootprint(pup, file_path1); + ExpectDiskFootprint(pup, file_path2); +} + +TEST(MatcherUtilTest, CollectDiskFootprintRecursively) { + base::FilePath local_appdata_path( + ExpandSpecialFolderPath(CSIDL_LOCAL_APPDATA, base::FilePath())); + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDirUnderPath(local_appdata_path)); + + // Add a folder to the main folder. + base::FilePath folder = temp_dir.GetPath().Append(L"folder"); + ASSERT_TRUE(base::CreateDirectory(folder)); + base::FilePath subfolder = folder.Append(L"subfolder"); + ASSERT_TRUE(base::CreateDirectory(subfolder)); + + base::FilePath file_path1(folder.Append(kFileName1)); + CreateFileWithContent(file_path1, kFileContent, sizeof(kFileContent)); + base::FilePath file_path2(subfolder.Append(kFileName2)); + CreateFileWithContent(file_path2, kFileContent, sizeof(kFileContent)); + + // Create the relative paths. + base::FilePath basename = temp_dir.GetPath().BaseName(); + base::FilePath folder_path = basename.Append(L"Folder"); + base::FilePath not_folder_path = basename.Append(L"not_Folder"); + + SimpleTestPUP pup; + // Collect in the wrong CSIDL. + CollectDiskFootprintRecursively(CSIDL_APPDATA, folder_path.value().c_str(), + &pup); + EXPECT_TRUE(pup.expanded_disk_footprints.empty()); + + // Collect in the good CSIDL but an inexisting folder. + CollectDiskFootprintRecursively(CSIDL_LOCAL_APPDATA, + not_folder_path.value().c_str(), &pup); + EXPECT_TRUE(pup.expanded_disk_footprints.empty()); + + // Collect the right files. + CollectDiskFootprintRecursively(CSIDL_LOCAL_APPDATA, + folder_path.value().c_str(), &pup); + EXPECT_FALSE(pup.expanded_disk_footprints.empty()); + + ExpectDiskFootprint(pup, folder); + ExpectDiskFootprint(pup, subfolder); + ExpectDiskFootprint(pup, file_path1); + ExpectDiskFootprint(pup, file_path2); +} + +TEST_F(LoggingTest, LogFolderContent) { + base::ScopedTempDir temp_dir; + ASSERT_TRUE(temp_dir.CreateUniqueTempDir()); + base::FilePath temp_dir_path = temp_dir.GetPath(); + base::FilePath file_path1(temp_dir_path.Append(kFileName1)); + base::FilePath file_path2(temp_dir_path.Append(kFileName2)); + CreateFileWithContent(file_path1, kFileContent, sizeof(kFileContent)); + CreateFileWithContent(file_path2, kFileContent, sizeof(kFileContent)); + + // Add a folder to the main folder. + base::FilePath subfolder = temp_dir.GetPath().Append(L"folder"); + ASSERT_TRUE(base::CreateDirectory(subfolder)); + base::FilePath file_path3(subfolder.Append(kFileName3)); + CreateFileWithContent(file_path3, kFileContent, sizeof(kFileContent)); + + LOG(INFO) << "Logging content of " << temp_dir.GetPath().value(); + + LogFolderContent(temp_dir.GetPath()); + + const std::string filename1 = base::WideToUTF8(kFileName1); + const std::string filename2 = base::WideToUTF8(kFileName2); + const std::string filename3 = base::WideToUTF8(kFileName3); + EXPECT_TRUE(logger_.LoggingMessagesContain(filename1)); + EXPECT_TRUE(logger_.LoggingMessagesContain(filename2)); + EXPECT_TRUE(logger_.LoggingMessagesContain(filename3)); + + // Add more files in the folder than maximum to be logged. + logger_.FlushMessages(); + for (size_t count = 0; count < kMaxFilesInFolderToLog; ++count) { + base::FilePath file_path(temp_dir_path.Append( + base::StrCat({L"dummy", base::NumberToString16(count)}))); + CreateFileWithContent(file_path, kFileContent, sizeof(kFileContent)); + } + + LOG(INFO) << "Logging content of " << temp_dir.GetPath().value(); + LogFolderContent(temp_dir.GetPath()); + + EXPECT_TRUE( + logger_.LoggingMessagesContain("The folder contains too many files")); +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/scanner/scanner.h b/chrome/chrome_cleaner/scanner/scanner.h new file mode 100644 index 0000000..b80c64c --- /dev/null +++ b/chrome/chrome_cleaner/scanner/scanner.h
@@ -0,0 +1,54 @@ +// Copyright 2018 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_CHROME_CLEANER_SCANNER_SCANNER_H_ +#define CHROME_CHROME_CLEANER_SCANNER_SCANNER_H_ + +#include <memory> +#include <vector> + +#include "base/callback.h" +#include "chrome/chrome_cleaner/constants/uws_id.h" +#include "components/chrome_cleaner/public/constants/result_codes.h" + +namespace chrome_cleaner { + +// This class defines the scanning interface and is used as a base for the +// scanners for different engines. +class Scanner { + public: + // The type of callback to be called when an UwS is detected. + typedef base::RepeatingCallback<void(UwSId found_uws)> FoundUwSCallback; + + // The type of callback that is called when the scan completes. + // |status| should contain RESULT_CODE_SUCCESS if no failures were encountered + // or error status code otherwise. + typedef base::OnceCallback<void(ResultCode status, + const std::vector<UwSId>& found_pups)> + DoneCallback; + + virtual ~Scanner() {} + + // Start scanning for UwS. When an UwS is detected and if |Stop| has not been + // called, |found_uws_callback| is called. If scan is done in number of tasks, + // |progress_callback| may be called to report ratio of completed tasks. If + // the scan completes before |Stop| is called, then |done_callback| is called. + // Returns true if startup succeeded. If the startup fails, |done_callback| + // will be called with the failure code. + virtual bool Start(const FoundUwSCallback& found_uws_callback, + const DoneCallback done_callback) = 0; + + // Interrupts the current scanning. It's a noop when scanning has not started + // or is already done, or has already been stopped. + virtual void Stop() = 0; + + // When calling |Stop|, some tasks may still be running, so make sure to call + // |IsCompletelyDone| and allow the main UI to pump messages to let the task + // tracker mark all tasks as done before clearing data passed to the scanner. + virtual bool IsCompletelyDone() const = 0; +}; + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_SCANNER_SCANNER_H_
diff --git a/chrome/chrome_cleaner/scanner/scanner_controller.cc b/chrome/chrome_cleaner/scanner/scanner_controller.cc new file mode 100644 index 0000000..8c32d70 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/scanner_controller.cc
@@ -0,0 +1,164 @@ +// Copyright 2018 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/chrome_cleaner/scanner/scanner_controller.h" + +#include <stdlib.h> +#include <time.h> +#include <memory> + +#include "base/bind.h" +#include "base/logging.h" +#include "base/run_loop.h" +#include "base/threading/thread_task_runner_handle.h" +#include "chrome/chrome_cleaner/ipc/sandbox.h" +#include "chrome/chrome_cleaner/logging/logging_service_api.h" +#include "chrome/chrome_cleaner/os/process.h" +#include "chrome/chrome_cleaner/os/shutdown_watchdog.h" +#include "chrome/chrome_cleaner/settings/settings.h" + +namespace chrome_cleaner { + +namespace { + +// The maximal allowed time to run the scanner (5 minutes). +const uint32_t kWatchdogTimeoutInSeconds = 5 * 60; + +ResultCode GetResultCodeFromFoundUws(const std::vector<UwSId>& found_uws) { + for (UwSId uws_id : found_uws) { + if (!PUPData::IsKnownPUP(uws_id)) + return RESULT_CODE_ENGINE_REPORTED_UNSUPPORTED_UWS; + } + + // Removal has precedence over other states. + if (PUPData::HasFlaggedPUP(found_uws, &PUPData::HasRemovalFlag)) { + return RESULT_CODE_SUCCESS; + } + + if (PUPData::HasFlaggedPUP(found_uws, &PUPData::HasConfirmedUwSFlag)) { + return RESULT_CODE_EXAMINED_FOR_REMOVAL_ONLY; + } + + if (PUPData::HasFlaggedPUP(found_uws, &PUPData::HasReportOnlyFlag)) { + return RESULT_CODE_REPORT_ONLY_PUPS_FOUND; + } + + DCHECK(found_uws.empty()); + return RESULT_CODE_NO_PUPS_FOUND; +} + +} // namespace + +ScannerController::~ScannerController() = default; + +int ScannerController::ScanOnly() { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + + // Make sure the scanning process gets completed in a reasonable amount of + // time, otherwise log it and terminate the process. + base::TimeDelta watchdog_timeout = + base::TimeDelta::FromSeconds(watchdog_timeout_in_seconds_); + + Settings* settings = Settings::GetInstance(); + if (settings->scanning_timeout_overridden()) + watchdog_timeout = settings->scanning_timeout(); + + std::unique_ptr<ShutdownWatchdog> watchdog; + if (!watchdog_timeout.is_zero()) { + watchdog = std::make_unique<ShutdownWatchdog>( + watchdog_timeout, + base::BindOnce(&ScannerController::WatchdogTimeoutCallback, + base::Unretained(this))); + watchdog->Arm(); + } + + base::RunLoop run_loop; + quit_closure_ = run_loop.QuitWhenIdleClosure(); + StartScan(); + run_loop.Run(); + + if (watchdog) + watchdog->Disarm(); + + DCHECK_NE(RESULT_CODE_INVALID, result_code_); + return static_cast<int>(result_code_); +} + +ScannerController::ScannerController(RegistryLogger* registry_logger) + : registry_logger_(registry_logger), + watchdog_timeout_in_seconds_(kWatchdogTimeoutInSeconds) { + DCHECK(registry_logger); +} + +void ScannerController::DoneScanning(ResultCode status, + const std::vector<UwSId>& found_pups) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + + UpdateScanResults(found_pups); + if (status == RESULT_CODE_SUCCESS) + status = GetResultCodeFromFoundUws(found_pups); + { + base::AutoLock lock(lock_); + result_code_ = status; + } + + LoggingServiceAPI* logging_service_api = LoggingServiceAPI::GetInstance(); + + SystemResourceUsage stats; + if (GetSystemResourceUsage(::GetCurrentProcess(), &stats)) + logging_service_api->LogProcessInformation(SandboxType::kNonSandboxed, + stats); + std::map<SandboxType, SystemResourceUsage> sbox_process_usage = + GetSandboxSystemResourceUsage(); + for (const auto& type_usage : sbox_process_usage) { + LoggingServiceAPI::GetInstance()->LogProcessInformation(type_usage.first, + type_usage.second); + } + + logging_service_api->SetExitCode(status); + logging_service_api->MaybeSaveLogsToFile(L""); + logging_service_api->SendLogsToSafeBrowsing( + base::BindRepeating(&ScannerController::LogsUploadComplete, + base::Unretained(this)), + registry_logger_); +} + +void ScannerController::UpdateScanResults( + const std::vector<UwSId>& found_pups) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + // Log which PUPs were found. + registry_logger_->RecordFoundPUPs(found_pups); + + ResultCode result = GetResultCodeFromFoundUws(found_pups); + { + base::AutoLock lock(lock_); + result_code_ = result; + } +} + +int ScannerController::WatchdogTimeoutCallback() { + ResultCode result_code; + { + base::AutoLock lock(lock_); + result_code = result_code_; + } + + int watchdog_result_code = + result_code == RESULT_CODE_SUCCESS + ? RESULT_CODE_WATCHDOG_TIMEOUT_WITH_REMOVABLE_UWS + : RESULT_CODE_WATCHDOG_TIMEOUT_WITHOUT_REMOVABLE_UWS; + + registry_logger_->WriteExitCode(watchdog_result_code); + registry_logger_->WriteEndTime(); + + return watchdog_result_code; +} + +void ScannerController::LogsUploadComplete(bool success) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE, + std::move(quit_closure_)); +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/scanner/scanner_controller.h b/chrome/chrome_cleaner/scanner/scanner_controller.h new file mode 100644 index 0000000..a584f676 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/scanner_controller.h
@@ -0,0 +1,71 @@ +// Copyright 2018 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_CHROME_CLEANER_SCANNER_SCANNER_CONTROLLER_H_ +#define CHROME_CHROME_CLEANER_SCANNER_SCANNER_CONTROLLER_H_ + +#include <vector> + +#include "base/callback_forward.h" +#include "base/macros.h" +#include "base/message_loop/message_loop.h" +#include "base/sequence_checker.h" +#include "base/synchronization/lock.h" +#include "chrome/chrome_cleaner/constants/uws_id.h" +#include "chrome/chrome_cleaner/logging/registry_logger.h" +#include "components/chrome_cleaner/public/constants/result_codes.h" + +namespace chrome_cleaner { + +// An abstract class which handles synchronization for the scan loop. +class ScannerController { + public: + virtual ~ScannerController(); + + int ScanOnly(); + + protected: + explicit ScannerController(RegistryLogger* registry_logger); + + virtual void StartScan() = 0; + + // Callback for StartScan which records which PUPs were found. + // Expects |status| to be RESULT_CODE_SUCCESS if there were no failures. + virtual void DoneScanning(ResultCode status, + const std::vector<UwSId>& found_pups); + + // Record |found_pups| to the registry and update |result_code_| in a + // thread-safe manner. + void UpdateScanResults(const std::vector<UwSId>& found_pups); + + // This callback is called from the watchdog's thread and must synchronize + // access to result_code_. + virtual int WatchdogTimeoutCallback(); + + RegistryLogger* registry_logger_; + SEQUENCE_CHECKER(sequence_checker_); + // Defines a task runner for the current thread, which will be accessible + // via base::ThreadTaskRunnerHandle::Get(). + base::MessageLoopForUI ui_message_loop_; + + // Allow subclasses to override the default watchdog timeout. + uint32_t watchdog_timeout_in_seconds_; + + private: + // Callback for LoggingServiceAPI::SendLogsToSafeBrowsing() that finishes the + // current run loop. + void LogsUploadComplete(bool success); + + mutable base::Lock lock_; // Protects |result_code_|. + ResultCode result_code_ = RESULT_CODE_INVALID; + + // Called by LogsUploadComplete() to quit the current run loop. + base::OnceClosure quit_closure_; + + DISALLOW_COPY_AND_ASSIGN(ScannerController); +}; + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_SCANNER_SCANNER_CONTROLLER_H_
diff --git a/chrome/chrome_cleaner/scanner/signature_matcher.cc b/chrome/chrome_cleaner/scanner/signature_matcher.cc new file mode 100644 index 0000000..a74eec5 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/signature_matcher.cc
@@ -0,0 +1,99 @@ +// Copyright 2018 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/chrome_cleaner/scanner/signature_matcher.h" + +#include <windows.h> + +#include <stdint.h> + +#include <memory> +#include <utility> + +#include "base/bind.h" +#include "base/callback_helpers.h" +#include "base/file_version_info.h" +#include "base/files/file.h" +#include "base/files/file_path.h" +#include "base/files/file_util.h" +#include "base/logging.h" +#include "base/sha1.h" +#include "base/strings/string_number_conversions.h" +#include "base/strings/string_util.h" +#include "base/strings/utf_string_conversions.h" +#include "chrome/chrome_cleaner/os/disk_util.h" +#include "chrome/chrome_cleaner/os/file_path_sanitization.h" +#include "chrome/chrome_cleaner/os/system_util.h" +#include "chrome/chrome_cleaner/scanner/matcher_util.h" + +namespace chrome_cleaner { + +bool SignatureMatcher::MatchFileDigestInfo( + const base::FilePath& path, + size_t* filesize, + std::string* digest, + const FileDigestInfo& digest_info) const { + DCHECK(filesize); + DCHECK(digest); + + if (*filesize == 0) { + DCHECK(digest->empty()); + int64_t local_filesize = 0; + if (!base::GetFileSize(path, &local_filesize)) { + LOG(ERROR) << "Failed to get filesize of path: '" << SanitizePath(path) + << "'."; + return false; + } + *filesize = local_filesize; + } else { + int64_t dcheck_filesize = 0; + DCHECK(base::GetFileSize(path, &dcheck_filesize) && + *filesize == static_cast<size_t>(dcheck_filesize)); + } + + if (digest_info.filesize != *filesize) + return false; + + if (digest->empty()) { + if (!ComputeSHA256DigestOfPath(path, digest)) { + digest->clear(); + LOG(ERROR) << "Unable to compute digest SHA256 for: '" + << SanitizePath(path) << "'."; + return false; + } + } else { + std::string dcheck_digest; + DCHECK(ComputeSHA256DigestOfPath(path, &dcheck_digest) && + *digest == dcheck_digest); + } + + return digest->compare(digest_info.digest) == 0; +} + +bool SignatureMatcher::ComputeSHA256DigestOfPath(const base::FilePath& path, + std::string* digest) const { + // TODO(pmbureau): Add caching to avoid recomputing digests. + // TODO(pmbureau): Add synchronization to avoid multiple file operation. + // TODO(pmbureau): Add copy of locked files. + return chrome_cleaner::ComputeSHA256DigestOfPath(path, digest); +} + +// TODO(pmbureau): Add a unittest for this function. +bool SignatureMatcher::RetrieveVersionInformation( + const base::FilePath& path, + VersionInformation* information) const { + DCHECK(information); + // TODO(pmbureau): Add caching to avoid recomputing information. + + std::unique_ptr<FileVersionInfo> version( + FileVersionInfo::CreateFileVersionInfo(path)); + if (!version.get()) + return false; + + information->company_name = version->company_name(); + information->original_filename = version->original_filename(); + return true; +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/scanner/signature_matcher.h b/chrome/chrome_cleaner/scanner/signature_matcher.h new file mode 100644 index 0000000..db0fe3f9 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/signature_matcher.h
@@ -0,0 +1,31 @@ +// Copyright 2018 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_CHROME_CLEANER_SCANNER_SIGNATURE_MATCHER_H_ +#define CHROME_CHROME_CLEANER_SCANNER_SIGNATURE_MATCHER_H_ + +#include "chrome/chrome_cleaner/scanner/signature_matcher_api.h" + +namespace chrome_cleaner { + +class SignatureMatcher : public SignatureMatcherAPI { + public: + SignatureMatcher() = default; + virtual ~SignatureMatcher() = default; + + // SignatureMatcherAPI implementation. + bool MatchFileDigestInfo(const base::FilePath& path, + size_t* filesize, + std::string* digest, + const FileDigestInfo& digest_info) const override; + bool ComputeSHA256DigestOfPath(const base::FilePath& path, + std::string* digest) const override; + bool RetrieveVersionInformation( + const base::FilePath& path, + VersionInformation* information) const override; +}; + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_SCANNER_SIGNATURE_MATCHER_H_
diff --git a/chrome/chrome_cleaner/scanner/signature_matcher_api.h b/chrome/chrome_cleaner/scanner/signature_matcher_api.h new file mode 100644 index 0000000..882f826 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/signature_matcher_api.h
@@ -0,0 +1,55 @@ +// Copyright 2018 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_CHROME_CLEANER_SCANNER_SIGNATURE_MATCHER_API_H_ +#define CHROME_CHROME_CLEANER_SCANNER_SIGNATURE_MATCHER_API_H_ + +#include <string> +#include <vector> + +#include "base/files/file_path.h" +#include "base/strings/string16.h" + +namespace chrome_cleaner { + +struct FileDigestInfo; + +// This structure holds version information about an executable. +// (see: base/file_version_info.h) +struct VersionInformation { + base::string16 company_name; + base::string16 original_filename; +}; + +// This class is used as a wrapper around the signature matcher calls. The +// purpose of the signature matcher is to match a sequence of bytes against +// a set of known signals and report the name of the rules that matches. +class SignatureMatcherAPI { + public: + virtual ~SignatureMatcherAPI() {} + + // Compare the file's digest info and return true on a successful match. + // |filesize| & |digest| are used if they are not initialized (e.g., 0 for + // |filesize| and an empty string for |digest|), and otherwise they are set + // using |path|. This is mainly so that tests can overload it. + virtual bool MatchFileDigestInfo(const base::FilePath& path, + size_t* filesize, + std::string* digest, + const FileDigestInfo& digest_info) const = 0; + + // Compute the SHA256 checksum of |path| and store it as base16 into |digest|. + // Return true on success. + virtual bool ComputeSHA256DigestOfPath(const base::FilePath& path, + std::string* digest) const = 0; + + // Retrieve version information fields of a given executable |path|. Return + // false if an error occurred. + virtual bool RetrieveVersionInformation( + const base::FilePath& path, + VersionInformation* information) const = 0; +}; + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_SCANNER_SIGNATURE_MATCHER_API_H_
diff --git a/chrome/chrome_cleaner/scanner/signature_matcher_unittest.cc b/chrome/chrome_cleaner/scanner/signature_matcher_unittest.cc new file mode 100644 index 0000000..a242e706 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/signature_matcher_unittest.cc
@@ -0,0 +1,103 @@ +// Copyright 2018 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/chrome_cleaner/scanner/signature_matcher.h" + +#include <memory> + +#include "base/bind.h" +#include "base/files/file_util.h" +#include "base/files/scoped_temp_dir.h" +#include "base/strings/string_util.h" +#include "base/synchronization/waitable_event.h" +#include "base/threading/thread.h" +#include "chrome/chrome_cleaner/scanner/matcher_util.h" +#include "chrome/chrome_cleaner/test/resources/grit/test_resources.h" +#include "chrome/chrome_cleaner/test/test_file_util.h" +#include "chrome/chrome_cleaner/test/test_strings.h" +#include "chrome/chrome_cleaner/test/test_util.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace chrome_cleaner { + +// Contents to be scanned. +const char kGoogleName1[] = "This is Google."; +const char kGoogleName2[] = "This is G00gle."; + +namespace { + +class SignatureMatcherTest : public testing::Test { + public: + void SetUp() override { + ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); + signature_matcher_ = std::make_unique<SignatureMatcher>(); + } + + SignatureMatcherAPI* signature_matcher() const { + return signature_matcher_.get(); + } + + private: + // The root of the scoped temporary folder that is used by some tests. + base::ScopedTempDir temp_dir_; + + // The signature matcher under test. + std::unique_ptr<SignatureMatcherAPI> signature_matcher_; +}; + +} // namespace + +TEST_F(SignatureMatcherTest, MatchFileDigestInfo) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + + size_t filesize = 0; + std::string digest; + + // Inexistent file. + base::FilePath path1(scoped_temp_dir.GetPath().Append(L"file1")); + EXPECT_FALSE(signature_matcher()->MatchFileDigestInfo(path1, &filesize, + &digest, {"", 0})); + // Wrong size. + CreateFileWithContent(path1, kGoogleName1, sizeof(kGoogleName1)); + EXPECT_FALSE(signature_matcher()->MatchFileDigestInfo(path1, &filesize, + &digest, {"", 0})); + EXPECT_EQ(sizeof(kGoogleName1), filesize); + filesize = 0; + + // Wrong digest. + EXPECT_FALSE(signature_matcher()->MatchFileDigestInfo( + path1, &filesize, &digest, {"", sizeof(kGoogleName1)})); + EXPECT_EQ(sizeof(kGoogleName1), filesize); + std::string digest1; + ASSERT_TRUE(signature_matcher()->ComputeSHA256DigestOfPath(path1, &digest1)); + EXPECT_EQ(digest1, digest); + + // Successful match. + EXPECT_TRUE(signature_matcher()->MatchFileDigestInfo( + path1, &filesize, &digest, {digest1.c_str(), sizeof(kGoogleName1)})); + // Should work again. + EXPECT_TRUE(signature_matcher()->MatchFileDigestInfo( + path1, &filesize, &digest, {digest1.c_str(), sizeof(kGoogleName1)})); + // And now with another file. + filesize = 0; + digest.clear(); + + base::FilePath path2(scoped_temp_dir.GetPath().Append(L"file2")); + EXPECT_FALSE(signature_matcher()->MatchFileDigestInfo( + path2, &filesize, &digest, {digest1.c_str(), sizeof(kGoogleName1)})); + + CreateFileWithContent(path2, kGoogleName2, sizeof(kGoogleName2)); + + std::string digest2; + ASSERT_TRUE(signature_matcher()->ComputeSHA256DigestOfPath(path2, &digest2)); + EXPECT_TRUE(signature_matcher()->MatchFileDigestInfo( + path2, &filesize, &digest, {digest2.c_str(), sizeof(kGoogleName2)})); + EXPECT_EQ(sizeof(kGoogleName2), filesize); + EXPECT_EQ(digest2, digest); + EXPECT_TRUE(signature_matcher()->MatchFileDigestInfo( + path2, &filesize, &digest, {digest2.c_str(), sizeof(kGoogleName2)})); +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/scanner/urza_scanner_controller.cc b/chrome/chrome_cleaner/scanner/urza_scanner_controller.cc new file mode 100644 index 0000000..12358210 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/urza_scanner_controller.cc
@@ -0,0 +1,46 @@ +// Copyright 2018 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/chrome_cleaner/scanner/urza_scanner_controller.h" + +#include "base/bind.h" +#include "base/bind_helpers.h" +#include "base/run_loop.h" + +namespace chrome_cleaner { + +UrzaScannerController::UrzaScannerController( + MatchingOptions* options, + std::unique_ptr<SignatureMatcherAPI> signature_matcher, + RegistryLogger* registry_logger) + : ScannerController(registry_logger), + signature_matcher_(std::move(signature_matcher)), + scanner_(*options, signature_matcher_.get(), registry_logger) { + DCHECK(signature_matcher_); +} + +UrzaScannerController::~UrzaScannerController() { + CHECK(!base::RunLoop::IsRunningOnCurrentThread()); + // TODO(joenotcharles): Clean up RunUntilIdle usage in loops. + while (!scanner_.IsCompletelyDone()) + base::RunLoop().RunUntilIdle(); +} + +void UrzaScannerController::StartScan() { + found_pups_.clear(); + scanner_.Start(base::BindRepeating(&UrzaScannerController::FoundUwSCallback, + base::Unretained(this)), + base::BindOnce(&UrzaScannerController::DoneScanning, + base::Unretained(this))); +} + +void UrzaScannerController::FoundUwSCallback(UwSId pup_id) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + // UrzaScannerImpl reports PUP only once when they are found, so the result + // code is updated only when necessary. + found_pups_.push_back(pup_id); + UpdateScanResults(found_pups_); +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/scanner/urza_scanner_controller.h b/chrome/chrome_cleaner/scanner/urza_scanner_controller.h new file mode 100644 index 0000000..f08a046 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/urza_scanner_controller.h
@@ -0,0 +1,42 @@ +// Copyright 2018 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_CHROME_CLEANER_SCANNER_URZA_SCANNER_CONTROLLER_H_ +#define CHROME_CHROME_CLEANER_SCANNER_URZA_SCANNER_CONTROLLER_H_ + +#include <vector> + +#include "chrome/chrome_cleaner/constants/uws_id.h" +#include "chrome/chrome_cleaner/logging/registry_logger.h" +#include "chrome/chrome_cleaner/scanner/scanner_controller.h" +#include "chrome/chrome_cleaner/scanner/signature_matcher_api.h" +#include "chrome/chrome_cleaner/scanner/urza_scanner_impl.h" +#include "chrome/chrome_cleaner/settings/matching_options.h" + +namespace chrome_cleaner { + +// The Urza (pre-ESET) implementation of the ScannerController. +class UrzaScannerController : public ScannerController { + public: + UrzaScannerController(MatchingOptions* options, + std::unique_ptr<SignatureMatcherAPI> signature_matcher, + RegistryLogger* registry_logger); + ~UrzaScannerController() override; + + protected: + void StartScan() override; + + private: + void FoundUwSCallback(UwSId pup_id); + + std::unique_ptr<SignatureMatcherAPI> signature_matcher_; + UrzaScannerImpl scanner_; + std::vector<UwSId> found_pups_; + + DISALLOW_COPY_AND_ASSIGN(UrzaScannerController); +}; + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_SCANNER_URZA_SCANNER_CONTROLLER_H_
diff --git a/chrome/chrome_cleaner/scanner/urza_scanner_impl.cc b/chrome/chrome_cleaner/scanner/urza_scanner_impl.cc new file mode 100644 index 0000000..045fd010e --- /dev/null +++ b/chrome/chrome_cleaner/scanner/urza_scanner_impl.cc
@@ -0,0 +1,627 @@ +// Copyright 2018 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/chrome_cleaner/scanner/urza_scanner_impl.h" + +#include <shlobj.h> + +#include <locale> +#include <map> +#include <set> +#include <string> +#include <utility> +#include <vector> + +#include "base/barrier_closure.h" +#include "base/bind.h" +#include "base/callback_helpers.h" +#include "base/command_line.h" +#include "base/files/file_enumerator.h" +#include "base/files/file_path.h" +#include "base/files/file_util.h" +#include "base/logging.h" +#include "base/path_service.h" +#include "base/strings/strcat.h" +#include "base/strings/string16.h" +#include "base/strings/string_number_conversions.h" +#include "base/strings/string_util.h" +#include "base/strings/utf_string_conversions.h" +#include "base/task/post_task.h" +#include "base/task_runner.h" +#include "base/threading/sequenced_task_runner_handle.h" +#include "base/time/time.h" +#include "base/win/registry.h" +#include "chrome/chrome_cleaner/constants/chrome_cleaner_switches.h" +#include "chrome/chrome_cleaner/logging/logging_definitions.h" +#include "chrome/chrome_cleaner/logging/logging_service_api.h" +#include "chrome/chrome_cleaner/logging/registry_logger.h" +#include "chrome/chrome_cleaner/logging/scoped_timed_task_logger.h" +#include "chrome/chrome_cleaner/logging/utils.h" +#include "chrome/chrome_cleaner/os/disk_util.h" +#include "chrome/chrome_cleaner/os/file_path_sanitization.h" +#include "chrome/chrome_cleaner/os/file_path_set.h" +#include "chrome/chrome_cleaner/os/pre_fetched_paths.h" +#include "chrome/chrome_cleaner/os/registry_util.h" +#include "chrome/chrome_cleaner/proto/shared_pup_enums.pb.h" +#include "chrome/chrome_cleaner/pup_data/pup_disk_util.h" +#include "chrome/chrome_cleaner/scanner/matcher_util.h" +#include "chrome/chrome_cleaner/scanner/signature_matcher_api.h" +#include "chrome/chrome_cleaner/settings/settings_definitions.h" +#include "chrome/chrome_cleaner/strings/string_util.h" + +namespace chrome_cleaner { + +namespace { + +bool FileMatchesRule(const base::FilePath& file_path, + PUPData::DiskMatchRule rule) { + if (rule == PUPData::DISK_MATCH_ANY_FILE || + (PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1 <= rule && + rule < PUPData::DISK_MATCH_FILE_IN_FOLDER_END)) { + return !file_path.empty(); + } + // This is the only other rule we support so far. + DCHECK(rule == PUPData::DISK_MATCH_BINARY_FILE); + return PathHasActiveExtension(file_path); +} + +base::FilePath FolderToRemove(const base::FilePath& file, + PUPData::DiskMatchRule rule) { + DCHECK(PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1 <= rule && + rule < PUPData::DISK_MATCH_FILE_IN_FOLDER_END); + base::FilePath folder_to_remove(file); + for (int i = PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1; i <= rule; ++i) { + folder_to_remove = folder_to_remove.DirName(); + } + return folder_to_remove; +} + +// Return true if the file matches |rule| or if at least one file that matches +// |rule| can be found in the hierarchy of descendant if |file_path| is a +// directory. Also update |expanded_disk_footprints| with the full path of all +// matched files, or just the first one if |options.only_one_footprint()| is +// true. +bool AnyFileMatches(const base::FilePath& file_path, + PUPData::DiskMatchRule rule, + const MatchingOptions& options, + PUPData::PUP* pup) { + DCHECK(pup); + if (!base::PathExists(file_path)) + return false; + // If the path isn't a folder, then simply check if it matches |rule|. + if (!base::DirectoryExists(file_path)) { + if (FileMatchesRule(file_path, rule)) { + // When we match a file in a folder structure, remove the appropriate + // folder. + if (PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1 <= rule && + rule < PUPData::DISK_MATCH_FILE_IN_FOLDER_END) { + if (options.only_one_footprint()) + pup->AddDiskFootprint(file_path); + else + CollectPathsRecursively(FolderToRemove(file_path, rule), pup); + } else { + // No need to know if the file had already been added or not, it will + // simply be ignored by the file path set of |pup|. + pup->AddDiskFootprint(file_path); + } + return true; + } else { + return false; + } + } + + // Look for files recursively, and find at least one that matches |rule|, yet + // collect all the files, since we'll need to delete them all if a match is + // found. Unless this folder has already been matched (|AddDiskFootprint| + // returns false when the item already exists). + if (!pup->AddDiskFootprint(file_path)) + return true; + + base::FileEnumerator file_enum( + file_path, true, + base::FileEnumerator::FILES | base::FileEnumerator::DIRECTORIES); + bool found_file = false; + for (base::FilePath file = file_enum.Next(); !file.empty(); + file = file_enum.Next()) { + pup->AddDiskFootprint(file); + if (!base::DirectoryExists(file) && FileMatchesRule(file, rule)) { + if (options.only_one_footprint()) + return true; + found_file = true; + } + } + return found_file; +} + +// Performs expansion of |path|. If |csidl| is not |kInvalidCsidl|, |path| is +// expanded under that CSIDL. If a path can be expanded to multiple paths (e.g. +// if it's under Program Files), all expansions will be returned. +FilePathSet ExpandPath(int csidl, const base::FilePath& path) { + FilePathSet expanded_paths; + + base::FilePath expanded_path; + if (!ExpandEnvPath(path, &expanded_path)) + expanded_path = path; + + if (csidl == PUPData::kInvalidCsidl) { + expanded_paths.Insert(expanded_path); + } else { + expanded_paths.Insert(ExpandSpecialFolderPath(csidl, expanded_path)); + switch (csidl) { + case CSIDL_PROGRAM_FILES: +#if defined(_WIN64) + expanded_paths.Insert(GetX86ProgramFilesPath(expanded_path)); +#else + expanded_paths.Insert(GetX64ProgramFilesPath(expanded_path)); +#endif // defined(_WIN64) + break; + case CSIDL_SYSTEM: { + const base::FilePath system_path = + PreFetchedPaths::GetInstance()->GetWindowsFolder(); + expanded_paths.Insert(system_path.Append(L"sysnative").Append(path)); + break; + } + } + } + + return expanded_paths; +} + +// Fill the |expanded_disk_footprints| field of |pup| and set +// |footprint_found| to true when a scan and remove footprint was found. +// When |options.only_one_footprint()| is true, this function returns as soon as +// one footprint is found (or immediately if |footprint_found| == true). +// Return false if an error occurred and scanning |pup| must be cancelled and +// marked as not found. +bool ExpandDiskFootprint(const MatchingOptions& options, + PUPData::PUP* pup, + bool* footprint_found) { + DCHECK(pup); + DCHECK(footprint_found); + + if (options.only_one_footprint() && *footprint_found) + return true; + + // String format: Expanding disk footprints for: '%s' + const std::string logging_text = base::StrCat( + {"Expanding disk footprints for: '", PUPData::GetPUPName(pup), "'"}); + ScopedTimedTaskLogger scoped_timed_task_logger(logging_text.c_str()); + + const PUPData::StaticDiskFootprint* disk_footprints = + pup->signature().disk_footprints; + for (size_t i = 0; disk_footprints[i].path != nullptr; ++i) { + // Make sure to never try to remove a whole CSIDL folder. + if (disk_footprints[i].csidl != PUPData::kInvalidCsidl && + wcslen(disk_footprints[i].path) == 0) { + NOTREACHED() << "A CSIDL with no path!!!"; + pup->ClearDiskFootprints(); + return false; + } + + const FilePathSet expanded_paths = ExpandPath( + disk_footprints[i].csidl, base::FilePath(disk_footprints[i].path)); + + std::vector<base::FilePath> matches; + for (const auto& expanded_path : expanded_paths.file_paths()) + CollectMatchingPaths(expanded_path, &matches); + for (const auto& file_path : matches) { + if (AnyFileMatches(file_path, disk_footprints[i].rule, options, pup)) { + *footprint_found = true; + LOG(INFO) << "Found disk footprint: " << SanitizePath(file_path); + if (options.only_one_footprint()) + return true; + } + } + } + return true; +} + +bool DoesValueMatchAgainstRegistryRule(const base::string16& value, + const base::string16& value_substring, + RegistryMatchRule rule) { + switch (rule) { + case REGISTRY_VALUE_MATCH_EXACT: + if (String16EqualsCaseInsensitive(value, value_substring)) + return true; + break; + case REGISTRY_VALUE_MATCH_CONTAINS: + case REGISTRY_VALUE_MATCH_PARTIAL: + if (String16ContainsCaseInsensitive(value, value_substring)) + return true; + break; + case REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_EXACT: { + // This variable is needed to call the string constructor with size to + // keep the null characters. + base::string16 delimiters(PUPData::kCommonDelimiters, + PUPData::kCommonDelimitersLength); + if (String16SetMatchEntry(value, delimiters, value_substring, + String16EqualsCaseInsensitive)) { + return true; + } + break; + } + case REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_CONTAINS: { + // This variable is needed to call the string constructor with size to + // keep the null characters. + base::string16 delimiters(PUPData::kCommonDelimiters, + PUPData::kCommonDelimitersLength); + if (String16SetMatchEntry(value, delimiters, value_substring, + String16ContainsCaseInsensitive)) { + return true; + } + break; + } + case REGISTRY_VALUE_MATCH_COMMA_SEPARATED_SET_EXACT: + if (String16SetMatchEntry(value, PUPData::kCommaDelimiter, + value_substring, + String16EqualsCaseInsensitive)) { + return true; + } + break; + case REGISTRY_VALUE_MATCH_COMMA_SEPARATED_SET_CONTAINS: + if (String16SetMatchEntry(value, PUPData::kCommaDelimiter, + value_substring, + String16ContainsCaseInsensitive)) { + return true; + } + FALLTHROUGH; + case REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_CONTAINS_PATH: + if (String16SetMatchEntry(value, PUPData::kCommonDelimiters, + value_substring, + ShortPathContainsCaseInsensitive)) { + return true; + } + break; + default: + LOG(ERROR) << "Missing rule to match registry key value."; + return false; + } + + return false; +} + +// Set |footprint_found| to true when a scan and remove registry +// footprint was found. When |options.only_one_footprint()| is true, this +// function returns as +// soon as one footprint is found (or immediately if |footprint_found| +// == true). Return false if an error occurred and scanning |pup| must be +// cancelled and marked as not found. +bool ExpandRegistryFootprint(const MatchingOptions& options, + PUPData::PUP* pup, + bool* footprint_found) { + DCHECK(pup); + DCHECK(footprint_found); + + if (options.only_one_footprint() && *footprint_found) + return true; + + // String format: Expanding registry footprints for: '%s' + const std::string logging_text = base::StrCat( + {"Expanding registry footprints for: '", PUPData::GetPUPName(pup), "'"}); + ScopedTimedTaskLogger scoped_timed_task_logger(logging_text.c_str()); + + const PUPData::StaticRegistryFootprint* registry_footprints = + pup->signature().registry_footprints; + for (const PUPData::StaticRegistryFootprint* footprint = + ®istry_footprints[0]; + footprint->key_path != nullptr; ++footprint) { + RegistryRoot registry_root = footprint->registry_root; + base::FilePath policy_file; + HKEY hkroot = nullptr; + + bool success = PUPData::GetRootKeyFromRegistryRoot(registry_root, &hkroot, + &policy_file); + CHECK(success) << "Internal data should not have invalid registry roots."; + + // The function |CollectMatchingRegistryPaths| enumerates registry paths + // matching the regular expression in both 32 and 64-bit view. + std::vector<RegKeyPath> key_paths; + CollectMatchingRegistryPaths(hkroot, footprint->key_path, + PUPData::kRegistryPatternEscapeCharacter, + &key_paths); + + for (const auto& key_path : key_paths) { + base::win::RegKey reg_key; + base::FilePath policy_file; + + if (!key_path.Open(KEY_READ, ®_key)) + continue; + LOG_IF(WARNING, !policy_file.empty()) + << "Group Policies are not supported."; + DCHECK(reg_key.Valid()); + + // If we are not looking for a value name, then we have already found the + // footprint, which is simply a valid key path. + if (footprint->rule == REGISTRY_VALUE_MATCH_KEY) { + PUPData::DeleteRegistryKey(key_path, pup); + + LOG(INFO) << "Found registry key: " << key_path.FullPath(); + *footprint_found = true; + if (options.only_one_footprint()) + return true; + + continue; + } + + // Collect the matching value names from the registry key. + std::vector<base::string16> value_names; + CollectMatchingRegistryNames(reg_key, footprint->value_name, + PUPData::kRegistryPatternEscapeCharacter, + &value_names); + + for (const auto& value_name : value_names) { + // If the value doesn't exists, do not perform any rules matching. + if (!reg_key.HasValue(value_name.c_str())) + continue; + + base::string16 value; + if (!ReadRegistryValue(reg_key, value_name.c_str(), &value, nullptr, + nullptr)) { + DVPLOG(1) << "Failed to read value: " << key_path.FullPath(); + } + + // When looking for a value name, collect the footprint as soon as the + // value name is matching. + if (footprint->rule == REGISTRY_VALUE_MATCH_VALUE_NAME) { + DCHECK(!footprint->value_substring); + PUPData::DeleteRegistryValue(key_path, value_name.c_str(), pup); + + LOG(INFO) << "Found registry value: " << key_path.FullPath() << ", " + << value_name << ", with value: " << value; + *footprint_found = true; + if (options.only_one_footprint()) + return true; + continue; + } + DCHECK(footprint->value_substring); + + // Match against pre-defined PUPData registry rules. + if (DoesValueMatchAgainstRegistryRule(value, footprint->value_substring, + footprint->rule)) { + PUPData::UpdateRegistryValue(key_path, value_name.c_str(), + footprint->value_substring, + footprint->rule, pup); + + // TODO(csharp): Sanitize footprint->value_substring which is a + // path. + LOG(INFO) << "Found registry value: " << key_path.FullPath() << ", " + << value_name << ", " << footprint->value_substring; + *footprint_found = true; + if (options.only_one_footprint()) + return true; + + continue; + } + } + } + } + + // No footprint found, but no errors occurred. + return true; +} + +// Runs the custom matchers to fill the fields of |pup| and set +// |footprint_found| to true when a scan and remove footprint was found. +// When |options.only_one_footprint()| is true, returns as soon as one +// footprint is found (or immediately if |footprint_found| == true). +// Returns false if an error occurred and scanning |pup| must be cancelled and +// marked as not found. +bool RunCustomMatchers(const MatchingOptions& options, + const SignatureMatcherAPI* signature_matcher, + PUPData::PUP* pup, + bool* footprint_found) { + DCHECK(pup); + DCHECK(footprint_found); + + if (options.only_one_footprint() && *footprint_found) + return true; + + int custom_matcher_index = 0; + const PUPData::CustomMatcher* custom_matchers = + pup->signature().custom_matchers; + for (const PUPData::CustomMatcher *custom_matcher = custom_matchers; + *custom_matcher; ++custom_matcher, ++custom_matcher_index) { + // String format: Running custom matcher %d for UwS '%s' + const std::string logging_text = base::StrCat( + {"Running custom matcher ", base::NumberToString(custom_matcher_index), + " for UwS '", PUPData::GetPUPName(pup), "'"}); + ScopedTimedTaskLogger scoped_timed_task_logger(logging_text.c_str()); + + // Pass a copy of |footprint_found| to ensure custom matchers don't + // change the state from true to false. + bool current_matcher_footprint_found = *footprint_found; + if (!(*custom_matcher)(options, signature_matcher, pup, + ¤t_matcher_footprint_found)) + return false; + + // Try and detect if any custom matchers incorrectly set + // |current_matcher_footprint_found| to false. + DCHECK(!(*footprint_found && !current_matcher_footprint_found)); + + if (current_matcher_footprint_found) { + *footprint_found = true; + if (options.only_one_footprint()) + return true; + } + } + return true; +} + +void LogAndWriteScanTimeToRegistry(RegistryLogger* registry_logger, + const PUPData::PUP* const pup, + const base::TimeDelta& scan_time) { + DCHECK(pup); + // String format: Scanning of: '%s' + const std::string logging_text = + base::StrCat({"Scanning of: '", PUPData::GetPUPName(pup), "'"}); + ScopedTimedTaskLogger::LogIfExceedThreshold( + logging_text.c_str(), base::TimeDelta::FromSeconds(1), scan_time); + + if (registry_logger) + registry_logger->WriteScanTime(pup->signature().id, scan_time); +} + +// Scan the footprint of the PUP identified by |pup_id|, run all the collectors +// by calling |run_collectors|. If the UwS was found, call |uws_found|. +// The collectors are run via a callback to enable tests to skip running the +// collectors for performance reasons. +// |task_done| will run whenever it goes out of scope, either when this function +// ends, or when |uws_found| ends (since it is passed as an argument to it). +void ScanThisPUP( + UwSId pup_id, + const MatchingOptions& options, + const SignatureMatcherAPI* signature_matcher, + scoped_refptr<base::TaskRunner> task_runner, + RegistryLogger* registry_logger, + base::RepeatingCallback<void(UwSId, base::ScopedClosureRunner)> uws_found, + base::ScopedClosureRunner task_done) { + DCHECK(task_runner); + DCHECK(signature_matcher); + PUPData::PUP* pup = PUPData::GetPUP(pup_id); + + ScopedTimedTaskLogger scoped_timed_task_logger( + base::BindOnce(&LogAndWriteScanTimeToRegistry, registry_logger, pup)); + + // Make sure to start from scratch, mainly important for tests for now. + pup->ClearDiskFootprints(); + pup->expanded_registry_footprints.clear(); + pup->expanded_scheduled_tasks.clear(); + + UwSId found_pup_id = PUPData::kInvalidUwSId; + bool footprint_found = false; + + // The functions below will return true immediately if + // |options.only_one_footprint()| and |uws_detected| are both true. + if (ExpandDiskFootprint(options, pup, &footprint_found) && + ExpandRegistryFootprint(options, pup, &footprint_found) && + RunCustomMatchers(options, signature_matcher, pup, &footprint_found) && + footprint_found) { + found_pup_id = pup_id; + } + + bool uws_detected = found_pup_id != PUPData::kInvalidUwSId; + if (uws_detected) { + UwSDetectedFlags flags = kUwSDetectedFlagsNone; + + if (options.only_one_footprint()) + flags |= kUwSDetectedFlagsOnlyOneFootprint; + + LoggingServiceAPI::GetInstance()->AddDetectedUwS(pup, flags); + } + + if (uws_detected) { + task_runner->PostTask( + FROM_HERE, + base::BindRepeating(uws_found, found_pup_id, base::Passed(&task_done))); + } +} + +} // namespace + +UrzaScannerImpl::UrzaScannerImpl(const MatchingOptions& options, + SignatureMatcherAPI* signature_matcher, + RegistryLogger* registry_logger) + : options_(options), + signature_matcher_(signature_matcher), + registry_logger_(registry_logger), + all_tasks_done_(false), + num_pups_(0), + stopped_(false) {} + +UrzaScannerImpl::~UrzaScannerImpl() {} + +bool UrzaScannerImpl::Start(const FoundUwSCallback& found_uws_callback, + DoneCallback done_callback) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + stopped_ = false; + found_uws_callback_ = found_uws_callback; + done_callback_ = std::move(done_callback); + + // It's not a valid state to have no PUPs at all. + num_pups_ = PUPData::GetUwSIds()->size(); + DCHECK(num_pups_); + + // We currently create one task per PUP to scan. + auto task_runner = base::CreateTaskRunnerWithTraits({base::MayBlock()}); + all_tasks_done_ = false; + base::RepeatingClosure task_done_closure = base::BarrierClosure( + num_pups_, base::BindOnce(&UrzaScannerImpl::InvokeAllTasksDone, + base::Unretained(this), + base::SequencedTaskRunnerHandle::Get())); + for (const auto& pup_id : *PUPData::GetUwSIds()) { + // The ScopedClosureRunner will be executed whenever it falls out of scope, + // which ensures that |task_done_closure| will be executed whenever the task + // finishes or is cancelled. + cancelable_task_tracker_.PostTask( + task_runner.get(), FROM_HERE, + base::BindOnce( + &ScanThisPUP, pup_id, options_, signature_matcher_, + base::SequencedTaskRunnerHandle::Get(), registry_logger_, + base::BindRepeating(&UrzaScannerImpl::UwSFound, + base::Unretained(this)), + base::Passed(base::ScopedClosureRunner(task_done_closure)))); + } + return true; +} + +void UrzaScannerImpl::Stop() { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + cancelable_task_tracker_.TryCancelAll(); + stopped_ = true; +} + +bool UrzaScannerImpl::IsCompletelyDone() const { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + + // If some cleanup code does not run we get hangs in ScannerTest.Nonexistent* + return all_tasks_done_ && !cancelable_task_tracker_.HasTrackedTasks(); +} + +// |task_done| will run whenever it falls out of scoped, so it doesn't need to +// be directly called. +void UrzaScannerImpl::UwSFound(UwSId found_pup_id, + base::ScopedClosureRunner task_done) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + DCHECK_NE(found_pup_id, PUPData::kInvalidUwSId); + if (stopped_) + return; + + found_pups_.push_back(found_pup_id); + + // Report the detected PUP. + const PUPData::UwSSignature& signature = + PUPData::GetPUP(found_pup_id)->signature(); + + if (signature.name) { + LoggingServiceAPI::GetInstance()->AddFoundUwS(signature.name); + if (PUPData::HasReportOnlyFlag(signature.flags)) { + LOG(INFO) << "Report only UwS detected: " << signature.name; + } else { + LOG(INFO) << "UwS detected: " << signature.name; + } + } else { + LOG(ERROR) << "Missing name for detected UwS with id " << found_pup_id; + } + + found_uws_callback_.Run(found_pup_id); +} + +void UrzaScannerImpl::InvokeAllTasksDone( + scoped_refptr<base::TaskRunner> task_runner) { + task_runner->PostTask( + FROM_HERE, + base::BindOnce(&UrzaScannerImpl::AllTasksDone, base::Unretained(this))); +} + +void UrzaScannerImpl::AllTasksDone() { + all_tasks_done_ = true; + if (stopped_) + return; + + std::move(done_callback_).Run(RESULT_CODE_SUCCESS, found_pups_); + found_pups_.clear(); + done_callback_.Reset(); +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/scanner/urza_scanner_impl.h b/chrome/chrome_cleaner/scanner/urza_scanner_impl.h new file mode 100644 index 0000000..5e92740 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/urza_scanner_impl.h
@@ -0,0 +1,94 @@ +// Copyright 2018 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_CHROME_CLEANER_SCANNER_URZA_SCANNER_IMPL_H_ +#define CHROME_CHROME_CLEANER_SCANNER_URZA_SCANNER_IMPL_H_ + +#include <vector> + +#include "base/callback.h" +#include "base/callback_helpers.h" +#include "base/sequence_checker.h" +#include "base/task/cancelable_task_tracker.h" +#include "chrome/chrome_cleaner/pup_data/pup_data.h" +#include "chrome/chrome_cleaner/scanner/scanner.h" +#include "chrome/chrome_cleaner/settings/matching_options.h" + +namespace chrome_cleaner { + +// Forward declarations. +class SignatureMatcherAPI; +class RegistryLogger; + +// This class is used to scan for the footprints of all PUPs in PUPData. It uses +// a worker thread pool to scan asynchronously and be interruptable, but is not +// thread safe, in the sense that the Start/Stop/IsStopDone methods must all be +// called from the same thread that created the class instance. +class UrzaScannerImpl : public Scanner { + public: + // Create instance of scanner that uses Urza engine. + // If |registry_logger| is not null, write scan times of individual PUPs to + // the registry. Any |RegistryLogger| object pointed to by |registry_logger| + // must stay alive for the entire lifetime of this scanner instance. + UrzaScannerImpl(const MatchingOptions& options, + SignatureMatcherAPI* signature_matcher, + RegistryLogger* registry_logger); + + ~UrzaScannerImpl() override; + + // UrzaScanner. + + // Start a set of tasks in worker pool threads to scan the disk and registry + // for PUP footprints. A PUP is deemed "found" if at least one of its + // footprints can be found. If a PUP was found, |found_uws_callback| is + // called. If the scan completes before |Stop| is called, then |done_callback| + // is called. Returns true if scan startup succeeds. + bool Start(const FoundUwSCallback& found_uws_callback, + DoneCallback done_callback) override; + void Stop() override; + + // When calling |Stop|, some tasks may still be running, so make sure to call + // |IsCompletelyDone| and allow the main UI to pump messages to let the task + // tracker mark all tasks as done before clearing PUPData, which should not be + // an issue in production code where it's all static, but can be an issue with + // dynamic PUPData in test code. Return true if there's nothing left to be + // completed asynchronously by the scanner (i.e, a stop was started and + // finished, or everything was completely done). + bool IsCompletelyDone() const override; + + private: + void UwSFound(UwSId found_uws_id, base::ScopedClosureRunner task_done); + + void InvokeAllTasksDone(scoped_refptr<base::TaskRunner> task_runner); + + void AllTasksDone(); + + MatchingOptions options_; + SignatureMatcherAPI* signature_matcher_; + RegistryLogger* registry_logger_; + + // The task tracker that can be used to cancel pending tasks. + base::CancelableTaskTracker cancelable_task_tracker_; + SEQUENCE_CHECKER(sequence_checker_); + + // Callbacks to report progress and completion. + FoundUwSCallback found_uws_callback_; + DoneCallback done_callback_; + + // To accumulate the list of found PUPs passed to |TaskCompleted|. + std::vector<UwSId> found_pups_; + + // Whether all tasks are done, either having been cancelled or completed. + bool all_tasks_done_; + + // The number of PUPs, which is also the total number of tasks to run. + size_t num_pups_; + + // Whether |Stop| has been called or not. Reset to false in |Start|. + bool stopped_; +}; + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_SCANNER_URZA_SCANNER_IMPL_H_
diff --git a/chrome/chrome_cleaner/scanner/urza_scanner_impl_unittest.cc b/chrome/chrome_cleaner/scanner/urza_scanner_impl_unittest.cc new file mode 100644 index 0000000..dec29d90 --- /dev/null +++ b/chrome/chrome_cleaner/scanner/urza_scanner_impl_unittest.cc
@@ -0,0 +1,2294 @@ +// Copyright 2018 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/chrome_cleaner/scanner/urza_scanner_impl.h" + +#include <shlobj.h> + +#include <algorithm> +#include <iterator> +#include <list> +#include <map> +#include <memory> +#include <set> +#include <string> +#include <utility> +#include <vector> + +#include "base/bind.h" +#include "base/files/file.h" +#include "base/files/file_util.h" +#include "base/files/scoped_temp_dir.h" +#include "base/path_service.h" +#include "base/rand_util.h" +#include "base/run_loop.h" +#include "base/strings/strcat.h" +#include "base/strings/string16.h" +#include "base/strings/string_number_conversions.h" +#include "base/strings/string_util.h" +#include "base/test/scoped_path_override.h" +#include "base/test/scoped_task_environment.h" +#include "base/test/test_reg_util_win.h" +#include "base/test/test_shortcut_win.h" +#include "base/threading/thread_task_runner_handle.h" +#include "base/win/windows_version.h" +#include "chrome/chrome_cleaner/logging/logging_service_api.h" +#include "chrome/chrome_cleaner/logging/mock_logging_service.h" +#include "chrome/chrome_cleaner/logging/proto/shared_data.pb.h" +#include "chrome/chrome_cleaner/logging/utils.h" +#include "chrome/chrome_cleaner/os/disk_util.h" +#include "chrome/chrome_cleaner/proto/shared_pup_enums.pb.h" +#include "chrome/chrome_cleaner/strings/string_util.h" +#include "chrome/chrome_cleaner/test/test_file_util.h" +#include "chrome/chrome_cleaner/test/test_name_helper.h" +#include "chrome/chrome_cleaner/test/test_pup_data.h" +#include "chrome/chrome_cleaner/test/test_registry_util.h" +#include "chrome/chrome_cleaner/test/test_signature_matcher.h" +#include "chrome/chrome_cleaner/test/test_strings.h" +#include "chrome/chrome_cleaner/test/test_util.h" +#include "testing/gmock/include/gmock/gmock.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace chrome_cleaner { + +namespace { + +using testing::_; +using testing::Eq; + +// To make git cl lint happy. +constexpr size_t kMaxPath = _MAX_PATH; + +constexpr UwSId k12ID = 12; +constexpr UwSId k24ID = 24; +constexpr UwSId k42ID = 42; +constexpr UwSId k84ID = 84; + +constexpr UwSId kNonExistentID = 666; + +constexpr base::char16 kBaseName[] = L"foo"; +constexpr base::char16 kOtherBaseName[] = L"goo"; +constexpr base::char16 kBadBaseName[] = L"fo"; +constexpr base::char16 kValueName[] = L"bar"; +constexpr base::char16 kValue[] = L"bla"; +constexpr base::char16 kValueDifferentCase[] = L"bLa"; +constexpr base::char16 kBadValue[] = L"bl"; +constexpr base::char16 kBaValue[] = L"ba"; +constexpr base::char16 kFooValue[] = L"foo"; +constexpr base::char16 kComplexValue[] = L"bli bla blue"; +constexpr base::char16 kCommaSetValue[] = L"bli,bla,blue"; +constexpr base::char16 kCommonSetValue[] = L"bli,bla blue"; +constexpr base::char16 kCommonSetWithNullValue[] = L"bli\0bla\0blue"; +constexpr base::char16 kBiggerCommaSetValue[] = L"bli,blablabla,blue"; +constexpr base::char16 kBadCommaSetValue[] = L"bli,bah,blue"; +constexpr base::char16 kWildcardSearch1[] = L"*"; +constexpr base::char16 kWildcardSearch2[] = L"f??"; +constexpr base::char16 kDummyFullPath[] = L"c:\\foo\\bar\\bat.exe"; +constexpr base::char16 kOtherFullPath[] = L"c:\\foo\\bar.exe"; +constexpr base::char16 kLongFileName[] = L"bla bla bla.exe"; + +constexpr base::char16 kRegistryKeyPath[] = L"software\\foo"; +constexpr base::char16 kValueName1[] = L"foo1"; +constexpr base::char16 kValueName2[] = L"foo2"; +constexpr base::char16 kValueName3[] = L"foo3"; +constexpr base::char16 kValueNameSingleWildcard[] = L"foo?"; +constexpr base::char16 kValueNameMultiWildcard[] = L"fo*"; +constexpr base::char16 kSetWithCommonValue1[] = L"foo bar bat"; +constexpr base::char16 kSetWithCommonValue2[] = L"bar foo bat"; +constexpr base::char16 kSetWithCommonValue3[] = L"bar bat foo"; + +constexpr size_t kManyPUPs = 1000; +constexpr size_t kSomePUPs = 20; +constexpr size_t kFoundPUPsModuloBase = 10; + +bool g_test_custom_matcher1_called = false; +bool g_test_custom_matcher2_called = false; +bool g_test_custom_matcher3_called = false; +bool g_test_custom_matcher5_found = false; + +// Computes the set difference between two sets and outputs to a vector. +template <typename T> +void set_difference(const std::set<T>& set1, + const std::set<T>& set2, + std::vector<T>* output) { + std::set_difference(set1.begin(), set1.end(), set2.begin(), set2.end(), + std::back_inserter(*output)); +} + +class TestScanner : public UrzaScannerImpl { + public: + TestScanner() = default; + explicit TestScanner(const MatchingOptions& options, + SignatureMatcherAPI* signature_matcher, + RegistryLogger* registry_logger) + : UrzaScannerImpl(options, signature_matcher, registry_logger) {} + ~TestScanner() override = default; +}; + +// This test fixture is used to expose callbacks to the scanner and some utility +// functions. It keeps data for the found PUPs, as well as the done and stopped +// state. It also creates the main/UI task scheduler. +class ScannerTest : public testing::Test { + public: + ScannerTest() + : done_scanning_(false), + found_report_only_(false), + found_pup_to_remove_(false), + stopped_(false), + scoped_task_environment_( + base::test::ScopedTaskEnvironment::MainThreadType::UI) {} + + void TearDown() override { + // Even though not all tests override the logging instance, we reset it + // during test tear down, so test failures don't keep them in an invalid + // status. + LoggingServiceAPI::SetInstanceForTesting(nullptr); + } + + // Scanner callbacks. + void DoneScanning(ResultCode status, const std::vector<UwSId>& found_pups) { + ASSERT_FALSE(done_scanning_); + found_pups_.insert(found_pups_.begin(), found_pups.begin(), + found_pups.end()); + done_scanning_ = true; + + // Urza is so cool, it never fails. + EXPECT_EQ(RESULT_CODE_SUCCESS, status); + + found_report_only_ = + PUPData::HasFlaggedPUP(found_pups, &PUPData::HasReportOnlyFlag); + } + + void FoundUwS(UwSId found_pup) { + EXPECT_FALSE(done_scanning_); + EXPECT_EQ(pups_seen_in_progress_callback_.end(), + pups_seen_in_progress_callback_.find(found_pup)); + pups_seen_in_progress_callback_.insert(found_pup); + } + + // Start/Stop the scanner. + void Scan() { + done_scanning_ = false; + g_test_custom_matcher1_called = false; + g_test_custom_matcher2_called = false; + g_test_custom_matcher3_called = false; + g_test_custom_matcher5_found = false; + found_pups_.clear(); + pups_seen_in_progress_callback_.clear(); + + test_scanner_.reset( + new TestScanner(options_, &test_signature_matcher_, nullptr)); + + test_scanner_->Start( + base::BindRepeating(&ScannerTest::FoundUwS, base::Unretained(this)), + base::BindOnce(&ScannerTest::DoneScanning, base::Unretained(this))); + // Now wait for the scanner to be done or stopped. + while (!(done_scanning_ || stopped_) || !test_scanner_->IsCompletelyDone()) + base::RunLoop().RunUntilIdle(); + } + + void StopScanner() { + test_scanner_->Stop(); + stopped_ = true; + } + + // Expectations utility functions. + void ExpectNoPUPsFound() { ExpectFoundPUPs({}); } + + void ExpectSinglePUP(UwSId pup_id) { ExpectFoundPUPs({pup_id}); } + + void ExpectFoundPUPs(const std::set<UwSId>& pups) { + EXPECT_EQ(pups.size(), found_pups_.size()); + std::set<UwSId>::const_iterator pup = pups.begin(); + for (; pup != pups.end(); ++pup) { + EXPECT_NE(found_pups_.end(), + std::find(found_pups_.begin(), found_pups_.end(), *pup)); + } + EXPECT_EQ(pups.size(), pups_seen_in_progress_callback_.size()); + EXPECT_EQ(pups, pups_seen_in_progress_callback_); + } + + // Add disk footprint for PUP |pup_id| to |test_pup_data|. If + // |disk_footprint_exist| is true, create files matching the newly created + // footprint. + // Return true on success. + bool SetupDiskFootprint(TestPUPData* test_pup_data, + UwSId pup_id, + bool disk_footprint_exist) { + // Create temporary directory. + std::shared_ptr<base::ScopedTempDir> temp_dir(new base::ScopedTempDir); + if (!temp_dir->CreateUniqueTempDir() || !temp_dir->IsValid()) + return false; + + // Setup disk footprint rule. PUPData holds C-style strings, so provide + // C string equivalent of the stored filepath. + pup_data_filepaths_.push_back(temp_dir->GetPath().value()); + test_pup_data->AddDiskFootprint(pup_id, 0, + pup_data_filepaths_.back().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + + // If footprint rule should match, create a file and ensure the directory is + // not deleted until the end of the test. + if (disk_footprint_exist) { + base::FilePath temp_file; + if (!CreateTemporaryFileInDir(temp_dir->GetPath(), &temp_file)) + return false; + pup_data_temp_dirs_.push_back(temp_dir); + } + + return true; + } + + protected: + std::unique_ptr<TestScanner> test_scanner_; + MatchingOptions options_; + TestSignatureMatcher test_signature_matcher_; + std::vector<UwSId> found_pups_; + std::set<UwSId> pups_seen_in_progress_callback_; + bool done_scanning_; + bool found_report_only_; + bool found_pup_to_remove_; + bool stopped_; + + private: + base::test::ScopedTaskEnvironment scoped_task_environment_; + + // This vector holds temporary directories which should be released at the end + // of the test. + std::vector<std::shared_ptr<base::ScopedTempDir>> pup_data_temp_dirs_; + // This vector holds C++ strings representing PUP disk footprints filepaths. + // This is to allow proper memory management of C string equivalents in + // PUPData. + std::vector<base::string16> pup_data_filepaths_; +}; + +class ScannerTestWithBitness : public ScannerTest, + public ::testing::WithParamInterface<int> {}; + +INSTANTIATE_TEST_CASE_P(ScannerBitnessTest, + ScannerTestWithBitness, + testing::Values(32, 64), + GetParamNameForTest()); + +// A custom matcher finding an active disk footprint. +bool TestCustomMatcher1(const MatchingOptions& options, + const SignatureMatcherAPI* signature_matcher, + PUPData::PUP* pup, + bool* active_footprint_found) { + DCHECK(pup); + DCHECK(active_footprint_found); + base::FilePath path(kDummyFullPath); + pup->AddDiskFootprint(path); + *active_footprint_found = true; + g_test_custom_matcher1_called = true; + return true; +} + +// A custom matcher finding an inactive (left-over) disk footprint. +bool TestCustomMatcher2(const MatchingOptions& options, + const SignatureMatcherAPI* signature_matcher, + PUPData::PUP* pup, + bool* active_footprint_found) { + DCHECK(pup); + DCHECK(active_footprint_found); + base::FilePath path(kOtherFullPath); + pup->AddDiskFootprint(path); + g_test_custom_matcher2_called = true; + return true; +} + +// A custom matcher finding nothing. +bool TestCustomMatcher3(const MatchingOptions& options, + const SignatureMatcherAPI* signature_matcher, + PUPData::PUP* pup, + bool* active_footprint_found) { + DCHECK(pup); + DCHECK(active_footprint_found); + g_test_custom_matcher3_called = true; + return true; +} + +// A custom matcher producing an error. +bool TestCustomMatcher4(const MatchingOptions& options, + const SignatureMatcherAPI* signature_matcher, + PUPData::PUP* pup, + bool* active_footprint_found) { + DCHECK(pup); + DCHECK(active_footprint_found); + base::FilePath path(kDummyFullPath); + pup->AddDiskFootprint(path); + *active_footprint_found = true; + // Return an error, abort scanning this pup. + return false; +} + +// A custom matcher setting |g_test_custom_matcher5_found| to +// |active_footprint_found|. +bool TestCustomMatcher5(const MatchingOptions& options, + const SignatureMatcherAPI* signature_matcher, + PUPData::PUP* pup, + bool* active_footprint_found) { + DCHECK(pup); + DCHECK(active_footprint_found); + g_test_custom_matcher5_found = *active_footprint_found; + return true; +} + +} // namespace + +TEST_F(ScannerTest, NonexistentDiskFootprint) { + // Set up a disk footprint. + base::ScopedTempDir scoped_temp_dir1; + ASSERT_TRUE(scoped_temp_dir1.CreateUniqueTempDir()); + // Only the folder was actually created, so base name is nonexistent. + base::FilePath nonexistent_file(scoped_temp_dir1.GetPath().Append(kBaseName)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, nonexistent_file.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, NonexistentRelativeDiskFootprint) { + base::char16 special_folder_path[kMaxPath]; + HRESULT hr = SHGetFolderPath(nullptr, CSIDL_LOCAL_APPDATA, nullptr, + SHGFP_TYPE_CURRENT, special_folder_path); + ASSERT_EQ(S_OK, hr); + + base::ScopedTempDir scoped_temp_dir2; + ASSERT_TRUE(scoped_temp_dir2.CreateUniqueTempDirUnderPath( + base::FilePath(special_folder_path))); + base::FilePath nonexistent_footprint( + scoped_temp_dir2.GetPath().BaseName().Append(kBaseName)); + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, CSIDL_LOCAL_APPDATA, + nonexistent_footprint.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + ASSERT_FALSE(base::PathExists(scoped_temp_dir2.GetPath().Append(kBaseName))); + + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, NonexistentWildcardDiskFootprint) { + // Set up a disk footprint. + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir.GetPath()); + // Only the folder was actually created, so base name is nonexistent. + base::FilePath nonexistent_file( + scoped_temp_dir.GetPath().Append(kWildcardSearch2)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, nonexistent_file.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + + // File should not be found because it doesn't match the pattern. + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder, &temp_file)); + + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, NonexistentRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Make sure the key doesn't exist. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_FILE_NOT_FOUND, + system_registry_key.Open(HKEY_LOCAL_MACHINE, kBaseName, KEY_READ)); + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + + Scan(); + ExpectNoPUPsFound(); + + // Now create the key, so that we can look for a nonexistent value. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + test_pup_data.Reset({}); + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + Scan(); + ExpectNoPUPsFound(); + + // Now create the value, but with a bad name while we look for the good one. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBadValue)); + + test_pup_data.Reset({}); + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_PARTIAL); + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, ExistentDiskFootprint) { + // Set up a folder only disk footprint. + base::ScopedTempDir scoped_temp_dir1; + ASSERT_TRUE(scoped_temp_dir1.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir1.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + + base::ScopedTempDir scoped_temp_dir2; + ASSERT_TRUE(scoped_temp_dir2.CreateUniqueTempDirUnderPath( + scoped_temp_dir1.GetPath())); + base::FilePath existent_subfolder(scoped_temp_dir2.GetPath()); + ASSERT_TRUE(base::PathExists(existent_subfolder)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, existent_folder.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + + // No PUP should be found when only folders are under the marked footprints. + Scan(); + ExpectNoPUPsFound(); + + // Add a file, and it should be found. + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_subfolder, &temp_file)); + + Scan(); + ExpectSinglePUP(k42ID); + + EXPECT_EQ(3UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, existent_folder); + ExpectDiskFootprint(*found_pup, existent_subfolder); + ExpectDiskFootprint(*found_pup, temp_file); + + ASSERT_TRUE(base::DeleteFile(temp_file, false)); + Scan(); + ExpectNoPUPsFound(); + + // Add a file deeper in a folder hierarchy, and it should still be found. + base::FilePath temp_folder; + ASSERT_TRUE(CreateTemporaryDirInDir(existent_subfolder, L"", &temp_folder)); + ASSERT_TRUE(CreateTemporaryFileInDir(temp_folder, &temp_file)); + + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(4UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, existent_folder); + ExpectDiskFootprint(*found_pup, existent_subfolder); + ExpectDiskFootprint(*found_pup, temp_folder); + ExpectDiskFootprint(*found_pup, temp_file); +} + +TEST_F(ScannerTest, ExistentRelativeDiskFootprint) { + // Set up a relative disk footprint. + base::char16 special_folder_path[kMaxPath]; + HRESULT hr = SHGetFolderPath(nullptr, CSIDL_PROGRAM_FILES, nullptr, + SHGFP_TYPE_CURRENT, special_folder_path); + ASSERT_EQ(S_OK, hr); + + base::ScopedTempDir scoped_temp_dir3; + ASSERT_TRUE(scoped_temp_dir3.CreateUniqueTempDirUnderPath( + base::FilePath(special_folder_path))); + base::FilePath existent_relative_footprint( + scoped_temp_dir3.GetPath().BaseName()); + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k24ID, CSIDL_PROGRAM_FILES, + existent_relative_footprint.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + const PUPData::PUP* found_pup = PUPData::GetPUP(k24ID); + + // Empty folder should not be found. + Scan(); + ExpectNoPUPsFound(); + + // Now create a file in it, so it can be found. + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(scoped_temp_dir3.GetPath(), &temp_file)); + + Scan(); + ExpectSinglePUP(k24ID); + EXPECT_EQ(2UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, scoped_temp_dir3.GetPath()); + ExpectDiskFootprint(*found_pup, temp_file); +} + +TEST_P(ScannerTestWithBitness, ProgramFilesDiskFootprint) { + ASSERT_TRUE(GetParam() == 32 || GetParam() == 64); + + base::FilePath program_files; + if (GetParam() == 32) { + program_files = GetX86ProgramFilesPath(base::FilePath()); + } else { + program_files = GetX64ProgramFilesPath(base::FilePath()); + } + + if (program_files.empty()) { + ASSERT_EQ(64, GetParam()); + ASSERT_EQ(base::win::OSInfo::X86_ARCHITECTURE, + base::win::OSInfo::GetInstance()->architecture()); + return; + } + + base::ScopedTempDir scoped_temp_dir3; + ASSERT_TRUE(scoped_temp_dir3.CreateUniqueTempDirUnderPath(program_files)); + base::FilePath existent_relative_footprint( + scoped_temp_dir3.GetPath().BaseName()); + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k24ID, CSIDL_PROGRAM_FILES, + existent_relative_footprint.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + const PUPData::PUP* found_pup = PUPData::GetPUP(k24ID); + + // Empty folder should not be found. + Scan(); + ExpectNoPUPsFound(); + + // Now create a file in it, so it can be found. + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(scoped_temp_dir3.GetPath(), &temp_file)); + + Scan(); + ExpectSinglePUP(k24ID); + EXPECT_EQ(2UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, scoped_temp_dir3.GetPath()); + ExpectDiskFootprint(*found_pup, temp_file); +} + +TEST_F(ScannerTest, UnicodeDiskFootprint) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + base::FilePath sub_folder(scoped_temp_dir.GetPath().Append(kValidUtf8Name)); + ASSERT_TRUE(base::CreateDirectory(sub_folder)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, sub_folder.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + + // Now create a file in it, so it can be found. + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(sub_folder, &temp_file)); + + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(2UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, sub_folder); + ExpectDiskFootprint(*found_pup, temp_file); +} + +TEST_F(ScannerTest, ExistentWildcardDiskFootprint) { + // Set up a folder only disk footprint. + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + + base::FilePath existent_file( + scoped_temp_dir.GetPath().Append(kWildcardSearch1)); + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, existent_file.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + + // Add a file, and it should be found. + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder, &temp_file)); + + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(1UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, temp_file); + + ASSERT_TRUE(base::DeleteFile(temp_file, false)); + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, ExistentRegistryFootprint) { + // Set up a registry footprint. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + Scan(); + ExpectSinglePUP(k42ID); + + test_pup_data.Reset({}); + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kComplexValue)); + + Scan(); + ExpectSinglePUP(k42ID); + + test_pup_data.Reset({}); + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_PARTIAL); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_P(ScannerTestWithBitness, RedirectedRegistryFootprint) { + // This test doesn't use registry overriding because it relies on registry + // redirection between 32 bit and 64 bit views, which is impossible with + // registry overriding. + + // Skip the test about 64-bit registry on 32-bit platforms. + if (GetParam() == 64 && + base::win::OSInfo::X86_ARCHITECTURE == + base::win::OSInfo::GetInstance()->architecture()) { + return; + } + + // Use a GUID for the subkey to reduce the risk of collisions with real + // software. + base::string16 subkey = + base::StrCat({L"software\\cct-", kGUID1Str, L"\\dummy"}); + + // Remove existing keys. + REGSAM registry_views[] = {KEY_WOW64_32KEY, KEY_WOW64_64KEY}; + for (REGSAM view : registry_views) { + base::win::RegKey test_key; + if (ERROR_SUCCESS == + test_key.Open(HKEY_LOCAL_MACHINE, subkey.c_str(), KEY_READ | view)) { + test_key.DeleteKey(L""); + } + } + + // Add a registry footprint matching under software. + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + subkey.c_str(), nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + + // Create the key, so that we can look for an existent value. + REGSAM registry_view = GetParam() == 32 ? KEY_WOW64_32KEY : KEY_WOW64_64KEY; + ScopedTempRegistryKey system_registry_key(HKEY_LOCAL_MACHINE, subkey.c_str(), + KEY_WRITE | registry_view); + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.Get()->WriteValue(kValueName, kValue)); + + // If the current system is 64-bit, check that the created key is not visible + // under the other registry view, otherwise we test nothing here. + if (base::win::OSInfo::X64_ARCHITECTURE == + base::win::OSInfo::GetInstance()->architecture()) { + REGSAM other_view = GetParam() == 32 ? KEY_WOW64_64KEY : KEY_WOW64_32KEY; + base::win::RegKey missing_registry_key; + EXPECT_EQ(ERROR_FILE_NOT_FOUND, + missing_registry_key.Open(HKEY_LOCAL_MACHINE, subkey.c_str(), + KEY_READ | other_view)); + } + + Scan(); + ExpectSinglePUP(k42ID); + + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + EXPECT_EQ(1UL, found_pup->expanded_registry_footprints.size()); + const RegKeyPath key_path(HKEY_LOCAL_MACHINE, subkey.c_str(), registry_view); + ExpectRegistryFootprint(*found_pup, key_path, L"", L"", + REGISTRY_VALUE_MATCH_KEY); +} + +TEST_F(ScannerTest, ExistentRegistryFootprintWithExactShortenPath) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath long_name_path( + scoped_temp_dir.GetPath().Append(kLongFileName)); + + // The file must exist for the short to long path name conversion to work. + base::File file(long_name_path, base::File::FLAG_OPEN_ALWAYS); + file.Close(); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_USERS, kBaseName, kValueName, + long_name_path.value().c_str(), + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_CONTAINS_PATH); + + DWORD short_name_len = + GetShortPathName(long_name_path.value().c_str(), nullptr, 0); + ASSERT_GT(short_name_len, 0UL); + + base::string16 short_name_path; + short_name_len = ::GetShortPathName( + long_name_path.value().c_str(), + base::WriteInto(&short_name_path, short_name_len), short_name_len); + ASSERT_GT(short_name_len, 0UL); + + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_CURRENT_USER); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_CURRENT_USER, + kBaseName, KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, short_name_path.c_str())); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, ExistentRegistryFootprintWithShortenPathSubString) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + + base::FilePath long_name_path( + scoped_temp_dir.GetPath().Append(kLongFileName)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_USERS, kBaseName, kValueName, + long_name_path.value().c_str(), + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_CONTAINS_PATH); + + // The file must exist for the short to long path name conversion to work. + base::File file(long_name_path, base::File::FLAG_OPEN_ALWAYS); + file.Close(); + + DWORD short_name_len = + GetShortPathName(long_name_path.value().c_str(), nullptr, 0); + ASSERT_GT(short_name_len, 0UL); + + base::string16 short_name_path; + short_name_len = ::GetShortPathName( + long_name_path.value().c_str(), + base::WriteInto(&short_name_path, short_name_len), short_name_len); + ASSERT_GT(short_name_len, 0UL); + + DCHECK_GT(PUPData::kCommonDelimitersLength, 2UL); + base::string16 complete_substr(kDummyFullPath); + complete_substr += PUPData::kCommonDelimiters[0]; + complete_substr += short_name_path.c_str(); + complete_substr += PUPData::kCommonDelimiters[1]; + complete_substr += kOtherFullPath; + + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_CURRENT_USER); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_CURRENT_USER, + kBaseName, KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, complete_substr.c_str())); + + Scan(); + ExpectSinglePUP(k42ID); + + // Now try when the requested substring is at the beginning. + complete_substr = short_name_path.data(); + complete_substr += PUPData::kCommonDelimiters[2]; + complete_substr += kOtherFullPath; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, complete_substr.c_str())); + + Scan(); + ExpectSinglePUP(k42ID); + + // Now try when the requested substring is at the end. + complete_substr = kOtherFullPath; + complete_substr += PUPData::kCommonDelimiters[0]; + complete_substr += short_name_path.data(); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, complete_substr.c_str())); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, ExistentUsersRegistryFootprint) { + // Set up a users registry footprint. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_CURRENT_USER); + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k24ID, REGISTRY_ROOT_USERS, kBaseName, + nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + + base::win::RegKey users_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + users_registry_key.Create(HKEY_CURRENT_USER, kBaseName, KEY_WRITE)); + + Scan(); + ExpectSinglePUP(k24ID); + + test_pup_data.Reset({}); + test_pup_data.AddRegistryFootprint(k24ID, REGISTRY_ROOT_USERS, kBaseName, + kValueName, nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + ASSERT_EQ(ERROR_SUCCESS, users_registry_key.WriteValue(kValueName, kValue)); + + Scan(); + ExpectSinglePUP(k24ID); + + test_pup_data.Reset({}); + test_pup_data.AddRegistryFootprint(k24ID, REGISTRY_ROOT_USERS, kBaseName, + kValueName, kValueDifferentCase, + REGISTRY_VALUE_MATCH_CONTAINS); + + Scan(); + ExpectSinglePUP(k24ID); +} + +TEST_F(ScannerTest, NonexistentWildcardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kWildcardSearch2, nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Make sure the key doesn't exist. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_FILE_NOT_FOUND, + system_registry_key.Open(HKEY_LOCAL_MACHINE, kBaseName, KEY_READ)); + + // Now create the key, so that we can look for a nonexistent value. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBadValue)); + + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, ExistentWildcardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Add a registry footprint matching any value names (i.e. "*"). + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, L"*", nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Create the key, so that we can look for an existent value. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(kValueName, kValue)); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, ExistentSingleCharacterWildcardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Add a registry footprint matching any the "bar" name (i.e. "b?r"). + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, L"b?r", nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Create the key, so that we can look for an existent value. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(L"bar", kValue)); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, ExistentMultiCharactersWildcardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Add a registry footprint matching any the "bar" name (i.e. "b*"). + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, L"b*", nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Create the key, so that we can look for an existent value. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(L"bar", kValue)); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, ExistentMixedWildcardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Add a registry footprint matching a temporary filename (i.e. "tmp*.???") + // which should match the given filename "tmp123456.log". + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, LR"(tmp*.???)", nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Create the key, so that we can look for an existent value. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(L"tmp123456.log", kValue)); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, KeyPathWithWildCardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Add a registry footprint matching under software. + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + L"software\\t?st\\d*y", kValueName, + nullptr, REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Create the key, so that we can look for an existent value. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.Create(HKEY_LOCAL_MACHINE, + L"software\\test\\dummy", KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(kValueName, kValue)); + + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, KeyPathWithNotMatchingWildCardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Add a registry footprint matching under software. + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + L"software\\t?st\\foo*", kValueName, + nullptr, REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Create the key and a value that doesn't match the registry footprint + // pattern. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.Create(HKEY_LOCAL_MACHINE, + L"software\\test\\dummy", KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(kValueName, kValue)); + + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, KeyPathWithEscapedWildCardRegistryFootprint) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + // Add a registry footprint matching under software with an escaped wild-card. + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + L"software\\t?st\\d" ESCAPE_REGISTRY_STR("*") L"y", kValueName, nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + + // Create the key, so that we can look for an existent value. + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.Create(HKEY_LOCAL_MACHINE, + L"software\\test\\dummy", KEY_WRITE)); + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(kValueName, kValue)); + + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, MixedFootprints) { + // Set up disk footprints. + base::ScopedTempDir scoped_temp_dir1; + ASSERT_TRUE(scoped_temp_dir1.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir1.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + + base::FilePath temp_file1; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder, &temp_file1)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, existent_folder.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + + std::set<UwSId> pups_to_be_scanned; + pups_to_be_scanned.insert(k42ID); + std::set<UwSId> pups_to_be_found; + pups_to_be_found.insert(k42ID); + + base::FilePath nonexistent_file(scoped_temp_dir1.GetPath().Append(kBaseName)); + test_pup_data.AddDiskFootprint(kNonExistentID, 0, + nonexistent_file.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + pups_to_be_scanned.insert(kNonExistentID); + + // Set up relative disk footprints. + base::char16 special_folder_path[kMaxPath]; + HRESULT hr = SHGetFolderPath(nullptr, CSIDL_LOCAL_APPDATA, nullptr, + SHGFP_TYPE_CURRENT, special_folder_path); + ASSERT_EQ(S_OK, hr); + + base::ScopedTempDir scoped_temp_dir2; + ASSERT_TRUE(scoped_temp_dir2.CreateUniqueTempDirUnderPath( + base::FilePath(special_folder_path))); + + base::FilePath relative_path(scoped_temp_dir2.GetPath().BaseName()); + test_pup_data.AddDiskFootprint(k24ID, CSIDL_LOCAL_APPDATA, + relative_path.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + pups_to_be_scanned.insert(k24ID); + pups_to_be_found.insert(k24ID); + + base::string16 nonexistent_relative_path( + base::FilePath(relative_path).Append(kBaseName).value()); + test_pup_data.AddDiskFootprint(kNonExistentID, 0, + nonexistent_relative_path.c_str(), + PUPData::DISK_MATCH_ANY_FILE); + pups_to_be_scanned.insert(kNonExistentID); + + test_pup_data.AddDiskFootprint(k42ID, CSIDL_LOCAL_APPDATA, + relative_path.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + pups_to_be_scanned.insert(k42ID); + pups_to_be_found.insert(k42ID); + + base::FilePath temp_file2; + ASSERT_TRUE( + CreateTemporaryFileInDir(scoped_temp_dir2.GetPath(), &temp_file2)); + + Scan(); + ExpectFoundPUPs(pups_to_be_found); + + // Set up registry footprints. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + struct TestData { + UwSId id; + const base::char16* key_path; + const base::char16* value_name; + const base::char16* value; + RegistryMatchRule rule; + } test_data[] = { + {k24ID, kBaseName, nullptr, nullptr, REGISTRY_VALUE_MATCH_KEY}, + {kNonExistentID, kBadBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_PARTIAL}, + {k12ID, kBaseName, kValueName, kValue, REGISTRY_VALUE_MATCH_PARTIAL}, + {kNonExistentID, kBaseName, kValueName, kBaValue, + REGISTRY_VALUE_MATCH_PARTIAL}, + {kNonExistentID, kBaseName, kBaValue, kValue, + REGISTRY_VALUE_MATCH_PARTIAL}, + {k42ID, kBaseName, kValueName, nullptr, REGISTRY_VALUE_MATCH_VALUE_NAME}, + }; + for (size_t i = 0; i < base::size(test_data); ++i) { + test_pup_data.AddRegistryFootprint( + test_data[i].id, REGISTRY_ROOT_LOCAL_MACHINE, test_data[i].key_path, + test_data[i].value_name, test_data[i].value, test_data[i].rule); + pups_to_be_scanned.insert(test_data[i].id); + } + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + pups_to_be_found.insert(k24ID); + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kComplexValue)); + pups_to_be_found.insert(k12ID); + pups_to_be_found.insert(k42ID); + + Scan(); + ExpectFoundPUPs(pups_to_be_found); + + // Set up users registry footprints. + registry_override.OverrideRegistry(HKEY_CURRENT_USER); + + test_pup_data.AddRegistryFootprint(k12ID, REGISTRY_ROOT_USERS, kBaseName, + kValueName, nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + pups_to_be_scanned.insert(k12ID); + test_pup_data.AddRegistryFootprint(kNonExistentID, REGISTRY_ROOT_USERS, + kBadBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_EXACT); + pups_to_be_scanned.insert(kNonExistentID); + test_pup_data.AddRegistryFootprint(k84ID, REGISTRY_ROOT_USERS, kBaseName, + nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + pups_to_be_scanned.insert(k84ID); + + base::win::RegKey users_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + users_registry_key.Create(HKEY_CURRENT_USER, kBaseName, KEY_WRITE)); + pups_to_be_found.insert(k84ID); + ASSERT_EQ(ERROR_SUCCESS, users_registry_key.WriteValue(kValueName, kValue)); + pups_to_be_found.insert(k12ID); + + Scan(); + ExpectFoundPUPs(pups_to_be_found); +} + +TEST_F(ScannerTest, FindSomeWithinMany) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_CURRENT_USER); + + base::win::RegKey users_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + users_registry_key.Create(HKEY_CURRENT_USER, kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + std::set<UwSId> pups_to_find; + for (UwSId pup_id = 0; pup_id < kManyPUPs; ++pup_id) { + if (base::RandGenerator(kManyPUPs) % kFoundPUPsModuloBase == 0) { + test_pup_data.AddRegistryFootprint(pup_id, REGISTRY_ROOT_USERS, kBaseName, + nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + pups_to_find.insert(pup_id); + } else { + test_pup_data.AddRegistryFootprint(pup_id, REGISTRY_ROOT_USERS, + kBadBaseName, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + } + } + + Scan(); + ExpectFoundPUPs(pups_to_find); +} + +TEST_F(ScannerTest, DiskMatchActiveFileRule) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, existent_folder.value().c_str(), + PUPData::DISK_MATCH_BINARY_FILE); + const PUPData::PUP* pup42 = PUPData::GetPUP(k42ID); + + // No PUP should be found when no files are found. + Scan(); + ExpectNoPUPsFound(); + + // Add a non-active file, and it should still not be found. + base::FilePath temp_file1 = existent_folder.Append(L"file.inactive"); + ASSERT_TRUE(CreateEmptyFile(temp_file1)); + + // No PUP should be found when no active files are found. + Scan(); + ExpectNoPUPsFound(); + + // Add a active file, and it should be found. + base::FilePath temp_file2; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder, &temp_file2)); + + const base::char16* extensions[] = { + L".bla", L".dLl", L".ExE", L".foo", L".mshxml", L".URL", L".sys", + }; + + bool found_active = false; + bool found_not_active = false; + for (size_t i = 0; i < base::size(extensions); ++i) { + base::FilePath previous_file(temp_file2); + temp_file2 = temp_file2.ReplaceExtension(extensions[i]); + ASSERT_TRUE(ReplaceFile(previous_file, temp_file2, nullptr)); + Scan(); + if (PathHasActiveExtension(temp_file2)) { + found_active = true; + ExpectSinglePUP(k42ID); + EXPECT_EQ(3UL, pup42->expanded_disk_footprints.size()); + ExpectDiskFootprint(*pup42, existent_folder); + ExpectDiskFootprint(*pup42, temp_file1); + ExpectDiskFootprint(*pup42, temp_file2); + } else { + found_not_active = true; + ExpectNoPUPsFound(); + } + } + EXPECT_TRUE(found_not_active); + EXPECT_TRUE(found_active); +} + +// Creates |num_folders| in |root_folder| returning the deepest folder created. +// All of the created folders are added to |folders_created|, which is +// intentionally not cleared by this function. +// If |num_folders| <= 0, |root_folder| is returned. +// If the directories aren't created, an empty FilePath is returned. +base::FilePath CreateNestedFolders( + const base::FilePath& root_folder, + const base::string16& folder_name, + int num_folders, + std::vector<base::FilePath>* folders_created) { + base::FilePath folder(root_folder); + for (int i = 0; i < num_folders; ++i) { + folder = folder.Append(base::FilePath(folder_name)); + folders_created->push_back(folder); + } + + if (!CreateDirectory(folder)) + folder.clear(); + + return folder; +} + +int DiskMatchFileInFolderDepth(PUPData::DiskMatchRule rule) { + return rule - PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1 + 1; +} + +TEST_F(ScannerTest, DiskMatchFileInFolderRule) { + for (auto rule = PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1; + rule < PUPData::DISK_MATCH_FILE_IN_FOLDER_END; + rule = static_cast<PUPData::DiskMatchRule>(rule + 1)) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath root_folder(scoped_temp_dir.GetPath()); + + std::vector<base::FilePath> folders; + base::FilePath sub_folder = CreateNestedFolders( + root_folder, kBaseName, DiskMatchFileInFolderDepth(rule), &folders); + ASSERT_FALSE(sub_folder.empty()); + base::FilePath file_to_match(sub_folder.Append(kOtherBaseName)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, file_to_match.value().c_str(), + rule); + const PUPData::PUP* pup42 = PUPData::GetPUP(k42ID); + + // No PUP should be found when no files are found. + Scan(); + ExpectNoPUPsFound(); + + // Add the file, and it should be found, as well as all its siblings. + ASSERT_TRUE(CreateEmptyFile(file_to_match)) << "Rule: " << rule; + base::FilePath temp_file1; + ASSERT_TRUE(CreateTemporaryFileInDir(sub_folder, &temp_file1)) + << "Rule: " << rule; + base::FilePath temp_file2; + ASSERT_TRUE(CreateTemporaryFileInDir(sub_folder, &temp_file2)) + << "Rule: " << rule; + + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(3UL + folders.size(), pup42->expanded_disk_footprints.size()) + << "Rule: " << rule; + for (const auto& folder : folders) { + ExpectDiskFootprint(*pup42, folder); + } + ExpectDiskFootprint(*pup42, file_to_match); + ExpectDiskFootprint(*pup42, temp_file1); + ExpectDiskFootprint(*pup42, temp_file2); + } +} + +TEST_F(ScannerTest, DiskMatchAllFilesInFolderRule) { + for (auto rule = PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1; + rule < PUPData::DISK_MATCH_FILE_IN_FOLDER_END; + rule = static_cast<PUPData::DiskMatchRule>(rule + 1)) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath root_folder(scoped_temp_dir.GetPath()); + + std::vector<base::FilePath> folders; + base::FilePath sub_folder = CreateNestedFolders( + root_folder, kBaseName, DiskMatchFileInFolderDepth(rule), &folders); + ASSERT_FALSE(sub_folder.empty()); + base::FilePath file_to_match(sub_folder.Append(kOtherBaseName)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, file_to_match.value().c_str(), + rule); + const PUPData::PUP* pup42 = PUPData::GetPUP(k42ID); + + // No PUP should be found when no files are found. + Scan(); + ExpectNoPUPsFound(); + + // Add the file, and it should be found, as well as a file in each folder. + ASSERT_TRUE(CreateEmptyFile(file_to_match)) << "Rule: " << rule; + std::vector<base::FilePath> extra_files; + for (const auto& folder : folders) { + base::FilePath extra_file; + ASSERT_TRUE(CreateTemporaryFileInDir(folder, &extra_file)) + << "Rule: " << rule; + extra_files.push_back(extra_file); + } + + Scan(); + ExpectSinglePUP(k42ID); + // The initial 1 below is for the initial file that is matched. + EXPECT_EQ(1UL + folders.size() + extra_files.size(), + pup42->expanded_disk_footprints.size()) + << "Rule: " << rule; + ExpectDiskFootprint(*pup42, file_to_match); + for (const auto& folder : folders) { + ExpectDiskFootprint(*pup42, folder); + } + for (const auto& extra_file : extra_files) { + ExpectDiskFootprint(*pup42, extra_file); + } + } +} + +TEST_F(ScannerTest, DiskMatchFileIn3FoldersRule) { + for (auto rule = PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1; + rule < PUPData::DISK_MATCH_FILE_IN_FOLDER_END; + rule = static_cast<PUPData::DiskMatchRule>(rule + 1)) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath root_folder(scoped_temp_dir.GetPath()); + ASSERT_TRUE(base::PathExists(root_folder)); + + std::vector<base::FilePath> folders; + + folders.push_back(root_folder.Append(L"abc1")); + base::FilePath sub_folder = + CreateNestedFolders(*folders.rbegin(), kBaseName, + DiskMatchFileInFolderDepth(rule) - 1, &folders); + ASSERT_FALSE(sub_folder.empty()); + base::FilePath file_in_folder1(sub_folder.Append(kOtherBaseName)); + + folders.push_back(root_folder.Append(L"abc2")); + sub_folder = + CreateNestedFolders(*folders.rbegin(), kBaseName, + DiskMatchFileInFolderDepth(rule) - 1, &folders); + ASSERT_FALSE(sub_folder.empty()); + base::FilePath file_in_folder2(sub_folder.Append(kOtherBaseName)); + + folders.push_back(root_folder.Append(L"abc3")); + sub_folder = + CreateNestedFolders(*folders.rbegin(), kBaseName, + DiskMatchFileInFolderDepth(rule) - 1, &folders); + ASSERT_FALSE(sub_folder.empty()); + base::FilePath file_in_folder3(sub_folder.Append(kOtherBaseName)); + + base::FilePath pattern(root_folder.Append(L"abc?")); + for (int i = 0; i < DiskMatchFileInFolderDepth(rule) - 1; ++i) { + pattern = pattern.Append(kBaseName); + } + pattern = pattern.Append(kOtherBaseName); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, pattern.value().c_str(), rule); + const PUPData::PUP* pup42 = PUPData::GetPUP(k42ID); + + // No PUP should be found when no files are found. + Scan(); + EXPECT_TRUE(found_pups_.empty()) << "Rule: " << rule; + + // Add the files, and they should be found. + ASSERT_TRUE(CreateEmptyFile(file_in_folder1)) << "Rule: " << rule; + ASSERT_TRUE(CreateEmptyFile(file_in_folder2)) << "Rule: " << rule; + ASSERT_TRUE(CreateEmptyFile(file_in_folder3)) << "Rule: " << rule; + + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(3UL + folders.size(), pup42->expanded_disk_footprints.size()) + << "Rule: " << rule; + for (const auto& folder : folders) { + ExpectDiskFootprint(*pup42, folder); + } + ExpectDiskFootprint(*pup42, file_in_folder1); + ExpectDiskFootprint(*pup42, file_in_folder2); + ExpectDiskFootprint(*pup42, file_in_folder3); + } +} + +TEST_F(ScannerTest, DiskDontMatchFolderInFolderRule) { + for (auto rule = PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1; + rule < PUPData::DISK_MATCH_FILE_IN_FOLDER_END; + rule = static_cast<PUPData::DiskMatchRule>(1 + rule)) { + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath root_folder(scoped_temp_dir.GetPath()); + + std::vector<base::FilePath> folders; + base::FilePath sub_folder = CreateNestedFolders( + root_folder, kBaseName, DiskMatchFileInFolderDepth(rule), &folders); + ASSERT_FALSE(sub_folder.empty()); + base::FilePath file_to_match(sub_folder.Append(kBaseName)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, file_to_match.value().c_str(), + rule); + + // No PUP should be found when no files are found. + Scan(); + ExpectNoPUPsFound(); + + // Add the footprint as a folder, and it should not be found. + ASSERT_TRUE(CreateDirectory(file_to_match)); + + // No PUP should be found when no files are found. + Scan(); + EXPECT_TRUE(found_pups_.empty()) << "Rule: " << rule; + } +} + +TEST_F(ScannerTest, DiskWithWow64Entry) { + base::ScopedPathOverride windows_override(base::DIR_WINDOWS); + base::FilePath windows_dir; + ASSERT_TRUE(base::PathService::Get(base::DIR_WINDOWS, &windows_dir)); + base::FilePath native_dir(windows_dir.Append(L"sysnative")); + ASSERT_TRUE(CreateDirectory(native_dir)); + + // Set up a folder with a file in 64-bit system folder. + ASSERT_TRUE(CreateFileInFolder(native_dir, L"dummy")); + + TestPUPData test_pup_data; + test_pup_data.AddPUP(k42ID, PUPData::FLAGS_ACTION_REMOVE, nullptr, + PUPData::kMaxFilesToRemoveSmallUwS); + test_pup_data.AddDiskFootprint(k42ID, CSIDL_SYSTEM, L"d?mm?", + PUPData::DISK_MATCH_ANY_FILE); + + Scan(); + ExpectSinglePUP(k42ID); + + const PUPData::PUP* pup = PUPData::GetPUP(k42ID); + ExpectDiskFootprint(*pup, native_dir.Append(L"dummy")); +} + +TEST_F(ScannerTest, RegistryMatchRuleExactValue) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, kComplexValue, + REGISTRY_VALUE_MATCH_EXACT); + + // Empty key must not match. + Scan(); + ExpectNoPUPsFound(); + + // Write a different value. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(kValueName, kValue)); + Scan(); + ExpectNoPUPsFound(); + + // Write the same value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kComplexValue)); + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, RegistryMatchRuleContainsValue) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_CONTAINS); + + // Empty key must not match. + Scan(); + ExpectNoPUPsFound(); + + // Write a different value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kValueDifferentCase)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write a different value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBaValue)); + Scan(); + ExpectNoPUPsFound(); + + // Write the same value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kComplexValue)); + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, RegistryMatchRulePartialValue) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_PARTIAL); + + // Empty key must not match. + Scan(); + ExpectNoPUPsFound(); + + // Write a same value with different case. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kValueDifferentCase)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write a different value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBaValue)); + Scan(); + ExpectNoPUPsFound(); + + // Write the complex value which contains the value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kComplexValue)); + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, RegistryMatchRuleCommonSetSeparatedExactValue) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_LOCAL_MACHINE, kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_EXACT); + + // Write a set separated by common delimiters with the value as an element. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kCommonSetValue)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write a set separated by a null character. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, kCommonSetWithNullValue, + sizeof(kCommonSetWithNullValue), REG_SZ)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write a set which contains the value, but isn't equals to. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, kBiggerCommaSetValue, + sizeof(kBiggerCommaSetValue), REG_SZ)); + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, RegistryMatchRuleCommonSetSeparatedContainsValue) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_LOCAL_MACHINE, kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_CONTAINS); + + // Write a set separated by common delimiters with the value as an element. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kCommonSetValue)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write a set separated by a null character. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, kCommonSetWithNullValue, + sizeof(kCommonSetWithNullValue), REG_SZ)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write a set which contains the value, but isn't equals to. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue( + kValueName, kBiggerCommaSetValue, + sizeof(kBiggerCommaSetValue), REG_SZ)); + Scan(); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, RegistryMatchRuleCommaSetSeparatedExactValue) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_LOCAL_MACHINE, kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_COMMA_SEPARATED_SET_EXACT); + + // Empty key must not match. + Scan(); + ExpectNoPUPsFound(); + + // Write the same value. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(kValueName, kValue)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write set which contains the exact value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kCommaSetValue)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write set which contains a partial match. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBiggerCommaSetValue)); + Scan(); + ExpectNoPUPsFound(); + + // Write set without the value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBadCommaSetValue)); + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, RegistryMatchRuleCommaSetSeparatedContainstValue) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_LOCAL_MACHINE, kBaseName, kValueName, kValue, + REGISTRY_VALUE_MATCH_COMMA_SEPARATED_SET_CONTAINS); + + // Empty key must not match. + Scan(); + ExpectNoPUPsFound(); + + // Write the same value. + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.WriteValue(kValueName, kValue)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write set which contains the exact value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kCommaSetValue)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write set which contains a partial match. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBiggerCommaSetValue)); + Scan(); + ExpectSinglePUP(k42ID); + + // Write set without the value. + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kBadCommaSetValue)); + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, ReportOnlyPUP) { + // Set up a folder only disk footprint. + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + + TestPUPData test_pup_data; + test_pup_data.AddPUP(k42ID, PUPData::FLAGS_NONE, nullptr, + PUPData::kMaxFilesToRemoveSmallUwS); + test_pup_data.AddDiskFootprint(k42ID, 0, existent_folder.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + + // Add a file, and it should be reported but not found. + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder, &temp_file)); + + Scan(); + EXPECT_FALSE(found_pups_.empty()); + EXPECT_FALSE(found_pup_to_remove_); + EXPECT_TRUE(found_report_only_); +} + +TEST_F(ScannerTest, StopScanning) { + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_CURRENT_USER); + + base::win::RegKey users_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + users_registry_key.Create(HKEY_CURRENT_USER, kBaseName, KEY_WRITE)); + + TestPUPData test_pup_data; + std::set<UwSId> pups_to_find; + for (UwSId pup_id = 0; pup_id < kSomePUPs; ++pup_id) { + if (base::RandGenerator(kSomePUPs) % kFoundPUPsModuloBase == 0) { + test_pup_data.AddRegistryFootprint(pup_id, REGISTRY_ROOT_USERS, kBaseName, + nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + pups_to_find.insert(pup_id); + } else { + for (size_t i = 0; i < 100; ++i) { + test_pup_data.AddRegistryFootprint(pup_id, REGISTRY_ROOT_USERS, + kBadBaseName, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + test_pup_data.AddDiskFootprint(pup_id, 0, kBadBaseName, + PUPData::DISK_MATCH_ANY_FILE); + } + } + } + + // Post the stop call to the main loop so that we can start the scan and get + // it to stop while we wait for it to be done. + base::ThreadTaskRunnerHandle::Get()->PostTask( + FROM_HERE, + base::BindOnce(&ScannerTest::StopScanner, base::Unretained(this))); + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, RunningCustomMatchers) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher1); + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher3); + + g_test_custom_matcher1_called = false; + g_test_custom_matcher2_called = false; + g_test_custom_matcher3_called = false; + Scan(); + ASSERT_TRUE(g_test_custom_matcher1_called); + ASSERT_FALSE(g_test_custom_matcher2_called); + ASSERT_TRUE(g_test_custom_matcher3_called); + ExpectSinglePUP(k42ID); +} + +TEST_F(ScannerTest, RunningCustomMatchersNoScanAndRemove) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher2); + + g_test_custom_matcher1_called = false; + g_test_custom_matcher2_called = false; + g_test_custom_matcher3_called = false; + Scan(); + ASSERT_FALSE(g_test_custom_matcher1_called); + ASSERT_TRUE(g_test_custom_matcher2_called); + ASSERT_FALSE(g_test_custom_matcher3_called); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, RunningCustomMatchersNothingFound) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher3); + + g_test_custom_matcher1_called = false; + g_test_custom_matcher2_called = false; + g_test_custom_matcher3_called = false; + Scan(); + ASSERT_FALSE(g_test_custom_matcher1_called); + ASSERT_FALSE(g_test_custom_matcher2_called); + ASSERT_TRUE(g_test_custom_matcher3_called); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, RunningCustomMatchersWithError) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher4); + + // The custom scanner returns an error, and scanning this pup is aborted. + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, RunningCustomMatchersWithErrorAndFootprint) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher1); + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher4); + + // The custom scanner returns an error, and scanning this pup is aborted + // even if there is a footprint matched by |TestCustomMatcher1|. + Scan(); + ExpectNoPUPsFound(); +} + +TEST_F(ScannerTest, RunningCustomMatchersKeepDiskActiveFootprintFound) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher5); + + // Add a found disk footprint + base::ScopedTempDir scoped_temp_dir1; + ASSERT_TRUE(scoped_temp_dir1.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir1.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder, &temp_file)); + + test_pup_data.AddDiskFootprint(k42ID, 0, existent_folder.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + + g_test_custom_matcher5_found = false; + Scan(); + EXPECT_TRUE(g_test_custom_matcher5_found); +} + +TEST_F(ScannerTest, RunningCustomMatchersDefaultActiveFootprintFound) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher5); + + g_test_custom_matcher5_found = false; + Scan(); + EXPECT_FALSE(g_test_custom_matcher5_found); +} + +TEST_F(ScannerTest, ScanRegistrySingleCharacterWildcardFootprints) { + TestPUPData test_pup_data; + std::vector<UwSId> pup_ids; + pup_ids.push_back(k42ID); + + // Set up a local machine registry footprint. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kRegistryKeyPath, kValueNameSingleWildcard, + nullptr, REGISTRY_VALUE_MATCH_VALUE_NAME); + + base::win::RegKey registry_key; + ASSERT_EQ(ERROR_SUCCESS, + registry_key.Create(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_ALL_ACCESS)); + + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kValueName, kComplexValue)); + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kValueName1, kComplexValue)); + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kValueName2, kComplexValue)); + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kValueName3, kComplexValue)); + + Scan(); + ExpectSinglePUP(k42ID); + + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + EXPECT_EQ(3UL, found_pup->expanded_registry_footprints.size()); + + // |kValueName| should not match the regular expression but |kValueName1|, + // |kValueName2| and |kValueName3| must be matched. + const RegKeyPath key_path(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_WOW64_32KEY); + ExpectRegistryFootprint(*found_pup, key_path, kValueName1, L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, kValueName2, L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, kValueName3, L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); +} + +TEST_F(ScannerTest, ScanWithRegistryMultiCharactersWildcardFootprints) { + TestPUPData test_pup_data; + std::vector<UwSId> pup_ids; + pup_ids.push_back(k42ID); + + // Set up a local machine registry footprint. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kRegistryKeyPath, kValueNameMultiWildcard, + nullptr, REGISTRY_VALUE_MATCH_VALUE_NAME); + + base::win::RegKey registry_key; + ASSERT_EQ(ERROR_SUCCESS, + registry_key.Create(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_ALL_ACCESS)); + + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kOtherBaseName, kFooValue)); + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kBaseName, kComplexValue)); + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kValueName1, kComplexValue)); + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kValueName2, kComplexValue)); + ASSERT_EQ(ERROR_SUCCESS, registry_key.WriteValue(kValueName3, kComplexValue)); + + Scan(); + ExpectSinglePUP(k42ID); + + // The footprint |kOtherBaseName| is not matched by the regular expression. + // |kBaseName|, |kValueName1|, |kValueName2| and |kValueName3| must be + // matched. + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + EXPECT_EQ(4UL, found_pup->expanded_registry_footprints.size()); + + const RegKeyPath key_path(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_WOW64_32KEY); + ExpectRegistryFootprint(*found_pup, key_path, kBaseName, L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, kValueName1, L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, kValueName2, L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, kValueName3, L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); +} + +TEST_F(ScannerTest, ScanWithRegistryWildcardAndRuleFootprints) { + TestPUPData test_pup_data; + std::vector<UwSId> pup_ids; + pup_ids.push_back(k42ID); + + // Set up a local machine registry footprint. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + test_pup_data.AddRegistryFootprint( + k42ID, REGISTRY_ROOT_LOCAL_MACHINE, kRegistryKeyPath, + kValueNameSingleWildcard, kFooValue, + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_EXACT); + + base::win::RegKey registry_key; + ASSERT_EQ(ERROR_SUCCESS, + registry_key.Create(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_ALL_ACCESS)); + + ASSERT_EQ(ERROR_SUCCESS, + registry_key.WriteValue(kValueName1, kSetWithCommonValue1)); + ASSERT_EQ(ERROR_SUCCESS, + registry_key.WriteValue(kValueName2, kSetWithCommonValue2)); + ASSERT_EQ(ERROR_SUCCESS, + registry_key.WriteValue(kValueName3, kSetWithCommonValue3)); + + Scan(); + ExpectSinglePUP(k42ID); + + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + EXPECT_EQ(3UL, found_pup->expanded_registry_footprints.size()); + + const RegKeyPath key_path(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_WOW64_32KEY); + ExpectRegistryFootprint(*found_pup, key_path, kValueName1, kFooValue, + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_EXACT); + + ExpectRegistryFootprint(*found_pup, key_path, kValueName2, kFooValue, + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_EXACT); + + ExpectRegistryFootprint(*found_pup, key_path, kValueName3, kFooValue, + REGISTRY_VALUE_MATCH_COMMON_SEPARATED_SET_EXACT); +} + +TEST_F(ScannerTest, ScanWithKeyPathWildCardsRegistryFootprints) { + TestPUPData test_pup_data; + std::vector<UwSId> pup_ids; + pup_ids.push_back(k42ID); + + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + L"software\\t*\\du??y", L"b*", nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + + base::win::RegKey test1_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + test1_registry_key.Create( + HKEY_LOCAL_MACHINE, L"software\\test1\\dummy", KEY_ALL_ACCESS)); + base::win::RegKey test2_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + test2_registry_key.Create( + HKEY_LOCAL_MACHINE, L"software\\test2\\dummy", KEY_ALL_ACCESS)); + + base::win::RegKey best_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + best_registry_key.Create(HKEY_LOCAL_MACHINE, + L"software\\best\\dummy", KEY_ALL_ACCESS)); + + base::win::RegKey unused_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + unused_registry_key.Create(HKEY_LOCAL_MACHINE, L"software\\best", + KEY_ALL_ACCESS)); + + ASSERT_EQ(ERROR_SUCCESS, test1_registry_key.WriteValue(L"foo", kValue)); + ASSERT_EQ(ERROR_SUCCESS, test1_registry_key.WriteValue(L"bar", kValue)); + ASSERT_EQ(ERROR_SUCCESS, test1_registry_key.WriteValue(L"bat", kValue)); + ASSERT_EQ(ERROR_SUCCESS, test2_registry_key.WriteValue(L"foo", kValue)); + ASSERT_EQ(ERROR_SUCCESS, test2_registry_key.WriteValue(L"bar", kValue)); + ASSERT_EQ(ERROR_SUCCESS, test2_registry_key.WriteValue(L"bat", kValue)); + ASSERT_EQ(ERROR_SUCCESS, best_registry_key.WriteValue(L"bat", kValue)); + + Scan(); + ExpectSinglePUP(k42ID); + + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + EXPECT_EQ(4UL, found_pup->expanded_registry_footprints.size()); + + const RegKeyPath key_path(HKEY_LOCAL_MACHINE, L"software\\test1\\dummy", + KEY_WOW64_32KEY); + ExpectRegistryFootprint(*found_pup, key_path, L"bar", L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, L"bat", L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, L"bar", L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); + + ExpectRegistryFootprint(*found_pup, key_path, L"bat", L"", + REGISTRY_VALUE_MATCH_VALUE_NAME); +} + +TEST_F(ScannerTest, ScanRegistryKeyWithEscapedStar) { + TestPUPData test_pup_data; + std::vector<UwSId> pup_ids; + pup_ids.push_back(k42ID); + + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + constexpr base::char16 kRegistryPathWithStar[] = L"foo\\*"; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + L"foo\\" ESCAPE_REGISTRY_STR("*"), nullptr, + nullptr, REGISTRY_VALUE_MATCH_KEY); + + base::win::RegKey test_registry_key; + ASSERT_EQ(ERROR_SUCCESS, + test_registry_key.Create(HKEY_LOCAL_MACHINE, kRegistryPathWithStar, + KEY_ALL_ACCESS)); + + ASSERT_EQ(ERROR_SUCCESS, + test_registry_key.Create(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_ALL_ACCESS)); + Scan(); + ExpectSinglePUP(k42ID); + + // As the regular expression contains an escaped wild-card, only the exact + // key |kRegistryPathWithStar| must be matched. |kRegistryKeyPath| must not + // be matched. + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + EXPECT_EQ(1UL, found_pup->expanded_registry_footprints.size()); + + ExpectRegistryFootprint( + *found_pup, RegKeyPath(HKEY_LOCAL_MACHINE, L"foo\\*", KEY_WOW64_32KEY), + L"", L"", REGISTRY_VALUE_MATCH_KEY); +} + +TEST_F(ScannerTest, RegistryFootprintForDetectOnlyUws) { + TestPUPData test_pup_data; + test_pup_data.AddPUP(k12ID, PUPData::FLAGS_NONE, "test", + PUPData::kMaxFilesToRemoveSmallUwS); + test_pup_data.AddPUP(k24ID, PUPData::FLAGS_NONE, "test2", + PUPData::kMaxFilesToRemoveSmallUwS); + + // Set up a local machine registry footprint. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + test_pup_data.AddRegistryFootprint(k12ID, REGISTRY_ROOT_LOCAL_MACHINE, + kRegistryKeyPath, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + + test_pup_data.AddRegistryFootprint(k24ID, REGISTRY_ROOT_LOCAL_MACHINE, + kRegistryKeyPath, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + + base::win::RegKey registry_key; + ASSERT_EQ(ERROR_SUCCESS, + registry_key.Create(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_ALL_ACCESS)); + + Scan(); + + const RegKeyPath key_path(HKEY_LOCAL_MACHINE, kRegistryKeyPath, + KEY_WOW64_32KEY); + + std::set<UwSId> pups_to_be_found; + pups_to_be_found.insert(k12ID); + pups_to_be_found.insert(k24ID); + ExpectFoundPUPs(pups_to_be_found); + + const PUPData::PUP* found_pup12 = PUPData::GetPUP(k12ID); + ExpectRegistryFootprint(*found_pup12, key_path, L"", L"", + REGISTRY_VALUE_MATCH_KEY); + + const PUPData::PUP* found_pup24 = PUPData::GetPUP(k24ID); + ExpectRegistryFootprint(*found_pup24, key_path, L"", L"", + REGISTRY_VALUE_MATCH_KEY); +} + +TEST_F(ScannerTest, FindOnlyOneDiskFootprint) { + base::ScopedTempDir scoped_temp_dir1; + ASSERT_TRUE(scoped_temp_dir1.CreateUniqueTempDir()); + base::FilePath existent_folder_1(scoped_temp_dir1.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder_1)); + base::FilePath temp_file_1; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder_1, &temp_file_1)); + base::FilePath temp_file_2; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder_1, &temp_file_2)); + + base::ScopedTempDir scoped_temp_dir2; + ASSERT_TRUE(scoped_temp_dir2.CreateUniqueTempDir()); + base::FilePath existent_folder_2(scoped_temp_dir2.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder_2)); + base::FilePath temp_file_3; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder_2, &temp_file_3)); + + TestPUPData test_pup_data; + test_pup_data.AddDiskFootprint(k42ID, 0, temp_file_1.value().c_str(), + PUPData::DISK_MATCH_FILE_IN_FOLDER_DEPTH_1); + test_pup_data.AddDiskFootprint(k42ID, 0, temp_file_3.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + + options_.set_only_one_footprint(false); + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(4UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, temp_file_1); + ExpectDiskFootprint(*found_pup, temp_file_2); + ExpectDiskFootprint(*found_pup, existent_folder_1); + ExpectDiskFootprint(*found_pup, temp_file_3); + + options_.set_only_one_footprint(true); + Scan(); + ExpectSinglePUP(k42ID); + ASSERT_EQ(1UL, found_pups_.size()); + EXPECT_EQ(1UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, temp_file_1); +} + +TEST_F(ScannerTest, FindOnlyOneRegistryFootprints) { + // Set up a registry footprint. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + TestPUPData test_pup_data; + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, kValueName, nullptr, + REGISTRY_VALUE_MATCH_VALUE_NAME); + ASSERT_EQ(ERROR_SUCCESS, + system_registry_key.WriteValue(kValueName, kComplexValue)); + + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + + options_.set_only_one_footprint(false); + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(2UL, found_pup->expanded_registry_footprints.size()); + + options_.set_only_one_footprint(true); + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(1UL, found_pup->expanded_registry_footprints.size()); +} + +TEST_F(ScannerTest, FindOnlyOneCustomMatchers) { + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher1); + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher2); + + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + + options_.set_only_one_footprint(false); + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(2UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, base::FilePath(kDummyFullPath)); + ExpectDiskFootprint(*found_pup, base::FilePath(kOtherFullPath)); + EXPECT_TRUE(g_test_custom_matcher1_called); + EXPECT_TRUE(g_test_custom_matcher2_called); + + options_.set_only_one_footprint(true); + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(1UL, found_pup->expanded_disk_footprints.size()); + ExpectDiskFootprint(*found_pup, base::FilePath(kDummyFullPath)); + EXPECT_TRUE(g_test_custom_matcher1_called); + EXPECT_FALSE(g_test_custom_matcher2_called); +} + +TEST_F(ScannerTest, FindOnlyOneAmongAllTypes) { + // Start with just a custom matcher. + TestPUPData test_pup_data; + test_pup_data.AddCustomMatcher(k42ID, &TestCustomMatcher1); + + const PUPData::PUP* found_pup = PUPData::GetPUP(k42ID); + + options_.set_only_one_footprint(true); + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(1UL, found_pup->expanded_disk_footprints.size()); + EXPECT_EQ(0UL, found_pup->expanded_registry_footprints.size()); + ExpectDiskFootprint(*found_pup, base::FilePath(kDummyFullPath)); + EXPECT_TRUE(g_test_custom_matcher1_called); + + // Now add a registry footprint and only it should be found. + registry_util::RegistryOverrideManager registry_override; + registry_override.OverrideRegistry(HKEY_LOCAL_MACHINE); + + test_pup_data.AddRegistryFootprint(k42ID, REGISTRY_ROOT_LOCAL_MACHINE, + kBaseName, nullptr, nullptr, + REGISTRY_VALUE_MATCH_KEY); + base::win::RegKey system_registry_key; + ASSERT_EQ(ERROR_SUCCESS, system_registry_key.Create(HKEY_LOCAL_MACHINE, + kBaseName, KEY_WRITE)); + + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(0UL, found_pup->expanded_disk_footprints.size()); + EXPECT_EQ(1UL, found_pup->expanded_registry_footprints.size()); + EXPECT_FALSE(g_test_custom_matcher1_called); + + // Now add a disk footprint and onlyit should be found. + // Set up a folder only disk footprint. + base::ScopedTempDir scoped_temp_dir; + ASSERT_TRUE(scoped_temp_dir.CreateUniqueTempDir()); + base::FilePath existent_folder(scoped_temp_dir.GetPath()); + ASSERT_TRUE(base::PathExists(existent_folder)); + base::FilePath temp_file; + ASSERT_TRUE(CreateTemporaryFileInDir(existent_folder, &temp_file)); + + test_pup_data.AddDiskFootprint(k42ID, 0, temp_file.value().c_str(), + PUPData::DISK_MATCH_ANY_FILE); + + Scan(); + ExpectSinglePUP(k42ID); + EXPECT_EQ(1UL, found_pup->expanded_disk_footprints.size()); + EXPECT_EQ(0UL, found_pup->expanded_registry_footprints.size()); + ExpectDiskFootprint(*found_pup, temp_file); + EXPECT_FALSE(g_test_custom_matcher1_called); +} + +} // namespace chrome_cleaner
diff --git a/chrome/chrome_cleaner/test/BUILD.gn b/chrome/chrome_cleaner/test/BUILD.gn index 3a6894e1..e8201d9 100644 --- a/chrome/chrome_cleaner/test/BUILD.gn +++ b/chrome/chrome_cleaner/test/BUILD.gn
@@ -67,6 +67,7 @@ "test_registry_util.h", "test_settings_util.cc", "test_settings_util.h", + "test_signature_matcher.h", "test_task_scheduler.cc", "test_task_scheduler.h", "test_util.cc", @@ -82,6 +83,8 @@ "//chrome/chrome_cleaner/os:cleaner_os", "//chrome/chrome_cleaner/os:common_os", "//chrome/chrome_cleaner/pup_data:pup_data_base", + "//chrome/chrome_cleaner/scanner:matcher_util", + "//chrome/chrome_cleaner/scanner:signature_matcher_api", "//chrome/chrome_cleaner/settings:settings", "//chrome/chrome_cleaner/strings", "//components/chrome_cleaner/public/constants:constants",
diff --git a/chrome/chrome_cleaner/test/test_signature_matcher.h b/chrome/chrome_cleaner/test/test_signature_matcher.h new file mode 100644 index 0000000..17266a83 --- /dev/null +++ b/chrome/chrome_cleaner/test/test_signature_matcher.h
@@ -0,0 +1,150 @@ +// Copyright 2018 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_CHROME_CLEANER_TEST_TEST_SIGNATURE_MATCHER_H_ +#define CHROME_CHROME_CLEANER_TEST_TEST_SIGNATURE_MATCHER_H_ + +#include <map> +#include <set> +#include <string> +#include <vector> + +#include "base/file_version_info.h" +#include "base/files/file_util.h" +#include "base/strings/string_util.h" +#include "base/synchronization/lock.h" +#include "chrome/chrome_cleaner/os/file_path_sanitization.h" +#include "chrome/chrome_cleaner/scanner/matcher_util.h" +#include "chrome/chrome_cleaner/scanner/signature_matcher_api.h" + +namespace chrome_cleaner { + +// A signature matcher implementation used for testing. +class TestSignatureMatcher : public SignatureMatcherAPI { + public: + TestSignatureMatcher() : scan_error_(false) {} + + bool MatchFileDigestInfo(const base::FilePath& path, + size_t* filesize, + std::string* digest, + const FileDigestInfo& digest_info) const override { + DCHECK(filesize); + DCHECK(digest); + base::AutoLock lock(lock_); + const auto& matched_digest_info = + matched_digest_info_.find(NormalizePath(path)); + if (matched_digest_info == matched_digest_info_.end()) + return false; + if (*filesize == 0) { + DCHECK(digest->empty()); + *filesize = matched_digest_info->second.filesize; + *digest = matched_digest_info->second.digest; + } else { + DCHECK_EQ(matched_digest_info->second.filesize, *filesize); + DCHECK_EQ(matched_digest_info->second.digest, *digest); + } + return matched_digest_info->second.filesize == digest_info.filesize && + matched_digest_info->second.digest == digest_info.digest; + } + + bool ComputeSHA256DigestOfPath(const base::FilePath& path, + std::string* digest) const override { + DCHECK(digest); + base::AutoLock lock(lock_); + const auto& matched_digest = matched_digests_.find(NormalizePath(path)); + if (matched_digest == matched_digests_.end()) + return false; + *digest = matched_digest->second; + return true; + } + + bool RetrieveVersionInformation( + const base::FilePath& path, + VersionInformation* information) const override { + DCHECK(information); + base::AutoLock lock(lock_); + + const auto& matched_information = + matched_version_informations_.find(NormalizePath(path)); + if (matched_information == matched_version_informations_.end()) + return false; + *information = matched_information->second; + return true; + } + + void Reset() { + base::AutoLock lock(lock_); + scan_error_ = false; + matched_basenames_.clear(); + matched_digests_.clear(); + computed_digests_.clear(); + matched_version_informations_.clear(); + } + + void MatchDigest(const base::FilePath& path, const char* digest) { + base::AutoLock lock(lock_); + matched_digests_[NormalizePath(path)] = digest; + } + + void MatchDigestInfo(const base::FilePath& path, + const char* digest, + size_t filesize) { + base::AutoLock lock(lock_); + const base::FilePath normalized_path = NormalizePath(path); + matched_digest_info_[normalized_path].digest = digest; + matched_digest_info_[normalized_path].filesize = filesize; + } + + void MatchVersionInformation(const base::FilePath& path, + const VersionInformation& information) { + matched_version_informations_[NormalizePath(path)] = information; + } + + size_t CountMatchDigestCalled() { + base::AutoLock lock(lock_); + return matched_digests_.size(); + } + + bool IsMatchDigestCalled(const base::FilePath& path) { + base::AutoLock lock(lock_); + return matched_digests_.find(NormalizePath(path)) != matched_digests_.end(); + } + + void MatchBaseName(const base::FilePath& path, + const std::string& identifier) { + base::AutoLock lock(lock_); + matched_basenames_[NormalizePath(path).BaseName()] = identifier; + } + + void ForceScanFailure() { + base::AutoLock lock(lock_); + scan_error_ = true; + } + + private: + struct TestFileDigestInfo { + std::string digest; + size_t filesize; + }; + + bool scan_error_; + + // Map paths to signature identifiers. When the given path is scanned, the + // mapped identifier is returned. + std::map<base::FilePath, std::string> matched_basenames_; + std::map<base::FilePath, std::string> matched_digests_; + std::map<base::FilePath, TestFileDigestInfo> matched_digest_info_; + std::map<base::FilePath, VersionInformation> matched_version_informations_; + + // Keep track of calls and parameters done. + std::set<base::FilePath> computed_digests_; + + // Must be held for all access to all data since |ScanFile| can be called + // from other threads. + mutable base::Lock lock_; +}; + +} // namespace chrome_cleaner + +#endif // CHROME_CHROME_CLEANER_TEST_TEST_SIGNATURE_MATCHER_H_
diff --git a/chrome/common/pref_names.cc b/chrome/common/pref_names.cc index 7b7c6536..1c03afd7 100644 --- a/chrome/common/pref_names.cc +++ b/chrome/common/pref_names.cc
@@ -1148,17 +1148,10 @@ #endif // !OS_CHROMEOS && !OS_ANDROID #if defined(OS_CHROMEOS) -// List of all printers that the user has configured. -const char kPrintingDevices[] = "printing.devices"; - // List of printers configured by policy. const char kRecommendedNativePrinters[] = "native_printing.recommended_printers"; -// External resource containing all printer configurations for an enterprise. -const char kRecommendedNativePrintersFile[] = - "native_printing.recommended_printers_file"; - // Enum designating the type of restrictions bulk printers are using. const char kRecommendedNativePrintersAccessMode[] = "native_printing.recommended_printers_access_mode";
diff --git a/chrome/common/pref_names.h b/chrome/common/pref_names.h index 9d8c15f2..9336e07 100644 --- a/chrome/common/pref_names.h +++ b/chrome/common/pref_names.h
@@ -386,9 +386,7 @@ #endif #if defined(OS_CHROMEOS) -extern const char kPrintingDevices[]; extern const char kRecommendedNativePrinters[]; -extern const char kRecommendedNativePrintersFile[]; extern const char kRecommendedNativePrintersAccessMode[]; extern const char kRecommendedNativePrintersBlacklist[]; extern const char kRecommendedNativePrintersWhitelist[];
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn index 9408de4..3c86f62b 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn
@@ -4477,6 +4477,9 @@ ] } } + if (use_nss_certs) { + sources += [ "../browser/certificate_manager_model_unittest.cc" ] + } if (!is_android && use_nss_certs) { sources += [ "../common/net/x509_certificate_model_nss_unittest.cc" ] }
diff --git a/chrome/test/data/background_fetch/background_fetch.js b/chrome/test/data/background_fetch/background_fetch.js index 5586a31..8a3ffae 100644 --- a/chrome/test/data/background_fetch/background_fetch.js +++ b/chrome/test/data/background_fetch/background_fetch.js
@@ -86,8 +86,13 @@ } // Listens for a postMessage from sw.js and sends the result to the test. -navigator.serviceWorker.addEventListener('message', (event) => { - if (['backgroundfetchsuccess', 'backgroundfetchfail'].includes(event.data)) +navigator.serviceWorker.addEventListener('message', event => { + const expectedResponses = [ + 'backgroundfetchsuccess', + 'backgroundfetchfail', + 'permissionerror', + ]; + if (expectedResponses.includes(event.data)) sendResultToTest(event.data); else sendErrorToTest(Error('Unexpected message received: ' + event.data)); @@ -116,3 +121,27 @@ kBackgroundFetchId, resources); }).catch(sendErrorToTest); } + +// Starts a Background Fetch that should fail due to a missing resource. +function RunFetchAnExpectAnException() { + const resources = [ + '/background_fetch/types_of_cheese.txt', + '/background_fetch/missing_cat.txt', + ]; + navigator.serviceWorker.ready.then(swRegistration => { + return swRegistration.backgroundFetch.fetch(kBackgroundFetchId, resources); + }).then(sendErrorToTest) + .catch(e => sendResultToTest(e.message)); +} + +function StartFetchFromServiceWorker() { + navigator.serviceWorker.ready.then(() => { + navigator.serviceWorker.controller.postMessage('fetch'); + }); +} + +function StartFetchFromIframe() { + const iframe = document.createElement('iframe'); + iframe.src = '/background_fetch/background_fetch_iframe.html'; + document.body.appendChild(iframe); +}
diff --git a/chrome/test/data/background_fetch/background_fetch_iframe.html b/chrome/test/data/background_fetch/background_fetch_iframe.html new file mode 100644 index 0000000..80798ed --- /dev/null +++ b/chrome/test/data/background_fetch/background_fetch_iframe.html
@@ -0,0 +1,15 @@ +<!doctype html> +<html> + <head> + <meta charset="utf-8" /> + <script src="../result_queue.js"></script> + </head> + <body> + <script> + navigator.serviceWorker.ready.then(swRegistration => { + return swRegistration.backgroundFetch.fetch( + 'iframe-fetch', '/background_fetch/types_of_cheese.txt'); + }).catch(e => sendResultToTest('permissionerror')); + </script> + </body> +</html>
diff --git a/chrome/test/data/background_fetch/sw.js b/chrome/test/data/background_fetch/sw.js index 407f2c4..7105346 100644 --- a/chrome/test/data/background_fetch/sw.js +++ b/chrome/test/data/background_fetch/sw.js
@@ -13,6 +13,14 @@ }); } +self.addEventListener('message', e => { + if (e.data !== 'fetch') throw "unexpected message"; + + self.registration.backgroundFetch.fetch( + 'sw-fetch', '/background_fetch/types_of_cheese.txt') + .catch(e => postToWindowClients('permissionerror')); +}); + // Background Fetch event listeners. self.addEventListener('backgroundfetchsuccess', e => { e.waitUntil(e.updateUI({title: 'New Fetched Title!'}).then(
diff --git a/chrome/test/data/extensions/api_test/file_browser/file_watcher_test/test.js b/chrome/test/data/extensions/api_test/file_browser/file_watcher_test/test.js index d99cfe43..fab6e70 100644 --- a/chrome/test/data/extensions/api_test/file_browser/file_watcher_test/test.js +++ b/chrome/test/data/extensions/api_test/file_browser/file_watcher_test/test.js
@@ -235,7 +235,7 @@ var sortedVolumeMetadataList = volumeMetadataList.filter(function(volume) { return possibleVolumeTypes.indexOf(volume.volumeType) != -1; }).sort(function(volumeA, volumeB) { - return possibleVolumeTypes.indexOf(volumeA.volumeType) > + return possibleVolumeTypes.indexOf(volumeA.volumeType) - possibleVolumeTypes.indexOf(volumeB.volumeType); });
diff --git a/chrome/test/data/extensions/api_test/file_browser/filesystem_operations_test/test.js b/chrome/test/data/extensions/api_test/file_browser/filesystem_operations_test/test.js index e6ed5696..fc332bad 100644 --- a/chrome/test/data/extensions/api_test/file_browser/filesystem_operations_test/test.js +++ b/chrome/test/data/extensions/api_test/file_browser/filesystem_operations_test/test.js
@@ -490,7 +490,7 @@ var sortedVolumeMetadataList = volumeMetadataList.filter(function(volume) { return possibleVolumeTypes.indexOf(volume.volumeType) != -1; }).sort(function(volumeA, volumeB) { - return possibleVolumeTypes.indexOf(volumeA.volumeType) > + return possibleVolumeTypes.indexOf(volumeA.volumeType) - possibleVolumeTypes.indexOf(volumeB.volumeType); });
diff --git a/chrome/test/data/extensions/api_test/file_browser/handler_test_runner/test.js b/chrome/test/data/extensions/api_test/file_browser/handler_test_runner/test.js index 514aeff..c32ebe5 100644 --- a/chrome/test/data/extensions/api_test/file_browser/handler_test_runner/test.js +++ b/chrome/test/data/extensions/api_test/file_browser/handler_test_runner/test.js
@@ -194,7 +194,7 @@ var sortedVolumeMetadataList = volumeMetadataList.filter(function(volume) { return possibleVolumeTypes.indexOf(volume.volumeType) != -1; }).sort(function(volumeA, volumeB) { - return possibleVolumeTypes.indexOf(volumeA.volumeType) > + return possibleVolumeTypes.indexOf(volumeA.volumeType) - possibleVolumeTypes.indexOf(volumeB.volumeType); }); if (sortedVolumeMetadataList.length == 0) {
diff --git a/chrome/test/data/extensions/api_test/file_browser/mount_test/test.js b/chrome/test/data/extensions/api_test/file_browser/mount_test/test.js index 36d9b45..4718974 100644 --- a/chrome/test/data/extensions/api_test/file_browser/mount_test/test.js +++ b/chrome/test/data/extensions/api_test/file_browser/mount_test/test.js
@@ -179,6 +179,14 @@ chrome.test.runTests([ function removeMount() { + chrome.fileManagerPrivate.removeMount('removable:mount_path1'); + + // We actually check this one on C++ side. If MountLibrary.RemoveMount + // doesn't get called, test will fail. + chrome.test.succeed(); + }, + + function removeMountArchive() { chrome.fileManagerPrivate.removeMount('archive:archive_mount_path'); // We actually check this one on C++ side. If MountLibrary.RemoveMount
diff --git a/chrome/test/data/extensions/platform_apps/touchpad_pinch/background.js b/chrome/test/data/extensions/platform_apps/touchpad_pinch/background.js new file mode 100644 index 0000000..3c9f502 --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/touchpad_pinch/background.js
@@ -0,0 +1,7 @@ +// Copyright 2018 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. + +chrome.app.runtime.onLaunched.addListener(function() { + chrome.app.window.create('window.html'); +});
diff --git a/chrome/test/data/extensions/platform_apps/touchpad_pinch/manifest.json b/chrome/test/data/extensions/platform_apps/touchpad_pinch/manifest.json new file mode 100644 index 0000000..c47a5d4 --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/touchpad_pinch/manifest.json
@@ -0,0 +1,10 @@ +{ + "name": "Touchpad pinch synthetic wheel event", + "version": "1", + "manifest_version": 2, + "app": { + "background": { + "scripts": ["background.js"] + } + } +}
diff --git a/chrome/test/data/extensions/platform_apps/touchpad_pinch/window.html b/chrome/test/data/extensions/platform_apps/touchpad_pinch/window.html new file mode 100644 index 0000000..8047bf9 --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/touchpad_pinch/window.html
@@ -0,0 +1,18 @@ +<!-- + * Copyright (c) 2018 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. +--> +<html> +<head> + <style> + html,body { + height: 100%; + } + </style> +</head> +<body> + <p>Hello.</p> + <script src="window.js"></script> +</body> +</html>
diff --git a/chrome/test/data/extensions/platform_apps/touchpad_pinch/window.js b/chrome/test/data/extensions/platform_apps/touchpad_pinch/window.js new file mode 100644 index 0000000..f260647 --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/touchpad_pinch/window.js
@@ -0,0 +1,10 @@ +// Copyright 2018 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. + +window.onload = () => { + document.body.addEventListener('wheel', (e) => { + chrome.test.sendMessage('Seen wheel event'); + }); + chrome.test.sendMessage('Launched'); +};
diff --git a/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/embedder.html b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/embedder.html new file mode 100644 index 0000000..72a7e7af --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/embedder.html
@@ -0,0 +1,10 @@ +<!-- + * Copyright (c) 2018 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. +--> +<html> +<body> +<script src="embedder.js"></script> +</body> +</html>
diff --git a/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/embedder.js b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/embedder.js new file mode 100644 index 0000000..7fc9d1a --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/embedder.js
@@ -0,0 +1,20 @@ +// Copyright 2018 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. + +window.onload = () => { + chrome.test.getConfig(function(config) { + var guestURL = 'http://localhost:' + config.testServer.port + + '/extensions/platform_apps/web_view/touchpad_pinch/guest.html'; + var webview = document.createElement('webview'); + webview.src = guestURL; + webview.addEventListener('loadstop', () => { + webview.contentWindow.postMessage({}, '*'); + }); + document.body.appendChild(webview); + }); +}; + +window.addEventListener('message', (e) => { + chrome.test.sendMessage(e.data); +});
diff --git a/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/guest.html b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/guest.html new file mode 100644 index 0000000..d2ae6764 --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/guest.html
@@ -0,0 +1,18 @@ +<!-- + * Copyright (c) 2018 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. +--> +<html> +<head> + <style> + html,body { + height: 100%; + } + </style> +</head> +<body> + <p>Hello.</p> + <script src="guest.js"></script> +</body> +</html>
diff --git a/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/guest.js b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/guest.js new file mode 100644 index 0000000..bca3c5a4 --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/guest.js
@@ -0,0 +1,16 @@ +// Copyright 2018 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. + +var parentWindow = null; + +window.onload = () => { + document.body.addEventListener('wheel', (e) => { + parentWindow.postMessage('Seen wheel event', '*'); + }); +}; + +window.addEventListener('message', (e) => { + parentWindow = e.source; + parentWindow.postMessage('WebViewTest.LAUNCHED', '*'); +});
diff --git a/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/manifest.json b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/manifest.json new file mode 100644 index 0000000..b58b16f --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/manifest.json
@@ -0,0 +1,13 @@ +{ + "name": "<webview> Touchpad pinch synthetic wheel event", + "version": "1", + "manifest_version": 2, + "permissions": [ + "webview" + ], + "app": { + "background": { + "scripts": ["test.js"] + } + } +}
diff --git a/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/test.js b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/test.js new file mode 100644 index 0000000..1bb2b22 --- /dev/null +++ b/chrome/test/data/extensions/platform_apps/web_view/touchpad_pinch/test.js
@@ -0,0 +1,7 @@ +// Copyright 2018 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. + +chrome.app.runtime.onLaunched.addListener(function() { + chrome.app.window.create('embedder.html'); +});
diff --git a/chrome/test/data/policy/policy_test_cases.json b/chrome/test/data/policy/policy_test_cases.json index 38d0d57..c0618e4 100644 --- a/chrome/test/data/policy/policy_test_cases.json +++ b/chrome/test/data/policy/policy_test_cases.json
@@ -3861,6 +3861,22 @@ "note": "Chrome OS device policy used by update_engine only, not used in Chrome." }, + "WebAppInstallForceList": { + "os": ["win", "linux", "mac", "chromeos"], + "test_policy": { + "WebAppInstallForceList": [{ + "url": "https://www.google.com", + "launch_container": "tab" + }, { + "url": "https://docs.google.com", + "launch_container": "window" + }] + }, + "pref_mappings": [ + { "pref": "profile.web_app.install.forcelist" } + ] + }, + "----- Chrome Frame policies -------------------------------------------": {}, "ChromeFrameRendererSettings": {
diff --git a/chrome/test/data/webui/settings/certificate_manager_test.js b/chrome/test/data/webui/settings/certificate_manager_test.js index 051d38f..d61fefb 100644 --- a/chrome/test/data/webui/settings/certificate_manager_test.js +++ b/chrome/test/data/webui/settings/certificate_manager_test.js
@@ -143,11 +143,12 @@ } } - /** @return {!Certificate} */ - function createSampleCertificate() { + /** @return {!CertificatesOrgGroup} */ + function createSampleCertificateOrgGroup() { return { id: 'dummyCertificateId', name: 'dummyCertificateName', + containsPolicyCerts: false, subnodes: [createSampleCertificateSubnode()], }; } @@ -682,10 +683,10 @@ // Simulate response for personal and CA certificates. cr.webUIListenerCallback( 'certificates-changed', 'personalCerts', - [createSampleCertificate()]); - cr.webUIListenerCallback( - 'certificates-changed', 'caCerts', - [createSampleCertificate(), createSampleCertificate()]); + [createSampleCertificateOrgGroup()]); + cr.webUIListenerCallback('certificates-changed', 'caCerts', [ + createSampleCertificateOrgGroup(), createSampleCertificateOrgGroup() + ]); Polymer.dom.flush(); assertCertificateListLength(CertificateCategoryIndex.PERSONAL, 1);
diff --git a/chromeos/CHROMEOS_LKGM b/chromeos/CHROMEOS_LKGM index 4f18189a..ec28eaf 100644 --- a/chromeos/CHROMEOS_LKGM +++ b/chromeos/CHROMEOS_LKGM
@@ -1 +1 @@ -10974.0.0 \ No newline at end of file +10993.0.0 \ No newline at end of file
diff --git a/chromeos/account_manager/account_manager.h b/chromeos/account_manager/account_manager.h index 61e69e9..af6838f 100644 --- a/chromeos/account_manager/account_manager.h +++ b/chromeos/account_manager/account_manager.h
@@ -102,7 +102,12 @@ scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, DelayNetworkCallRunner delay_network_call_runner); - // Gets (async) a list of account keys known to |AccountManager|. + // Gets (async) a list of account keys known to |AccountManager|. Note that + // |callback| will be immediately called in the same thread if + // |AccountManager| has been fully initialized and hence it may not be safe to + // call this method directly in some class's constructor, with a callback on + // the same class, since it may result in a method call on a partially + // constructed object. void GetAccounts(AccountListCallback callback); // Removes an account. Does not do anything if |account_key| is not known by
diff --git a/components/BUILD.gn b/components/BUILD.gn index 8aa2cb1..31806d7 100644 --- a/components/BUILD.gn +++ b/components/BUILD.gn
@@ -272,6 +272,7 @@ if (is_android) { deps += [ "//base:base_java_unittest_support", + "//components/autofill_assistant/browser:unit_tests", "//components/cdm/browser:unit_tests", "//components/gcm_driver/instance_id:test_support", "//components/gcm_driver/instance_id/android:instance_id_driver_java",
diff --git a/components/arc/common/auth.mojom b/components/arc/common/auth.mojom index 4498975..9b64261 100644 --- a/components/arc/common/auth.mojom +++ b/components/arc/common/auth.mojom
@@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -// Next MinVersion: 15 +// Next MinVersion: 17 module arc.mojom; @@ -170,6 +170,7 @@ }; // The necessary information for Android to sign in and provision itself. +// Next ordinal value: 6. struct AccountInfo { // Name of account, used to map to existing Android account. [MinVersion=9] string? account_name@4; @@ -189,6 +190,9 @@ // Whether the account is managed from Chrome OS. bool is_managed@2; + + // Whether this account is a Chrome OS Secondary Account. + [MinVersion=16] bool is_secondary_account@5; }; // Next Method ID: 12. @@ -209,7 +213,11 @@ // Asynchronously requests an authorization code, as well as the account // information. If |initial_signin| is true then that means request is for // initial signin flow. Otherwise it is used for reauthorization flow. - [MinVersion=5] RequestAccountInfo@7([MinVersion=11] bool initial_signin); + // Optionally, an |account_name| can be provided to fetch |AccountInfo| for + // Secondary Accounts in Chrome OS Account Manager. Absence of |account_name| + // will default to the Device Account in Chrome OS. + [MinVersion=5] RequestAccountInfo@7([MinVersion=11] bool initial_signin, + [MinVersion=16] string? account_name); // Reports metrics to Chrome to be recorded in UMA. [MinVersion=7] ReportMetrics@8(MetricsType metrics_type, int32 value); @@ -225,7 +233,7 @@ SupervisionChangeStatus status); }; -// Next Method ID: 3 +// Next Method ID: 5 interface AuthInstance { // DEPRECATED: Please use Init@2 instead. InitDeprecated@0(AuthHost host_ptr); @@ -243,4 +251,13 @@ [MinVersion=5] OnAccountInfoReady@1( AccountInfo? account_info, [MinVersion=10] ArcSignInStatus status); + // A notification that a Secondary Account has been updated or inserted in + // Chrome OS Account Manager. This API is guaranteed to be idempotent. + // Note: This notification is guaranteed to be called at least once for every + // Secondary Account in Chrome OS Account Manager at startup. + [MinVersion=15] OnSecondaryAccountUpserted@3(string account_name); + + // A notification that a Secondary Account has been removed from Chrome OS + // Account Manager. This API is guaranteed to be idempotent. + [MinVersion=15] OnSecondaryAccountRemoved@4(string account_name); };
diff --git a/components/autofill/core/browser/autofill_metrics_unittest.cc b/components/autofill/core/browser/autofill_metrics_unittest.cc index dc9b8a7..bd323689 100644 --- a/components/autofill/core/browser/autofill_metrics_unittest.cc +++ b/components/autofill/core/browser/autofill_metrics_unittest.cc
@@ -7402,7 +7402,13 @@ } // Test the ukm recorded when Suggestion is shown. -TEST_F(AutofillMetricsTest, AutofillSuggestionShownTest) { +// Flaky on Win. http://crbug.com/876954 +#if defined(OS_WIN) +#define MAYBE_AutofillSuggestionShownTest DISABLED_AutofillSuggestionShownTest +#else +#define MAYBE_AutofillSuggestionShownTest AutofillSuggestionShownTest +#endif +TEST_F(AutofillMetricsTest, MAYBE_AutofillSuggestionShownTest) { RecreateCreditCards(true /* include_local_credit_card */, false /* include_masked_server_credit_card */, false /* include_full_server_credit_card */);
diff --git a/components/autofill_assistant/browser/BUILD.gn b/components/autofill_assistant/browser/BUILD.gn index 6715198..e2280796 100644 --- a/components/autofill_assistant/browser/BUILD.gn +++ b/components/autofill_assistant/browser/BUILD.gn
@@ -13,6 +13,7 @@ jumbo_static_library("browser") { sources = [ + "actions/assistant_action.cc", "actions/assistant_action.h", "actions/assistant_action_delegate.h", "actions/assistant_click_action.cc", @@ -53,3 +54,26 @@ "//net", ] } + +source_set("unit_tests") { + testonly = true + sources = [ + "assistant_script_executor_unittest.cc", + "mock_assistant_service.cc", + "mock_assistant_service.h", + "mock_assistant_ui_controller.cc", + "mock_assistant_ui_controller.h", + "mock_assistant_web_controller.cc", + "mock_assistant_web_controller.h", + "mock_run_once_callback.h", + ] + + deps = [ + ":browser", + ":proto", + "//base", + "//base/test:test_support", + "//testing/gmock", + "//testing/gtest", + ] +}
diff --git a/components/autofill_assistant/browser/actions/assistant_action.cc b/components/autofill_assistant/browser/actions/assistant_action.cc new file mode 100644 index 0000000..6ceb7634 --- /dev/null +++ b/components/autofill_assistant/browser/actions/assistant_action.cc
@@ -0,0 +1,12 @@ +// Copyright 2018 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 "components/autofill_assistant/browser/actions/assistant_action.h" + +namespace autofill_assistant { + +AssistantAction::AssistantAction(const AssistantActionProto& proto) + : proto_(proto) {} + +} // namespace autofill_assistant.
diff --git a/components/autofill_assistant/browser/actions/assistant_action.h b/components/autofill_assistant/browser/actions/assistant_action.h index 599da96..cff7420 100644 --- a/components/autofill_assistant/browser/actions/assistant_action.h +++ b/components/autofill_assistant/browser/actions/assistant_action.h
@@ -5,7 +5,8 @@ #ifndef COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_ACTION_H_ #define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_ACTION_H_ -#include "base/callback.h" +#include "base/callback_forward.h" +#include "components/autofill_assistant/browser/assistant.pb.h" namespace autofill_assistant { @@ -22,8 +23,12 @@ virtual void ProcessAction(AssistantActionDelegate* delegate, ProcessActionCallback callback) = 0; + const AssistantActionProto& proto() const { return proto_; } + protected: - AssistantAction() = default; + explicit AssistantAction(const AssistantActionProto& proto); + + const AssistantActionProto proto_; }; } // namespace autofill_assistant.
diff --git a/components/autofill_assistant/browser/actions/assistant_action_delegate.h b/components/autofill_assistant/browser/actions/assistant_action_delegate.h index cc7307d..fe92128 100644 --- a/components/autofill_assistant/browser/actions/assistant_action_delegate.h +++ b/components/autofill_assistant/browser/actions/assistant_action_delegate.h
@@ -27,6 +27,30 @@ virtual void ElementExists(const std::vector<std::string>& selectors, base::OnceCallback<void(bool)> callback) = 0; + // Ask user to choose an address in personal data manager. GUID of the chosen + // address will be returned through callback if succeed, otherwise empty + // string is returned. + virtual void ChooseAddress( + base::OnceCallback<void(const std::string&)> callback) = 0; + + // Fill the address form given by |selectors| with the given address |guid| in + // personal data manager. + virtual void FillAddressForm(const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) = 0; + + // Ask user to choose a card in personal data manager. GUID of the chosen card + // will be returned through callback if succeed, otherwise empty string is + // returned. + virtual void ChooseCard( + base::OnceCallback<void(const std::string&)> callback) = 0; + + // Fill the card form given by |selectors| with the given card |guid| in + // personal data manager. + virtual void FillCardForm(const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) = 0; + protected: AssistantActionDelegate() = default; };
diff --git a/components/autofill_assistant/browser/actions/assistant_click_action.cc b/components/autofill_assistant/browser/actions/assistant_click_action.cc index f79dca3..4b2dc72e 100644 --- a/components/autofill_assistant/browser/actions/assistant_click_action.cc +++ b/components/autofill_assistant/browser/actions/assistant_click_action.cc
@@ -4,19 +4,28 @@ #include "components/autofill_assistant/browser/actions/assistant_click_action.h" +#include <utility> + +#include "base/callback.h" #include "components/autofill_assistant/browser/actions/assistant_action_delegate.h" namespace autofill_assistant { -AssistantClickAction::AssistantClickAction( - const std::vector<std::string>& selectors) - : target_element_selectors_(selectors) {} +AssistantClickAction::AssistantClickAction(const AssistantActionProto& proto) + : AssistantAction(proto) { + DCHECK(proto_.has_click()); +} AssistantClickAction::~AssistantClickAction() {} void AssistantClickAction::ProcessAction(AssistantActionDelegate* delegate, ProcessActionCallback callback) { - delegate->ClickElement(target_element_selectors_, std::move(callback)); + std::vector<std::string> selectors; + for (const auto& selector : proto_.click().element_to_click().selectors()) { + selectors.emplace_back(selector); + } + DCHECK(!selectors.empty()); + delegate->ClickElement(selectors, std::move(callback)); } -} // namespace autofill_assistant. \ No newline at end of file +} // namespace autofill_assistant.
diff --git a/components/autofill_assistant/browser/actions/assistant_click_action.h b/components/autofill_assistant/browser/actions/assistant_click_action.h index 663a10a..c817e0d 100644 --- a/components/autofill_assistant/browser/actions/assistant_click_action.h +++ b/components/autofill_assistant/browser/actions/assistant_click_action.h
@@ -16,9 +16,7 @@ // An action to perform a mouse left button click on a given element on Web. class AssistantClickAction : public AssistantAction { public: - // CSS selectors in |selectors| are ordered from top frame to the frame - // contains the element and the element. - explicit AssistantClickAction(const std::vector<std::string>& selectors); + explicit AssistantClickAction(const AssistantActionProto& proto); ~AssistantClickAction() override; // Overrides AssistantAction: @@ -32,4 +30,4 @@ }; } // namespace autofill_assistant. -#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_CLICK_ACTION_H_ \ No newline at end of file +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_CLICK_ACTION_H_
diff --git a/components/autofill_assistant/browser/actions/assistant_tell_action.cc b/components/autofill_assistant/browser/actions/assistant_tell_action.cc index ab54192..943e8b6d 100644 --- a/components/autofill_assistant/browser/actions/assistant_tell_action.cc +++ b/components/autofill_assistant/browser/actions/assistant_tell_action.cc
@@ -4,19 +4,25 @@ #include "components/autofill_assistant/browser/actions/assistant_tell_action.h" +#include <utility> + +#include "base/callback.h" #include "components/autofill_assistant/browser/actions/assistant_action_delegate.h" namespace autofill_assistant { -AssistantTellAction::AssistantTellAction(const std::string& message) - : message_(message) {} +AssistantTellAction::AssistantTellAction(const AssistantActionProto& proto) + : AssistantAction(proto) { + DCHECK(proto_.has_tell()); +} AssistantTellAction::~AssistantTellAction() {} void AssistantTellAction::ProcessAction(AssistantActionDelegate* delegate, ProcessActionCallback callback) { - delegate->ShowStatusMessage(message_); + // tell.message in the proto is localized. + delegate->ShowStatusMessage(proto_.tell().message()); std::move(callback).Run(true); } -} // namespace autofill_assistant. \ No newline at end of file +} // namespace autofill_assistant.
diff --git a/components/autofill_assistant/browser/actions/assistant_tell_action.h b/components/autofill_assistant/browser/actions/assistant_tell_action.h index 3bcf2ff..e4855121 100644 --- a/components/autofill_assistant/browser/actions/assistant_tell_action.h +++ b/components/autofill_assistant/browser/actions/assistant_tell_action.h
@@ -5,18 +5,16 @@ #ifndef COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_TELL_ACTION_H_ #define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_TELL_ACTION_H_ -#include "components/autofill_assistant/browser/actions/assistant_action.h" - #include <string> #include "base/macros.h" +#include "components/autofill_assistant/browser/actions/assistant_action.h" namespace autofill_assistant { // An action to display a message. class AssistantTellAction : public AssistantAction { public: - // The |message| is a localized text message from the server to show user. - explicit AssistantTellAction(const std::string& message); + explicit AssistantTellAction(const AssistantActionProto& proto); ~AssistantTellAction() override; // Overrides AssistantAction: @@ -24,10 +22,8 @@ ProcessActionCallback callback) override; private: - std::string message_; - DISALLOW_COPY_AND_ASSIGN(AssistantTellAction); }; } // namespace autofill_assistant. -#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_TELL_ACTION_H_ \ No newline at end of file +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_TELL_ACTION_H_
diff --git a/components/autofill_assistant/browser/actions/assistant_use_address_action.cc b/components/autofill_assistant/browser/actions/assistant_use_address_action.cc index 25b5f5d..d8a305a 100644 --- a/components/autofill_assistant/browser/actions/assistant_use_address_action.cc +++ b/components/autofill_assistant/browser/actions/assistant_use_address_action.cc
@@ -4,20 +4,57 @@ #include "components/autofill_assistant/browser/actions/assistant_use_address_action.h" +#include <vector> + +#include "base/bind.h" +#include "base/callback.h" #include "components/autofill_assistant/browser/actions/assistant_action_delegate.h" namespace autofill_assistant { AssistantUseAddressAction::AssistantUseAddressAction( - const std::string& usage_message, - const std::vector<std::string>& selectors) - : usage_message_(usage_message), target_element_selectors_(selectors) {} + const AssistantActionProto& proto) + : AssistantAction(proto), weak_ptr_factory_(this) {} AssistantUseAddressAction::~AssistantUseAddressAction() {} void AssistantUseAddressAction::ProcessAction(AssistantActionDelegate* delegate, ProcessActionCallback callback) { - NOTIMPLEMENTED(); + if (proto_.use_address().has_usage()) { + delegate->ShowStatusMessage(proto_.use_address().usage()); + } + + delegate->ChooseAddress(base::BindOnce( + &AssistantUseAddressAction::OnChooseAddress, + weak_ptr_factory_.GetWeakPtr(), delegate, std::move(callback))); +} + +void AssistantUseAddressAction::OnChooseAddress( + AssistantActionDelegate* delegate, + ProcessActionCallback callback, + const std::string& guid) { + if (guid.empty()) { + DVLOG(1) << "Failed to choose address."; + std::move(callback).Run(false); + return; + } + + std::vector<std::string> selectors; + for (const auto& selector : + proto_.use_address().form_field_element().selectors()) { + selectors.emplace_back(selector); + } + DCHECK(!selectors.empty()); + delegate->FillAddressForm( + guid, selectors, + base::BindOnce(&AssistantUseAddressAction::OnFillAddressForm, + weak_ptr_factory_.GetWeakPtr(), std::move(callback))); +} + +void AssistantUseAddressAction::OnFillAddressForm( + ProcessActionCallback callback, + bool result) { + std::move(callback).Run(result); } } // namespace autofill_assistant.
diff --git a/components/autofill_assistant/browser/actions/assistant_use_address_action.h b/components/autofill_assistant/browser/actions/assistant_use_address_action.h index 1d08034..24a132a 100644 --- a/components/autofill_assistant/browser/actions/assistant_use_address_action.h +++ b/components/autofill_assistant/browser/actions/assistant_use_address_action.h
@@ -5,22 +5,18 @@ #ifndef COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_USE_ADDRESS_ACTION_H_ #define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_USE_ADDRESS_ACTION_H_ -#include "components/autofill_assistant/browser/actions/assistant_action.h" - #include <string> -#include <vector> #include "base/macros.h" +#include "base/memory/weak_ptr.h" +#include "components/autofill_assistant/browser/actions/assistant_action.h" namespace autofill_assistant { // An action to ask user to choose a local address to fill the form. class AssistantUseAddressAction : public AssistantAction { public: - // The |usage_message| indicates the usage of the address, like billing - // address or shipping address. The |selectors| specifies an element in the - // form to be filled. - AssistantUseAddressAction(const std::string& usage_message, - const std::vector<std::string>& selectors); + explicit AssistantUseAddressAction(const AssistantActionProto& proto); + ~AssistantUseAddressAction() override; // Overrides AssistantAction: @@ -28,8 +24,12 @@ ProcessActionCallback callback) override; private: - std::string usage_message_; - std::vector<std::string> target_element_selectors_; + void OnChooseAddress(AssistantActionDelegate* delegate, + ProcessActionCallback callback, + const std::string& guid); + void OnFillAddressForm(ProcessActionCallback callback, bool result); + + base::WeakPtrFactory<AssistantUseAddressAction> weak_ptr_factory_; DISALLOW_COPY_AND_ASSIGN(AssistantUseAddressAction); };
diff --git a/components/autofill_assistant/browser/actions/assistant_use_card_action.cc b/components/autofill_assistant/browser/actions/assistant_use_card_action.cc index d4952ac..f394ae4 100644 --- a/components/autofill_assistant/browser/actions/assistant_use_card_action.cc +++ b/components/autofill_assistant/browser/actions/assistant_use_card_action.cc
@@ -4,19 +4,51 @@ #include "components/autofill_assistant/browser/actions/assistant_use_card_action.h" +#include <vector> + +#include "base/bind.h" +#include "base/callback.h" #include "components/autofill_assistant/browser/actions/assistant_action_delegate.h" namespace autofill_assistant { AssistantUseCardAction::AssistantUseCardAction( - const std::vector<std::string>& selectors) - : target_element_selectors_(selectors) {} + const AssistantActionProto& proto) + : AssistantAction(proto), weak_ptr_factory_(this) {} AssistantUseCardAction::~AssistantUseCardAction() {} void AssistantUseCardAction::ProcessAction(AssistantActionDelegate* delegate, ProcessActionCallback callback) { - NOTIMPLEMENTED(); + delegate->ChooseCard(base::BindOnce(&AssistantUseCardAction::OnChooseCard, + weak_ptr_factory_.GetWeakPtr(), delegate, + std::move(callback))); +} + +void AssistantUseCardAction::OnChooseCard(AssistantActionDelegate* delegate, + ProcessActionCallback callback, + const std::string& guid) { + if (guid.empty()) { + DVLOG(1) << "Failed to choose card."; + std::move(callback).Run(false); + return; + } + + std::vector<std::string> selectors; + for (const auto& selector : + proto_.use_card().form_field_element().selectors()) { + selectors.emplace_back(selector); + } + DCHECK(!selectors.empty()); + delegate->FillCardForm( + guid, selectors, + base::BindOnce(&AssistantUseCardAction::OnFillCardForm, + weak_ptr_factory_.GetWeakPtr(), std::move(callback))); +} + +void AssistantUseCardAction::OnFillCardForm(ProcessActionCallback callback, + bool result) { + std::move(callback).Run(result); } } // namespace autofill_assistant.
diff --git a/components/autofill_assistant/browser/actions/assistant_use_card_action.h b/components/autofill_assistant/browser/actions/assistant_use_card_action.h index b16ea6e..967f9524 100644 --- a/components/autofill_assistant/browser/actions/assistant_use_card_action.h +++ b/components/autofill_assistant/browser/actions/assistant_use_card_action.h
@@ -5,19 +5,18 @@ #ifndef COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_USE_CARD_ACTION_H_ #define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_USE_CARD_ACTION_H_ -#include "components/autofill_assistant/browser/actions/assistant_action.h" - #include <string> #include <vector> #include "base/macros.h" +#include "base/memory/weak_ptr.h" +#include "components/autofill_assistant/browser/actions/assistant_action.h" namespace autofill_assistant { // An action to ask user to choose a local card to fill the form. class AssistantUseCardAction : public AssistantAction { public: - // The |selectors| specifies the card number field in the form to be filled. - explicit AssistantUseCardAction(const std::vector<std::string>& selectors); + explicit AssistantUseCardAction(const AssistantActionProto& proto); ~AssistantUseCardAction() override; // Overrides AssistantAction: @@ -25,7 +24,12 @@ ProcessActionCallback callback) override; private: - std::vector<std::string> target_element_selectors_; + void OnChooseCard(AssistantActionDelegate* delegate, + ProcessActionCallback callback, + const std::string& guid); + void OnFillCardForm(ProcessActionCallback callback, bool result); + + base::WeakPtrFactory<AssistantUseCardAction> weak_ptr_factory_; DISALLOW_COPY_AND_ASSIGN(AssistantUseCardAction); };
diff --git a/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.cc b/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.cc index 008ef98..4916f0d 100644 --- a/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.cc +++ b/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.cc
@@ -22,21 +22,18 @@ namespace autofill_assistant { AssistantWaitForDomAction::AssistantWaitForDomAction( - int timeout_ms, - const std::vector<std::string>& selectors, - bool for_absence) - : timeout_ms_(timeout_ms), - target_element_selectors_(selectors), - for_absence_(for_absence), - weak_ptr_factory_(this) {} + const AssistantActionProto& proto) + : AssistantAction(proto), weak_ptr_factory_(this) {} AssistantWaitForDomAction::~AssistantWaitForDomAction() {} void AssistantWaitForDomAction::ProcessAction(AssistantActionDelegate* delegate, ProcessActionCallback callback) { int check_rounds = kDefaultCheckRounds; - if (timeout_ms_ > 0) - check_rounds = std::ceil(timeout_ms_ / kCheckPeriodInMilliseconds); + + int timeout_ms = proto_.wait_for_dom().timeout_ms(); + if (timeout_ms > 0) + check_rounds = std::ceil(timeout_ms / kCheckPeriodInMilliseconds); CheckElementExists(delegate, check_rounds, std::move(callback)); } @@ -46,9 +43,12 @@ int rounds, ProcessActionCallback callback) { DCHECK(rounds > 0); - + std::vector<std::string> selectors; + for (const auto& selector : proto_.wait_for_dom().element().selectors()) { + selectors.emplace_back(selector); + } delegate->ElementExists( - target_element_selectors_, + selectors, base::BindOnce(&AssistantWaitForDomAction::OnCheckElementExists, weak_ptr_factory_.GetWeakPtr(), delegate, rounds, std::move(callback))); @@ -59,12 +59,13 @@ int rounds, ProcessActionCallback callback, bool result) { - if (for_absence_ && !result) { + bool for_absence = proto_.wait_for_dom().check_for_absence(); + if (for_absence && !result) { std::move(callback).Run(true); return; } - if (!for_absence_ && result) { + if (!for_absence && result) { std::move(callback).Run(true); return; }
diff --git a/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.h b/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.h index 9501839..5cfe49f 100644 --- a/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.h +++ b/components/autofill_assistant/browser/actions/assistant_wait_for_dom_action.h
@@ -5,25 +5,19 @@ #ifndef COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_WAIT_FOR_DOM_ACTION_H_ #define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_WAIT_FOR_DOM_ACTION_H_ -#include "components/autofill_assistant/browser/actions/assistant_action.h" - #include <string> #include <vector> -#include "base/callback_forward.h" #include "base/macros.h" #include "base/memory/weak_ptr.h" +#include "components/autofill_assistant/browser/actions/assistant_action.h" +#include "components/autofill_assistant/browser/assistant.pb.h" namespace autofill_assistant { // An action to ask Chrome to wait for a DOM element to process next action. class AssistantWaitForDomAction : public AssistantAction { public: - // |timeout_ms| indicates waiting timeout period. |selectors| specifies the - // DOM element to wait. |for_absence| indicates whether waiting for absence of - // the element. - AssistantWaitForDomAction(int timeout_ms, - const std::vector<std::string>& selectors, - bool for_absence); + explicit AssistantWaitForDomAction(const AssistantActionProto& proto); ~AssistantWaitForDomAction() override; // Overrides AssistantAction: @@ -39,13 +33,9 @@ ProcessActionCallback callback, bool result); - int timeout_ms_; - std::vector<std::string> target_element_selectors_; - bool for_absence_; - base::WeakPtrFactory<AssistantWaitForDomAction> weak_ptr_factory_; DISALLOW_COPY_AND_ASSIGN(AssistantWaitForDomAction); }; } // namespace autofill_assistant. -#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_WAIT_FOR_DOM_ACTION_H_ \ No newline at end of file +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ACTIONS_ASSISTANT_WAIT_FOR_DOM_ACTION_H_
diff --git a/components/autofill_assistant/browser/assistant.proto b/components/autofill_assistant/browser/assistant.proto index db48c24..fcd9ffd 100644 --- a/components/autofill_assistant/browser/assistant.proto +++ b/components/autofill_assistant/browser/assistant.proto
@@ -55,6 +55,18 @@ TRACE = 4; } +message ScriptActionRequestProto { + optional ClientContextProto client_context = 7; + + // The server payload received from the previous response. + optional bytes server_payload = 1; + + oneof request { + InitialScriptActionsRequestProto initial_request = 4; + NextScriptActionsRequestProto next_request = 5; + } +} + // Initial request to get a script's actions. message InitialScriptActionsRequestProto { message QueryProto { @@ -66,8 +78,10 @@ // Next request to get a script's actions. message NextScriptActionsRequestProto { - // The server payload received from the previous response. - required bytes server_payload = 1; + // The result of processing each AssistantActionProto from the previous + // response. This field must be in the same order as the actions in the + // original response. It may have less actions in case of failure. + repeated ProcessedAssistantActionProto processed_actions = 1; } // Response of a script's actions. @@ -83,16 +97,33 @@ // An assistant action could be performed. message AssistantActionProto { - // Next action id: 3. + // Opaque data that should not be interpreted by the client. The client must + // pass this back unchanged in the next request + optional bytes server_payload = 4; + oneof action_info { - ClickProto click = 1; - TellProto tell = 2; - UseAddressProto use_address = 3; - UseCreditCardProto use_card = 4; - WaitForDomProto wait_for_dom = 5; + ClickProto click = 5; + TellProto tell = 11; + WaitForDomProto wait_for_dom = 19; + UseCreditCardProto use_card = 28; + UseAddressProto use_address = 29; } } +message ProcessedAssistantActionProto { + // The action that was processed. + optional AssistantActionProto action = 1; + + optional ProcessedAssistantActionStatus status = 2; +} + +enum ProcessedAssistantActionStatus { + UNKNOWN_ACTION_STATUS = 0; + ELEMENT_RESOLUTION_FAILED = 1; + ACTION_APPLIED = 2; + OTHER_ACTION_STATUS = 3; +} + // A reference to an unique element on the page, possibly nested in frames. message ElementReferenceProto { // A sequence of CSS selectors. Any non-final CSS selector is expected to @@ -108,7 +139,7 @@ required ElementReferenceProto element_to_click = 1; } -// Contain a message to tell the user. +// Contain a localized text message from the server to show to the user. message TellProto { required string message = 1; } @@ -130,7 +161,7 @@ // this action. message UseCreditCardProto { // A reference to the card number field in the form that should be filled. - optional ElementReferenceProto form_field_element = 1; + required ElementReferenceProto form_field_element = 1; } // Ask Chrome to wait for an element in the DOM. This can be used to only
diff --git a/components/autofill_assistant/browser/assistant_protocol_utils.cc b/components/autofill_assistant/browser/assistant_protocol_utils.cc index 90304f7..78dcfd7 100644 --- a/components/autofill_assistant/browser/assistant_protocol_utils.cc +++ b/components/autofill_assistant/browser/assistant_protocol_utils.cc
@@ -4,6 +4,8 @@ #include "components/autofill_assistant/browser/assistant_protocol_utils.h" +#include <utility> + #include "base/logging.h" #include "components/autofill_assistant/browser/actions/assistant_click_action.h" #include "components/autofill_assistant/browser/actions/assistant_tell_action.h" @@ -80,26 +82,30 @@ // static std::string AssistantProtocolUtils::CreateInitialScriptActionsRequest( const std::string& script_path) { - InitialScriptActionsRequestProto::QueryProto query; - query.set_script_path(script_path); - query.set_policy(PolicyType::SCRIPT); - - InitialScriptActionsRequestProto initial_request_proto; - initial_request_proto.set_allocated_query(&query); + ScriptActionRequestProto request_proto; + InitialScriptActionsRequestProto::QueryProto* query = + request_proto.mutable_initial_request()->mutable_query(); + query->set_script_path(script_path); + query->set_policy(PolicyType::SCRIPT); std::string serialized_initial_request_proto; - bool success = initial_request_proto.SerializeToString( - &serialized_initial_request_proto); + bool success = + request_proto.SerializeToString(&serialized_initial_request_proto); DCHECK(success); return serialized_initial_request_proto; } // static std::string AssistantProtocolUtils::CreateNextScriptActionsRequest( - const std::string& previous_server_payload) { - NextScriptActionsRequestProto request_proto; + const std::string& previous_server_payload, + const std::vector<ProcessedAssistantActionProto>& processed_actions) { + ScriptActionRequestProto request_proto; request_proto.set_server_payload(previous_server_payload); - + NextScriptActionsRequestProto* next_request = + request_proto.mutable_next_request(); + for (const auto& processed_action : processed_actions) { + next_request->add_processed_actions()->MergeFrom(processed_action); + } std::string serialized_request_proto; bool success = request_proto.SerializeToString(&serialized_request_proto); DCHECK(success); @@ -110,8 +116,7 @@ bool AssistantProtocolUtils::ParseAssistantActions( const std::string& response, std::string* return_server_payload, - std::vector<std::unique_ptr<AssistantAction>>* assistant_actions) { - DCHECK(!response.empty()); + std::deque<std::unique_ptr<AssistantAction>>* assistant_actions) { DCHECK(assistant_actions); ActionsResponseProto response_proto; @@ -127,66 +132,28 @@ for (const auto& action : response_proto.actions()) { switch (action.action_info_case()) { case AssistantActionProto::ActionInfoCase::kClick: { - DCHECK(action.has_click()); - std::vector<std::string> selectors; - for (const auto& selector : - action.click().element_to_click().selectors()) { - selectors.emplace_back(selector); - } - DCHECK(!selectors.empty()); assistant_actions->emplace_back( - std::make_unique<AssistantClickAction>(selectors)); + std::make_unique<AssistantClickAction>(action)); break; } case AssistantActionProto::ActionInfoCase::kTell: { - DCHECK(action.has_tell()); assistant_actions->emplace_back( - std::make_unique<AssistantTellAction>(action.tell().message())); + std::make_unique<AssistantTellAction>(action)); break; } case AssistantActionProto::ActionInfoCase::kUseAddress: { - DCHECK(action.has_use_address()); - std::vector<std::string> selectors; - for (const auto& selector : - action.use_address().form_field_element().selectors()) { - selectors.emplace_back(selector); - } - DCHECK(!selectors.empty()); assistant_actions->emplace_back( - std::make_unique<AssistantUseAddressAction>( - action.use_address().has_usage() ? action.use_address().usage() - : "", - selectors)); + std::make_unique<AssistantUseAddressAction>(action)); break; } case AssistantActionProto::ActionInfoCase::kUseCard: { - DCHECK(action.has_use_card()); - std::vector<std::string> selectors; - for (const auto& selector : - action.use_card().form_field_element().selectors()) { - selectors.emplace_back(selector); - } - DCHECK(!selectors.empty()); assistant_actions->emplace_back( - std::make_unique<AssistantUseCardAction>(selectors)); + std::make_unique<AssistantUseCardAction>(action)); break; } case AssistantActionProto::ActionInfoCase::kWaitForDom: { - DCHECK(action.has_wait_for_dom()); - std::vector<std::string> selectors; - for (const auto& selector : - action.wait_for_dom().element().selectors()) { - selectors.emplace_back(selector); - } - DCHECK(!selectors.empty()); assistant_actions->emplace_back( - std::make_unique<AssistantWaitForDomAction>( - action.wait_for_dom().has_timeout_ms() - ? action.wait_for_dom().timeout_ms() - : 0, - selectors, - action.wait_for_dom().has_check_for_absence() && - action.wait_for_dom().check_for_absence())); + std::make_unique<AssistantUseCardAction>(action)); break; } case AssistantActionProto::ActionInfoCase::ACTION_INFO_NOT_SET: {
diff --git a/components/autofill_assistant/browser/assistant_protocol_utils.h b/components/autofill_assistant/browser/assistant_protocol_utils.h index 0bd54ed..616ca18 100644 --- a/components/autofill_assistant/browser/assistant_protocol_utils.h +++ b/components/autofill_assistant/browser/assistant_protocol_utils.h
@@ -5,14 +5,16 @@ #ifndef COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ASSISTANT_PROTOCOL_UTILS_H_ #define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ASSISTANT_PROTOCOL_UTILS_H_ -#include "components/autofill_assistant/browser/actions/assistant_action.h" -#include "components/autofill_assistant/browser/assistant_script.h" - +#include <deque> #include <map> #include <memory> #include <string> #include <vector> +#include "components/autofill_assistant/browser/actions/assistant_action.h" +#include "components/autofill_assistant/browser/assistant.pb.h" +#include "components/autofill_assistant/browser/assistant_script.h" + class GURL; namespace autofill_assistant { @@ -40,7 +42,8 @@ // Create request to get next sequence of actions for a script. static std::string CreateNextScriptActionsRequest( - const std::string& previous_server_payload); + const std::string& previous_server_payload, + const std::vector<ProcessedAssistantActionProto>& processed_actions); // Parse assistant actions from the given |response|, which should not be an // empty string. @@ -51,7 +54,7 @@ static bool ParseAssistantActions( const std::string& response, std::string* return_server_payload, - std::vector<std::unique_ptr<AssistantAction>>* assistant_actions); + std::deque<std::unique_ptr<AssistantAction>>* assistant_actions); private: // To avoid instantiate this class by accident. @@ -60,4 +63,4 @@ }; } // namespace autofill_assistant -#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ASSISTANT_PROTOCOL_UTILS_H_ \ No newline at end of file +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ASSISTANT_PROTOCOL_UTILS_H_
diff --git a/components/autofill_assistant/browser/assistant_script_executor.cc b/components/autofill_assistant/browser/assistant_script_executor.cc index d3b6767..872ad55 100644 --- a/components/autofill_assistant/browser/assistant_script_executor.cc +++ b/components/autofill_assistant/browser/assistant_script_executor.cc
@@ -4,6 +4,9 @@ #include "components/autofill_assistant/browser/assistant_script_executor.h" +#include <string> +#include <utility> + #include "base/bind.h" #include "base/callback.h" #include "components/autofill_assistant/browser/assistant_protocol_utils.h" @@ -12,6 +15,7 @@ #include "components/autofill_assistant/browser/assistant_web_controller.h" namespace autofill_assistant { + AssistantScriptExecutor::AssistantScriptExecutor( AssistantScript* script, AssistantScriptExecutorDelegate* delegate) @@ -49,6 +53,32 @@ std::move(callback)); } +void AssistantScriptExecutor::ChooseAddress( + base::OnceCallback<void(const std::string&)> callback) { + delegate_->GetAssistantUiController()->ChooseAddress(std::move(callback)); +} + +void AssistantScriptExecutor::FillAddressForm( + const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) { + delegate_->GetAssistantWebController()->FillAddressForm(guid, selectors, + std::move(callback)); +} + +void AssistantScriptExecutor::ChooseCard( + base::OnceCallback<void(const std::string&)> callback) { + delegate_->GetAssistantUiController()->ChooseCard(std::move(callback)); +} + +void AssistantScriptExecutor::FillCardForm( + const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) { + delegate_->GetAssistantWebController()->FillCardForm(guid, selectors, + std::move(callback)); +} + void AssistantScriptExecutor::OnGetAssistantActions( bool result, const std::string& response) { @@ -56,8 +86,9 @@ std::move(callback_).Run(false); return; } + processed_actions_.clear(); + actions_.clear(); - DCHECK(!response.empty()); bool parse_result = AssistantProtocolUtils::ParseAssistantActions( response, &last_server_payload_, &actions_); if (!parse_result) { @@ -68,30 +99,48 @@ if (actions_.empty()) { // Finished executing the script if there are no more actions. std::move(callback_).Run(true); + return; } + ProcessNextAction(); } -void AssistantScriptExecutor::ProcessActions(size_t index) { - // Request next sequence of actions after process current sequence of actions. - if (index >= actions_.size()) { +void AssistantScriptExecutor::ProcessNextAction() { + if (actions_.empty()) { + // Request more actions to execute. GetNextAssistantActions(); return; } - actions_[index]->ProcessAction( + std::unique_ptr<AssistantAction> action = std::move(actions_.front()); + actions_.pop_front(); + AssistantAction* action_ptr = action.get(); + action_ptr->ProcessAction( this, base::BindOnce(&AssistantScriptExecutor::OnProcessedAction, - weak_ptr_factory_.GetWeakPtr(), index)); + weak_ptr_factory_.GetWeakPtr(), std::move(action))); } -void AssistantScriptExecutor::GetNextAssistantActions() {} +void AssistantScriptExecutor::GetNextAssistantActions() { + delegate_->GetAssistantService()->GetNextAssistantActions( + last_server_payload_, processed_actions_, + base::BindOnce(&AssistantScriptExecutor::OnGetAssistantActions, + weak_ptr_factory_.GetWeakPtr())); +} -void AssistantScriptExecutor::OnProcessedAction(size_t index, bool status) { - if (!status) { - std::move(callback_).Run(false); +void AssistantScriptExecutor::OnProcessedAction( + std::unique_ptr<AssistantAction> action, + bool success) { + processed_actions_.emplace_back(); + ProcessedAssistantActionProto* proto = &processed_actions_.back(); + proto->mutable_action()->MergeFrom(action->proto()); + proto->set_status(success + ? ProcessedAssistantActionStatus::ACTION_APPLIED + : ProcessedAssistantActionStatus::OTHER_ACTION_STATUS); + if (!success) { + // Report error immediately, interrupting action processing. + GetNextAssistantActions(); return; } - - ProcessActions(index++); + ProcessNextAction(); } } // namespace autofill_assistant
diff --git a/components/autofill_assistant/browser/assistant_script_executor.h b/components/autofill_assistant/browser/assistant_script_executor.h index 07cc415..8001a64 100644 --- a/components/autofill_assistant/browser/assistant_script_executor.h +++ b/components/autofill_assistant/browser/assistant_script_executor.h
@@ -5,10 +5,16 @@ #ifndef COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ASSISTANT_SCRIPT_EXECUTOR_H_ #define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_ASSISTANT_SCRIPT_EXECUTOR_H_ +#include <deque> +#include <memory> +#include <string> +#include <vector> + #include "base/callback_forward.h" #include "base/memory/weak_ptr.h" #include "components/autofill_assistant/browser/actions/assistant_action.h" #include "components/autofill_assistant/browser/actions/assistant_action_delegate.h" +#include "components/autofill_assistant/browser/assistant.pb.h" #include "components/autofill_assistant/browser/assistant_script.h" #include "components/autofill_assistant/browser/assistant_script_executor_delegate.h" @@ -31,18 +37,29 @@ base::OnceCallback<void(bool)> callback) override; void ElementExists(const std::vector<std::string>& selectors, base::OnceCallback<void(bool)> callback) override; + void ChooseAddress( + base::OnceCallback<void(const std::string&)> callback) override; + void FillAddressForm(const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) override; + void ChooseCard( + base::OnceCallback<void(const std::string&)> callback) override; + void FillCardForm(const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) override; private: void OnGetAssistantActions(bool result, const std::string& response); - void ProcessActions(size_t index); + void ProcessNextAction(); void GetNextAssistantActions(); - void OnProcessedAction(size_t index, bool status); + void OnProcessedAction(std::unique_ptr<AssistantAction> action, bool status); AssistantScript* script_; AssistantScriptExecutorDelegate* delegate_; RunScriptCallback callback_; - std::vector<std::unique_ptr<AssistantAction>> actions_; + std::deque<std::unique_ptr<AssistantAction>> actions_; + std::vector<ProcessedAssistantActionProto> processed_actions_; std::string last_server_payload_; base::WeakPtrFactory<AssistantScriptExecutor> weak_ptr_factory_;
diff --git a/components/autofill_assistant/browser/assistant_script_executor_unittest.cc b/components/autofill_assistant/browser/assistant_script_executor_unittest.cc new file mode 100644 index 0000000..47e8eba --- /dev/null +++ b/components/autofill_assistant/browser/assistant_script_executor_unittest.cc
@@ -0,0 +1,169 @@ +// Copyright 2018 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 "components/autofill_assistant/browser/assistant_script_executor.h" + +#include "base/test/mock_callback.h" +#include "components/autofill_assistant/browser/assistant_service.h" +#include "components/autofill_assistant/browser/mock_assistant_service.h" +#include "components/autofill_assistant/browser/mock_assistant_ui_controller.h" +#include "components/autofill_assistant/browser/mock_assistant_web_controller.h" +#include "components/autofill_assistant/browser/mock_run_once_callback.h" +#include "testing/gmock/include/gmock/gmock.h" + +namespace autofill_assistant { + +namespace { + +using ::testing::DoAll; +using ::testing::SaveArg; +using ::testing::StrEq; +using ::testing::StrictMock; +using ::testing::NiceMock; +using ::testing::_; + +class AssistantScriptExecutorTest : public testing::Test, + public AssistantScriptExecutorDelegate { + public: + void SetUp() override { + script_.name = "script name"; + script_.path = "script path"; + + executor_ = std::make_unique<AssistantScriptExecutor>(&script_, this); + + // In this test, "tell" actions always succeed and "click" actions always + // fail. + ON_CALL(mock_assistant_web_controller_, OnClickElement(_, _)) + .WillByDefault(RunOnceCallback<1>(false)); + } + + protected: + AssistantScriptExecutorTest() {} + + AssistantService* GetAssistantService() override { + return &mock_assistant_service_; + } + + AssistantUiController* GetAssistantUiController() override { + return &mock_assistant_ui_controller_; + } + + AssistantWebController* GetAssistantWebController() override { + return &mock_assistant_web_controller_; + } + + std::string Serialize(const google::protobuf::MessageLite& message) { + std::string output; + message.SerializeToString(&output); + return output; + } + + AssistantScript script_; + StrictMock<MockAssistantService> mock_assistant_service_; + NiceMock<MockAssistantWebController> mock_assistant_web_controller_; + NiceMock<MockAssistantUiController> mock_assistant_ui_controller_; + std::unique_ptr<AssistantScriptExecutor> executor_; + StrictMock<base::MockCallback<AssistantScriptExecutor::RunScriptCallback>> + executor_callback_; +}; + +TEST_F(AssistantScriptExecutorTest, GetAssistantActionsFails) { + EXPECT_CALL(mock_assistant_service_, OnGetAssistantActions(_, _)) + .WillOnce(RunOnceCallback<1>(false, "")); + EXPECT_CALL(executor_callback_, Run(false)); + executor_->Run(executor_callback_.Get()); +} + +TEST_F(AssistantScriptExecutorTest, RunOneActionReportFailureAndStop) { + ActionsResponseProto actions_response; + actions_response.set_server_payload("payload"); + actions_response.add_actions() + ->mutable_click() + ->mutable_element_to_click() + ->add_selectors("will fail"); + + EXPECT_CALL(mock_assistant_service_, OnGetAssistantActions(_, _)) + .WillOnce(RunOnceCallback<1>(true, Serialize(actions_response))); + + std::vector<ProcessedAssistantActionProto> processed_actions_capture; + EXPECT_CALL(mock_assistant_service_, OnGetNextAssistantActions(_, _, _)) + .WillOnce(DoAll(SaveArg<1>(&processed_actions_capture), + RunOnceCallback<2>(true, ""))); + EXPECT_CALL(executor_callback_, Run(true)); + executor_->Run(executor_callback_.Get()); + + ASSERT_EQ(1u, processed_actions_capture.size()); + EXPECT_EQ(OTHER_ACTION_STATUS, processed_actions_capture[0].status()); +} + +TEST_F(AssistantScriptExecutorTest, RunMultipleActions) { + ActionsResponseProto initial_actions_response; + initial_actions_response.set_server_payload("payload1"); + initial_actions_response.add_actions()->mutable_tell()->set_message("1"); + initial_actions_response.add_actions()->mutable_tell()->set_message("2"); + EXPECT_CALL(mock_assistant_service_, + OnGetAssistantActions(StrEq("script path"), _)) + .WillOnce(RunOnceCallback<1>(true, Serialize(initial_actions_response))); + + ActionsResponseProto next_actions_response; + next_actions_response.set_server_payload("payload2"); + next_actions_response.add_actions()->mutable_tell()->set_message("3"); + std::vector<ProcessedAssistantActionProto> processed_actions1_capture; + std::vector<ProcessedAssistantActionProto> processed_actions2_capture; + EXPECT_CALL(mock_assistant_service_, OnGetNextAssistantActions(_, _, _)) + .WillOnce( + DoAll(SaveArg<1>(&processed_actions1_capture), + RunOnceCallback<2>(true, Serialize(next_actions_response)))) + .WillOnce(DoAll(SaveArg<1>(&processed_actions2_capture), + RunOnceCallback<2>(true, ""))); + EXPECT_CALL(executor_callback_, Run(true)); + executor_->Run(executor_callback_.Get()); + + EXPECT_EQ(2u, processed_actions1_capture.size()); + EXPECT_EQ(1u, processed_actions2_capture.size()); +} + +TEST_F(AssistantScriptExecutorTest, InterruptActionListOnError) { + ActionsResponseProto initial_actions_response; + initial_actions_response.set_server_payload("payload"); + initial_actions_response.add_actions()->mutable_tell()->set_message( + "will pass"); + initial_actions_response.add_actions() + ->mutable_click() + ->mutable_element_to_click() + ->add_selectors("will fail"); + initial_actions_response.add_actions()->mutable_tell()->set_message( + "never run"); + + EXPECT_CALL(mock_assistant_service_, OnGetAssistantActions(_, _)) + .WillOnce(RunOnceCallback<1>(true, Serialize(initial_actions_response))); + + ActionsResponseProto next_actions_response; + next_actions_response.set_server_payload("payload2"); + next_actions_response.add_actions()->mutable_tell()->set_message( + "will run after error"); + std::vector<ProcessedAssistantActionProto> processed_actions1_capture; + std::vector<ProcessedAssistantActionProto> processed_actions2_capture; + EXPECT_CALL(mock_assistant_service_, OnGetNextAssistantActions(_, _, _)) + .WillOnce( + DoAll(SaveArg<1>(&processed_actions1_capture), + RunOnceCallback<2>(true, Serialize(next_actions_response)))) + .WillOnce(DoAll(SaveArg<1>(&processed_actions2_capture), + RunOnceCallback<2>(true, ""))); + EXPECT_CALL(executor_callback_, Run(true)); + executor_->Run(executor_callback_.Get()); + + ASSERT_EQ(2u, processed_actions1_capture.size()); + EXPECT_EQ(ACTION_APPLIED, processed_actions1_capture[0].status()); + EXPECT_EQ(OTHER_ACTION_STATUS, processed_actions1_capture[1].status()); + + ASSERT_EQ(1u, processed_actions2_capture.size()); + EXPECT_EQ(ACTION_APPLIED, processed_actions2_capture[0].status()); + // make sure "never run" wasn't the one that was run. + EXPECT_EQ("will run after error", + processed_actions2_capture[0].action().tell().message()); +} + +} // namespace +} // namespace autofill_assistant
diff --git a/components/autofill_assistant/browser/assistant_service.cc b/components/autofill_assistant/browser/assistant_service.cc index e33faef..65962d6 100644 --- a/components/autofill_assistant/browser/assistant_service.cc +++ b/components/autofill_assistant/browser/assistant_service.cc
@@ -4,6 +4,10 @@ #include "components/autofill_assistant/browser/assistant_service.h" +#include <string> +#include <utility> +#include <vector> + #include "base/strings/strcat.h" #include "components/autofill_assistant/browser/assistant_protocol_utils.h" #include "content/public/browser/browser_context.h" @@ -92,6 +96,7 @@ void AssistantService::GetNextAssistantActions( const std::string& previous_server_payload, + const std::vector<ProcessedAssistantActionProto>& processed_actions, ResponseCallback callback) { DCHECK(!previous_server_payload.empty()); @@ -101,7 +106,7 @@ assistant_loader->loader = CreateAndStartLoader( assistant_script_action_server_url_, AssistantProtocolUtils::CreateNextScriptActionsRequest( - previous_server_payload), + previous_server_payload, processed_actions), assistant_loader.get()); assistant_loaders_[assistant_loader.get()] = std::move(assistant_loader); }
diff --git a/components/autofill_assistant/browser/assistant_service.h b/components/autofill_assistant/browser/assistant_service.h index 48edb44..8059a026 100644 --- a/components/autofill_assistant/browser/assistant_service.h +++ b/components/autofill_assistant/browser/assistant_service.h
@@ -7,8 +7,11 @@ #include <map> #include <memory> +#include <string> +#include <vector> #include "base/callback.h" +#include "components/autofill_assistant/browser/assistant.pb.h" #include "services/network/public/cpp/simple_url_loader.h" #include "url/gurl.h" @@ -21,22 +24,25 @@ // client actions. class AssistantService { public: - AssistantService(content::BrowserContext* context); - ~AssistantService(); + explicit AssistantService(content::BrowserContext* context); + virtual ~AssistantService(); using ResponseCallback = base::OnceCallback<void(bool result, const std::string&)>; // Get assistant scripts for a given |url|, which should be a valid URL. - void GetAssistantScriptsForUrl(const GURL& url, ResponseCallback callback); + virtual void GetAssistantScriptsForUrl(const GURL& url, + ResponseCallback callback); // Get assistant actions. - void GetAssistantActions(const std::string& script_path, - ResponseCallback callback); + virtual void GetAssistantActions(const std::string& script_path, + ResponseCallback callback); // Get next sequence of assistant actions according to server payload in // previous reponse. - void GetNextAssistantActions(const std::string& previous_server_payload, - ResponseCallback callback); + virtual void GetNextAssistantActions( + const std::string& previous_server_payload, + const std::vector<ProcessedAssistantActionProto>& processed_actions, + ResponseCallback callback); private: // Struct to store assistant scripts and actions request.
diff --git a/components/autofill_assistant/browser/assistant_ui_controller.h b/components/autofill_assistant/browser/assistant_ui_controller.h index f8066a3..ed11132 100644 --- a/components/autofill_assistant/browser/assistant_ui_controller.h +++ b/components/autofill_assistant/browser/assistant_ui_controller.h
@@ -9,6 +9,8 @@ #include <string> +#include "base/callback_forward.h" + namespace autofill_assistant { // Controller to control autofill assistant UI. class AssistantUiController { @@ -27,6 +29,18 @@ // Hide the overlay. virtual void HideOverlay() = 0; + // Show UI to ask user to choose an address in personal data manager. GUID of + // the chosen address will be returned through callback if succeed, otherwise + // empty string is returned. + virtual void ChooseAddress( + base::OnceCallback<void(const std::string&)> callback) = 0; + + // Show UI to ask user to choose a card in personal data manager. GUID of the + // chosen card will be returned through callback if succeed, otherwise empty + // string is returned. + virtual void ChooseCard( + base::OnceCallback<void(const std::string&)> callback) = 0; + protected: AssistantUiController() = default; };
diff --git a/components/autofill_assistant/browser/assistant_web_controller.cc b/components/autofill_assistant/browser/assistant_web_controller.cc index 3becf80e..f4f9d0ca 100644 --- a/components/autofill_assistant/browser/assistant_web_controller.cc +++ b/components/autofill_assistant/browser/assistant_web_controller.cc
@@ -26,4 +26,20 @@ std::move(callback).Run(true); } +void AssistantWebController::FillAddressForm( + const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) { + // TODO(crbug.com/806868): Implement fill address form operation. + std::move(callback).Run(true); +} + +void AssistantWebController::FillCardForm( + const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) { + // TODO(crbug.com/806868): Implement fill card form operation. + std::move(callback).Run(true); +} + } // namespace autofill_assistant.
diff --git a/components/autofill_assistant/browser/assistant_web_controller.h b/components/autofill_assistant/browser/assistant_web_controller.h index 2bc189da..e29457dd 100644 --- a/components/autofill_assistant/browser/assistant_web_controller.h +++ b/components/autofill_assistant/browser/assistant_web_controller.h
@@ -16,18 +16,30 @@ class AssistantWebController { public: AssistantWebController(); - ~AssistantWebController(); + virtual ~AssistantWebController(); // Perform a moust left button click on the element given by |selectors| and // return the result through callback. // CSS selectors in |selectors| are ordered from top frame to the frame // contains the element and the element. - void ClickElement(const std::vector<std::string>& selectors, - base::OnceCallback<void(bool)> callback); + virtual void ClickElement(const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback); // Check whether the element given by |selectors| exists on the web page. - void ElementExists(const std::vector<std::string>& selectors, - base::OnceCallback<void(bool)> callback); + virtual void ElementExists(const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback); + + // Fill the address form given by |selectors| with the given address |guid| in + // personal data manager. + virtual void FillAddressForm(const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback); + + // Fill the card form given by |selectors| with the given card |guid| in + // personal data manager. + virtual void FillCardForm(const std::string& guid, + const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback); private: DISALLOW_COPY_AND_ASSIGN(AssistantWebController);
diff --git a/components/autofill_assistant/browser/mock_assistant_service.cc b/components/autofill_assistant/browser/mock_assistant_service.cc new file mode 100644 index 0000000..9674b6d --- /dev/null +++ b/components/autofill_assistant/browser/mock_assistant_service.cc
@@ -0,0 +1,12 @@ +// Copyright 2018 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 "components/autofill_assistant/browser/mock_assistant_service.h" + +namespace autofill_assistant { + +MockAssistantService::MockAssistantService() : AssistantService(nullptr) {} +MockAssistantService::~MockAssistantService() {} + +} // namespace autofill_assistant
diff --git a/components/autofill_assistant/browser/mock_assistant_service.h b/components/autofill_assistant/browser/mock_assistant_service.h new file mode 100644 index 0000000..47c0d42c --- /dev/null +++ b/components/autofill_assistant/browser/mock_assistant_service.h
@@ -0,0 +1,53 @@ +// Copyright 2018 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_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_SERVICE_H_ +#define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_SERVICE_H_ + +#include <string> + +#include "components/autofill_assistant/browser/assistant_service.h" +#include "testing/gmock/include/gmock/gmock.h" + +namespace autofill_assistant { + +class MockAssistantService : public AssistantService { + public: + MockAssistantService(); + ~MockAssistantService() override; + + void GetAssistantScriptsForUrl(const GURL& url, + ResponseCallback callback) override { + // Transforming callback into a references allows using RunOnceCallback on + // the argument. + OnGetAssistantScriptsForUrl(url, callback); + } + MOCK_METHOD2(OnGetAssistantScriptsForUrl, + void(const GURL& url, ResponseCallback& callback)); + + void GetAssistantActions(const std::string& script_path, + ResponseCallback callback) override { + OnGetAssistantActions(script_path, callback); + } + MOCK_METHOD2(OnGetAssistantActions, + void(const std::string& script_path, + ResponseCallback& callback)); + + void GetNextAssistantActions( + const std::string& previous_server_payload, + const std::vector<ProcessedAssistantActionProto>& processed_actions, + ResponseCallback callback) override { + OnGetNextAssistantActions(previous_server_payload, processed_actions, + callback); + } + MOCK_METHOD3( + OnGetNextAssistantActions, + void(const std::string& previous_server_payload, + const std::vector<ProcessedAssistantActionProto>& processed_actions, + ResponseCallback& callback)); +}; + +} // namespace autofill_assistant + +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_SERVICE_H_
diff --git a/components/autofill_assistant/browser/mock_assistant_ui_controller.cc b/components/autofill_assistant/browser/mock_assistant_ui_controller.cc new file mode 100644 index 0000000..7cd9f30 --- /dev/null +++ b/components/autofill_assistant/browser/mock_assistant_ui_controller.cc
@@ -0,0 +1,12 @@ +// Copyright 2018 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 "components/autofill_assistant/browser/mock_assistant_ui_controller.h" + +namespace autofill_assistant { + +MockAssistantUiController::MockAssistantUiController() {} +MockAssistantUiController::~MockAssistantUiController() {} + +} // namespace autofill_assistant
diff --git a/components/autofill_assistant/browser/mock_assistant_ui_controller.h b/components/autofill_assistant/browser/mock_assistant_ui_controller.h new file mode 100644 index 0000000..9680a20 --- /dev/null +++ b/components/autofill_assistant/browser/mock_assistant_ui_controller.h
@@ -0,0 +1,41 @@ +// Copyright 2018 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_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_UI_CONTROLLER_H_ +#define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_UI_CONTROLLER_H_ + +#include "base/callback.h" +#include "components/autofill_assistant/browser/assistant_ui_controller.h" +#include "testing/gmock/include/gmock/gmock.h" + +namespace autofill_assistant { + +class MockAssistantUiController : public AssistantUiController { + public: + MockAssistantUiController(); + ~MockAssistantUiController() override; + + MOCK_METHOD1(SetUiDelegate, void(AssistantUiDelegate* ui_delegate)); + MOCK_METHOD1(ShowStatusMessage, void(const std::string& message)); + MOCK_METHOD0(ShowOverlay, void()); + MOCK_METHOD0(HideOverlay, void()); + + void ChooseAddress( + base::OnceCallback<void(const std::string&)> callback) override { + OnChooseAddress(callback); + } + MOCK_METHOD1(OnChooseAddress, + void(base::OnceCallback<void(const std::string&)>& callback)); + + void ChooseCard( + base::OnceCallback<void(const std::string&)> callback) override { + OnChooseCard(callback); + } + MOCK_METHOD1(OnChooseCard, + void(base::OnceCallback<void(const std::string&)>& callback)); +}; + +} // namespace autofill_assistant + +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_UI_CONTROLLER_H_
diff --git a/components/autofill_assistant/browser/mock_assistant_web_controller.cc b/components/autofill_assistant/browser/mock_assistant_web_controller.cc new file mode 100644 index 0000000..a3d7022 --- /dev/null +++ b/components/autofill_assistant/browser/mock_assistant_web_controller.cc
@@ -0,0 +1,12 @@ +// Copyright 2018 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 "components/autofill_assistant/browser/mock_assistant_web_controller.h" + +namespace autofill_assistant { + +MockAssistantWebController::MockAssistantWebController() {} +MockAssistantWebController::~MockAssistantWebController() {} + +} // namespace autofill_assistant
diff --git a/components/autofill_assistant/browser/mock_assistant_web_controller.h b/components/autofill_assistant/browser/mock_assistant_web_controller.h new file mode 100644 index 0000000..a560203 --- /dev/null +++ b/components/autofill_assistant/browser/mock_assistant_web_controller.h
@@ -0,0 +1,43 @@ +// Copyright 2018 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_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_WEB_CONTROLLER_H_ +#define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_WEB_CONTROLLER_H_ + +#include <string> +#include <vector> + +#include "base/callback.h" +#include "components/autofill_assistant/browser/assistant_web_controller.h" +#include "testing/gmock/include/gmock/gmock.h" + +namespace autofill_assistant { + +class MockAssistantWebController : public AssistantWebController { + public: + MockAssistantWebController(); + ~MockAssistantWebController() override; + + void ClickElement(const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) override { + // Transforming callback into a references allows using RunOnceCallback on + // the argument. + OnClickElement(selectors, callback); + } + MOCK_METHOD2(OnClickElement, + void(const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)>& callback)); + + void ElementExists(const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)> callback) override { + OnElementExists(selectors, callback); + } + MOCK_METHOD2(OnElementExists, + void(const std::vector<std::string>& selectors, + base::OnceCallback<void(bool)>& callback)); +}; + +} // namespace autofill_assistant + +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_ASSISTANT_WEB_CONTROLLER_H_
diff --git a/components/autofill_assistant/browser/mock_run_once_callback.h b/components/autofill_assistant/browser/mock_run_once_callback.h new file mode 100644 index 0000000..97e3bf3a --- /dev/null +++ b/components/autofill_assistant/browser/mock_run_once_callback.h
@@ -0,0 +1,46 @@ +// Copyright 2018 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_AUTOFILL_ASSISTANT_BROWSER_MOCK_RUN_ONCE_CALLBACK_H_ +#define COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_RUN_ONCE_CALLBACK_H_ + +#include "testing/gmock/include/gmock/gmock.h" + +namespace autofill_assistant { + +// Templates for calling base::OnceCallback from gmock actions. +// +// To work around the fact that OnceCallback can't be copied, the method +// to be mocked needs to take the callback as a reference. To do it without +// changing the original interface, follow this pattern: +// +// void DoSomething(..., base::OnceCallback<void(bool)> callback) override { +// OnDoSomething(..., callback); +// } +// MOCK_METHOD2(OnDoSomething, +// void(..., base::OnceCallback<void(bool)>& callback)); +// +// + +ACTION_TEMPLATE(RunOnceCallback, + HAS_1_TEMPLATE_PARAMS(int, k), + AND_1_VALUE_PARAMS(p0)) { + return std::move(std::get<k>(args)).Run(p0); +} + +ACTION_TEMPLATE(RunOnceCallback, + HAS_1_TEMPLATE_PARAMS(int, k), + AND_2_VALUE_PARAMS(p0, p1)) { + return std::move(std::get<k>(args)).Run(p0, p1); +} + +ACTION_TEMPLATE(RunOnceCallback, + HAS_1_TEMPLATE_PARAMS(int, k), + AND_3_VALUE_PARAMS(p0, p1, p2)) { + return std::move(std::get<k>(args)).Run(p0, p1, p2); +} + +} // namespace autofill_assistant + +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_MOCK_RUN_ONCE_CALLBACK_H_
diff --git a/components/browser_sync/profile_sync_test_util.cc b/components/browser_sync/profile_sync_test_util.cc index 71421182..6605660 100644 --- a/components/browser_sync/profile_sync_test_util.cc +++ b/components/browser_sync/profile_sync_test_util.cc
@@ -271,7 +271,7 @@ base::ThreadTaskRunnerHandle::Get())) { RegisterPrefsForProfileSyncService(pref_service_.registry()); auth_service_.set_auto_post_fetch_response_on_message_loop(true); - account_tracker_.Initialize(&signin_client_); + account_tracker_.Initialize(&pref_service_, base::FilePath()); signin_manager_.Initialize(&pref_service_); local_session_event_router_ = std::make_unique<DummyRouter>(); ON_CALL(sync_sessions_client_, GetLocalSessionEventRouter())
diff --git a/components/domain_reliability/OWNERS b/components/domain_reliability/OWNERS index fdcdcec..1cfbdee 100644 --- a/components/domain_reliability/OWNERS +++ b/components/domain_reliability/OWNERS
@@ -1,5 +1,3 @@ -davidben@chromium.org - file://net/OWNERS per-file quic_error_mapping*=rch@chromium.org
diff --git a/components/guest_view/browser/guest_view_base.cc b/components/guest_view/browser/guest_view_base.cc index 18cd29c..7951f7d6 100644 --- a/components/guest_view/browser/guest_view_base.cc +++ b/components/guest_view/browser/guest_view_base.cc
@@ -683,7 +683,11 @@ bool GuestViewBase::PreHandleGestureEvent(WebContents* source, const blink::WebGestureEvent& event) { - return blink::WebInputEvent::IsPinchGestureEventType(event.GetType()); + // Pinch events which cause a scale change should not be routed to a guest. + // We still allow synthetic wheel events for touchpad pinch to go to the page. + DCHECK(!blink::WebInputEvent::IsPinchGestureEventType(event.GetType()) || + event.NeedsWheelEvent()); + return false; } void GuestViewBase::UpdatePreferredSize(WebContents* target_web_contents,
diff --git a/components/leveldb_proto/leveldb_database.cc b/components/leveldb_proto/leveldb_database.cc index 16d891a..b514d5fd 100644 --- a/components/leveldb_proto/leveldb_database.cc +++ b/components/leveldb_proto/leveldb_database.cc
@@ -168,13 +168,22 @@ bool LevelDB::LoadWithFilter(const KeyFilter& filter, std::vector<std::string>* entries) { + return LoadWithFilter(filter, entries, leveldb::ReadOptions(), std::string()); +} + +bool LevelDB::LoadWithFilter(const KeyFilter& filter, + std::vector<std::string>* entries, + const leveldb::ReadOptions& options, + const std::string& target_prefix) { DFAKE_SCOPED_LOCK(thread_checker_); if (!db_) return false; - leveldb::ReadOptions options; std::unique_ptr<leveldb::Iterator> db_iterator(db_->NewIterator(options)); - for (db_iterator->SeekToFirst(); db_iterator->Valid(); db_iterator->Next()) { + leveldb::Slice target(target_prefix); + for (db_iterator->Seek(target); + db_iterator->Valid() && db_iterator->key().starts_with(target); + db_iterator->Next()) { if (!filter.is_null()) { leveldb::Slice key_slice = db_iterator->key(); if (!filter.Run(std::string(key_slice.data(), key_slice.size())))
diff --git a/components/leveldb_proto/leveldb_database.h b/components/leveldb_proto/leveldb_database.h index b90f1f2..715ca62 100644 --- a/components/leveldb_proto/leveldb_database.h +++ b/components/leveldb_proto/leveldb_database.h
@@ -58,6 +58,10 @@ virtual bool Load(std::vector<std::string>* entries); virtual bool LoadWithFilter(const KeyFilter& filter, std::vector<std::string>* entries); + virtual bool LoadWithFilter(const KeyFilter& filter, + std::vector<std::string>* entries, + const leveldb::ReadOptions& options, + const std::string& target_prefix); virtual bool LoadKeys(std::vector<std::string>* keys); virtual bool Get(const std::string& key, bool* found, std::string* entry); // Close (if currently open) and then destroy (i.e. delete) the database
diff --git a/components/leveldb_proto/proto_database.h b/components/leveldb_proto/proto_database.h index d8adc5f..1d0e543 100644 --- a/components/leveldb_proto/proto_database.h +++ b/components/leveldb_proto/proto_database.h
@@ -74,6 +74,10 @@ // ProtoDatabase's taskrunner. virtual void LoadEntriesWithFilter(const LevelDB::KeyFilter& filter, LoadCallback callback) = 0; + virtual void LoadEntriesWithFilter(const LevelDB::KeyFilter& filter, + const leveldb::ReadOptions& options, + const std::string& target_prefix, + LoadCallback callback) = 0; // Asynchronously loads all keys from the database and invokes |callback| with // those keys when complete.
diff --git a/components/leveldb_proto/proto_database_impl.h b/components/leveldb_proto/proto_database_impl.h index 4a60fe36..f7bc921 100644 --- a/components/leveldb_proto/proto_database_impl.h +++ b/components/leveldb_proto/proto_database_impl.h
@@ -57,7 +57,12 @@ typename ProtoDatabase<T>::UpdateCallback callback) override; void LoadEntries(typename ProtoDatabase<T>::LoadCallback callback) override; void LoadEntriesWithFilter( - const LevelDB::KeyFilter& key_filter, + const LevelDB::KeyFilter& filter, + typename ProtoDatabase<T>::LoadCallback callback) override; + void LoadEntriesWithFilter( + const LevelDB::KeyFilter& filter, + const leveldb::ReadOptions& options, + const std::string& target_prefix, typename ProtoDatabase<T>::LoadCallback callback) override; void LoadKeys(typename ProtoDatabase<T>::LoadKeysCallback callback) override; void GetEntry(const std::string& key, @@ -181,6 +186,8 @@ template <typename T> void LoadEntriesFromTaskRunner(LevelDB* database, const LevelDB::KeyFilter& filter, + const leveldb::ReadOptions& options, + const std::string& target_prefix, std::vector<T>* entries, bool* success) { DCHECK(success); @@ -189,7 +196,8 @@ entries->clear(); std::vector<std::string> loaded_entries; - *success = database->LoadWithFilter(filter, &loaded_entries); + *success = + database->LoadWithFilter(filter, &loaded_entries, options, target_prefix); for (const auto& serialized_entry : loaded_entries) { T entry; @@ -339,6 +347,16 @@ void ProtoDatabaseImpl<T>::LoadEntriesWithFilter( const LevelDB::KeyFilter& key_filter, typename ProtoDatabase<T>::LoadCallback callback) { + LoadEntriesWithFilter(key_filter, leveldb::ReadOptions(), std::string(), + std::move(callback)); +} + +template <typename T> +void ProtoDatabaseImpl<T>::LoadEntriesWithFilter( + const LevelDB::KeyFilter& key_filter, + const leveldb::ReadOptions& options, + const std::string& target_prefix, + typename ProtoDatabase<T>::LoadCallback callback) { DCHECK(thread_checker_.CalledOnValidThread()); bool* success = new bool(false); @@ -349,7 +367,7 @@ task_runner_->PostTaskAndReply( FROM_HERE, base::BindOnce(LoadEntriesFromTaskRunner<T>, base::Unretained(db_.get()), - key_filter, entries_ptr, success), + key_filter, options, target_prefix, entries_ptr, success), base::BindOnce(RunLoadCallback<T>, std::move(callback), base::Owned(success), std::move(entries))); }
diff --git a/components/leveldb_proto/proto_database_impl_unittest.cc b/components/leveldb_proto/proto_database_impl_unittest.cc index 9fd1a2eb..a49bb64 100644 --- a/components/leveldb_proto/proto_database_impl_unittest.cc +++ b/components/leveldb_proto/proto_database_impl_unittest.cc
@@ -57,6 +57,11 @@ MOCK_METHOD1(Load, bool(std::vector<std::string>*)); MOCK_METHOD2(LoadWithFilter, bool(const KeyFilter&, std::vector<std::string>*)); + MOCK_METHOD4(LoadWithFilter, + bool(const KeyFilter&, + std::vector<std::string>*, + const leveldb::ReadOptions&, + const std::string&)); MOCK_METHOD3(Get, bool(const std::string&, bool*, std::string*)); MOCK_METHOD0(Destroy, bool()); @@ -282,7 +287,7 @@ base::BindOnce(&MockDatabaseCaller::InitCallback, base::Unretained(&caller))); - EXPECT_CALL(*mock_db, LoadWithFilter(_, _)) + EXPECT_CALL(*mock_db, LoadWithFilter(_, _, _, _)) .WillOnce(AppendLoadEntries(model)); EXPECT_CALL(caller, LoadCallback1(true, _)) .WillOnce(VerifyLoadEntries(testing::ByRef(model))); @@ -304,7 +309,7 @@ base::BindOnce(&MockDatabaseCaller::InitCallback, base::Unretained(&caller))); - EXPECT_CALL(*mock_db, LoadWithFilter(_, _)).WillOnce(Return(false)); + EXPECT_CALL(*mock_db, LoadWithFilter(_, _, _, _)).WillOnce(Return(false)); EXPECT_CALL(caller, LoadCallback1(false, _)); db_->LoadEntries(base::BindOnce(&MockDatabaseCaller::LoadCallback, base::Unretained(&caller)));
diff --git a/components/leveldb_proto/testing/fake_db.h b/components/leveldb_proto/testing/fake_db.h index 234809d..bfce3cd 100644 --- a/components/leveldb_proto/testing/fake_db.h +++ b/components/leveldb_proto/testing/fake_db.h
@@ -48,6 +48,11 @@ void LoadEntriesWithFilter( const LevelDB::KeyFilter& key_filter, typename ProtoDatabase<T>::LoadCallback callback) override; + void LoadEntriesWithFilter( + const LevelDB::KeyFilter& filter, + const leveldb::ReadOptions& options, + const std::string& target_prefix, + typename ProtoDatabase<T>::LoadCallback callback) override; void LoadKeys(typename ProtoDatabase<T>::LoadKeysCallback callback) override; void GetEntry(const std::string& key, typename ProtoDatabase<T>::GetCallback callback) override; @@ -152,10 +157,22 @@ void FakeDB<T>::LoadEntriesWithFilter( const LevelDB::KeyFilter& key_filter, typename ProtoDatabase<T>::LoadCallback callback) { + LoadEntriesWithFilter(key_filter, leveldb::ReadOptions(), std::string(), + std::move(callback)); +} + +template <typename T> +void FakeDB<T>::LoadEntriesWithFilter( + const LevelDB::KeyFilter& key_filter, + const leveldb::ReadOptions& options, + const std::string& target_prefix, + typename ProtoDatabase<T>::LoadCallback callback) { std::unique_ptr<std::vector<T>> entries(new std::vector<T>()); for (const auto& pair : *db_) { - if (key_filter.is_null() || key_filter.Run(pair.first)) - entries->push_back(pair.second); + if (key_filter.is_null() || key_filter.Run(pair.first)) { + if (pair.first.compare(0, target_prefix.length(), target_prefix) == 0) + entries->push_back(pair.second); + } } load_callback_ =
diff --git a/components/password_manager/sync/browser/sync_username_test_base.cc b/components/password_manager/sync/browser/sync_username_test_base.cc index 58ab04f..112a5ea 100644 --- a/components/password_manager/sync/browser/sync_username_test_base.cc +++ b/components/password_manager/sync/browser/sync_username_test_base.cc
@@ -28,7 +28,7 @@ signin_manager_(&signin_client_, &account_tracker_) { SigninManagerBase::RegisterProfilePrefs(prefs_.registry()); AccountTrackerService::RegisterPrefs(prefs_.registry()); - account_tracker_.Initialize(&signin_client_); + account_tracker_.Initialize(&prefs_, base::FilePath()); } SyncUsernameTestBase::~SyncUsernameTestBase() {}
diff --git a/components/payments/content/payment_request.cc b/components/payments/content/payment_request.cc index dbc6518..54fcb97 100644 --- a/components/payments/content/payment_request.cc +++ b/components/payments/content/payment_request.cc
@@ -203,8 +203,10 @@ void PaymentRequest::AreRequestedMethodsSupportedCallback( bool methods_supported) { if (methods_supported) { - if (SatisfiesSkipUIConstraints()) + if (SatisfiesSkipUIConstraints()) { + skipped_payment_request_ui_ = true; Pay(); + } } else { journey_logger_.SetNotShown( JourneyLogger::NOT_SHOWN_REASON_NO_SUPPORTED_PAYMENT_METHOD); @@ -215,6 +217,19 @@ } } +bool PaymentRequest::SatisfiesSkipUIConstraints() const { + return base::FeatureList::IsEnabled(features::kWebPaymentsSingleAppUiSkip) && + base::FeatureList::IsEnabled(::features::kServiceWorkerPaymentApps) && + is_show_user_gesture_ && state()->is_get_all_instruments_finished() && + state()->available_instruments().size() == 1 && + spec()->stringified_method_data().size() == 1 && + !spec()->request_shipping() && !spec()->request_payer_name() && + !spec()->request_payer_phone() && + !spec()->request_payer_email() + // Only allowing URL base payment apps to skip the payment sheet. + && spec()->url_payment_method_identifiers().size() == 1; +} + void PaymentRequest::UpdateWith(mojom::PaymentDetailsPtr details) { std::string error; if (!ValidatePaymentDetails(ConvertPaymentDetails(details), &error)) { @@ -394,19 +409,6 @@ return delegate_->IsIncognito(); } -bool PaymentRequest::SatisfiesSkipUIConstraints() const { - return base::FeatureList::IsEnabled(features::kWebPaymentsSingleAppUiSkip) && - base::FeatureList::IsEnabled(::features::kServiceWorkerPaymentApps) && - is_show_user_gesture_ && state()->is_get_all_instruments_finished() && - state()->available_instruments().size() == 1 && - spec()->stringified_method_data().size() == 1 && - !spec()->request_shipping() && !spec()->request_payer_name() && - !spec()->request_payer_phone() && - !spec()->request_payer_email() - // Only allowing URL base payment apps to skip the payment sheet. - && spec()->url_payment_method_identifiers().size() == 1; -} - void PaymentRequest::RecordFirstAbortReason( JourneyLogger::AbortReason abort_reason) { if (!has_recorded_completion_) {
diff --git a/components/payments/content/payment_request.h b/components/payments/content/payment_request.h index 25b15e9a7..9753d08e 100644 --- a/components/payments/content/payment_request.h +++ b/components/payments/content/payment_request.h
@@ -107,13 +107,10 @@ bool IsIncognito() const; - // Returns true if this payment request supports skipping the Payment Sheet. - // Typically, this means only one payment method is supported, it's a URL - // based method, and no other info is requested from the user. - bool SatisfiesSkipUIConstraints() const; - content::WebContents* web_contents() { return web_contents_; } + bool skipped_payment_request_ui() { return skipped_payment_request_ui_; } + PaymentRequestSpec* spec() { return spec_.get(); } PaymentRequestState* state() { return state_.get(); } @@ -121,6 +118,11 @@ PaymentRequestState* state() const { return state_.get(); } private: + // Returns true if this payment request supports skipping the Payment Sheet. + // Typically, this means only one payment method is supported, it's a URL + // based method, and no other info is requested from the user. + bool SatisfiesSkipUIConstraints() const; + // Only records the abort reason if it's the first completion for this Payment // Request. This is necessary since the aborts cascade into one another with // the first one being the most precise. @@ -172,6 +174,9 @@ // Whether PaymentRequest.show() was invoked with a user gesture. bool is_show_user_gesture_ = false; + // Whether PaymentRequest.show() was invoked by skipping payment request UI. + bool skipped_payment_request_ui_ = false; + base::WeakPtrFactory<PaymentRequest> weak_ptr_factory_; DISALLOW_COPY_AND_ASSIGN(PaymentRequest);
diff --git a/components/payments/content/payment_request_dialog.h b/components/payments/content/payment_request_dialog.h index a08c1e64..3d23fcb 100644 --- a/components/payments/content/payment_request_dialog.h +++ b/components/payments/content/payment_request_dialog.h
@@ -22,10 +22,6 @@ virtual void ShowDialog() = 0; - virtual void ShowDialogAtPaymentHandlerSheet( - const GURL& url, - PaymentHandlerOpenWindowCallback callback) = 0; - virtual void CloseDialog() = 0; virtual void ShowErrorMessage() = 0;
diff --git a/components/policy/resources/policy_templates.json b/components/policy/resources/policy_templates.json index f52b960..f6ccbb3 100644 --- a/components/policy/resources/policy_templates.json +++ b/components/policy/resources/policy_templates.json
@@ -12819,6 +12819,46 @@ When this policy is set to False, share discovery will not use the <ph name="NETBIOS_PROTOCOL">NetBIOS Name Query Request protocol</ph> protocol to discover shares. If the policy is left not set, the default is disabled for enterprise-managed users and enabled for non-managed users.''', }, + { + 'name': 'WebAppInstallForceList', + 'type': 'dict', + 'schema': { + 'type': 'array', + 'items': { + 'type': 'object', + 'properties': { + 'url': { 'type': 'string' }, + 'launch_container': { + 'type': 'string', + 'enum': [ + 'tab', + 'window' + ] + } + }, + 'required': ['url'] + } + }, + 'supported_on': ['chrome.*:70-', 'chrome_os:70-'], + 'features': { + 'dynamic_refresh': True, + 'per_profile': True, + }, + 'example_value': [{ + 'url': 'https://www.google.com/maps', + 'launch_container': 'window' + }, { + 'url': 'https://docs.google.com', + 'launch_container': 'tab' + }], + 'id': 468, + 'caption': '''Configure list of force-installed Web Apps''', + 'tags': [], + 'desc': '''Specifies a list of websites that are installed silently, without user interaction, and which cannot be uninstalled nor disabled by the user. + + Each list item of the policy is an object with two members: "url" and "launch_container". "url" should be the URL of the web app to install and "launch_container" should be either "window" or "tab" to indicate how the Web App will be opened once installed. If "launch_container" is ommitted, the app will launch in a window if Chrome considers it a Progressive Web App and in a tab otherwise.''', + 'label': '''URLs for Web Apps to be silently installed.''', + }, ], 'messages': { @@ -12960,5 +13000,5 @@ }, 'placeholders': [], 'deleted_policy_ids': [412], - 'highest_id_currently_used': 467 + 'highest_id_currently_used': 468 }
diff --git a/components/previews/content/previews_content_util_unittest.cc b/components/previews/content/previews_content_util_unittest.cc index a4aa11a..ff164e9 100644 --- a/components/previews/content/previews_content_util_unittest.cc +++ b/components/previews/content/previews_content_util_unittest.cc
@@ -223,7 +223,8 @@ TEST_F(PreviewsContentUtilTest, DetermineCommittedClientPreviewsStateNoScriptCheckIfStillAllowed) { base::test::ScopedFeatureList scoped_feature_list; - scoped_feature_list.InitFromCommandLine("Previews,ClientLoFi", std::string()); + scoped_feature_list.InitFromCommandLine("Previews,ClientLoFi", + "NoScriptPreviews"); // NoScript not allowed at commit time so Client LoFi chosen: EXPECT_EQ(content::PREVIEWS_OFF, previews::DetermineCommittedClientPreviewsState(
diff --git a/components/previews/content/previews_decider_impl_unittest.cc b/components/previews/content/previews_decider_impl_unittest.cc index 0cb1b01..380914e 100644 --- a/components/previews/content/previews_decider_impl_unittest.cc +++ b/components/previews/content/previews_decider_impl_unittest.cc
@@ -27,6 +27,7 @@ #include "base/threading/thread_task_runner_handle.h" #include "base/time/default_clock.h" #include "base/time/time.h" +#include "build/build_config.h" #include "components/blacklist/opt_out_blacklist/opt_out_blacklist_data.h" #include "components/blacklist/opt_out_blacklist/opt_out_blacklist_delegate.h" #include "components/blacklist/opt_out_blacklist/opt_out_blacklist_item.h" @@ -836,7 +837,7 @@ } } -TEST_F(PreviewsDeciderImplTest, NoScriptDisallowedByDefault) { +TEST_F(PreviewsDeciderImplTest, NoScriptFeatureDefaultBehavior) { base::test::ScopedFeatureList scoped_feature_list; scoped_feature_list.InitAndEnableFeature(features::kPreviews); InitializeUIService(); @@ -850,13 +851,25 @@ previews::params::GetECTThresholdForPreview( previews::PreviewsType::NOSCRIPT), std::vector<std::string>(), false)); +#if defined(OS_ANDROID) + // Enabled by default on Android but no server whitelist. + histogram_tester.ExpectTotalCount("Previews.EligibilityReason.NoScript", 1); + histogram_tester.ExpectUniqueSample( + "Previews.EligibilityReason.NoScript", + static_cast<int>( + PreviewsEligibilityReason::HOST_NOT_WHITELISTED_BY_SERVER), + 1); +#else // !defined(OS_ANDROID) + // Disabled by default on non-Android. histogram_tester.ExpectTotalCount("Previews.EligibilityReason.NoScript", 0); +#endif // defined(OS_ANDROID) } TEST_F(PreviewsDeciderImplTest, NoScriptAllowedByFeature) { base::test::ScopedFeatureList scoped_feature_list; scoped_feature_list.InitWithFeatures( - {features::kPreviews, features::kNoScriptPreviews}, {}); + {features::kPreviews, features::kNoScriptPreviews}, + {features::kOptimizationHints}); InitializeUIService(); const struct { @@ -999,7 +1012,8 @@ ResourceLoadingHintsDisallowedWithoutOptimizationHints) { base::test::ScopedFeatureList scoped_feature_list; scoped_feature_list.InitWithFeatures( - {features::kPreviews, features::kResourceLoadingHints}, {}); + {features::kPreviews, features::kResourceLoadingHints}, + {features::kOptimizationHints}); InitializeUIService(); network_quality_estimator()->set_effective_connection_type( @@ -1314,7 +1328,8 @@ TEST_F(PreviewsDeciderImplTest, IsURLAllowedForPreviewBlacklistStatuses) { base::test::ScopedFeatureList scoped_feature_list; scoped_feature_list.InitWithFeatures( - {features::kPreviews, features::kNoScriptPreviews}, {}); + {features::kPreviews, features::kNoScriptPreviews}, + {features::kOptimizationHints}); InitializeUIService(); auto expected_type = PreviewsType::NOSCRIPT;
diff --git a/components/previews/core/previews_features.cc b/components/previews/core/previews_features.cc index 499b5141..5bad470c 100644 --- a/components/previews/core/previews_features.cc +++ b/components/previews/core/previews_features.cc
@@ -37,8 +37,14 @@ }; // Enables the NoScript previews for Android. -const base::Feature kNoScriptPreviews{"NoScriptPreviews", - base::FEATURE_DISABLED_BY_DEFAULT}; +const base::Feature kNoScriptPreviews { + "NoScriptPreviews", +#if defined(OS_ANDROID) + base::FEATURE_ENABLED_BY_DEFAULT +#else // !defined(OS_ANDROID) + base::FEATURE_DISABLED_BY_DEFAULT +#endif // defined(OS_ANDROID) +}; // Enables the Stale Previews timestamp on Previews infobars. const base::Feature kStalePreviewsTimestamp{"StalePreviewsTimestamp", @@ -46,8 +52,14 @@ // Enables the syncing of the Optimization Hints component, which provides // hints for what Previews can be applied on a page load. -const base::Feature kOptimizationHints{"OptimizationHints", - base::FEATURE_DISABLED_BY_DEFAULT}; +const base::Feature kOptimizationHints { + "OptimizationHints", +#if defined(OS_ANDROID) + base::FEATURE_ENABLED_BY_DEFAULT +#else // !defined(OS_ANDROID) + base::FEATURE_DISABLED_BY_DEFAULT +#endif // defined(OS_ANDROID) +}; // Enables Optimization Hints that are marked as experimental. Optimizations are // marked experimental by setting an experiment name in the "experiment_name"
diff --git a/components/printing/common/print_messages.h b/components/printing/common/print_messages.h index 0c311c9a..e3c11e1 100644 --- a/components/printing/common/print_messages.h +++ b/components/printing/common/print_messages.h
@@ -26,7 +26,6 @@ #include "ui/gfx/geometry/rect.h" #include "ui/gfx/ipc/geometry/gfx_param_traits.h" #include "ui/gfx/ipc/skia/gfx_skia_param_traits.h" -#include "ui/gfx/native_widget_types.h" #ifndef INTERNAL_COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ #define INTERNAL_COMPONENTS_PRINTING_COMMON_PRINT_MESSAGES_H_ @@ -316,9 +315,6 @@ // Store the expected pages count. IPC_STRUCT_MEMBER(int, expected_pages_count) - - // Whether the preview can be modified. - IPC_STRUCT_MEMBER(bool, modifiable) IPC_STRUCT_END() #endif // BUILDFLAG(ENABLE_PRINT_PREVIEW)
diff --git a/components/printing/renderer/print_render_frame_helper.cc b/components/printing/renderer/print_render_frame_helper.cc index efb0827..a212616 100644 --- a/components/printing/renderer/print_render_frame_helper.cc +++ b/components/printing/renderer/print_render_frame_helper.cc
@@ -1346,7 +1346,6 @@ preview_params.document_cookie = print_pages_params_->params.document_cookie; preview_params.expected_pages_count = print_preview_context_.total_page_count(); - preview_params.modifiable = print_preview_context_.IsModifiable(); PrintHostMsg_PreviewIds ids(print_pages_params_->params.preview_request_id, print_pages_params_->params.preview_ui_id);
diff --git a/components/signin/core/browser/account_investigator_unittest.cc b/components/signin/core/browser/account_investigator_unittest.cc index aef935b..a261bfa 100644 --- a/components/signin/core/browser/account_investigator_unittest.cc +++ b/components/signin/core/browser/account_investigator_unittest.cc
@@ -49,7 +49,7 @@ AccountTrackerService::RegisterPrefs(prefs_.registry()); AccountInvestigator::RegisterPrefs(prefs_.registry()); SigninManagerBase::RegisterProfilePrefs(prefs_.registry()); - account_tracker_service_.Initialize(&signin_client_); + account_tracker_service_.Initialize(&prefs_, base::FilePath()); } ~AccountInvestigatorTest() override { investigator_.Shutdown(); }
diff --git a/components/signin/core/browser/account_reconcilor_unittest.cc b/components/signin/core/browser/account_reconcilor_unittest.cc index dd488d339..c49f7fe4 100644 --- a/components/signin/core/browser/account_reconcilor_unittest.cc +++ b/components/signin/core/browser/account_reconcilor_unittest.cc
@@ -323,7 +323,7 @@ GaiaUrls::GetInstance()->GetCheckConnectionInfoURLWithSource( GaiaConstants::kChromeSource); - account_tracker_.Initialize(&test_signin_client_); + account_tracker_.Initialize(&pref_service_, base::FilePath()); cookie_manager_service_.SetListAccountsResponseHttpNotFound(); signin_manager_.Initialize(nullptr);
diff --git a/components/signin/core/browser/account_tracker_service.cc b/components/signin/core/browser/account_tracker_service.cc index c0bb26a..fe4451e 100644 --- a/components/signin/core/browser/account_tracker_service.cc +++ b/components/signin/core/browser/account_tracker_service.cc
@@ -21,7 +21,6 @@ #include "build/build_config.h" #include "components/pref_registry/pref_registry_syncable.h" #include "components/prefs/scoped_user_pref_update.h" -#include "components/signin/core/browser/signin_client.h" #include "components/signin/core/browser/signin_manager.h" #include "components/signin/core/browser/signin_pref_names.h" @@ -104,8 +103,7 @@ const char AccountTrackerService::kAccountsFolder[] = "Accounts"; const char AccountTrackerService::kAvatarImagesFolder[] = "Avatar Images"; -AccountTrackerService::AccountTrackerService() - : signin_client_(nullptr), weak_factory_(this) {} +AccountTrackerService::AccountTrackerService() : weak_factory_(this) {} AccountTrackerService::~AccountTrackerService() { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); @@ -119,13 +117,13 @@ AccountTrackerService::MIGRATION_NOT_STARTED); } -void AccountTrackerService::Initialize(SigninClient* signin_client, - const base::FilePath& user_data_dir) { - DCHECK(signin_client); - DCHECK(!signin_client_); - signin_client_ = signin_client; +void AccountTrackerService::Initialize(PrefService* pref_service, + base::FilePath user_data_dir) { + DCHECK(pref_service); + DCHECK(!pref_service_); + pref_service_ = pref_service; LoadFromPrefs(); - user_data_dir_ = user_data_dir; + user_data_dir_ = std::move(user_data_dir); if (!user_data_dir_.empty()) { // |image_storage_task_runner_| is a sequenced runner because we want to // avoid read and write operations to the same file at the same time. @@ -137,7 +135,7 @@ } void AccountTrackerService::Shutdown() { - signin_client_ = nullptr; + pref_service_ = nullptr; accounts_.clear(); } @@ -212,12 +210,11 @@ AccountTrackerService::AccountIdMigrationState AccountTrackerService::GetMigrationState() const { - return GetMigrationState(signin_client_->GetPrefs()); + return GetMigrationState(pref_service_); } void AccountTrackerService::SetMigrationState(AccountIdMigrationState state) { - signin_client_->GetPrefs()->SetInteger(prefs::kAccountIdMigrationState, - state); + pref_service_->SetInteger(prefs::kAccountIdMigrationState, state); } void AccountTrackerService::SetMigrationDone() { @@ -450,8 +447,7 @@ } void AccountTrackerService::LoadFromPrefs() { - const base::ListValue* list = - signin_client_->GetPrefs()->GetList(kAccountInfoPref); + const base::ListValue* list = pref_service_->GetList(kAccountInfoPref); std::set<std::string> to_remove; bool contains_deprecated_service_flags = false; for (size_t i = 0; i < list->GetSize(); ++i) { @@ -518,7 +514,7 @@ } if (contains_deprecated_service_flags) - RemoveDeprecatedServiceFlags(signin_client_->GetPrefs()); + RemoveDeprecatedServiceFlags(pref_service_); // Remove any obsolete prefs. for (auto account_id : to_remove) { @@ -541,12 +537,12 @@ } void AccountTrackerService::SaveToPrefs(const AccountState& state) { - if (!signin_client_->GetPrefs()) + if (!pref_service_) return; base::DictionaryValue* dict = nullptr; base::string16 account_id_16 = base::UTF8ToUTF16(state.info.account_id); - ListPrefUpdate update(signin_client_->GetPrefs(), kAccountInfoPref); + ListPrefUpdate update(pref_service_, kAccountInfoPref); for (size_t i = 0; i < update->GetSize(); ++i, dict = nullptr) { if (update->GetDictionary(i, &dict)) { base::string16 value; @@ -576,11 +572,11 @@ } void AccountTrackerService::RemoveFromPrefs(const AccountState& state) { - if (!signin_client_->GetPrefs()) + if (!pref_service_) return; base::string16 account_id_16 = base::UTF8ToUTF16(state.info.account_id); - ListPrefUpdate update(signin_client_->GetPrefs(), kAccountInfoPref); + ListPrefUpdate update(pref_service_, kAccountInfoPref); for(size_t i = 0; i < update->GetSize(); ++i) { base::DictionaryValue* dict = nullptr; if (update->GetDictionary(i, &dict)) { @@ -596,7 +592,7 @@ std::string AccountTrackerService::PickAccountIdForAccount( const std::string& gaia, const std::string& email) const { - return PickAccountIdForAccount(signin_client_->GetPrefs(), gaia, email); + return PickAccountIdForAccount(pref_service_, gaia, email); } // static
diff --git a/components/signin/core/browser/account_tracker_service.h b/components/signin/core/browser/account_tracker_service.h index c5dc4eea..739583dda 100644 --- a/components/signin/core/browser/account_tracker_service.h +++ b/components/signin/core/browser/account_tracker_service.h
@@ -22,7 +22,6 @@ #include "ui/gfx/image/image.h" class PrefService; -class SigninClient; namespace base { class DictionaryValue; @@ -89,13 +88,10 @@ void AddObserver(Observer* observer); void RemoveObserver(Observer* observer); - // Take a SigninClient rather than a PrefService and a URLRequestContextGetter - // since RequestContext cannot be created at startup. - // (see http://crbug.com/171406) - // If |user_data_dir| is empty, images will not be saved to or loaded from - // disk. - void Initialize(SigninClient* signin_client, - const base::FilePath& user_data_dir = base::FilePath()); + // Initializes the list of accounts from |pref_service| and load images from + // |user_data_dir|. If |user_data_dir| is empty, images will not be saved to + // nor loaded from disk. + void Initialize(PrefService* pref_service, base::FilePath user_data_dir); // Returns the list of known accounts and for which gaia IDs // have been fetched. @@ -186,7 +182,7 @@ void MigrateToGaiaId(); void SetMigrationState(AccountIdMigrationState state); - SigninClient* signin_client_; // Not owned. + PrefService* pref_service_ = nullptr; // Not owned. std::map<std::string, AccountState> accounts_; base::ObserverList<Observer>::Unchecked observer_list_;
diff --git a/components/signin/core/browser/account_tracker_service_unittest.cc b/components/signin/core/browser/account_tracker_service_unittest.cc index e1b623ff..fd4bc591 100644 --- a/components/signin/core/browser/account_tracker_service_unittest.cc +++ b/components/signin/core/browser/account_tracker_service_unittest.cc
@@ -295,7 +295,7 @@ signin_client_.reset(new TestSigninClient(&pref_service_)); account_tracker_.reset(new AccountTrackerService()); - account_tracker_->Initialize(signin_client_.get()); + account_tracker_->Initialize(&pref_service_, base::FilePath()); account_fetcher_.reset(new AccountFetcherService()); account_fetcher_->Initialize( @@ -354,6 +354,7 @@ return fake_oauth2_token_service_.get(); } SigninClient* signin_client() { return signin_client_.get(); } + PrefService* prefs() { return &pref_service_; } network::TestURLLoaderFactory* test_url_loader_factory() { return signin_client_->test_url_loader_factory(); @@ -520,7 +521,7 @@ AccountFetcherService fetcher; tracker.AddObserver(&observer); - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -602,7 +603,7 @@ // Create an account tracker and an account fetcher service but do not enable // network fetches. AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher_service; fetcher_service.Initialize(signin_client(), token_service(), &tracker, @@ -669,7 +670,7 @@ // to be saved to persistence. { AccountTrackerService tracker; - tracker.Initialize(signin_client(), scoped_user_data_dir.GetPath()); + tracker.Initialize(prefs(), scoped_user_data_dir.GetPath()); SimulateTokenAvailable("alpha"); ReturnAccountInfoFetchSuccess("alpha"); ReturnAccountImageFetchSuccess("alpha"); @@ -685,7 +686,7 @@ AccountTrackerService tracker; AccountTrackerObserver observer; tracker.AddObserver(&observer); - tracker.Initialize(signin_client(), scoped_user_data_dir.GetPath()); + tracker.Initialize(prefs(), scoped_user_data_dir.GetPath()); ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "alpha"), TrackingEvent(UPDATED, "beta"))); // Wait until all account images are loaded. @@ -726,7 +727,7 @@ // persistence. Also verify it is a child account. { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); std::vector<AccountInfo> infos = tracker.GetAccounts(); ASSERT_EQ(1u, infos.size()); @@ -807,7 +808,7 @@ // prefs. { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -820,7 +821,7 @@ { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -849,7 +850,7 @@ AccountTrackerService tracker; AccountTrackerObserver observer; tracker.AddObserver(&observer); - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -876,7 +877,7 @@ // prefs. { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -900,7 +901,7 @@ // and that no network fetches happen. { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -927,7 +928,7 @@ // are still valid, the network fetches are started. { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -951,7 +952,7 @@ // a correct non-dotted account id for the same account. { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -972,7 +973,7 @@ // it is the correct non dotted one. { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); AccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -1017,9 +1018,7 @@ dict->SetString("gaia", base::UTF8ToUTF16(gaia_beta)); update->Append(std::move(dict)); - std::unique_ptr<TestSigninClient> client; - client.reset(new TestSigninClient(&pref)); - tracker.Initialize(client.get()); + tracker.Initialize(&pref, base::FilePath()); ASSERT_EQ(tracker.GetMigrationState(), AccountTrackerService::MIGRATION_IN_PROGRESS); @@ -1069,9 +1068,7 @@ dict->SetString("gaia", base::UTF8ToUTF16(std::string())); update->Append(std::move(dict)); - std::unique_ptr<TestSigninClient> client; - client.reset(new TestSigninClient(&pref)); - tracker.Initialize(client.get()); + tracker.Initialize(&pref, base::FilePath()); ASSERT_EQ(tracker.GetMigrationState(), AccountTrackerService::MIGRATION_NOT_STARTED); @@ -1128,9 +1125,7 @@ dict->SetString("gaia", base::UTF8ToUTF16(gaia_alpha)); update->Append(std::move(dict)); - std::unique_ptr<TestSigninClient> client; - client.reset(new TestSigninClient(&pref)); - tracker.Initialize(client.get()); + tracker.Initialize(&pref, base::FilePath()); ASSERT_EQ(tracker.GetMigrationState(), AccountTrackerService::MIGRATION_IN_PROGRESS); @@ -1150,7 +1145,7 @@ tracker.SetMigrationDone(); tracker.Shutdown(); - tracker.Initialize(client.get()); + tracker.Initialize(&pref, base::FilePath()); ASSERT_EQ(tracker.GetMigrationState(), AccountTrackerService::MIGRATION_DONE); @@ -1173,7 +1168,7 @@ TEST_F(AccountTrackerServiceTest, ChildAccountBasic) { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); FakeAccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -1203,7 +1198,7 @@ TEST_F(AccountTrackerServiceTest, ChildAccountUpdatedAndRevoked) { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); FakeAccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -1233,7 +1228,7 @@ TEST_F(AccountTrackerServiceTest, ChildAccountUpdatedAndRevokedWithUpdate) { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); FakeAccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -1269,7 +1264,7 @@ TEST_F(AccountTrackerServiceTest, ChildAccountUpdatedTwiceThenRevoked) { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); FakeAccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -1307,7 +1302,7 @@ TEST_F(AccountTrackerServiceTest, ChildAccountGraduation) { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); FakeAccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>()); @@ -1366,7 +1361,7 @@ #if !defined(OS_ANDROID) && !defined(OS_CHROMEOS) && !defined(OS_IOS) TEST_F(AccountTrackerServiceTest, AdvancedProtectionAccountBasic) { AccountTrackerService tracker; - tracker.Initialize(signin_client()); + tracker.Initialize(prefs(), base::FilePath()); FakeAccountFetcherService fetcher; fetcher.Initialize(signin_client(), token_service(), &tracker, std::make_unique<TestImageDecoder>());
diff --git a/components/signin/core/browser/signin_manager_unittest.cc b/components/signin/core/browser/signin_manager_unittest.cc index e9daf4e4..e84be48d 100644 --- a/components/signin/core/browser/signin_manager_unittest.cc +++ b/components/signin/core/browser/signin_manager_unittest.cc
@@ -90,7 +90,7 @@ AccountTrackerService::RegisterPrefs(user_prefs_.registry()); SigninManagerBase::RegisterProfilePrefs(user_prefs_.registry()); SigninManagerBase::RegisterPrefs(local_state_.registry()); - account_tracker_.Initialize(&test_signin_client_); + account_tracker_.Initialize(&user_prefs_, base::FilePath()); account_fetcher_.Initialize(&test_signin_client_, &token_service_, &account_tracker_, std::make_unique<TestImageDecoder>()); @@ -112,6 +112,7 @@ AccountTrackerService* account_tracker() { return &account_tracker_; } FakeAccountFetcherService* account_fetcher() { return &account_fetcher_; } + PrefService* prefs() { return &user_prefs_; } // Seed the account tracker with information from logged in user. Normally // this is done by UI code before calling SigninManager. Returns the string @@ -513,7 +514,7 @@ update->Append(std::move(dict)); account_tracker()->Shutdown(); - account_tracker()->Initialize(signin_client()); + account_tracker()->Initialize(prefs(), base::FilePath()); client_prefs->SetString(prefs::kGoogleServicesAccountId, email); @@ -543,7 +544,7 @@ update->Append(std::move(dict)); account_tracker()->Shutdown(); - account_tracker()->Initialize(signin_client()); + account_tracker()->Initialize(prefs(), base::FilePath()); client_prefs->ClearPref(prefs::kGoogleServicesAccountId); client_prefs->SetString(prefs::kGoogleServicesUsername, email); @@ -573,7 +574,7 @@ update->Append(std::move(dict)); account_tracker()->Shutdown(); - account_tracker()->Initialize(signin_client()); + account_tracker()->Initialize(prefs(), base::FilePath()); client_prefs->SetString(prefs::kGoogleServicesAccountId, gaia_id);
diff --git a/components/signin/ios/browser/account_consistency_service_unittest.mm b/components/signin/ios/browser/account_consistency_service_unittest.mm index 2d37318..ab90643 100644 --- a/components/signin/ios/browser/account_consistency_service_unittest.mm +++ b/components/signin/ios/browser/account_consistency_service_unittest.mm
@@ -149,7 +149,7 @@ web_view_load_expection_count_ = 0; gaia_cookie_manager_service_.reset(new MockGaiaCookieManagerService()); signin_client_.reset(new TestSigninClient(&prefs_)); - account_tracker_service_.Initialize(signin_client_.get()); + account_tracker_service_.Initialize(&prefs_, base::FilePath()); signin_manager_.reset(new FakeSigninManager( signin_client_.get(), nullptr, &account_tracker_service_, nullptr)); signin_manager_->Initialize(nullptr);
diff --git a/components/signin/ios/browser/profile_oauth2_token_service_ios_delegate_unittest.mm b/components/signin/ios/browser/profile_oauth2_token_service_ios_delegate_unittest.mm index f36924c..83f1ee4 100644 --- a/components/signin/ios/browser/profile_oauth2_token_service_ios_delegate_unittest.mm +++ b/components/signin/ios/browser/profile_oauth2_token_service_ios_delegate_unittest.mm
@@ -53,7 +53,7 @@ prefs_.registry()->RegisterIntegerPref( prefs::kAccountIdMigrationState, AccountTrackerService::MIGRATION_NOT_STARTED); - account_tracker_.Initialize(&client_); + account_tracker_.Initialize(&prefs_, base::FilePath()); prefs_.registry()->RegisterBooleanPref( prefs::kTokenServiceExcludeAllSecondaryAccounts, false);
diff --git a/components/sync/test/fake_server/fake_server.cc b/components/sync/test/fake_server/fake_server.cc index 944d7f69..1523e2b8 100644 --- a/components/sync/test/fake_server/fake_server.cc +++ b/components/sync/test/fake_server/fake_server.cc
@@ -10,6 +10,7 @@ #include <utility> #include "base/guid.h" +#include "base/hash.h" #include "base/logging.h" #include "base/stl_util.h" #include "base/strings/string_number_conversions.h" @@ -49,6 +50,70 @@ FakeServer::~FakeServer() {} +namespace { + +std::unique_ptr<sync_pb::DataTypeProgressMarker> RemoveWalletProgressMarker( + sync_pb::ClientToServerMessage* message) { + google::protobuf::RepeatedPtrField<sync_pb::DataTypeProgressMarker>* + progress_markers = + message->mutable_get_updates()->mutable_from_progress_marker(); + for (int index = 0; index < progress_markers->size(); ++index) { + if (syncer::GetModelTypeFromSpecificsFieldNumber( + progress_markers->Get(index).data_type_id()) == + syncer::AUTOFILL_WALLET_DATA) { + auto result = std::make_unique<sync_pb::DataTypeProgressMarker>( + progress_markers->Get(index)); + progress_markers->erase(progress_markers->begin() + index); + return result; + } + } + return nullptr; +} + +sync_pb::DataTypeProgressMarker* GetMutableWalletDataProgressMarker( + sync_pb::GetUpdatesResponse* gu_response) { + for (sync_pb::DataTypeProgressMarker& marker : + *gu_response->mutable_new_progress_marker()) { + if (syncer::GetModelTypeFromSpecificsFieldNumber(marker.data_type_id()) == + syncer::AUTOFILL_WALLET_DATA) { + return ▮ + } + } + auto* new_marker = gu_response->add_new_progress_marker(); + new_marker->set_data_type_id( + GetSpecificsFieldNumberFromModelType(syncer::AUTOFILL_WALLET_DATA)); + return new_marker; +} + +void PopulateWalletResults(const std::vector<sync_pb::SyncEntity>& entities, + sync_pb::GetUpdatesResponse* gu_response) { + int64_t version = + (base::Time::Now() - base::Time::UnixEpoch()).InMilliseconds(); + for (const auto& entity : entities) { + sync_pb::SyncEntity* response_entity = gu_response->add_entries(); + *response_entity = entity; + response_entity->set_version(version); + } + sync_pb::DataTypeProgressMarker* response_marker = + GetMutableWalletDataProgressMarker(gu_response); + // Make sure to pick a token that will be consistent across clients when + // receiving the same data. We sum up the hashes which has the nice side + // effect of being independent of the order. + int64_t token = 0; + for (const auto& entity : entities) { + // PersistentHash returns 32-bit integers, so summing them up is defined + // behavior. + token += base::PersistentHash(entity.id_string()); + } + response_marker->set_token(base::Int64ToString(token)); + // Set the GC directive to implement non-incremental reads. + response_marker->mutable_gc_directive()->set_type( + sync_pb::GarbageCollectionDirective::VERSION_WATERMARK); + response_marker->mutable_gc_directive()->set_version_watermark(version - 1); +} + +} // namespace + void FakeServer::HandleCommand(const std::string& request, const base::Closure& completion_closure, int* error_code, @@ -98,8 +163,22 @@ break; // Don't care. } - *response_code = SendToLoopbackServer(request, response); + // The loopback server does not know how to handle Wallet requests -- and + // should not. The FakeServer is handling those instead. The loopback server + // has a strong expectations about how progress tokens are structured. To + // not interfere with this, we remove wallet progress markers before passing + // the request to the loopback server and add them back again afterwards + // before handling those requests. + std::unique_ptr<sync_pb::DataTypeProgressMarker> wallet_marker = + RemoveWalletProgressMarker(&message); + *response_code = + SendToLoopbackServer(message.SerializeAsString(), response); + if (wallet_marker != nullptr) { + *message.mutable_get_updates()->add_from_progress_marker() = + *wallet_marker; + } if (*response_code == net::HTTP_OK) { + HandleWalletRequest(message, wallet_marker.get(), response); InjectClientCommand(response); } completion_closure.Run(); @@ -111,6 +190,21 @@ completion_closure.Run(); } +void FakeServer::HandleWalletRequest( + const sync_pb::ClientToServerMessage& request, + sync_pb::DataTypeProgressMarker* wallet_marker, + std::string* response_string) { + if (request.message_contents() != + sync_pb::ClientToServerMessage::GET_UPDATES || + wallet_marker == nullptr) { + return; + } + sync_pb::ClientToServerResponse response_proto; + CHECK(response_proto.ParseFromString(*response_string)); + PopulateWalletResults(wallet_entities_, response_proto.mutable_get_updates()); + *response_string = response_proto.SerializeAsString(); +} + int FakeServer::SendToLoopbackServer(const std::string& request, std::string* response) { int64_t response_code; @@ -167,9 +261,23 @@ void FakeServer::InjectEntity(std::unique_ptr<LoopbackServerEntity> entity) { DCHECK(thread_checker_.CalledOnValidThread()); + DCHECK(entity->GetModelType() != syncer::AUTOFILL_WALLET_DATA) + << "Wallet data must be injected via SetWalletData()"; loopback_server_->SaveEntity(std::move(entity)); } +void FakeServer::SetWalletData( + const std::vector<sync_pb::SyncEntity>& wallet_entities) { + for (const auto& entity : wallet_entities) { + DCHECK_EQ(GetModelTypeFromSpecifics(entity.specifics()), + syncer::AUTOFILL_WALLET_DATA); + DCHECK(!entity.has_client_defined_unique_tag()) + << "The sync server doesn not provide a client tag for wallet entries"; + DCHECK(!entity.id_string().empty()) << "server id required!"; + } + wallet_entities_ = wallet_entities; +} + bool FakeServer::ModifyEntitySpecifics( const std::string& id, const sync_pb::EntitySpecifics& updated_specifics) {
diff --git a/components/sync/test/fake_server/fake_server.h b/components/sync/test/fake_server/fake_server.h index ab740d9d..1fe144cc 100644 --- a/components/sync/test/fake_server/fake_server.h +++ b/components/sync/test/fake_server/fake_server.h
@@ -80,6 +80,10 @@ // operations. void InjectEntity(std::unique_ptr<syncer::LoopbackServerEntity> entity); + // Sets the Wallet card and address data to be served in following GetUpdates + // requests. + void SetWalletData(const std::vector<sync_pb::SyncEntity>& wallet_entities); + // Modifies the entity on the server with the given |id|. The entity's // EntitySpecifics are replaced with |updated_specifics| and its version is // updated. If the given |id| does not exist or the ModelType of @@ -170,6 +174,9 @@ bool ShouldSendTriggeredError() const; int SendToLoopbackServer(const std::string& request, std::string* response); void InjectClientCommand(std::string* response); + void HandleWalletRequest(const sync_pb::ClientToServerMessage& request, + sync_pb::DataTypeProgressMarker* wallet_marker, + std::string* response_string); // Whether the server should act as if incoming connections are properly // authenticated. @@ -217,6 +224,10 @@ std::unique_ptr<syncer::LoopbackServer> loopback_server_; std::unique_ptr<base::ScopedTempDir> loopback_server_storage_; + // The LoopbackServer does not know how to handle Wallet data properly, so + // the FakeServer handles those itself. + std::vector<sync_pb::SyncEntity> wallet_entities_; + // Creates WeakPtr versions of the current FakeServer. This must be the last // data member! base::WeakPtrFactory<FakeServer> weak_ptr_factory_;
diff --git a/components/translate/core/browser/resources/translate.js b/components/translate/core/browser/resources/translate.js index b2ece17..5b5ce6b4 100644 --- a/components/translate/core/browser/resources/translate.js +++ b/components/translate/core/browser/resources/translate.js
@@ -152,6 +152,8 @@ function invokeReadyCallback() { if (readyCallback) { readyCallback(); + // Don't notify ready if already notified. + readyCallback = null; } }
diff --git a/components/variations/service/variations_service.cc b/components/variations/service/variations_service.cc index 96705263..369b12ac 100644 --- a/components/variations/service/variations_service.cc +++ b/components/variations/service/variations_service.cc
@@ -419,15 +419,12 @@ PrefService* local_state, metrics::MetricsStateManager* state_manager, const char* disable_network_switch, - const UIStringOverrider& ui_string_overrider, - web_resource::ResourceRequestAllowedNotifier::NetworkConnectionTrackerGetter - network_connection_tracker_getter) { + const UIStringOverrider& ui_string_overrider) { std::unique_ptr<VariationsService> result; result.reset(new VariationsService( std::move(client), std::make_unique<web_resource::ResourceRequestAllowedNotifier>( - local_state, disable_network_switch, - std::move(network_connection_tracker_getter)), + local_state, disable_network_switch), local_state, state_manager, ui_string_overrider)); return result; } @@ -481,7 +478,8 @@ // ResourceRequestAllowedNotifier does not install an observer if there is no // NetworkChangeNotifier, which results in never being notified of changes to // network status. - resource_request_allowed_notifier_->Init(this, false /* leaky */); + DCHECK(net::NetworkChangeNotifier::HasNetworkChangeNotifier()); + resource_request_allowed_notifier_->Init(this); } bool VariationsService::DoFetchFromURL(const GURL& url, bool is_http_retry) {
diff --git a/components/variations/service/variations_service.h b/components/variations/service/variations_service.h index f754c45..cb9ada3 100644 --- a/components/variations/service/variations_service.h +++ b/components/variations/service/variations_service.h
@@ -147,9 +147,7 @@ PrefService* local_state, metrics::MetricsStateManager* state_manager, const char* disable_network_switch, - const UIStringOverrider& ui_string_overrider, - web_resource::ResourceRequestAllowedNotifier:: - NetworkConnectionTrackerGetter network_connection_tracker_getter); + const UIStringOverrider& ui_string_overrider); // Enables fetching the seed for testing, even for unofficial builds. This // should be used along with overriding |DoActualFetch| or using
diff --git a/components/variations/service/variations_service_unittest.cc b/components/variations/service/variations_service_unittest.cc index 5826d50..2c10125 100644 --- a/components/variations/service/variations_service_unittest.cc +++ b/components/variations/service/variations_service_unittest.cc
@@ -42,7 +42,6 @@ #include "net/url_request/test_url_fetcher_factory.h" #include "services/network/public/cpp/shared_url_loader_factory.h" #include "services/network/public/cpp/weak_wrapper_shared_url_loader_factory.h" -#include "services/network/test/test_network_connection_tracker.h" #include "services/network/test/test_url_loader_factory.h" #include "testing/gtest/include/gtest/gtest.h" @@ -280,9 +279,7 @@ class VariationsServiceTest : public ::testing::Test { protected: VariationsServiceTest() - : network_tracker_(true, - network::mojom::ConnectionType::CONNECTION_UNKNOWN), - enabled_state_provider_( + : enabled_state_provider_( new metrics::TestEnabledStateProvider(false, false)) { VariationsService::RegisterPrefs(prefs_.registry()); metrics::CleanExitBeacon::RegisterPrefs(prefs_.registry()); @@ -302,7 +299,6 @@ protected: TestingPrefServiceSimple prefs_; - network::TestNetworkConnectionTracker network_tracker_; private: base::test::ScopedTaskEnvironment scoped_task_environment_; @@ -322,8 +318,7 @@ TestVariationsServiceClient* raw_client = client.get(); VariationsService service( std::move(client), - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), UIStringOverrider()); GURL url = service.GetVariationsServerURL(&prefs_, std::string(), TestVariationsService::USE_HTTPS); @@ -364,8 +359,7 @@ TestVariationsServiceClient* raw_client = client.get(); VariationsService service( std::move(client), - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), UIStringOverrider()); raw_client->set_channel(version_info::Channel::UNKNOWN); GURL url = service.GetVariationsServerURL(&prefs_, std::string(), @@ -396,8 +390,7 @@ // Pass ownership to TestVariationsService, but keep a weak pointer to // manipulate it for this test. std::unique_ptr<web_resource::TestRequestAllowedNotifier> test_notifier = - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_); + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_); web_resource::TestRequestAllowedNotifier* raw_notifier = test_notifier.get(); TestVariationsService test_service(std::move(test_notifier), &prefs_, GetMetricsStateManager(), true); @@ -416,8 +409,7 @@ // Pass ownership to TestVariationsService, but keep a weak pointer to // manipulate it for this test. std::unique_ptr<web_resource::TestRequestAllowedNotifier> test_notifier = - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_); + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_); web_resource::TestRequestAllowedNotifier* raw_notifier = test_notifier.get(); TestVariationsService test_service(std::move(test_notifier), &prefs_, GetMetricsStateManager(), true); @@ -431,8 +423,7 @@ VariationsService::EnableFetchForTesting(); TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); EXPECT_FALSE(service.seed_stored()); @@ -455,8 +446,7 @@ VariationsService::EnableFetchForTesting(); TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); service.set_intercepts_fetch(false); for (size_t i = 0; i < arraysize(non_ok_status_codes); ++i) { @@ -476,8 +466,7 @@ VariationsService::EnableFetchForTesting(); TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); service.set_intercepts_fetch(false); net::HttpRequestHeaders intercepted_headers; @@ -514,8 +503,7 @@ VariationsService::EnableFetchForTesting(); for (size_t i = 0; i < arraysize(cases); ++i) { TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); service.set_intercepts_fetch(false); @@ -543,8 +531,7 @@ VariationsService::EnableFetchForTesting(); TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); EXPECT_FALSE(service.seed_stored()); service.set_intercepts_fetch(false); @@ -568,8 +555,7 @@ TEST_F(VariationsServiceTest, Observer) { VariationsService service( std::make_unique<TestVariationsServiceClient>(), - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), UIStringOverrider()); struct { @@ -667,8 +653,7 @@ for (const auto& test : test_cases) { VariationsService service( std::make_unique<TestVariationsServiceClient>(), - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), UIStringOverrider()); if (!test.pref_value_before) { @@ -739,8 +724,7 @@ for (const auto& test : test_cases) { TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); if (test.pref_value_before.empty()) { @@ -782,8 +766,7 @@ // Create a variations service and start the fetch. TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); service.set_intercepts_fetch(false); service.DoActualFetch(); @@ -801,8 +784,7 @@ // Create a variations service and perform a successful fetch. TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); service.set_intercepts_fetch(false); @@ -848,8 +830,7 @@ // Create a variations service and perform a successful fetch. TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); service.set_intercepts_fetch(false); @@ -869,8 +850,7 @@ TEST_F(VariationsServiceTest, FieldTrialCreatorInitializedCorrectly) { TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); // Call will crash in service's VariationsFieldTrialCreator if not initialized @@ -882,8 +862,7 @@ std::string serialized_seed = SerializeSeed(CreateTestSeed()); VariationsService::EnableFetchForTesting(); TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), false); service.set_intercepts_fetch(false); service.test_url_loader_factory()->AddResponse( @@ -895,8 +874,7 @@ TEST_F(VariationsServiceTest, InsecurelyFetchedNotSetWhenHTTPS) { std::string serialized_seed = SerializeSeed(CreateTestSeed()); TestVariationsService service( - std::make_unique<web_resource::TestRequestAllowedNotifier>( - &prefs_, &network_tracker_), + std::make_unique<web_resource::TestRequestAllowedNotifier>(&prefs_), &prefs_, GetMetricsStateManager(), true); VariationsService::EnableFetchForTesting(); service.set_intercepts_fetch(false);
diff --git a/components/viz/host/hit_test/hit_test_query.cc b/components/viz/host/hit_test/hit_test_query.cc index a6128d3e..2d5a6170 100644 --- a/components/viz/host/hit_test/hit_test_query.cc +++ b/components/viz/host/hit_test/hit_test_query.cc
@@ -110,6 +110,17 @@ uint32_t region_index, Target* target) const { gfx::PointF location_transformed(location_in_parent); + + // HasPerspective() is checked for the transform because the point will not + // be transformed correctly for a plane with a different normal. + // See https://crbug.com/854247. + if (hit_test_data_[region_index].transform().HasPerspective()) { + target->frame_sink_id = hit_test_data_[region_index].frame_sink_id; + target->location_in_target = gfx::PointF(); + target->flags = HitTestRegionFlags::kHitTestAsk; + return true; + } + hit_test_data_[region_index].transform().TransformPoint( &location_transformed); if (!gfx::RectF(hit_test_data_[region_index].rect)
diff --git a/components/viz/service/surfaces/surface_hittest.cc b/components/viz/service/surfaces/surface_hittest.cc index 83d6b0b..6b630def 100644 --- a/components/viz/service/surfaces/surface_hittest.cc +++ b/components/viz/service/surfaces/surface_hittest.cc
@@ -108,12 +108,17 @@ // The |transform_to_root_target| matrix may have no back-projection if the // forward projection is degenerate. + // HasPerspective() is checked for the transform because the point will not + // be transformed correctly for a plane with a different normal. + // See https://crbug.com/854247. gfx::Transform transform_from_root_target; gfx::Transform transform_to_root_target = render_pass->transform_to_root_target; transform_to_root_target.FlattenTo2d(); - if (!transform_to_root_target.GetInverse(&transform_from_root_target)) { - return false; + if (transform_to_root_target.HasPerspective() || + !transform_to_root_target.GetInverse(&transform_from_root_target)) { + *out_query_renderer = true; + return true; } gfx::Point point_in_render_pass_space(point_in_root_target); @@ -125,6 +130,10 @@ gfx::Point point_in_quad_space; if (!PointInQuad(quad, point_in_render_pass_space, &target_to_quad_transform, &point_in_quad_space)) { + if (target_to_quad_transform.HasPerspective()) { + *out_query_renderer = true; + return false; + } continue; } @@ -335,7 +344,8 @@ // rect. gfx::Transform transform = quad->shared_quad_state->quad_to_target_transform; transform.FlattenTo2d(); - if (!transform.GetInverse(target_to_quad_transform)) { + if (!transform.GetInverse(target_to_quad_transform) || + target_to_quad_transform->HasPerspective()) { return false; }
diff --git a/components/web_resource/BUILD.gn b/components/web_resource/BUILD.gn index 6771f91..74863cc 100644 --- a/components/web_resource/BUILD.gn +++ b/components/web_resource/BUILD.gn
@@ -36,7 +36,6 @@ deps = [ ":web_resource", "//base", - "//services/network/public/cpp", ] }
diff --git a/components/web_resource/resource_request_allowed_notifier.cc b/components/web_resource/resource_request_allowed_notifier.cc index d7c0714..34d7bc7 100644 --- a/components/web_resource/resource_request_allowed_notifier.cc +++ b/components/web_resource/resource_request_allowed_notifier.cc
@@ -10,39 +10,25 @@ ResourceRequestAllowedNotifier::ResourceRequestAllowedNotifier( PrefService* local_state, - const char* disable_network_switch, - NetworkConnectionTrackerGetter network_connection_tracker_getter) + const char* disable_network_switch) : disable_network_switch_(disable_network_switch), local_state_(local_state), observer_requested_permission_(false), waiting_for_user_to_accept_eula_(false), - observer_(nullptr), - network_connection_tracker_getter_( - std::move(network_connection_tracker_getter)), - weak_factory_(this) {} + observer_(nullptr) { +} ResourceRequestAllowedNotifier::~ResourceRequestAllowedNotifier() { if (observer_) - network_connection_tracker_->RemoveNetworkConnectionObserver(this); + net::NetworkChangeNotifier::RemoveNetworkChangeObserver(this); } -void ResourceRequestAllowedNotifier::Init(Observer* observer, bool leaky) { +void ResourceRequestAllowedNotifier::Init(Observer* observer) { DCHECK(!observer_); DCHECK(observer); observer_ = observer; - DCHECK(network_connection_tracker_getter_); - network_connection_tracker_ = - std::move(network_connection_tracker_getter_).Run(); - - if (leaky) - network_connection_tracker_->AddLeakyNetworkConnectionObserver(this); - else - network_connection_tracker_->AddNetworkConnectionObserver(this); - network_connection_tracker_->GetConnectionType( - &connection_type_, - base::BindOnce(&ResourceRequestAllowedNotifier::SetConnectionType, - weak_factory_.GetWeakPtr())); + net::NetworkChangeNotifier::AddNetworkChangeObserver(this); eula_notifier_.reset(CreateEulaNotifier()); if (eula_notifier_) { @@ -62,10 +48,8 @@ // The observer requested permission. Return the current criteria state and // set a flag to remind this class to notify the observer once the criteria // is met. - observer_requested_permission_ = - waiting_for_user_to_accept_eula_ || - connection_type_ == network::mojom::ConnectionType::CONNECTION_NONE || - !connection_initialized_; + observer_requested_permission_ = waiting_for_user_to_accept_eula_ || + net::NetworkChangeNotifier::IsOffline(); if (!observer_requested_permission_) return ALLOWED; return waiting_for_user_to_accept_eula_ ? DISALLOWED_EULA_NOT_ACCEPTED : @@ -85,11 +69,6 @@ observer_requested_permission_ = requested; } -void ResourceRequestAllowedNotifier::SetConnectionTypeForTesting( - network::mojom::ConnectionType type) { - SetConnectionType(type); -} - void ResourceRequestAllowedNotifier::MaybeNotifyObserver() { // Need to ensure that all criteria are met before notifying observers. if (observer_requested_permission_ && ResourceRequestsAllowed()) { @@ -114,10 +93,9 @@ MaybeNotifyObserver(); } -void ResourceRequestAllowedNotifier::OnConnectionChanged( - network::mojom::ConnectionType type) { - SetConnectionType(type); - if (type != network::mojom::ConnectionType::CONNECTION_NONE) { +void ResourceRequestAllowedNotifier::OnNetworkChanged( + net::NetworkChangeNotifier::ConnectionType type) { + if (type != net::NetworkChangeNotifier::CONNECTION_NONE) { DVLOG(1) << "Network came online."; // MaybeNotifyObserver() internally guarantees that it will only notify the // observer if it's currently waiting for the network to come online. @@ -125,10 +103,4 @@ } } -void ResourceRequestAllowedNotifier::SetConnectionType( - network::mojom::ConnectionType connection_type) { - connection_initialized_ = true; - connection_type_ = connection_type; -} - } // namespace web_resource
diff --git a/components/web_resource/resource_request_allowed_notifier.h b/components/web_resource/resource_request_allowed_notifier.h index f792dfa..695f60482 100644 --- a/components/web_resource/resource_request_allowed_notifier.h +++ b/components/web_resource/resource_request_allowed_notifier.h
@@ -9,7 +9,7 @@ #include "base/macros.h" #include "components/web_resource/eula_accepted_notifier.h" -#include "services/network/public/cpp/network_connection_tracker.h" +#include "net/base/network_change_notifier.h" class PrefService; @@ -37,7 +37,7 @@ // global instance. class ResourceRequestAllowedNotifier : public EulaAcceptedNotifier::Observer, - public network::NetworkConnectionTracker::NetworkConnectionObserver { + public net::NetworkChangeNotifier::NetworkChangeObserver { public: // Observes resource request allowed state changes. class Observer { @@ -54,26 +54,20 @@ DISALLOWED_COMMAND_LINE_DISABLED, }; - using NetworkConnectionTrackerGetter = - base::OnceCallback<network::NetworkConnectionTracker*()>; - // Creates a new ResourceRequestAllowedNotifier. // |local_state| is the PrefService to observe. // |disable_network_switch| is the command line switch to disable network // activity. It is expected to outlive the ResourceRequestAllowedNotifier and // may be null. - ResourceRequestAllowedNotifier( - PrefService* local_state, - const char* disable_network_switch, - NetworkConnectionTrackerGetter network_connection_tracker_getter); + ResourceRequestAllowedNotifier(PrefService* local_state, + const char* disable_network_switch); ~ResourceRequestAllowedNotifier() override; // Sets |observer| as the service to be notified by this instance, and // performs initial checks on the criteria. |observer| may not be null. // This is to be called immediately after construction of an instance of - // ResourceRequestAllowedNotifier to pass it the interested service. Set - // |leaky| to true if this class will not be destructed before shutdown. - void Init(Observer* observer, bool leaky); + // ResourceRequestAllowedNotifier to pass it the interested service. + void Init(Observer* observer); // Returns whether resource requests are allowed, per the various criteria. // If not, this call will set some flags so it knows to notify the observer @@ -88,8 +82,6 @@ void SetWaitingForEulaForTesting(bool waiting); void SetObserverRequestedForTesting(bool requested); - void SetConnectionTypeForTesting( - network::mojom::ConnectionType connection_type); protected: // Notifies the observer if all criteria needed for resource requests are met. @@ -104,10 +96,9 @@ // EulaAcceptedNotifier::Observer overrides: void OnEulaAccepted() override; - // network::NetworkConnectionTracker::NetworkConnectionObserver overrides: - void OnConnectionChanged(network::mojom::ConnectionType type) override; - - void SetConnectionType(network::mojom::ConnectionType connection_type); + // net::NetworkChangeNotifier::NetworkChangeObserver overrides: + void OnNetworkChanged( + net::NetworkChangeNotifier::ConnectionType type) override; // Name of the command line switch to disable the network activity. const char* disable_network_switch_; @@ -129,14 +120,6 @@ // Observing service interested in request permissions. Observer* observer_; - NetworkConnectionTrackerGetter network_connection_tracker_getter_; - network::NetworkConnectionTracker* network_connection_tracker_ = nullptr; - network::mojom::ConnectionType connection_type_ = - network::mojom::ConnectionType::CONNECTION_UNKNOWN; - bool connection_initialized_ = false; - - base::WeakPtrFactory<ResourceRequestAllowedNotifier> weak_factory_; - DISALLOW_COPY_AND_ASSIGN(ResourceRequestAllowedNotifier); };
diff --git a/components/web_resource/resource_request_allowed_notifier_test_util.cc b/components/web_resource/resource_request_allowed_notifier_test_util.cc index 3c12718f..e297452 100644 --- a/components/web_resource/resource_request_allowed_notifier_test_util.cc +++ b/components/web_resource/resource_request_allowed_notifier_test_util.cc
@@ -6,19 +6,11 @@ namespace web_resource { -TestRequestAllowedNotifier::TestRequestAllowedNotifier( - PrefService* local_state, - network::NetworkConnectionTracker* network_connection_tracker) - : ResourceRequestAllowedNotifier( - local_state, - nullptr, - base::BindOnce( - [](network::NetworkConnectionTracker* tracker) { - return tracker; - }, - network_connection_tracker)), +TestRequestAllowedNotifier::TestRequestAllowedNotifier(PrefService* local_state) + : ResourceRequestAllowedNotifier(local_state, nullptr), override_requests_allowed_(false), - requests_allowed_(true) {} + requests_allowed_(true) { +} TestRequestAllowedNotifier::~TestRequestAllowedNotifier() { } @@ -27,7 +19,7 @@ Observer* observer, std::unique_ptr<EulaAcceptedNotifier> eula_notifier) { test_eula_notifier_.swap(eula_notifier); - Init(observer, false /* leaky */); + Init(observer); } void TestRequestAllowedNotifier::SetRequestsAllowedOverride(bool allowed) {
diff --git a/components/web_resource/resource_request_allowed_notifier_test_util.h b/components/web_resource/resource_request_allowed_notifier_test_util.h index 9cd1c143..a9fadf1 100644 --- a/components/web_resource/resource_request_allowed_notifier_test_util.h +++ b/components/web_resource/resource_request_allowed_notifier_test_util.h
@@ -25,9 +25,7 @@ // it to return. class TestRequestAllowedNotifier : public ResourceRequestAllowedNotifier { public: - TestRequestAllowedNotifier( - PrefService* local_state, - network::NetworkConnectionTracker* network_connection_tracker); + explicit TestRequestAllowedNotifier(PrefService* local_state); ~TestRequestAllowedNotifier() override; // A version of |Init()| that accepts a custom EulaAcceptedNotifier.
diff --git a/components/web_resource/resource_request_allowed_notifier_unittest.cc b/components/web_resource/resource_request_allowed_notifier_unittest.cc index 69b41ac..a2b1d58e 100644 --- a/components/web_resource/resource_request_allowed_notifier_unittest.cc +++ b/components/web_resource/resource_request_allowed_notifier_unittest.cc
@@ -9,11 +9,38 @@ #include "components/prefs/testing_pref_service.h" #include "components/web_resource/eula_accepted_notifier.h" #include "components/web_resource/resource_request_allowed_notifier_test_util.h" -#include "services/network/test/test_network_connection_tracker.h" #include "testing/gtest/include/gtest/gtest.h" namespace web_resource { +// Override NetworkChangeNotifier to simulate connection type changes for tests. +class TestNetworkChangeNotifier : public net::NetworkChangeNotifier { + public: + TestNetworkChangeNotifier() + : connection_type_(net::NetworkChangeNotifier::CONNECTION_UNKNOWN) {} + + // Simulates a change of the connection type to |type|. This will notify any + // objects that are NetworkChangeNotifiers. + void SimulateNetworkConnectionChange( + net::NetworkChangeNotifier::ConnectionType type) { + connection_type_ = type; + net::NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests( + connection_type_); + base::RunLoop().RunUntilIdle(); + } + + private: + ConnectionType GetCurrentConnectionType() const override { + return connection_type_; + } + + // The currently simulated network connection type. If this is set to + // CONNECTION_NONE, then NetworkChangeNotifier::IsOffline will return true. + net::NetworkChangeNotifier::ConnectionType connection_type_; + + DISALLOW_COPY_AND_ASSIGN(TestNetworkChangeNotifier); +}; + // EulaAcceptedNotifier test class that allows mocking the EULA accepted state // and issuing simulated notifications. class TestEulaAcceptedNotifier : public EulaAcceptedNotifier { @@ -48,9 +75,7 @@ public ResourceRequestAllowedNotifier::Observer { public: ResourceRequestAllowedNotifierTest() - : network_tracker_(true, - network::mojom::ConnectionType::CONNECTION_UNKNOWN), - resource_request_allowed_notifier_(&prefs_, &network_tracker_), + : resource_request_allowed_notifier_(&prefs_), eula_notifier_(new TestEulaAcceptedNotifier), was_notified_(false) { resource_request_allowed_notifier_.InitWithEulaAcceptNotifier( @@ -63,9 +88,9 @@ // ResourceRequestAllowedNotifier::Observer override: void OnResourceRequestsAllowed() override { was_notified_ = true; } - void SimulateNetworkConnectionChange(network::mojom::ConnectionType type) { - network_tracker_.SetConnectionType(type); - base::RunLoop().RunUntilIdle(); + void SimulateNetworkConnectionChange( + net::NetworkChangeNotifier::ConnectionType type) { + network_notifier.SimulateNetworkConnectionChange(type); } // Simulate a resource request from the test service. It returns true if @@ -92,7 +117,7 @@ // and the network. void DisableEulaAndNetwork() { SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); + net::NetworkChangeNotifier::CONNECTION_NONE); SetWaitingForEula(true); SetNeedsEulaAcceptance(true); } @@ -107,8 +132,8 @@ } private: - base::MessageLoopForUI message_loop_; - network::TestNetworkConnectionTracker network_tracker_; + base::MessageLoopForUI message_loop; + TestNetworkChangeNotifier network_notifier; TestingPrefServiceSimple prefs_; TestRequestAllowedNotifier resource_request_allowed_notifier_; TestEulaAcceptedNotifier* eula_notifier_; // Weak, owned by RRAN. @@ -118,88 +143,71 @@ }; TEST_F(ResourceRequestAllowedNotifierTest, DoNotNotifyIfOffline) { - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_NONE); EXPECT_FALSE(SimulateResourceRequest()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_NONE); EXPECT_FALSE(was_notified()); } TEST_F(ResourceRequestAllowedNotifierTest, DoNotNotifyIfOnlineToOnline) { - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_TRUE(SimulateResourceRequest()); SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_ETHERNET); + net::NetworkChangeNotifier::CONNECTION_ETHERNET); EXPECT_FALSE(was_notified()); } TEST_F(ResourceRequestAllowedNotifierTest, NotifyOnReconnect) { - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_NONE); EXPECT_FALSE(SimulateResourceRequest()); SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_ETHERNET); + net::NetworkChangeNotifier::CONNECTION_ETHERNET); EXPECT_TRUE(was_notified()); } TEST_F(ResourceRequestAllowedNotifierTest, NoNotifyOnWardriving) { - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_TRUE(SimulateResourceRequest()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_3G); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_3G); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_4G); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_4G); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); } TEST_F(ResourceRequestAllowedNotifierTest, NoNotifyOnFlakyConnection) { - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_TRUE(SimulateResourceRequest()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_NONE); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); } TEST_F(ResourceRequestAllowedNotifierTest, NotifyOnFlakyConnection) { // First, the observer queries the state while the network is connected. - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_TRUE(SimulateResourceRequest()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_NONE); EXPECT_FALSE(was_notified()); // Now, the observer queries the state while the network is disconnected. EXPECT_FALSE(SimulateResourceRequest()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_TRUE(was_notified()); } @@ -207,11 +215,9 @@ DisableEulaAndNetwork(); EXPECT_FALSE(SimulateResourceRequest()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_NONE); EXPECT_FALSE(was_notified()); SimulateEulaAccepted(); EXPECT_FALSE(was_notified()); @@ -221,10 +227,9 @@ // Ensure that if the observing service does not request access, it does not // get notified, even if the criteria are met. Note that this is done by not // calling SimulateResourceRequest here. + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_NONE); SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_NONE); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_ETHERNET); + net::NetworkChangeNotifier::CONNECTION_ETHERNET); EXPECT_FALSE(was_notified()); } @@ -243,8 +248,7 @@ SimulateEulaAccepted(); EXPECT_FALSE(was_notified()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_TRUE(was_notified()); } @@ -252,8 +256,7 @@ DisableEulaAndNetwork(); EXPECT_FALSE(SimulateResourceRequest()); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); SimulateEulaAccepted(); @@ -266,8 +269,7 @@ // calling SimulateResourceRequest here. DisableEulaAndNetwork(); - SimulateNetworkConnectionChange( - network::mojom::ConnectionType::CONNECTION_WIFI); + SimulateNetworkConnectionChange(net::NetworkChangeNotifier::CONNECTION_WIFI); EXPECT_FALSE(was_notified()); SimulateEulaAccepted();
diff --git a/components/web_resource/web_resource_service.cc b/components/web_resource/web_resource_service.cc index c72c341..5680024 100644 --- a/components/web_resource/web_resource_service.cc +++ b/components/web_resource/web_resource_service.cc
@@ -44,14 +44,10 @@ scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, const char* disable_network_switch, const ParseJSONCallback& parse_json_callback, - const net::NetworkTrafficAnnotationTag& traffic_annotation, - ResourceRequestAllowedNotifier::NetworkConnectionTrackerGetter - network_connection_tracker_getter) + const net::NetworkTrafficAnnotationTag& traffic_annotation) : prefs_(prefs), - resource_request_allowed_notifier_(new ResourceRequestAllowedNotifier( - prefs, - disable_network_switch, - std::move(network_connection_tracker_getter))), + resource_request_allowed_notifier_( + new ResourceRequestAllowedNotifier(prefs, disable_network_switch)), fetch_scheduled_(false), in_fetch_(false), web_resource_server_(web_resource_server), @@ -63,7 +59,7 @@ parse_json_callback_(parse_json_callback), traffic_annotation_(traffic_annotation), weak_ptr_factory_(this) { - resource_request_allowed_notifier_->Init(this, false /* leaky */); + resource_request_allowed_notifier_->Init(this); DCHECK(prefs); } @@ -118,7 +114,7 @@ void WebResourceService::SetResourceRequestAllowedNotifier( std::unique_ptr<ResourceRequestAllowedNotifier> notifier) { resource_request_allowed_notifier_ = std::move(notifier); - resource_request_allowed_notifier_->Init(this, false /* leaky */); + resource_request_allowed_notifier_->Init(this); } bool WebResourceService::GetFetchScheduled() const {
diff --git a/components/web_resource/web_resource_service.h b/components/web_resource/web_resource_service.h index ba9d1407..279f793 100644 --- a/components/web_resource/web_resource_service.h +++ b/components/web_resource/web_resource_service.h
@@ -55,9 +55,7 @@ scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, const char* disable_network_switch, const ParseJSONCallback& parse_json_callback, - const net::NetworkTrafficAnnotationTag& traffic_annotation, - ResourceRequestAllowedNotifier::NetworkConnectionTrackerGetter - network_connection_tracker_getter); + const net::NetworkTrafficAnnotationTag& traffic_annotation); ~WebResourceService() override;
diff --git a/components/web_resource/web_resource_service_unittest.cc b/components/web_resource/web_resource_service_unittest.cc index 0250013..b12caae5 100644 --- a/components/web_resource/web_resource_service_unittest.cc +++ b/components/web_resource/web_resource_service_unittest.cc
@@ -15,7 +15,6 @@ #include "net/traffic_annotation/network_traffic_annotation_test_helper.h" #include "services/network/public/cpp/shared_url_loader_factory.h" #include "services/network/public/cpp/weak_wrapper_shared_url_loader_factory.h" -#include "services/network/test/test_network_connection_tracker.h" #include "services/network/test/test_url_loader_factory.h" #include "testing/gtest/include/gtest/gtest.h" @@ -30,18 +29,9 @@ class TestResourceRequestAllowedNotifier : public ResourceRequestAllowedNotifier { public: - TestResourceRequestAllowedNotifier( - PrefService* prefs, - const char* disable_network_switch, - network::NetworkConnectionTracker* network_connection_tracker) - : ResourceRequestAllowedNotifier( - prefs, - disable_network_switch, - base::BindOnce( - [](network::NetworkConnectionTracker* tracker) { - return tracker; - }, - network_connection_tracker)) {} + TestResourceRequestAllowedNotifier(PrefService* prefs, + const char* disable_network_switch) + : ResourceRequestAllowedNotifier(prefs, disable_network_switch) {} ResourceRequestAllowedNotifier::State GetResourceRequestsAllowedState() override { @@ -71,8 +61,7 @@ int cache_update_delay_ms, scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, const char* disable_network_switch, - const ParseJSONCallback& parse_json_callback, - network::NetworkConnectionTracker* network_connection_tracker) + const ParseJSONCallback& parse_json_callback) : WebResourceService(prefs, web_resource_server, application_locale, @@ -82,21 +71,14 @@ url_loader_factory, disable_network_switch, parse_json_callback, - TRAFFIC_ANNOTATION_FOR_TESTS, - base::BindOnce( - [](network::NetworkConnectionTracker* tracker) { - return tracker; - }, - network_connection_tracker)){}; + TRAFFIC_ANNOTATION_FOR_TESTS){}; void Unpack(const base::DictionaryValue& parsed_json) override {} }; class WebResourceServiceTest : public testing::Test { public: - WebResourceServiceTest() - : network_tracker_(true, - network::mojom::ConnectionType::CONNECTION_UNKNOWN) {} + WebResourceServiceTest() {} void SetUp() override { test_shared_loader_factory_ = @@ -107,12 +89,10 @@ test_web_resource_service_.reset(new TestWebResourceService( local_state_.get(), GURL(kTestUrl), "", kCacheUpdatePath.c_str(), 100, 5000, test_shared_loader_factory_, nullptr, - base::BindRepeating(web_resource::WebResourceServiceTest::Parse), - &network_tracker_)); + base::Bind(web_resource::WebResourceServiceTest::Parse))); error_message_ = ""; TestResourceRequestAllowedNotifier* notifier = - new TestResourceRequestAllowedNotifier(local_state_.get(), nullptr, - &network_tracker_); + new TestResourceRequestAllowedNotifier(local_state_.get(), nullptr); notifier->SetState(ResourceRequestAllowedNotifier::ALLOWED); test_web_resource_service_->SetResourceRequestAllowedNotifier( std::unique_ptr<ResourceRequestAllowedNotifier>(notifier)); @@ -152,7 +132,6 @@ network::TestURLLoaderFactory test_url_loader_factory_; scoped_refptr<network::SharedURLLoaderFactory> test_shared_loader_factory_; std::unique_ptr<TestingPrefServiceSimple> local_state_; - network::TestNetworkConnectionTracker network_tracker_; std::unique_ptr<TestWebResourceService> test_web_resource_service_; };
diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn index 752565f..be7c107 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn
@@ -1008,7 +1008,6 @@ "loader/detachable_resource_handler.h", "loader/download_utils_impl.cc", "loader/download_utils_impl.h", - "loader/global_routing_id.h", "loader/intercepting_resource_handler.cc", "loader/intercepting_resource_handler.h", "loader/layered_resource_handler.cc",
diff --git a/content/browser/accessibility/browser_accessibility_com_win.cc b/content/browser/accessibility/browser_accessibility_com_win.cc index 513f7cc..c874c05 100644 --- a/content/browser/accessibility/browser_accessibility_com_win.cc +++ b/content/browser/accessibility/browser_accessibility_com_win.cc
@@ -241,7 +241,7 @@ if (!out_x || !out_y || !out_width || !out_height) return E_INVALIDARG; - const base::string16& text_str = GetText(); + const base::string16& text_str = GetTextAsString16(); HandleSpecialTextOffset(&offset); if (offset < 0 || offset > static_cast<LONG>(text_str.size())) return E_INVALIDARG; @@ -289,7 +289,7 @@ if (!text) return E_INVALIDARG; - const base::string16& text_str = GetText(); + const base::string16& text_str = GetTextAsString16(); HandleSpecialTextOffset(&start_offset); HandleSpecialTextOffset(&end_offset); @@ -336,7 +336,7 @@ if (offset < 0) return E_INVALIDARG; - const base::string16& text_str = GetText(); + const base::string16& text_str = GetTextAsString16(); LONG text_len = text_str.length(); if (offset > text_len) return E_INVALIDARG; @@ -380,7 +380,7 @@ *end_offset = 0; *text = NULL; - const base::string16& text_str = GetText(); + const base::string16& text_str = GetTextAsString16(); LONG text_len = text_str.length(); if (offset > text_len) return E_INVALIDARG; @@ -414,7 +414,7 @@ *end_offset = 0; *text = NULL; - const base::string16& text_str = GetText(); + const base::string16& text_str = GetTextAsString16(); LONG text_len = text_str.length(); if (offset > text_len) return E_INVALIDARG; @@ -447,7 +447,7 @@ if (new_len == 0) return E_FAIL; - base::string16 substr = GetText().substr(start, new_len); + base::string16 substr = GetTextAsString16().substr(start, new_len); new_text->text = SysAllocString(substr.c_str()); new_text->start = static_cast<LONG>(start); new_text->end = static_cast<LONG>(start + new_len); @@ -584,7 +584,7 @@ if (!owner()) return E_FAIL; - const base::string16 text = GetText(); + const base::string16 text = GetTextAsString16(); HandleSpecialTextOffset(&offset); if (offset < 0 || offset > static_cast<LONG>(text.size())) return E_INVALIDARG; @@ -660,7 +660,8 @@ if (!hyperlink_index) return E_INVALIDARG; - if (char_index < 0 || char_index >= static_cast<LONG>(GetText().size())) { + if (char_index < 0 || + char_index >= static_cast<LONG>(GetTextAsString16().size())) { return E_INVALIDARG; } @@ -691,7 +692,7 @@ if (index != 0 || !anchor) return E_INVALIDARG; - BSTR ia2_hypertext = SysAllocString(GetText().c_str()); + BSTR ia2_hypertext = SysAllocString(GetTextAsString16().c_str()); DCHECK(ia2_hypertext); anchor->vt = VT_BSTR; anchor->bstrVal = ia2_hypertext; @@ -1454,7 +1455,8 @@ if (!out_x || !out_y || !out_width || !out_height) return E_INVALIDARG; - unsigned int text_length = static_cast<unsigned int>(GetText().size()); + unsigned int text_length = + static_cast<unsigned int>(GetTextAsString16().size()); if (start_index > text_length || end_index > text_length || start_index > end_index) { return E_INVALIDARG; @@ -1482,7 +1484,8 @@ if (!manager) return E_FAIL; - unsigned int text_length = static_cast<unsigned int>(GetText().size()); + unsigned int text_length = + static_cast<unsigned int>(GetTextAsString16().size()); if (start_index > text_length || end_index > text_length || start_index > end_index) { return E_INVALIDARG; @@ -1655,7 +1658,7 @@ child->GetSpellingAttributes(); MergeSpellingIntoTextAttributes(spelling_attributes, start_offset, &attributes_map); - start_offset += child->GetText().length(); + start_offset += child->GetTextAsString16().length(); } else { start_offset += 1; } @@ -2075,7 +2078,8 @@ spelling_attributes[start_offset + attribute.first] = std::move(attribute.second); } - start_offset += static_cast<int>(text_win->GetText().length()); + start_offset += + static_cast<int>(text_win->GetTextAsString16().length()); } } } @@ -2249,14 +2253,14 @@ // TODO(nektar): |AXPosition| can handle other types of boundaries as well. ui::TextBoundaryType boundary = IA2TextBoundaryToTextBoundary(ia2_boundary); return ui::FindAccessibleTextBoundary( - GetText(), owner()->GetLineStartOffsets(), boundary, start_offset, - direction, affinity); + GetTextAsString16(), owner()->GetLineStartOffsets(), boundary, + start_offset, direction, affinity); } LONG BrowserAccessibilityComWin::FindStartOfStyle( LONG start_offset, ui::TextBoundaryDirection direction) { - LONG text_length = static_cast<LONG>(GetText().length()); + LONG text_length = static_cast<LONG>(GetTextAsString16().length()); DCHECK_GE(start_offset, 0); DCHECK_LE(start_offset, text_length);
diff --git a/content/browser/accessibility/browser_accessibility_win.cc b/content/browser/accessibility/browser_accessibility_win.cc index 5b1585a..fbeb12c5 100644 --- a/content/browser/accessibility/browser_accessibility_win.cc +++ b/content/browser/accessibility/browser_accessibility_win.cc
@@ -53,7 +53,7 @@ } base::string16 BrowserAccessibilityWin::GetText() const { - return GetCOM()->AXPlatformNodeWin::GetText(); + return GetCOM()->AXPlatformNodeWin::GetTextAsString16(); } gfx::NativeViewAccessible BrowserAccessibilityWin::GetNativeViewAccessible() {
diff --git a/content/browser/appcache/appcache_service_impl.cc b/content/browser/appcache/appcache_service_impl.cc index 4dca31e..513eef22 100644 --- a/content/browser/appcache/appcache_service_impl.cc +++ b/content/browser/appcache/appcache_service_impl.cc
@@ -30,22 +30,13 @@ namespace content { -namespace { +AppCacheInfoCollection::AppCacheInfoCollection() = default; -void DeferredCallback(OnceCompletionCallback callback, int rv) { - std::move(callback).Run(rv); -} - -} // namespace - -AppCacheInfoCollection::AppCacheInfoCollection() {} - -AppCacheInfoCollection::~AppCacheInfoCollection() {} +AppCacheInfoCollection::~AppCacheInfoCollection() = default; // AsyncHelper ------- -class AppCacheServiceImpl::AsyncHelper - : public AppCacheStorage::Delegate { +class AppCacheServiceImpl::AsyncHelper : public AppCacheStorage::Delegate { public: AsyncHelper(AppCacheServiceImpl* service, OnceCompletionCallback callback) : service_(service), callback_(std::move(callback)) { @@ -64,13 +55,12 @@ protected: void CallCallback(int rv) { - if (!callback_.is_null()) { + if (callback_) { // Defer to guarantee async completion. base::SequencedTaskRunnerHandle::Get()->PostTask( - FROM_HERE, - base::BindOnce(&DeferredCallback, std::move(callback_), rv)); + FROM_HERE, base::BindOnce(std::move(callback_), rv)); } - callback_.Reset(); + DCHECK(!callback_); } AppCacheServiceImpl* service_; @@ -442,9 +432,9 @@ // leave the appcache disabled for an indefinite period of time. Some // users never shutdown the browser. - const base::TimeDelta kZeroDelta; - const base::TimeDelta kOneHour(base::TimeDelta::FromHours(1)); - const base::TimeDelta k30Seconds(base::TimeDelta::FromSeconds(30)); + constexpr base::TimeDelta kZeroDelta; + constexpr base::TimeDelta kOneHour = base::TimeDelta::FromHours(1); + constexpr base::TimeDelta kThirtySeconds = base::TimeDelta::FromSeconds(30); // If the system managed to stay up for long enough, reset the // delay so a new failure won't incur a long wait to get going again. @@ -456,7 +446,7 @@ this, &AppCacheServiceImpl::Reinitialize); // Adjust the delay for next time. - base::TimeDelta increment = std::max(k30Seconds, next_reinit_delay_); + base::TimeDelta increment = std::max(kThirtySeconds, next_reinit_delay_); next_reinit_delay_ = std::min(next_reinit_delay_ + increment, kOneHour); } @@ -514,8 +504,7 @@ void AppCacheServiceImpl::RegisterBackend( AppCacheBackendImpl* backend_impl) { DCHECK(backends_.find(backend_impl->process_id()) == backends_.end()); - backends_.insert( - BackendMap::value_type(backend_impl->process_id(), backend_impl)); + backends_.insert({backend_impl->process_id(), backend_impl}); } void AppCacheServiceImpl::UnregisterBackend(
diff --git a/content/browser/appcache/appcache_service_impl.h b/content/browser/appcache/appcache_service_impl.h index f9e5ed4a..d83fc409 100644 --- a/content/browser/appcache/appcache_service_impl.h +++ b/content/browser/appcache/appcache_service_impl.h
@@ -65,8 +65,7 @@ // Class that manages the application cache service. Sends notifications // to many frontends. One instance per user-profile. Each instance has // exclusive access to its cache_directory on disk. -class CONTENT_EXPORT AppCacheServiceImpl - : public AppCacheService { +class CONTENT_EXPORT AppCacheServiceImpl : public AppCacheService { public: class CONTENT_EXPORT Observer { @@ -154,8 +153,8 @@ void RegisterBackend(AppCacheBackendImpl* backend_impl); virtual void UnregisterBackend(AppCacheBackendImpl* backend_impl); AppCacheBackendImpl* GetBackend(int id) const { - BackendMap::const_iterator it = backends_.find(id); - return (it != backends_.end()) ? it->second : NULL; + auto it = backends_.find(id); + return (it != backends_.end()) ? it->second : nullptr; } AppCacheStorage* storage() const { return storage_.get(); } @@ -192,10 +191,6 @@ class GetInfoHelper; class CheckResponseHelper; - using PendingAsyncHelpers = - std::map<AsyncHelper*, std::unique_ptr<AsyncHelper>>; - using BackendMap = std::map<int, AppCacheBackendImpl*>; - void Reinitialize(); base::FilePath cache_directory_; @@ -205,8 +200,9 @@ std::unique_ptr<AppCacheStorage> storage_; scoped_refptr<storage::SpecialStoragePolicy> special_storage_policy_; scoped_refptr<storage::QuotaManagerProxy> quota_manager_proxy_; - PendingAsyncHelpers pending_helpers_; - BackendMap backends_; // One 'backend' per child process. + std::map<AsyncHelper*, std::unique_ptr<AsyncHelper>> pending_helpers_; + // One 'backend' per child process. + std::map<int, AppCacheBackendImpl*> backends_; // Context for use during cache updates. net::URLRequestContext* request_context_; // If true, nothing (not even session-only data) should be deleted on exit.
diff --git a/content/browser/background_fetch/background_fetch.proto b/content/browser/background_fetch/background_fetch.proto index 72ddf75..c14ad004 100644 --- a/content/browser/background_fetch/background_fetch.proto +++ b/content/browser/background_fetch/background_fetch.proto
@@ -11,8 +11,13 @@ // Stores per-registration (as opposed to per-request) data. // https://wicg.github.io/background-fetch/#background-fetch-registration // -// Next Tag: 7 +// Next Tag: 8 message BackgroundFetchRegistration { + enum BackgroundFetchState { + PENDING = 0; // Default value. + FAILURE = 1; + SUCCESS = 2; + } // See definition of |unique_id| in BackgroundFetchRegistrationId. optional string unique_id = 1; @@ -23,6 +28,7 @@ optional uint64 uploaded = 4; optional uint64 download_total = 5; optional uint64 downloaded = 6; + optional BackgroundFetchState state = 7; } // Developer provided options.
diff --git a/content/browser/background_fetch/background_fetch_context.cc b/content/browser/background_fetch/background_fetch_context.cc index 8fdf69d..6de73cb 100644 --- a/content/browser/background_fetch/background_fetch_context.cc +++ b/content/browser/background_fetch/background_fetch_context.cc
@@ -17,6 +17,8 @@ #include "content/browser/service_worker/service_worker_context_wrapper.h" #include "content/public/browser/background_fetch_delegate.h" #include "content/public/browser/browser_context.h" +#include "content/public/browser/render_frame_host.h" +#include "content/public/browser/web_contents.h" #include "net/url_request/url_request_context_getter.h" #include "storage/browser/blob/blob_data_handle.h" #include "storage/browser/quota/quota_manager_proxy.h" @@ -131,6 +133,7 @@ const std::vector<ServiceWorkerFetchRequest>& requests, const BackgroundFetchOptions& options, const SkBitmap& icon, + RenderFrameHost* render_frame_host, blink::mojom::BackgroundFetchService::FetchCallback callback) { DCHECK_CURRENTLY_ON(BrowserThread::IO); @@ -141,10 +144,58 @@ DCHECK_EQ(0u, fetch_callbacks_.count(registration_id)); fetch_callbacks_[registration_id] = std::move(callback); - data_manager_->CreateRegistration( - registration_id, requests, options, icon, + // |data_manager| is guaranteed to outlive |this|. |create_registration| is + // passed to `DidGetPermission`, which is tied to |weak_factory_|. That means + // that if |create_registration| runs, |this| is still alive, as is + // |data_manager| (a pointer owned by |this|). + auto create_registration = base::BindOnce( + &BackgroundFetchDataManager::CreateRegistration, + base::Unretained(data_manager_.get()), registration_id, requests, options, + icon, base::BindOnce(&BackgroundFetchContext::DidCreateRegistration, weak_factory_.GetWeakPtr(), registration_id)); + + GetPermissionForOrigin( + registration_id.origin(), render_frame_host, + base::BindOnce(&BackgroundFetchContext::DidGetPermission, + weak_factory_.GetWeakPtr(), std::move(create_registration), + registration_id)); +} + +void BackgroundFetchContext::GetPermissionForOrigin( + const url::Origin& origin, + RenderFrameHost* render_frame_host, + GetPermissionCallback callback) { + DCHECK_CURRENTLY_ON(BrowserThread::IO); + + ResourceRequestInfo::WebContentsGetter wc_getter = base::NullCallback(); + + // Permissions need to go through the DownloadRequestLimiter if the fetch + // is started from a top-level frame. + if (render_frame_host && !render_frame_host->GetParent()) { + wc_getter = base::BindRepeating(&WebContents::FromFrameTreeNodeId, + render_frame_host->GetFrameTreeNodeId()); + } + + delegate_proxy_.GetPermissionForOrigin(origin, std::move(wc_getter), + std::move(callback)); +} + +void BackgroundFetchContext::DidGetPermission( + base::OnceClosure permission_closure, + const BackgroundFetchRegistrationId& registration_id, + bool has_permission) { + if (has_permission) { + std::move(permission_closure).Run(); + return; + } + + // No permission, the fetch should be rejected. + background_fetch::RecordRegistrationCreatedError( + blink::mojom::BackgroundFetchError::PERMISSION_DENIED); + std::move(fetch_callbacks_[registration_id]) + .Run(blink::mojom::BackgroundFetchError::PERMISSION_DENIED, + base::nullopt); } void BackgroundFetchContext::GetIconDisplaySize( @@ -365,10 +416,14 @@ if (error != blink::mojom::BackgroundFetchError::NONE) return; + auto controllers_iter = job_controllers_.find(registration_id.unique_id()); + if (reason_to_abort == BackgroundFetchReasonToAbort::ABORTED_BY_DEVELOPER) { - DCHECK(job_controllers_.count(registration_id.unique_id())); - job_controllers_[registration_id.unique_id()]->Abort(reason_to_abort); + DCHECK(controllers_iter != job_controllers_.end()); + controllers_iter->second->Abort(reason_to_abort); } + auto registration = controllers_iter->second->NewRegistration( + blink::mojom::BackgroundFetchState::FAILURE); switch (reason_to_abort) { case BackgroundFetchReasonToAbort::ABORTED_BY_DEVELOPER: @@ -376,8 +431,7 @@ CleanupRegistration(registration_id, {}, blink::mojom::BackgroundFetchState::FAILURE); event_dispatcher_.DispatchBackgroundFetchAbortEvent( - registration_id, blink::mojom::BackgroundFetchState::FAILURE, - base::DoNothing()); + registration_id, std::move(registration), base::DoNothing()); return; case BackgroundFetchReasonToAbort::TOTAL_DOWNLOAD_SIZE_EXCEEDED: case BackgroundFetchReasonToAbort::SERVICE_WORKER_UNAVAILABLE: @@ -390,13 +444,15 @@ registration_id, std::make_unique<BackgroundFetchRequestMatchParams>(), base::BindOnce(&BackgroundFetchContext::DidGetSettledFetches, - weak_factory_.GetWeakPtr(), registration_id)); + weak_factory_.GetWeakPtr(), registration_id, + std::move(registration))); return; } } void BackgroundFetchContext::DidGetSettledFetches( const BackgroundFetchRegistrationId& registration_id, + std::unique_ptr<BackgroundFetchRegistration> registration, blink::mojom::BackgroundFetchError error, bool background_fetch_succeeded, std::vector<BackgroundFetchSettledFetch> settled_fetches, @@ -410,13 +466,21 @@ return; } + DCHECK(job_controllers_.count(registration_id.unique_id())); + + if (job_controllers_[registration_id.unique_id()]->total_downloads() != + static_cast<int>(settled_fetches.size())) { + // Something went wrong, and some information was lost. + background_fetch_succeeded = false; + } + // The `backgroundfetchsuccess` event will be invoked when all requests in the // registration have completed successfully. In all other cases, the // `backgroundfetchfail` event will be invoked instead. if (background_fetch_succeeded) { + registration->state = blink::mojom::BackgroundFetchState::SUCCESS; event_dispatcher_.DispatchBackgroundFetchSuccessEvent( - registration_id, blink::mojom::BackgroundFetchState::SUCCESS, - std::move(settled_fetches), + registration_id, std::move(registration), std::move(settled_fetches), base::BindOnce( &BackgroundFetchContext::CleanupRegistration, weak_factory_.GetWeakPtr(), registration_id, @@ -427,9 +491,9 @@ blink::mojom::BackgroundFetchState::SUCCESS, true /* preserve_info_to_dispatch_click_event */)); } else { + registration->state = blink::mojom::BackgroundFetchState::FAILURE; event_dispatcher_.DispatchBackgroundFetchFailEvent( - registration_id, blink::mojom::BackgroundFetchState::FAILURE, - std::move(settled_fetches), + registration_id, std::move(registration), std::move(settled_fetches), base::BindOnce( &BackgroundFetchContext::CleanupRegistration, weak_factory_.GetWeakPtr(), registration_id, @@ -455,9 +519,12 @@ // backgroundfetchsuccess/backgroundfetchfail event has been resolved. Store // the information we want to persist after the controller is gone, in // completed_fetches_. + auto controllers_iter = job_controllers_.find(registration_id.unique_id()); + DCHECK(controllers_iter != job_controllers_.end()); if (preserve_info_to_dispatch_click_event) { - completed_fetches_[registration_id.unique_id()] = {registration_id, - background_fetch_state}; + completed_fetches_[registration_id.unique_id()] = std::make_pair( + registration_id, + controllers_iter->second->NewRegistration(background_fetch_state)); } job_controllers_.erase(registration_id.unique_id()); @@ -481,7 +548,7 @@ // The fetch has succeeded or failed. (not aborted/cancelled). event_dispatcher_.DispatchBackgroundFetchClickEvent( iter->second.first /* registration_id */, - iter->second.second /* state */, base::DoNothing()); + std::move(iter->second.second) /* registration */, base::DoNothing()); completed_fetches_.erase(iter); return; } @@ -492,9 +559,11 @@ return; // TODO(crbug.com/873630): Implement a background fetch state manager to // keep track of states, and stop hard-coding it here. + auto registration = controllers_iter->second->NewRegistration( + blink::mojom::BackgroundFetchState::PENDING); event_dispatcher_.DispatchBackgroundFetchClickEvent( - controllers_iter->second->registration_id(), - blink::mojom::BackgroundFetchState::PENDING, base::DoNothing()); + controllers_iter->second->registration_id(), std::move(registration), + base::DoNothing()); } void BackgroundFetchContext::MatchRequests(
diff --git a/content/browser/background_fetch/background_fetch_context.h b/content/browser/background_fetch/background_fetch_context.h index 9c40e87..e25b915 100644 --- a/content/browser/background_fetch/background_fetch_context.h +++ b/content/browser/background_fetch/background_fetch_context.h
@@ -40,6 +40,7 @@ class BackgroundFetchScheduler; class BrowserContext; class CacheStorageContextImpl; +class RenderFrameHost; class ServiceWorkerContextWrapper; struct ServiceWorkerFetchRequest; @@ -90,6 +91,7 @@ const std::vector<ServiceWorkerFetchRequest>& requests, const BackgroundFetchOptions& options, const SkBitmap& icon, + RenderFrameHost* render_frame_host, blink::mojom::BackgroundFetchService::FetchCallback callback); // Gets display size for the icon for Background Fetch UI. @@ -148,6 +150,8 @@ void OnStorageWiped() override; private: + using GetPermissionCallback = base::OnceCallback<void(bool)>; + FRIEND_TEST_ALL_PREFIXES(BackgroundFetchServiceTest, JobsInitializedOnBrowserRestart); friend class BackgroundFetchServiceTest; @@ -204,6 +208,7 @@ // retrieved from storage, and the Service Worker event can be invoked. void DidGetSettledFetches( const BackgroundFetchRegistrationId& registration_id, + std::unique_ptr<BackgroundFetchRegistration> registration, blink::mojom::BackgroundFetchError error, bool background_fetch_succeeded, std::vector<BackgroundFetchSettledFetch> settled_fetches, @@ -259,6 +264,17 @@ // blink::mojom::kInvalidServiceWorkerRegistrationId. void AbandonFetches(int64_t service_worker_registration_id); + // Check if |origin| has permission to start a fetch. + // virtual for testing. + void GetPermissionForOrigin(const url::Origin& origin, + RenderFrameHost* render_frame_host, + GetPermissionCallback callback); + + // Callback for GetPermissionForOrigin. + void DidGetPermission(base::OnceClosure permission_closure, + const BackgroundFetchRegistrationId& registration_id, + bool has_permission); + // |this| is owned, indirectly, by the BrowserContext. BrowserContext* browser_context_; @@ -275,13 +291,13 @@ std::map<std::string, std::unique_ptr<BackgroundFetchJobController>> job_controllers_; - // Map from |unique_id|s to {|registration_id|s, BackgroundFetchState}. + // Map from |unique_id|s to {|registration_id|, |registration|}. // An entry in here means the fetch has completed. This information is needed // after the fetch has completed to dispatch the backgroundfetchclick event. // TODO(crbug.com/857122): Clean this up when the UI is no longer showing. std::map<std::string, std::pair<BackgroundFetchRegistrationId, - blink::mojom::BackgroundFetchState>> + std::unique_ptr<BackgroundFetchRegistration>>> completed_fetches_; // Map from BackgroundFetchRegistrationIds to FetchCallbacks for active // fetches. Must be destroyed before |data_manager_| and
diff --git a/content/browser/background_fetch/background_fetch_delegate_proxy.cc b/content/browser/background_fetch/background_fetch_delegate_proxy.cc index c698fe8..c8048fe 100644 --- a/content/browser/background_fetch/background_fetch_delegate_proxy.cc +++ b/content/browser/background_fetch/background_fetch_delegate_proxy.cc
@@ -41,6 +41,29 @@ return weak_ptr_factory_.GetWeakPtr(); } + void ForwardGetPermissionForOriginCallbackToIO( + BackgroundFetchDelegate::GetPermissionForOriginCallback callback, + bool has_permission) { + DCHECK_CURRENTLY_ON(BrowserThread::UI); + BrowserThread::PostTask( + BrowserThread::IO, FROM_HERE, + base::BindOnce(std::move(callback), has_permission)); + } + + void GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + BackgroundFetchDelegate::GetPermissionForOriginCallback callback) { + if (delegate_) { + delegate_->GetPermissionForOrigin( + origin, wc_getter, + base::BindOnce(&Core::ForwardGetPermissionForOriginCallbackToIO, + weak_ptr_factory_.GetWeakPtr(), std::move(callback))); + } else { + std::move(callback).Run(false /* has_permission */); + } + } + void ForwardGetIconDisplaySizeCallbackToIO( BackgroundFetchDelegate::GetIconDisplaySizeCallback callback, const gfx::Size& display_size) { @@ -289,6 +312,17 @@ ui_core_ptr_, std::move(callback))); } +void BackgroundFetchDelegateProxy::GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + BackgroundFetchDelegate::GetPermissionForOriginCallback callback) { + DCHECK_CURRENTLY_ON(BrowserThread::IO); + BrowserThread::PostTask( + BrowserThread::UI, FROM_HERE, + base::BindOnce(&Core::GetPermissionForOrigin, ui_core_ptr_, origin, + wc_getter, std::move(callback))); +} + void BackgroundFetchDelegateProxy::CreateDownloadJob( base::WeakPtr<Controller> controller, std::unique_ptr<BackgroundFetchDescription> fetch_description,
diff --git a/content/browser/background_fetch/background_fetch_delegate_proxy.h b/content/browser/background_fetch/background_fetch_delegate_proxy.h index 8272ba6..d393db4 100644 --- a/content/browser/background_fetch/background_fetch_delegate_proxy.h +++ b/content/browser/background_fetch/background_fetch_delegate_proxy.h
@@ -66,6 +66,12 @@ void GetIconDisplaySize( BackgroundFetchDelegate::GetIconDisplaySizeCallback callback); + // Checks if the provided origin has permission to start a Background Fetch. + void GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + BackgroundFetchDelegate::GetPermissionForOriginCallback callback); + // Creates a new download grouping described by |fetch_description|. Further // downloads started by StartRequest will also use // |fetch_description.job_unique_id| so that a notification can be updated
diff --git a/content/browser/background_fetch/background_fetch_delegate_proxy_unittest.cc b/content/browser/background_fetch/background_fetch_delegate_proxy_unittest.cc index 5bad5b7..8d14278 100644 --- a/content/browser/background_fetch/background_fetch_delegate_proxy_unittest.cc +++ b/content/browser/background_fetch/background_fetch_delegate_proxy_unittest.cc
@@ -33,6 +33,12 @@ BackgroundFetchDelegate::GetIconDisplaySizeCallback callback) override { std::move(callback).Run(gfx::Size(kIconDisplaySize, kIconDisplaySize)); } + void GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) override { + std::move(callback).Run(true /* has_permission */); + } void CreateDownloadJob( std::unique_ptr<BackgroundFetchDescription> fetch_description) override {} void DownloadUrl(const std::string& job_unique_id,
diff --git a/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.cc b/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.cc index c52f6b5..d280f1d 100644 --- a/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.cc +++ b/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.cc
@@ -20,13 +20,11 @@ ~BackgroundFetchEmbeddedWorkerTestHelper() = default; void BackgroundFetchEmbeddedWorkerTestHelper::OnBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchAbortEventCallback callback) { - last_developer_id_ = developer_id; - last_unique_id_ = unique_id; - last_state_ = state; + last_developer_id_ = registration.developer_id; + last_unique_id_ = registration.unique_id; + last_state_ = registration.state; if (fail_abort_event_) { std::move(callback).Run(blink::mojom::ServiceWorkerEventStatus::REJECTED, @@ -41,13 +39,11 @@ } void BackgroundFetchEmbeddedWorkerTestHelper::OnBackgroundFetchClickEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchClickEventCallback callback) { - last_developer_id_ = developer_id; - last_unique_id_ = unique_id; - last_state_ = state; + last_developer_id_ = registration.developer_id; + last_unique_id_ = registration.unique_id; + last_state_ = registration.state; if (fail_click_event_) { std::move(callback).Run(blink::mojom::ServiceWorkerEventStatus::REJECTED, @@ -62,14 +58,12 @@ } void BackgroundFetchEmbeddedWorkerTestHelper::OnBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchFailEventCallback callback) { - last_developer_id_ = developer_id; - last_unique_id_ = unique_id; - last_state_ = state; + last_developer_id_ = registration.developer_id; + last_unique_id_ = registration.unique_id; + last_state_ = registration.state; last_fetches_ = fetches; if (fail_fetch_fail_event_) { @@ -85,15 +79,13 @@ } void BackgroundFetchEmbeddedWorkerTestHelper::OnBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchSuccessEventCallback callback) { - last_developer_id_ = developer_id; - last_unique_id_ = unique_id; - last_state_ = state; + last_developer_id_ = registration.developer_id; + last_unique_id_ = registration.unique_id; + last_state_ = registration.state; last_fetches_ = fetches; if (fail_fetched_event_) {
diff --git a/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.h b/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.h index 5fcb21d..d6203654 100644 --- a/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.h +++ b/content/browser/background_fetch/background_fetch_embedded_worker_test_helper.h
@@ -63,28 +63,20 @@ protected: // EmbeddedWorkerTestHelper overrides: void OnBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchAbortEventCallback callback) override; void OnBackgroundFetchClickEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchClickEventCallback callback) override; void OnBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchFailEventCallback callback) override; void OnBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchSuccessEventCallback callback) override;
diff --git a/content/browser/background_fetch/background_fetch_event_dispatcher.cc b/content/browser/background_fetch/background_fetch_event_dispatcher.cc index 8bf88edc..fcbfaae4 100644 --- a/content/browser/background_fetch/background_fetch_event_dispatcher.cc +++ b/content/browser/background_fetch/background_fetch_event_dispatcher.cc
@@ -6,6 +6,7 @@ #include "base/bind.h" #include "base/callback.h" +#include "base/callback_helpers.h" #include "base/metrics/histogram_functions.h" #include "base/strings/stringprintf.h" #include "content/browser/background_fetch/background_fetch_registration_id.h" @@ -76,84 +77,81 @@ void BackgroundFetchEventDispatcher::DispatchBackgroundFetchAbortEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, base::OnceClosure finished_closure) { DCHECK_CURRENTLY_ON(BrowserThread::IO); LoadServiceWorkerRegistrationForDispatch( registration_id, ServiceWorkerMetrics::EventType::BACKGROUND_FETCH_ABORT, std::move(finished_closure), - base::Bind( + base::AdaptCallbackForRepeating(base::BindOnce( &BackgroundFetchEventDispatcher::DoDispatchBackgroundFetchAbortEvent, - registration_id.developer_id(), registration_id.unique_id(), state)); + std::move(registration)))); } void BackgroundFetchEventDispatcher::DoDispatchBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id) { DCHECK(service_worker_version); + DCHECK(registration); service_worker_version->endpoint()->DispatchBackgroundFetchAbortEvent( - developer_id, unique_id, state, + *registration, service_worker_version->CreateSimpleEventCallback(request_id)); } void BackgroundFetchEventDispatcher::DispatchBackgroundFetchClickEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, base::OnceClosure finished_closure) { DCHECK_CURRENTLY_ON(BrowserThread::IO); LoadServiceWorkerRegistrationForDispatch( registration_id, ServiceWorkerMetrics::EventType::BACKGROUND_FETCH_CLICK, std::move(finished_closure), - base::Bind( + base::AdaptCallbackForRepeating(base::BindOnce( &BackgroundFetchEventDispatcher::DoDispatchBackgroundFetchClickEvent, - registration_id, state)); + std::move(registration)))); } void BackgroundFetchEventDispatcher::DoDispatchBackgroundFetchClickEvent( - const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id) { DCHECK(service_worker_version); + DCHECK(registration); service_worker_version->endpoint()->DispatchBackgroundFetchClickEvent( - registration_id.developer_id(), registration_id.unique_id(), state, + *registration, service_worker_version->CreateSimpleEventCallback(request_id)); } void BackgroundFetchEventDispatcher::DispatchBackgroundFetchFailEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, base::OnceClosure finished_closure) { DCHECK_CURRENTLY_ON(BrowserThread::IO); LoadServiceWorkerRegistrationForDispatch( registration_id, ServiceWorkerMetrics::EventType::BACKGROUND_FETCH_FAIL, std::move(finished_closure), - base::Bind( + base::AdaptCallbackForRepeating(base::BindOnce( &BackgroundFetchEventDispatcher::DoDispatchBackgroundFetchFailEvent, - registration_id.developer_id(), registration_id.unique_id(), state, - fetches)); + std::move(registration), fetches))); } void BackgroundFetchEventDispatcher::DoDispatchBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id) { DCHECK(service_worker_version); + DCHECK(registration); service_worker_version->endpoint()->DispatchBackgroundFetchFailEvent( - developer_id, unique_id, state, fetches, + *registration, fetches, service_worker_version->CreateSimpleEventCallback(request_id)); } void BackgroundFetchEventDispatcher::DispatchBackgroundFetchSuccessEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, base::OnceClosure finished_closure) { DCHECK_CURRENTLY_ON(BrowserThread::IO); @@ -161,22 +159,21 @@ registration_id, ServiceWorkerMetrics::EventType::BACKGROUND_FETCH_SUCCESS, std::move(finished_closure), - base::Bind(&BackgroundFetchEventDispatcher:: - DoDispatchBackgroundFetchSuccessEvent, - registration_id.developer_id(), registration_id.unique_id(), - state, fetches)); + base::AdaptCallbackForRepeating( + base::BindOnce(&BackgroundFetchEventDispatcher:: + DoDispatchBackgroundFetchSuccessEvent, + std::move(registration), fetches))); } void BackgroundFetchEventDispatcher::DoDispatchBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id) { DCHECK(service_worker_version); + DCHECK(registration); service_worker_version->endpoint()->DispatchBackgroundFetchSuccessEvent( - developer_id, unique_id, state, fetches, + *registration, fetches, service_worker_version->CreateSimpleEventCallback(request_id)); }
diff --git a/content/browser/background_fetch/background_fetch_event_dispatcher.h b/content/browser/background_fetch/background_fetch_event_dispatcher.h index 5fa5af8..19bdacb3 100644 --- a/content/browser/background_fetch/background_fetch_event_dispatcher.h +++ b/content/browser/background_fetch/background_fetch_event_dispatcher.h
@@ -45,14 +45,14 @@ // background fetch was aborted by the user or another external event. void DispatchBackgroundFetchAbortEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, base::OnceClosure finished_closure); // Dispatches the `backgroundfetchclick` event, which indicates that the user // interface displayed for an active background fetch was activated. void DispatchBackgroundFetchClickEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, base::OnceClosure finished_closure); // Dispatches the `backgroundfetchfail` event, which indicates that a @@ -60,7 +60,7 @@ // response pairs are included. void DispatchBackgroundFetchFailEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, base::OnceClosure finished_closure); @@ -69,7 +69,7 @@ // included. void DispatchBackgroundFetchSuccessEvent( const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, base::OnceClosure finished_closure); @@ -117,27 +117,20 @@ // Methods that actually invoke the event on an activated Service Worker. static void DoDispatchBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id); static void DoDispatchBackgroundFetchClickEvent( - const BackgroundFetchRegistrationId& registration_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id); static void DoDispatchBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id); static void DoDispatchBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + std::unique_ptr<BackgroundFetchRegistration> registration, const std::vector<BackgroundFetchSettledFetch>& fetches, scoped_refptr<ServiceWorkerVersion> service_worker_version, int request_id);
diff --git a/content/browser/background_fetch/background_fetch_event_dispatcher_unittest.cc b/content/browser/background_fetch/background_fetch_event_dispatcher_unittest.cc index 3c34c478..ee26685 100644 --- a/content/browser/background_fetch/background_fetch_event_dispatcher_unittest.cc +++ b/content/browser/background_fetch/background_fetch_event_dispatcher_unittest.cc
@@ -45,9 +45,12 @@ kExampleUniqueId); base::RunLoop run_loop; + auto registration = CreateBackgroundFetchRegistration( + invalid_registration_id.developer_id(), + invalid_registration_id.unique_id(), + blink::mojom::BackgroundFetchState::FAILURE); event_dispatcher_.DispatchBackgroundFetchAbortEvent( - invalid_registration_id, blink::mojom::BackgroundFetchState::FAILURE, - run_loop.QuitClosure()); + invalid_registration_id, std::move(registration), run_loop.QuitClosure()); run_loop.Run(); @@ -73,9 +76,11 @@ { base::RunLoop run_loop; + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId, kExampleUniqueId, + blink::mojom::BackgroundFetchState::FAILURE); event_dispatcher_.DispatchBackgroundFetchAbortEvent( - registration_id, blink::mojom::BackgroundFetchState::FAILURE, - run_loop.QuitClosure()); + registration_id, std::move(registration), run_loop.QuitClosure()); run_loop.Run(); } @@ -99,9 +104,12 @@ { base::RunLoop run_loop; - event_dispatcher_.DispatchBackgroundFetchAbortEvent( - second_registration_id, blink::mojom::BackgroundFetchState::FAILURE, - run_loop.QuitClosure()); + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId2, kExampleUniqueId2, + blink::mojom::BackgroundFetchState::FAILURE); + event_dispatcher_.DispatchBackgroundFetchAbortEvent(second_registration_id, + std::move(registration), + run_loop.QuitClosure()); run_loop.Run(); } @@ -135,9 +143,11 @@ { base::RunLoop run_loop; + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId, kExampleUniqueId, + blink::mojom::BackgroundFetchState::PENDING); event_dispatcher_.DispatchBackgroundFetchClickEvent( - registration_id, blink::mojom::BackgroundFetchState::PENDING, - run_loop.QuitClosure()); + registration_id, std::move(registration), run_loop.QuitClosure()); run_loop.Run(); } @@ -161,9 +171,12 @@ { base::RunLoop run_loop; - event_dispatcher_.DispatchBackgroundFetchClickEvent( - second_registration_id, blink::mojom::BackgroundFetchState::FAILURE, - run_loop.QuitClosure()); + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId2, kExampleUniqueId2, + blink::mojom::BackgroundFetchState::FAILURE); + event_dispatcher_.DispatchBackgroundFetchClickEvent(second_registration_id, + std::move(registration), + run_loop.QuitClosure()); run_loop.Run(); } @@ -200,8 +213,11 @@ { base::RunLoop run_loop; + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId, kExampleUniqueId, + blink::mojom::BackgroundFetchState::FAILURE); event_dispatcher_.DispatchBackgroundFetchFailEvent( - registration_id, blink::mojom::BackgroundFetchState::FAILURE, fetches, + registration_id, std::move(registration), fetches, run_loop.QuitClosure()); run_loop.Run(); @@ -229,9 +245,12 @@ { base::RunLoop run_loop; + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId2, kExampleUniqueId2, + blink::mojom::BackgroundFetchState::FAILURE); event_dispatcher_.DispatchBackgroundFetchFailEvent( - second_registration_id, blink::mojom::BackgroundFetchState::FAILURE, - fetches, run_loop.QuitClosure()); + second_registration_id, std::move(registration), fetches, + run_loop.QuitClosure()); run_loop.Run(); } @@ -269,8 +288,11 @@ { base::RunLoop run_loop; + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId, kExampleUniqueId, + blink::mojom::BackgroundFetchState::SUCCESS); event_dispatcher_.DispatchBackgroundFetchSuccessEvent( - registration_id, blink::mojom::BackgroundFetchState::SUCCESS, fetches, + registration_id, std::move(registration), fetches, run_loop.QuitClosure()); run_loop.Run(); @@ -302,9 +324,12 @@ { base::RunLoop run_loop; + auto registration = CreateBackgroundFetchRegistration( + kExampleDeveloperId2, kExampleUniqueId2, + blink::mojom::BackgroundFetchState::SUCCESS); event_dispatcher_.DispatchBackgroundFetchSuccessEvent( - second_registration_id, blink::mojom::BackgroundFetchState::SUCCESS, - fetches, run_loop.QuitClosure()); + second_registration_id, std::move(registration), fetches, + run_loop.QuitClosure()); run_loop.Run(); }
diff --git a/content/browser/background_fetch/background_fetch_job_controller.cc b/content/browser/background_fetch/background_fetch_job_controller.cc index f95b4be..ef07c1c 100644 --- a/content/browser/background_fetch/background_fetch_job_controller.cc +++ b/content/browser/background_fetch/background_fetch_job_controller.cc
@@ -47,7 +47,7 @@ total_downloads_ = total_downloads; // TODO(nator): Update this when we support uploads. - int total_downloads_size = options_.download_total; + total_downloads_size_ = options_.download_total; std::vector<std::string> active_guids; active_guids.reserve(active_fetch_requests.size()); @@ -57,7 +57,7 @@ auto fetch_description = std::make_unique<BackgroundFetchDescription>( registration_id().unique_id(), ui_title, registration_id().origin(), icon_, completed_downloads, total_downloads, - complete_requests_downloaded_bytes_cache_, total_downloads_size, + complete_requests_downloaded_bytes_cache_, total_downloads_size_, std::move(active_guids)); delegate_proxy_->CreateDownloadJob(GetWeakPtr(), std::move(fetch_description), @@ -137,6 +137,15 @@ delegate_proxy_->UpdateUI(registration_id().unique_id(), title, icon); } +std::unique_ptr<BackgroundFetchRegistration> +BackgroundFetchJobController::NewRegistration( + blink::mojom::BackgroundFetchState state) const { + return std::make_unique<BackgroundFetchRegistration>( + registration_id().developer_id(), registration_id().unique_id(), + 0 /* upload_total */, 0 /* uploaded */, total_downloads_size_, + complete_requests_downloaded_bytes_cache_, state); +} + uint64_t BackgroundFetchJobController::GetInProgressDownloadedBytes() { return active_request_downloaded_bytes_; }
diff --git a/content/browser/background_fetch/background_fetch_job_controller.h b/content/browser/background_fetch/background_fetch_job_controller.h index e57a219..a69f7a0 100644 --- a/content/browser/background_fetch/background_fetch_job_controller.h +++ b/content/browser/background_fetch/background_fetch_job_controller.h
@@ -76,9 +76,23 @@ void UpdateUI(const base::Optional<std::string>& title, const base::Optional<SkBitmap>& icon); + // Returns a unique_ptr to a BackgroundFetchRegistration object + // created with member fields. + std::unique_ptr<BackgroundFetchRegistration> NewRegistration( + blink::mojom::BackgroundFetchState state) const; + // Returns the options with which this job is fetching data. const BackgroundFetchOptions& options() const { return options_; } + // Returns total downloaded bytes. + int downloaded() const { return complete_requests_downloaded_bytes_cache_; } + + // Returns total size of downloads, as indicated by the developer. + int download_total() const { return total_downloads_size_; } + + // Returns the number of requests that comprise the whole job. + int total_downloads() const { return total_downloads_; } + base::WeakPtr<BackgroundFetchJobController> GetWeakPtr() { return weak_ptr_factory_.GetWeakPtr(); } @@ -116,6 +130,9 @@ // delivering progress events without having to read from the database. uint64_t complete_requests_downloaded_bytes_cache_; + // Total downloads size, as indicated by the developer. + int total_downloads_size_ = 0; + // Proxy for interacting with the BackgroundFetchDelegate across thread // boundaries. It is owned by the BackgroundFetchContext. BackgroundFetchDelegateProxy* delegate_proxy_;
diff --git a/content/browser/background_fetch/background_fetch_service_impl.cc b/content/browser/background_fetch/background_fetch_service_impl.cc index 6bae7d6..f116ff5 100644 --- a/content/browser/background_fetch/background_fetch_service_impl.cc +++ b/content/browser/background_fetch/background_fetch_service_impl.cc
@@ -16,7 +16,6 @@ #include "content/browser/storage_partition_impl.h" #include "content/common/service_worker/service_worker_types.h" #include "content/public/browser/browser_thread.h" -#include "content/public/browser/render_frame_host.h" #include "content/public/browser/render_process_host.h" #include "mojo/public/cpp/bindings/strong_binding.h" @@ -91,7 +90,8 @@ url::Origin origin, RenderFrameHost* render_frame_host) : background_fetch_context_(std::move(background_fetch_context)), - origin_(std::move(origin)) { + origin_(std::move(origin)), + render_frame_host_(render_frame_host) { DCHECK(background_fetch_context_); } @@ -123,7 +123,8 @@ base::GenerateGUID()); background_fetch_context_->StartFetch(registration_id, requests, options, - icon, std::move(callback)); + icon, render_frame_host_, + std::move(callback)); } void BackgroundFetchServiceImpl::GetIconDisplaySize(
diff --git a/content/browser/background_fetch/background_fetch_service_impl.h b/content/browser/background_fetch/background_fetch_service_impl.h index 9eba08c9..5abcc9b 100644 --- a/content/browser/background_fetch/background_fetch_service_impl.h +++ b/content/browser/background_fetch/background_fetch_service_impl.h
@@ -100,6 +100,8 @@ const url::Origin origin_; + RenderFrameHost* render_frame_host_; + DISALLOW_COPY_AND_ASSIGN(BackgroundFetchServiceImpl); };
diff --git a/content/browser/background_fetch/background_fetch_test_base.cc b/content/browser/background_fetch/background_fetch_test_base.cc index fc5366e5..f8df776 100644 --- a/content/browser/background_fetch/background_fetch_test_base.cc +++ b/content/browser/background_fetch/background_fetch_test_base.cc
@@ -163,4 +163,15 @@ Referrer(), false /* is_reload */); } +std::unique_ptr<BackgroundFetchRegistration> +BackgroundFetchTestBase::CreateBackgroundFetchRegistration( + const std::string& developer_id, + const std::string& unique_id, + blink::mojom::BackgroundFetchState state) { + auto registration = std::make_unique<BackgroundFetchRegistration>( + developer_id, unique_id, 0 /* upload_total */, 0 /* uploaded */, + 0 /* download_total */, 0 /* downloaded */, state); + return registration; +} + } // namespace content
diff --git a/content/browser/background_fetch/background_fetch_test_base.h b/content/browser/background_fetch/background_fetch_test_base.h index a2bcc73..50680da7 100644 --- a/content/browser/background_fetch/background_fetch_test_base.h +++ b/content/browser/background_fetch/background_fetch_test_base.h
@@ -56,6 +56,12 @@ const GURL& url, std::unique_ptr<TestResponse> response); + // Creates a BackgroundFetchRegistration object. + static std::unique_ptr<BackgroundFetchRegistration> + CreateBackgroundFetchRegistration(const std::string& developer_id, + const std::string& unique_id, + blink::mojom::BackgroundFetchState state); + // Returns the embedded worker test helper instance, which can be used to // influence the behavior of the Service Worker events. BackgroundFetchEmbeddedWorkerTestHelper* embedded_worker_test_helper() {
diff --git a/content/browser/background_fetch/mock_background_fetch_delegate.cc b/content/browser/background_fetch/mock_background_fetch_delegate.cc index c9934a8..3655aae7 100644 --- a/content/browser/background_fetch/mock_background_fetch_delegate.cc +++ b/content/browser/background_fetch/mock_background_fetch_delegate.cc
@@ -6,6 +6,7 @@ #include <vector> #include "base/files/file_util.h" +#include "base/threading/sequenced_task_runner_handle.h" #include "base/threading/thread_task_runner_handle.h" #include "content/browser/background_fetch/mock_background_fetch_delegate.h" #include "content/public/browser/background_fetch_description.h" @@ -56,6 +57,15 @@ MockBackgroundFetchDelegate::~MockBackgroundFetchDelegate() {} +void MockBackgroundFetchDelegate::GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) { + base::SequencedTaskRunnerHandle::Get()->PostTask( + FROM_HERE, + base::BindOnce(std::move(callback), true /* has_permission */)); +} + void MockBackgroundFetchDelegate::GetIconDisplaySize( GetIconDisplaySizeCallback callback) {}
diff --git a/content/browser/background_fetch/mock_background_fetch_delegate.h b/content/browser/background_fetch/mock_background_fetch_delegate.h index 6d12cd4..fc64bab 100644 --- a/content/browser/background_fetch/mock_background_fetch_delegate.h +++ b/content/browser/background_fetch/mock_background_fetch_delegate.h
@@ -65,6 +65,10 @@ ~MockBackgroundFetchDelegate() override; // BackgroundFetchDelegate implementation: + void GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) override; void GetIconDisplaySize( BackgroundFetchDelegate::GetIconDisplaySizeCallback callback) override; void CreateDownloadJob(
diff --git a/content/browser/background_fetch/storage/create_metadata_task.cc b/content/browser/background_fetch/storage/create_metadata_task.cc index 5936af1..4604139 100644 --- a/content/browser/background_fetch/storage/create_metadata_task.cc +++ b/content/browser/background_fetch/storage/create_metadata_task.cc
@@ -101,6 +101,8 @@ registration_proto->set_unique_id(registration_id_.unique_id()); registration_proto->set_developer_id(registration_id_.developer_id()); registration_proto->set_download_total(options_.download_total); + registration_proto->set_state( + proto::BackgroundFetchRegistration_BackgroundFetchState_PENDING); // Set Options fields. auto* options_proto = metadata_proto_->mutable_options();
diff --git a/content/browser/background_fetch/storage/database_helpers.cc b/content/browser/background_fetch/storage/database_helpers.cc index 7079357..6045198 100644 --- a/content/browser/background_fetch/storage/database_helpers.cc +++ b/content/browser/background_fetch/storage/database_helpers.cc
@@ -6,6 +6,7 @@ #include "base/strings/string_number_conversions.h" #include "content/browser/background_fetch/background_fetch.pb.h" +#include "third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom.h" namespace content { @@ -99,7 +100,19 @@ registration.uploaded = registration_proto.uploaded(); registration.download_total = registration_proto.download_total(); registration.downloaded = registration_proto.downloaded(); - + switch (registration_proto.state()) { + case proto::BackgroundFetchRegistration_BackgroundFetchState_PENDING: + registration.state = blink::mojom::BackgroundFetchState::PENDING; + break; + case proto::BackgroundFetchRegistration_BackgroundFetchState_FAILURE: + registration.state = blink::mojom::BackgroundFetchState::FAILURE; + break; + case proto::BackgroundFetchRegistration_BackgroundFetchState_SUCCESS: + registration.state = blink::mojom::BackgroundFetchState::SUCCESS; + break; + default: + NOTREACHED(); + } return registration; }
diff --git a/content/browser/devtools/protocol/tracing_handler.cc b/content/browser/devtools/protocol/tracing_handler.cc index 2a67bcc..4fbe6ed 100644 --- a/content/browser/devtools/protocol/tracing_handler.cc +++ b/content/browser/devtools/protocol/tracing_handler.cc
@@ -34,7 +34,6 @@ #include "content/browser/frame_host/frame_tree_node.h" #include "content/browser/frame_host/navigation_handle_impl.h" #include "content/browser/frame_host/render_frame_host_impl.h" -#include "content/browser/gpu/gpu_process_host.h" #include "content/browser/renderer_host/render_widget_host_impl.h" #include "content/browser/tracing/tracing_controller_impl.h" #include "content/public/browser/browser_thread.h" @@ -405,28 +404,7 @@ options.fromMaybe("")); } - // GPU process id can only be retrieved on IO thread. Do some thread hopping. - BrowserThread::PostTaskAndReplyWithResult( - BrowserThread::IO, FROM_HERE, base::BindOnce([]() { - GpuProcessHost* gpu_process_host = GpuProcessHost::Get(); - return gpu_process_host ? gpu_process_host->GetProcessId() - : base::kNullProcessId; - }), - base::BindOnce(&TracingHandler::StartTracingWithGpuPid, - weak_factory_.GetWeakPtr(), std::move(callback))); -} - -void TracingHandler::StartTracingWithGpuPid( - std::unique_ptr<StartCallback> callback, - base::ProcessId gpu_pid) { - // Check if tracing was stopped in mid-air. - if (!did_initiate_recording_) { - callback->sendFailure(Response::Error( - "Tracing was stopped before start has been completed.")); - return; - } - - SetupProcessFilter(gpu_pid, nullptr); + SetupProcessFilter(nullptr); TracingController::GetInstance()->StartTracing( trace_config_, base::BindRepeating(&TracingHandler::OnRecordingEnabled, @@ -435,20 +413,14 @@ } void TracingHandler::SetupProcessFilter( - base::ProcessId gpu_pid, RenderFrameHost* new_render_frame_host) { if (!frame_tree_node_) return; base::ProcessId browser_pid = base::Process::Current().Pid(); std::unordered_set<base::ProcessId> included_process_ids({browser_pid}); - - if (gpu_pid != base::kNullProcessId) - included_process_ids.insert(gpu_pid); - if (new_render_frame_host) AppendProcessId(new_render_frame_host, &included_process_ids); - for (FrameTreeNode* node : frame_tree_node_->frame_tree()->SubtreeNodes(frame_tree_node_)) { RenderFrameHost* frame_host = node->current_frame_host(); @@ -523,13 +495,8 @@ void TracingHandler::OnRecordingEnabled( std::unique_ptr<StartCallback> callback) { - if (!did_initiate_recording_) { - callback->sendFailure(Response::Error( - "Tracing was stopped before start has been completed.")); - return; - } - EmitFrameTree(); + callback->sendSuccess(); bool screenshot_enabled; @@ -679,8 +646,7 @@ "FrameCommittedInBrowser", TRACE_EVENT_SCOPE_THREAD, "data", std::move(data)); - SetupProcessFilter(base::kNullProcessId, - navigation_handle->GetRenderFrameHost()); + SetupProcessFilter(navigation_handle->GetRenderFrameHost()); TracingController::GetInstance()->StartTracing( trace_config_, base::RepeatingCallback<void()>()); }
diff --git a/content/browser/devtools/protocol/tracing_handler.h b/content/browser/devtools/protocol/tracing_handler.h index 97ba228..fc3336a 100644 --- a/content/browser/devtools/protocol/tracing_handler.h +++ b/content/browser/devtools/protocol/tracing_handler.h
@@ -116,9 +116,7 @@ CONTENT_EXPORT static base::trace_event::TraceConfig GetTraceConfigFromDevToolsConfig( const base::DictionaryValue& devtools_config); - void SetupProcessFilter(base::ProcessId gpu_pid, RenderFrameHost*); - void StartTracingWithGpuPid(std::unique_ptr<StartCallback>, - base::ProcessId gpu_pid); + void SetupProcessFilter(RenderFrameHost*); void AppendProcessId(RenderFrameHost*, std::unordered_set<base::ProcessId>* process_set); void OnProcessReady(RenderProcessHost*);
diff --git a/content/browser/frame_host/render_frame_host_impl.h b/content/browser/frame_host/render_frame_host_impl.h index 29f8d70..1e3da54 100644 --- a/content/browser/frame_host/render_frame_host_impl.h +++ b/content/browser/frame_host/render_frame_host_impl.h
@@ -30,7 +30,6 @@ #include "build/build_config.h" #include "content/browser/accessibility/browser_accessibility_manager.h" #include "content/browser/bad_message.h" -#include "content/browser/loader/global_routing_id.h" #include "content/browser/renderer_host/media/old_render_frame_audio_input_stream_factory.h" #include "content/browser/renderer_host/media/old_render_frame_audio_output_stream_factory.h" #include "content/browser/renderer_host/media/render_frame_audio_input_stream_factory.h" @@ -50,6 +49,7 @@ #include "content/common/navigation_params.mojom.h" #include "content/public/browser/browser_thread.h" #include "content/public/browser/content_browser_client.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/render_frame_host.h" #include "content/public/common/javascript_dialog_type.h" #include "content/public/common/previews_state.h" @@ -850,6 +850,8 @@ SwapOutACKArrivesPriorToProcessShutdownRequest); FRIEND_TEST_ALL_PREFIXES(SecurityExploitBrowserTest, AttemptDuplicateRenderViewHost); + FRIEND_TEST_ALL_PREFIXES(WebContentsImplBrowserTest, + FullscreenAfterFrameSwap); class DroppedInterfaceRequestLogger;
diff --git a/content/browser/frame_host/render_frame_host_manager.cc b/content/browser/frame_host/render_frame_host_manager.cc index 2484bfa..b793768 100644 --- a/content/browser/frame_host/render_frame_host_manager.cc +++ b/content/browser/frame_host/render_frame_host_manager.cc
@@ -2163,6 +2163,13 @@ render_frame_host_->GetView() && render_frame_host_->GetView()->HasFocus(); + // Remove the current frame and its descendants from the set of fullscreen + // frames immediately. They can stay in pending deletion for some time. + // Removing them when they are deleted is too late. + // This needs to be done before updating the frame tree structure, else it + // will have trouble removing the descendants. + render_frame_delegate_->FullscreenStateChanged(current_frame_host(), false); + // While the old frame is still current, remove its children from the tree. frame_tree_node_->ResetForNewProcess();
diff --git a/content/browser/gpu/gpu_process_host.cc b/content/browser/gpu/gpu_process_host.cc index 11f7f15..0d8c115 100644 --- a/content/browser/gpu/gpu_process_host.cc +++ b/content/browser/gpu/gpu_process_host.cc
@@ -677,10 +677,6 @@ return nullptr; } -base::ProcessId GpuProcessHost::GetProcessId() const { - return initialized_ ? process_->GetProcess().Pid() : base::kNullProcessId; -} - // static int GpuProcessHost::GetGpuCrashCount() { return static_cast<int>(base::subtle::NoBarrier_Load(&gpu_crash_count_));
diff --git a/content/browser/gpu/gpu_process_host.h b/content/browser/gpu/gpu_process_host.h index c549b68..33ad6bd 100644 --- a/content/browser/gpu/gpu_process_host.h +++ b/content/browser/gpu/gpu_process_host.h
@@ -118,7 +118,6 @@ // null if the process no longer exists. static GpuProcessHost* FromID(int host_id); int host_id() const { return host_id_; } - base::ProcessId GetProcessId() const; // IPC::Sender implementation. bool Send(IPC::Message* msg) override;
diff --git a/content/browser/loader/global_routing_id.h b/content/browser/loader/global_routing_id.h deleted file mode 100644 index 3f5aadf..0000000 --- a/content/browser/loader/global_routing_id.h +++ /dev/null
@@ -1,72 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef CONTENT_BROWSER_LOADER_GLOBAL_ROUTING_ID_H_ -#define CONTENT_BROWSER_LOADER_GLOBAL_ROUTING_ID_H_ - -#include <tuple> - -#include "ipc/ipc_message.h" - -namespace content { - -// Uniquely identifies the route from which a net::URLRequest comes. -struct GlobalRoutingID { - GlobalRoutingID() : child_id(-1), route_id(-1) { - } - - GlobalRoutingID(int child_id, int route_id) - : child_id(child_id), - route_id(route_id) { - } - - // The unique ID of the child process (different from OS's PID). - int child_id; - - // The route ID (unique for each URLRequest source). - int route_id; - - bool operator<(const GlobalRoutingID& other) const { - return std::tie(child_id, route_id) < - std::tie(other.child_id, other.route_id); - } - bool operator==(const GlobalRoutingID& other) const { - return child_id == other.child_id && - route_id == other.route_id; - } - bool operator!=(const GlobalRoutingID& other) const { - return !(*this == other); - } -}; - -// Same as GlobalRoutingID except the route_id must be a RenderFrameHost routing -// id. -struct GlobalFrameRoutingId { - GlobalFrameRoutingId() : child_id(0), frame_routing_id(MSG_ROUTING_NONE) {} - - GlobalFrameRoutingId(int child_id, int frame_routing_id) - : child_id(child_id), frame_routing_id(frame_routing_id) {} - - // The unique ID of the child process (different from OS's PID). - int child_id; - - // The route ID (unique for each URLRequest source). - int frame_routing_id; - - bool operator<(const GlobalFrameRoutingId& other) const { - return std::tie(child_id, frame_routing_id) < - std::tie(other.child_id, other.frame_routing_id); - } - bool operator==(const GlobalFrameRoutingId& other) const { - return child_id == other.child_id && - frame_routing_id == other.frame_routing_id; - } - bool operator!=(const GlobalFrameRoutingId& other) const { - return !(*this == other); - } -}; - -} // namespace content - -#endif // CONTENT_BROWSER_LOADER_GLOBAL_ROUTING_ID_H_
diff --git a/content/browser/loader/loader_io_thread_notifier.cc b/content/browser/loader/loader_io_thread_notifier.cc index 47efe28..215e2f9 100644 --- a/content/browser/loader/loader_io_thread_notifier.cc +++ b/content/browser/loader/loader_io_thread_notifier.cc
@@ -5,9 +5,9 @@ #include "content/browser/loader/loader_io_thread_notifier.h" #include "content/browser/frame_host/render_frame_host_impl.h" -#include "content/browser/loader/global_routing_id.h" #include "content/browser/loader/resource_dispatcher_host_impl.h" #include "content/public/browser/browser_thread.h" +#include "content/public/browser/global_routing_id.h" namespace content {
diff --git a/content/browser/loader/prefetch_browsertest.cc b/content/browser/loader/prefetch_browsertest.cc index fb0726e..0b6a19f8 100644 --- a/content/browser/loader/prefetch_browsertest.cc +++ b/content/browser/loader/prefetch_browsertest.cc
@@ -110,12 +110,16 @@ return nullptr; } - void WatchURLAndRunClosure(const std::string& relative_url, - int* visit_count, - base::OnceClosure closure, - const net::test_server::HttpRequest& request) { + void WatchURLAndRunClosure( + const std::string& relative_url, + int* visit_count, + net::test_server::HttpRequest::HeaderMap* out_headers, + base::OnceClosure closure, + const net::test_server::HttpRequest& request) { if (request.relative_url == relative_url) { (*visit_count)++; + if (out_headers) + *out_headers = request.headers; if (closure) std::move(closure).Run(); } @@ -153,7 +157,7 @@ base::RunLoop prefetch_waiter; embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - target_url, &target_fetch_count, prefetch_waiter.QuitClosure())); + target_url, &target_fetch_count, nullptr, prefetch_waiter.QuitClosure())); embedded_test_server()->RegisterRequestHandler(base::BindRepeating( &PrefetchBrowserTest::ServeResponses, base::Unretained(this))); ASSERT_TRUE(embedded_test_server()->Start()); @@ -191,7 +195,7 @@ base::RunLoop prefetch_waiter; embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - target_url, &target_fetch_count, prefetch_waiter.QuitClosure())); + target_url, &target_fetch_count, nullptr, prefetch_waiter.QuitClosure())); embedded_test_server()->RegisterRequestHandler(base::BindRepeating( &PrefetchBrowserTest::ServeResponses, base::Unretained(this))); ASSERT_TRUE(embedded_test_server()->Start()); @@ -238,10 +242,12 @@ base::RunLoop nostore_waiter; embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - nocache_url, &nocache_fetch_count, nocache_waiter.QuitClosure())); + nocache_url, &nocache_fetch_count, nullptr, + nocache_waiter.QuitClosure())); embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - nostore_url, &nostore_fetch_count, nostore_waiter.QuitClosure())); + nostore_url, &nostore_fetch_count, nullptr, + nostore_waiter.QuitClosure())); embedded_test_server()->RegisterRequestHandler(base::BindRepeating( &PrefetchBrowserTest::ServeResponses, base::Unretained(this))); ASSERT_TRUE(embedded_test_server()->Start()); @@ -298,10 +304,11 @@ base::RunLoop preload_waiter; embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - target_url, &target_fetch_count, base::RepeatingClosure())); + target_url, &target_fetch_count, nullptr, base::RepeatingClosure())); embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - preload_url, &preload_fetch_count, preload_waiter.QuitClosure())); + preload_url, &preload_fetch_count, nullptr, + preload_waiter.QuitClosure())); embedded_test_server()->RegisterRequestHandler(base::BindRepeating( &PrefetchBrowserTest::ServeResponses, base::Unretained(this))); ASSERT_TRUE(embedded_test_server()->Start()); @@ -344,20 +351,23 @@ RegisterResponse( target_sxg, // We mock the SignedExchangeHandler, so just return a HTML content - // as "application/signed-exchange;v=b0". + // as "application/signed-exchange;v=b1". ResponseEntry("<head><title>Prefetch Target (SXG)</title></head>", - "application/signed-exchange;v=b0")); + "application/signed-exchange;v=b1")); RegisterResponse(preload_url_in_sxg, ResponseEntry("function foo() {}", "text/javascript")); base::RunLoop preload_waiter; base::RunLoop prefetch_waiter; + net::test_server::HttpRequest::HeaderMap prefetch_headers; embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - target_sxg, &target_fetch_count, prefetch_waiter.QuitClosure())); + target_sxg, &target_fetch_count, &prefetch_headers, + prefetch_waiter.QuitClosure())); embedded_test_server()->RegisterRequestMonitor(base::BindRepeating( &PrefetchBrowserTest::WatchURLAndRunClosure, base::Unretained(this), - preload_url_in_sxg, &preload_fetch_count, preload_waiter.QuitClosure())); + preload_url_in_sxg, &preload_fetch_count, nullptr, + preload_waiter.QuitClosure())); embedded_test_server()->RegisterRequestHandler(base::BindRepeating( &PrefetchBrowserTest::ServeResponses, base::Unretained(this))); ASSERT_TRUE(embedded_test_server()->Start()); @@ -376,6 +386,11 @@ prefetch_waiter.Run(); EXPECT_EQ(1, target_fetch_count); EXPECT_TRUE(CheckPrefetchURLLoaderCountIfSupported(1)); + if (base::FeatureList::IsEnabled(features::kSignedHTTPExchange)) + EXPECT_EQ(prefetch_headers["Accept"], + "application/signed-exchange;v=b1;q=0.9,*/*;q=0.8"); + else + EXPECT_EQ(prefetch_headers["Accept"], "*/*"); // Test after this point requires SignedHTTPExchange support, which is now // disabled when Network Service is enabled.
diff --git a/content/browser/loader/resource_dispatcher_host_impl.h b/content/browser/loader/resource_dispatcher_host_impl.h index fe1365c..ec89329 100644 --- a/content/browser/loader/resource_dispatcher_host_impl.h +++ b/content/browser/loader/resource_dispatcher_host_impl.h
@@ -29,10 +29,10 @@ #include "base/single_thread_task_runner.h" #include "base/time/time.h" #include "content/browser/blob_storage/chrome_blob_storage_context.h" -#include "content/browser/loader/global_routing_id.h" #include "content/browser/loader/resource_loader_delegate.h" #include "content/common/content_export.h" #include "content/public/browser/global_request_id.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/resource_dispatcher_host.h" #include "content/public/browser/resource_request_info.h" #include "content/public/browser/stream_handle.h"
diff --git a/content/browser/loader/resource_request_info_impl.cc b/content/browser/loader/resource_request_info_impl.cc index d0caf30..7fe59fe 100644 --- a/content/browser/loader/resource_request_info_impl.cc +++ b/content/browser/loader/resource_request_info_impl.cc
@@ -5,13 +5,13 @@ #include "content/browser/loader/resource_request_info_impl.h" #include "content/browser/frame_host/frame_tree_node.h" -#include "content/browser/loader/global_routing_id.h" #include "content/browser/loader/resource_message_filter.h" #include "content/browser/web_contents/web_contents_impl.h" #include "content/common/net/url_request_service_worker_data.h" #include "content/common/net/url_request_user_data.h" #include "content/public/browser/browser_thread.h" #include "content/public/browser/global_request_id.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/common/browser_side_navigation_policy.h" #include "content/public/common/process_type.h" #include "net/url_request/url_request.h"
diff --git a/content/browser/media/capture/audio_mirroring_manager.cc b/content/browser/media/capture/audio_mirroring_manager.cc index 1daaf6bf..32544941 100644 --- a/content/browser/media/capture/audio_mirroring_manager.cc +++ b/content/browser/media/capture/audio_mirroring_manager.cc
@@ -36,12 +36,11 @@ } #endif routes_.push_back(StreamRoutingState( - SourceFrameRef(render_process_id, render_frame_id), - diverter)); + GlobalFrameRoutingId(render_process_id, render_frame_id), diverter)); // Query existing destinations to see whether to immediately start diverting // the stream. - std::set<SourceFrameRef> candidates; + std::set<GlobalFrameRoutingId> candidates; candidates.insert(routes_.back().source_render_frame); InitiateQueriesToFindNewDestination(nullptr, candidates); } @@ -79,7 +78,7 @@ sessions_.push_back(destination); } - std::set<SourceFrameRef> candidates; + std::set<GlobalFrameRoutingId> candidates; // Query the MirroringDestination to see which of the audio streams should be // diverted. @@ -103,7 +102,7 @@ // Stop diverting each audio stream in the mirroring session being stopped. // Each stopped stream becomes a candidate to be diverted to another // destination. - std::set<SourceFrameRef> redivert_candidates; + std::set<GlobalFrameRoutingId> redivert_candidates; for (StreamRoutes::iterator it = routes_.begin(); it != routes_.end(); ++it) { if (it->destination == destination) { RouteDivertedFlow(&(*it), nullptr); @@ -158,7 +157,7 @@ void AudioMirroringManager::InitiateQueriesToFindNewDestination( MirroringDestination* old_destination, - const std::set<SourceFrameRef>& candidates) { + const std::set<GlobalFrameRoutingId>& candidates) { lock_.AssertAcquired(); for (Destinations::const_iterator it = sessions_.begin(); @@ -176,7 +175,7 @@ void AudioMirroringManager::UpdateRoutesToDestination( MirroringDestination* destination, bool add_only, - const std::set<SourceFrameRef>& matches, + const std::set<GlobalFrameRoutingId>& matches, bool is_duplicate) { base::AutoLock scoped_lock(lock_); @@ -189,7 +188,7 @@ void AudioMirroringManager::UpdateRoutesToDivertDestination( MirroringDestination* destination, bool add_only, - const std::set<SourceFrameRef>& matches) { + const std::set<GlobalFrameRoutingId>& matches) { lock_.AssertAcquired(); if (std::find(sessions_.begin(), sessions_.end(), destination) == @@ -202,7 +201,7 @@ // Start/stop diverting based on |matches|. Any stopped stream becomes a // candidate to be diverted to another destination. - std::set<SourceFrameRef> redivert_candidates; + std::set<GlobalFrameRoutingId> redivert_candidates; for (StreamRoutes::iterator it = routes_.begin(); it != routes_.end(); ++it) { if (matches.find(it->source_render_frame) != matches.end()) { // Only change the route if the stream is not already being diverted. @@ -223,7 +222,7 @@ void AudioMirroringManager::UpdateRoutesToDuplicateDestination( MirroringDestination* destination, bool add_only, - const std::set<SourceFrameRef>& matches) { + const std::set<GlobalFrameRoutingId>& matches) { lock_.AssertAcquired(); if (std::find(sessions_.begin(), sessions_.end(), destination) == @@ -267,18 +266,18 @@ if (route->destination) { DVLOG(1) << "Stop diverting render_process_id:render_frame_id=" - << route->source_render_frame.first << ':' - << route->source_render_frame.second + << route->source_render_frame.child_id << ':' + << route->source_render_frame.frame_routing_id << " --> MirroringDestination@" << route->destination; route->diverter->StopDiverting(); route->destination = nullptr; } if (new_destination) { - DVLOG(1) << "Start diverting of render_process_id:render_frame_id=" - << route->source_render_frame.first << ':' - << route->source_render_frame.second - << " --> MirroringDestination@" << new_destination; + DVLOG(1) << "Start diverting of render_process_id:render_frame_id=" + << route->source_render_frame.child_id << ':' + << route->source_render_frame.frame_routing_id + << " --> MirroringDestination@" << new_destination; route->diverter->StartDiverting( new_destination->AddInput(route->diverter->GetAudioParameters())); route->destination = new_destination; @@ -286,7 +285,7 @@ } AudioMirroringManager::StreamRoutingState::StreamRoutingState( - const SourceFrameRef& source_frame, + const GlobalFrameRoutingId& source_frame, Diverter* stream_diverter) : source_render_frame(source_frame), diverter(stream_diverter),
diff --git a/content/browser/media/capture/audio_mirroring_manager.h b/content/browser/media/capture/audio_mirroring_manager.h index 67ee6fb..f2c7739 100644 --- a/content/browser/media/capture/audio_mirroring_manager.h +++ b/content/browser/media/capture/audio_mirroring_manager.h
@@ -41,6 +41,7 @@ #include "base/synchronization/lock.h" #include "base/unguessable_token.h" #include "content/common/content_export.h" +#include "content/public/browser/global_routing_id.h" #include "media/audio/audio_source_diverter.h" namespace media { @@ -54,10 +55,6 @@ // Interface for diverting audio data to an alternative AudioOutputStream. typedef media::AudioSourceDiverter Diverter; - // A SourceFrameRef is a RenderFrameHost identified by a <render_process_id, - // render_frame_id> pair. - typedef std::pair<int, int> SourceFrameRef; - // Interface to be implemented by audio mirroring destinations. See comments // for StartMirroring() and StopMirroring() below. class MirroringDestination { @@ -70,11 +67,12 @@ // access to a diverted audio flow versus 2) a duplicate copy of the audio // flow. |results_callback| must be run on the same thread as the one that // called QueryForMatches(). - typedef base::Callback<void(const std::set<SourceFrameRef>&, bool)> + typedef base::OnceCallback<void(const std::set<GlobalFrameRoutingId>&, + bool)> MatchesCallback; virtual void QueryForMatches( - const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback) = 0; + const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback) = 0; // Create a consumer of audio data in the format specified by |params|, and // connect it as an input to mirroring. This is used to provide @@ -138,7 +136,7 @@ struct StreamRoutingState { // The source render frame associated with the audio stream. - SourceFrameRef source_render_frame; + GlobalFrameRoutingId source_render_frame; // The diverter for re-routing the audio stream. Diverter* diverter; @@ -152,7 +150,7 @@ // StopDuplicating() is called to release them. std::map<MirroringDestination*, media::AudioPushSink*> duplications; - StreamRoutingState(const SourceFrameRef& source_frame, + StreamRoutingState(const GlobalFrameRoutingId& source_frame, Diverter* stream_diverter); StreamRoutingState(const StreamRoutingState& other); ~StreamRoutingState(); @@ -165,7 +163,7 @@ // |candidates| to be diverted to. void InitiateQueriesToFindNewDestination( MirroringDestination* old_destination, - const std::set<SourceFrameRef>& candidates); + const std::set<GlobalFrameRoutingId>& candidates); // MirroringDestination query callback. |matches| contains all RenderFrame // sources that will be diverted or duplicated to |destination|. @@ -175,15 +173,16 @@ // destination instead of diverted. void UpdateRoutesToDestination(MirroringDestination* destination, bool add_only, - const std::set<SourceFrameRef>& matches, + const std::set<GlobalFrameRoutingId>& matches, bool is_duplicate); // |matches| contains all RenderFrame sources that will be diverted to // |destination|. If |add_only| is false, then any Diverters currently routed // to |destination| but not found in |matches| will be stopped. - void UpdateRoutesToDivertDestination(MirroringDestination* destination, - bool add_only, - const std::set<SourceFrameRef>& matches); + void UpdateRoutesToDivertDestination( + MirroringDestination* destination, + bool add_only, + const std::set<GlobalFrameRoutingId>& matches); // |matches| contains all RenderFrame sources that will be duplicated to // |destination|. If |add_only| is false, then any Diverters currently @@ -191,7 +190,7 @@ void UpdateRoutesToDuplicateDestination( MirroringDestination* destination, bool add_only, - const std::set<SourceFrameRef>& matches); + const std::set<GlobalFrameRoutingId>& matches); // Starts diverting audio to the |new_destination|, if not NULL. Otherwise, // stops diverting audio.
diff --git a/content/browser/media/capture/audio_mirroring_manager_unittest.cc b/content/browser/media/capture/audio_mirroring_manager_unittest.cc index a485e46..d128405 100644 --- a/content/browser/media/capture/audio_mirroring_manager_unittest.cc +++ b/content/browser/media/capture/audio_mirroring_manager_unittest.cc
@@ -5,6 +5,7 @@ #include "content/browser/media/capture/audio_mirroring_manager.h" #include <map> +#include <memory> #include <utility> #include "base/bind.h" @@ -44,8 +45,6 @@ class MockMirroringDestination : public AudioMirroringManager::MirroringDestination { public: - typedef AudioMirroringManager::SourceFrameRef SourceFrameRef; - MockMirroringDestination(int render_process_id, int render_frame_id, bool is_duplication) @@ -54,27 +53,34 @@ query_count_(0), is_duplication_(is_duplication) {} - MOCK_METHOD2(QueryForMatches, - void(const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback)); + void QueryForMatches(const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback) override { + // The indirection is needed, because gmock has trouble with move-only + // parameters (like |results_callback|). + MockedQueryForMatches(candidates, &results_callback); + } + MOCK_METHOD2(MockedQueryForMatches, + void(const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback* results_callback)); + MOCK_METHOD1(AddInput, media::AudioOutputStream*(const media::AudioParameters& params)); MOCK_METHOD1(AddPushInput, media::AudioPushSink*(const media::AudioParameters& params)); - void SimulateQuery(const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback) { + void SimulateQuery(const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback* results_callback) { ++query_count_; - std::set<SourceFrameRef> result; - if (candidates.find(SourceFrameRef(render_process_id_, render_frame_id_)) != - candidates.end()) { - result.insert(SourceFrameRef(render_process_id_, render_frame_id_)); + std::set<GlobalFrameRoutingId> result; + if (candidates.find(GlobalFrameRoutingId( + render_process_id_, render_frame_id_)) != candidates.end()) { + result.insert(GlobalFrameRoutingId(render_process_id_, render_frame_id_)); } - BrowserThread::PostTask( - BrowserThread::IO, FROM_HERE, - base::BindOnce(results_callback, std::move(result), is_duplication_)); + BrowserThread::PostTask(BrowserThread::IO, FROM_HERE, + base::BindOnce(std::move(*results_callback), + std::move(result), is_duplication_)); } media::AudioOutputStream* SimulateAddInput( @@ -157,9 +163,9 @@ void StartMirroringTo(const std::unique_ptr<MockMirroringDestination>& dest, int expected_inputs_added, int expected_push_inputs_added) { - EXPECT_CALL(*dest, QueryForMatches(_, _)) - .WillRepeatedly(Invoke(dest.get(), - &MockMirroringDestination::SimulateQuery)); + EXPECT_CALL(*dest, MockedQueryForMatches(_, _)) + .WillRepeatedly( + Invoke(dest.get(), &MockMirroringDestination::SimulateQuery)); if (expected_inputs_added > 0) { EXPECT_CALL(*dest, AddInput(Ref(params_))) .Times(expected_inputs_added)
diff --git a/content/browser/media/capture/web_contents_audio_input_stream.cc b/content/browser/media/capture/web_contents_audio_input_stream.cc index e1593cc..75d9bee 100644 --- a/content/browser/media/capture/web_contents_audio_input_stream.cc +++ b/content/browser/media/capture/web_contents_audio_input_stream.cc
@@ -5,6 +5,7 @@ #include "content/browser/media/capture/web_contents_audio_input_stream.h" #include <memory> +#include <set> #include <string> #include "base/bind.h" @@ -60,8 +61,6 @@ private: friend class base::RefCountedThreadSafe<WebContentsAudioInputStream::Impl>; - typedef AudioMirroringManager::SourceFrameRef SourceFrameRef; - enum State { CONSTRUCTED, OPENED, @@ -88,10 +87,11 @@ void UnmuteWebContentsAudio(); // AudioMirroringManager::MirroringDestination implementation - void QueryForMatches(const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback) override; - void QueryForMatchesOnUIThread(const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback); + void QueryForMatches(const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback) override; + void QueryForMatchesOnUIThread( + const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback); media::AudioOutputStream* AddInput( const media::AudioParameters& params) override; media::AudioPushSink* AddPushInput( @@ -297,35 +297,34 @@ } void WebContentsAudioInputStream::Impl::QueryForMatches( - const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback) { + const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback) { BrowserThread::PostTask( BrowserThread::UI, FROM_HERE, base::BindOnce(&Impl::QueryForMatchesOnUIThread, this, candidates, - media::BindToCurrentLoop(results_callback))); + media::BindToCurrentLoop(std::move(results_callback)))); } void WebContentsAudioInputStream::Impl::QueryForMatchesOnUIThread( - const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback) { + const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback) { DCHECK_CURRENTLY_ON(BrowserThread::UI); - std::set<SourceFrameRef> matches; + std::set<GlobalFrameRoutingId> matches; WebContents* const contents = tracker_->web_contents(); if (contents) { // Add each ID to |matches| if it maps to a RenderFrameHost that maps to the // currently-tracked WebContents. - for (std::set<SourceFrameRef>::const_iterator i = candidates.begin(); - i != candidates.end(); ++i) { + for (const auto& it : candidates) { WebContents* const contents_containing_frame = WebContents::FromRenderFrameHost( - RenderFrameHost::FromID(i->first, i->second)); + RenderFrameHost::FromID(it.child_id, it.frame_routing_id)); if (contents_containing_frame == contents) - matches.insert(*i); + matches.insert(it); } } - results_callback.Run(matches, is_duplication_); + std::move(results_callback).Run(matches, is_duplication_); } media::AudioOutputStream* WebContentsAudioInputStream::Impl::AddInput(
diff --git a/content/browser/media/capture/web_contents_audio_muter.cc b/content/browser/media/capture/web_contents_audio_muter.cc index 59a30348..c10f522 100644 --- a/content/browser/media/capture/web_contents_audio_muter.cc +++ b/content/browser/media/capture/web_contents_audio_muter.cc
@@ -80,33 +80,32 @@ private: friend class base::RefCountedThreadSafe<MuteDestination>; - typedef AudioMirroringManager::SourceFrameRef SourceFrameRef; - ~MuteDestination() override {} - void QueryForMatches(const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback) override { + void QueryForMatches(const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback) override { BrowserThread::PostTask( BrowserThread::UI, FROM_HERE, base::BindOnce(&MuteDestination::QueryForMatchesOnUIThread, this, - candidates, media::BindToCurrentLoop(results_callback))); + candidates, + media::BindToCurrentLoop(std::move(results_callback)))); } - void QueryForMatchesOnUIThread(const std::set<SourceFrameRef>& candidates, - const MatchesCallback& results_callback) { + void QueryForMatchesOnUIThread( + const std::set<GlobalFrameRoutingId>& candidates, + MatchesCallback results_callback) { DCHECK_CURRENTLY_ON(BrowserThread::UI); - std::set<SourceFrameRef> matches; + std::set<GlobalFrameRoutingId> matches; // Add each ID to |matches| if it maps to a RenderFrameHost that maps to the // WebContents being muted. - for (std::set<SourceFrameRef>::const_iterator i = candidates.begin(); - i != candidates.end(); ++i) { + for (const auto& it : candidates) { WebContents* const contents_containing_frame = WebContents::FromRenderFrameHost( - RenderFrameHost::FromID(i->first, i->second)); + RenderFrameHost::FromID(it.child_id, it.frame_routing_id)); if (contents_containing_frame == web_contents_) - matches.insert(*i); + matches.insert(it); } - results_callback.Run(matches, false); + std::move(results_callback).Run(matches, false); } media::AudioOutputStream* AddInput(
diff --git a/content/browser/payments/payment_app_info_fetcher.cc b/content/browser/payments/payment_app_info_fetcher.cc index 5ba89bc..de760fb 100644 --- a/content/browser/payments/payment_app_info_fetcher.cc +++ b/content/browser/payments/payment_app_info_fetcher.cc
@@ -4,12 +4,15 @@ #include "content/browser/payments/payment_app_info_fetcher.h" +#include <utility> + #include "base/base64.h" #include "base/bind_helpers.h" #include "content/browser/frame_host/render_frame_host_impl.h" #include "content/browser/service_worker/service_worker_context_wrapper.h" #include "content/browser/web_contents/web_contents_impl.h" #include "content/public/browser/browser_thread.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/manifest_icon_downloader.h" #include "content/public/common/console_message_level.h" #include "third_party/blink/public/common/manifest/manifest_icon_selector.h" @@ -28,7 +31,7 @@ PaymentAppInfoFetchCallback callback) { DCHECK_CURRENTLY_ON(BrowserThread::IO); - std::unique_ptr<std::vector<std::pair<int, int>>> provider_hosts = + std::unique_ptr<std::vector<GlobalFrameRoutingId>> provider_hosts = service_worker_context->GetProviderHostIds(context_url.GetOrigin()); BrowserThread::PostTask( @@ -39,7 +42,7 @@ void PaymentAppInfoFetcher::StartOnUI( const GURL& context_url, - const std::unique_ptr<std::vector<std::pair<int, int>>>& provider_hosts, + const std::unique_ptr<std::vector<GlobalFrameRoutingId>>& provider_hosts, PaymentAppInfoFetchCallback callback) { DCHECK_CURRENTLY_ON(BrowserThread::UI); @@ -70,7 +73,7 @@ void PaymentAppInfoFetcher::SelfDeleteFetcher::Start( const GURL& context_url, - const std::unique_ptr<std::vector<std::pair<int, int>>>& provider_hosts) { + const std::unique_ptr<std::vector<GlobalFrameRoutingId>>& provider_hosts) { DCHECK_CURRENTLY_ON(BrowserThread::UI); if (provider_hosts->size() == 0U) { @@ -81,7 +84,7 @@ for (const auto& frame : *provider_hosts) { // Find out the render frame host registering the payment app. RenderFrameHostImpl* render_frame_host = - RenderFrameHostImpl::FromID(frame.first, frame.second); + RenderFrameHostImpl::FromID(frame.child_id, frame.frame_routing_id); if (!render_frame_host || context_url.spec().compare( render_frame_host->GetLastCommittedURL().spec()) != 0) {
diff --git a/content/browser/payments/payment_app_info_fetcher.h b/content/browser/payments/payment_app_info_fetcher.h index 73dd74fc..756622e 100644 --- a/content/browser/payments/payment_app_info_fetcher.h +++ b/content/browser/payments/payment_app_info_fetcher.h
@@ -10,6 +10,7 @@ #include "base/macros.h" #include "content/browser/service_worker/service_worker_context_wrapper.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/stored_payment_app.h" #include "content/public/browser/web_contents_observer.h" #include "third_party/blink/public/common/manifest/manifest.h" @@ -41,7 +42,7 @@ // Only accessed on the UI thread. static void StartOnUI( const GURL& context_url, - const std::unique_ptr<std::vector<std::pair<int, int>>>& provider_hosts, + const std::unique_ptr<std::vector<GlobalFrameRoutingId>>& provider_hosts, PaymentAppInfoFetchCallback callback); // Keeps track of the web contents. @@ -59,7 +60,7 @@ ~SelfDeleteFetcher(); void Start(const GURL& context_url, - const std::unique_ptr<std::vector<std::pair<int, int>>>& + const std::unique_ptr<std::vector<GlobalFrameRoutingId>>& provider_hosts); private:
diff --git a/content/browser/payments/payment_instrument_icon_fetcher.cc b/content/browser/payments/payment_instrument_icon_fetcher.cc index 8ef0de4e..3101c496 100644 --- a/content/browser/payments/payment_instrument_icon_fetcher.cc +++ b/content/browser/payments/payment_instrument_icon_fetcher.cc
@@ -4,6 +4,8 @@ #include "content/browser/payments/payment_instrument_icon_fetcher.h" +#include <utility> + #include "base/base64.h" #include "base/bind_helpers.h" #include "content/browser/frame_host/render_frame_host_impl.h" @@ -99,12 +101,12 @@ WebContents* GetWebContentsFromProviderHostIds( const GURL& scope, - std::unique_ptr<std::vector<std::pair<int, int>>> provider_hosts) { + std::unique_ptr<std::vector<GlobalFrameRoutingId>> provider_hosts) { DCHECK_CURRENTLY_ON(BrowserThread::UI); for (const auto& host : *provider_hosts) { RenderFrameHostImpl* render_frame_host = - RenderFrameHostImpl::FromID(host.first, host.second); + RenderFrameHostImpl::FromID(host.child_id, host.frame_routing_id); if (!render_frame_host) continue; @@ -122,7 +124,7 @@ void StartOnUI( const GURL& scope, - std::unique_ptr<std::vector<std::pair<int, int>>> provider_hosts, + std::unique_ptr<std::vector<GlobalFrameRoutingId>> provider_hosts, const std::vector<blink::Manifest::ImageResource>& icons, PaymentInstrumentIconFetcher::PaymentInstrumentIconFetcherCallback callback) { @@ -138,7 +140,7 @@ // static void PaymentInstrumentIconFetcher::Start( const GURL& scope, - std::unique_ptr<std::vector<std::pair<int, int>>> provider_hosts, + std::unique_ptr<std::vector<GlobalFrameRoutingId>> provider_hosts, const std::vector<blink::Manifest::ImageResource>& icons, PaymentInstrumentIconFetcherCallback callback) { DCHECK_CURRENTLY_ON(BrowserThread::IO);
diff --git a/content/browser/payments/payment_instrument_icon_fetcher.h b/content/browser/payments/payment_instrument_icon_fetcher.h index c31d531..43ade57 100644 --- a/content/browser/payments/payment_instrument_icon_fetcher.h +++ b/content/browser/payments/payment_instrument_icon_fetcher.h
@@ -5,12 +5,14 @@ #ifndef CONTENT_BROWSER_PAYMENTS_PAYMENT_INSTRUMENT_ICON_FETCHER_H_ #define CONTENT_BROWSER_PAYMENTS_PAYMENT_INSTRUMENT_ICON_FETCHER_H_ +#include <memory> #include <string> #include <vector> #include "base/callback_forward.h" #include "base/macros.h" #include "base/memory/ref_counted.h" +#include "content/public/browser/global_routing_id.h" #include "third_party/blink/public/common/manifest/manifest.h" #include "third_party/blink/public/platform/modules/payments/payment_app.mojom.h" @@ -24,7 +26,7 @@ // Should be called on IO thread. static void Start( const GURL& scope, - std::unique_ptr<std::vector<std::pair<int, int>>> provider_hosts, + std::unique_ptr<std::vector<GlobalFrameRoutingId>> provider_hosts, const std::vector<blink::Manifest::ImageResource>& icons, PaymentInstrumentIconFetcherCallback callback);
diff --git a/content/browser/renderer_host/render_widget_targeter.cc b/content/browser/renderer_host/render_widget_targeter.cc index 1239e5d..fce3e14a 100644 --- a/content/browser/renderer_host/render_widget_targeter.cc +++ b/content/browser/renderer_host/render_widget_targeter.cc
@@ -245,7 +245,8 @@ uint32_t request_id, const gfx::PointF& target_location, TracingUmaTracker tracker, - const viz::FrameSinkId& frame_sink_id) { + const viz::FrameSinkId& frame_sink_id, + const gfx::PointF& transformed_location) { tracker.Stop(); if (request_id != last_request_id_ || !request_in_flight_) { // This is a response to a request that already timed out, so the event @@ -267,10 +268,8 @@ unresponsive_views_.find(view) != unresponsive_views_.end()) { FoundTarget(root_view.get(), view, *event, latency, target_location, false); } else { - gfx::PointF location = target_location; - target->TransformPointToCoordSpaceForView(location, view, &location); - QueryClient(root_view.get(), view, *event, latency, location, target.get(), - target_location); + QueryClient(root_view.get(), view, *event, latency, transformed_location, + target.get(), target_location); } }
diff --git a/content/browser/renderer_host/render_widget_targeter.h b/content/browser/renderer_host/render_widget_targeter.h index 6399b2ad..5e6dda1d 100644 --- a/content/browser/renderer_host/render_widget_targeter.h +++ b/content/browser/renderer_host/render_widget_targeter.h
@@ -117,6 +117,11 @@ // |event| is in the coordinate space of |root_view|. |target_location|, if // set, is the location in |target|'s coordinate space. + // |target| is the current target that will be queried using its + // InputTargetClient interface. + // |frame_sink_id| is returned from the InputTargetClient to indicate where + // the event should be routed, and |transformed_location| is the point in + // that new target's coordinate space. void FoundFrameSinkId(base::WeakPtr<RenderWidgetHostViewBase> root_view, base::WeakPtr<RenderWidgetHostViewBase> target, ui::WebScopedInputEvent event, @@ -124,7 +129,8 @@ uint32_t request_id, const gfx::PointF& target_location, TracingUmaTracker tracker, - const viz::FrameSinkId& frame_sink_id); + const viz::FrameSinkId& frame_sink_id, + const gfx::PointF& transformed_location); // |event| is in the coordinate space of |root_view|. |target_location|, if // set, is the location in |target|'s coordinate space. If |latched_target| is
diff --git a/content/browser/service_worker/embedded_worker_test_helper.cc b/content/browser/service_worker/embedded_worker_test_helper.cc index f432bee..191b0d1 100644 --- a/content/browser/service_worker/embedded_worker_test_helper.cc +++ b/content/browser/service_worker/embedded_worker_test_helper.cc
@@ -213,49 +213,39 @@ } void DispatchBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, DispatchBackgroundFetchAbortEventCallback callback) override { if (!helper_) return; - helper_->OnBackgroundFetchAbortEventStub(developer_id, unique_id, state, - std::move(callback)); + helper_->OnBackgroundFetchAbortEventStub(registration, std::move(callback)); } void DispatchBackgroundFetchClickEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, DispatchBackgroundFetchClickEventCallback callback) override { if (!helper_) return; - helper_->OnBackgroundFetchClickEventStub(developer_id, unique_id, state, - std::move(callback)); + helper_->OnBackgroundFetchClickEventStub(registration, std::move(callback)); } void DispatchBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, DispatchBackgroundFetchFailEventCallback callback) override { if (!helper_) return; - helper_->OnBackgroundFetchFailEventStub(developer_id, unique_id, state, - fetches, std::move(callback)); + helper_->OnBackgroundFetchFailEventStub(registration, fetches, + std::move(callback)); } void DispatchBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, DispatchBackgroundFetchSuccessEventCallback callback) override { if (!helper_) return; - helper_->OnBackgroundFetchSuccessEventStub(developer_id, unique_id, state, - fetches, std::move(callback)); + helper_->OnBackgroundFetchSuccessEventStub(registration, fetches, + std::move(callback)); } void DispatchCookieChangeEvent( @@ -599,27 +589,21 @@ } void EmbeddedWorkerTestHelper::OnBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchAbortEventCallback callback) { std::move(callback).Run(blink::mojom::ServiceWorkerEventStatus::COMPLETED, base::Time::Now()); } void EmbeddedWorkerTestHelper::OnBackgroundFetchClickEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchClickEventCallback callback) { std::move(callback).Run(blink::mojom::ServiceWorkerEventStatus::COMPLETED, base::Time::Now()); } void EmbeddedWorkerTestHelper::OnBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchFailEventCallback callback) { std::move(callback).Run(blink::mojom::ServiceWorkerEventStatus::COMPLETED, @@ -627,9 +611,7 @@ } void EmbeddedWorkerTestHelper::OnBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchSuccessEventCallback callback) { @@ -880,54 +862,42 @@ } void EmbeddedWorkerTestHelper::OnBackgroundFetchAbortEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchAbortEventCallback callback) { base::ThreadTaskRunnerHandle::Get()->PostTask( FROM_HERE, base::BindOnce(&EmbeddedWorkerTestHelper::OnBackgroundFetchAbortEvent, - AsWeakPtr(), developer_id, unique_id, state, - std::move(callback))); + AsWeakPtr(), registration, std::move(callback))); } void EmbeddedWorkerTestHelper::OnBackgroundFetchClickEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchClickEventCallback callback) { base::ThreadTaskRunnerHandle::Get()->PostTask( FROM_HERE, base::BindOnce(&EmbeddedWorkerTestHelper::OnBackgroundFetchClickEvent, - AsWeakPtr(), developer_id, unique_id, state, - std::move(callback))); + AsWeakPtr(), registration, std::move(callback))); } void EmbeddedWorkerTestHelper::OnBackgroundFetchFailEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchFailEventCallback callback) { base::ThreadTaskRunnerHandle::Get()->PostTask( FROM_HERE, base::BindOnce(&EmbeddedWorkerTestHelper::OnBackgroundFetchFailEvent, - AsWeakPtr(), developer_id, unique_id, state, fetches, - std::move(callback))); + AsWeakPtr(), registration, fetches, std::move(callback))); } void EmbeddedWorkerTestHelper::OnBackgroundFetchSuccessEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchSuccessEventCallback callback) { base::ThreadTaskRunnerHandle::Get()->PostTask( FROM_HERE, base::BindOnce(&EmbeddedWorkerTestHelper::OnBackgroundFetchSuccessEvent, - AsWeakPtr(), developer_id, unique_id, state, fetches, - std::move(callback))); + AsWeakPtr(), registration, fetches, std::move(callback))); } void EmbeddedWorkerTestHelper::OnCookieChangeEventStub(
diff --git a/content/browser/service_worker/embedded_worker_test_helper.h b/content/browser/service_worker/embedded_worker_test_helper.h index e632de9..ac8cff0 100644 --- a/content/browser/service_worker/embedded_worker_test_helper.h +++ b/content/browser/service_worker/embedded_worker_test_helper.h
@@ -35,6 +35,7 @@ namespace content { +struct BackgroundFetchRegistration; struct BackgroundFetchSettledFetch; class EmbeddedWorkerRegistry; class EmbeddedWorkerTestHelper; @@ -167,25 +168,17 @@ virtual void OnActivateEvent( mojom::ServiceWorker::DispatchActivateEventCallback callback); virtual void OnBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchAbortEventCallback callback); virtual void OnBackgroundFetchClickEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchClickEventCallback callback); virtual void OnBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchFailEventCallback callback); virtual void OnBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchSuccessEventCallback callback); @@ -271,25 +264,17 @@ void OnActivateEventStub( mojom::ServiceWorker::DispatchActivateEventCallback callback); void OnBackgroundFetchAbortEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchAbortEventCallback callback); void OnBackgroundFetchClickEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, mojom::ServiceWorker::DispatchBackgroundFetchClickEventCallback callback); void OnBackgroundFetchFailEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchFailEventCallback callback); void OnBackgroundFetchSuccessEventStub( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, mojom::ServiceWorker::DispatchBackgroundFetchSuccessEventCallback callback);
diff --git a/content/browser/service_worker/service_worker_content_settings_proxy_impl.cc b/content/browser/service_worker/service_worker_content_settings_proxy_impl.cc index e4b82677..3ba2c39c 100644 --- a/content/browser/service_worker/service_worker_content_settings_proxy_impl.cc +++ b/content/browser/service_worker/service_worker_content_settings_proxy_impl.cc
@@ -4,9 +4,13 @@ #include "content/browser/service_worker/service_worker_content_settings_proxy_impl.h" +#include <utility> +#include <vector> + #include "base/threading/thread.h" #include "content/public/browser/browser_thread.h" #include "content/public/browser/content_browser_client.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/common/content_client.h" #include "mojo/public/cpp/bindings/strong_binding.h" @@ -40,7 +44,7 @@ // content setting. However, service worker is not necessarily associated // with frames or making the request on behalf of frames, // so just pass an empty |render_frames|. - std::vector<std::pair<int, int>> render_frames; + std::vector<GlobalFrameRoutingId> render_frames; std::move(callback).Run(GetContentClient()->browser()->AllowWorkerIndexedDB( origin_.GetURL(), name, context_->wrapper()->resource_context(), render_frames));
diff --git a/content/browser/service_worker/service_worker_context_wrapper.cc b/content/browser/service_worker/service_worker_context_wrapper.cc index 513226c..ea8ec10 100644 --- a/content/browser/service_worker/service_worker_context_wrapper.cc +++ b/content/browser/service_worker/service_worker_context_wrapper.cc
@@ -631,20 +631,20 @@ context_core_->HasMainFrameProviderHost(origin, std::move(callback)); } -std::unique_ptr<std::vector<std::pair<int, int>>> +std::unique_ptr<std::vector<GlobalFrameRoutingId>> ServiceWorkerContextWrapper::GetProviderHostIds(const GURL& origin) const { DCHECK_CURRENTLY_ON(BrowserThread::IO); - std::unique_ptr<std::vector<std::pair<int, int>>> provider_host_ids( - new std::vector<std::pair<int, int>>()); + std::unique_ptr<std::vector<GlobalFrameRoutingId>> provider_host_ids( + new std::vector<GlobalFrameRoutingId>()); for (std::unique_ptr<ServiceWorkerContextCore::ProviderHostIterator> it = context_core_->GetClientProviderHostIterator( origin, false /* include_reserved_clients */); !it->IsAtEnd(); it->Advance()) { ServiceWorkerProviderHost* provider_host = it->GetProviderHost(); - provider_host_ids->push_back( - std::make_pair(provider_host->process_id(), provider_host->frame_id())); + provider_host_ids->push_back(GlobalFrameRoutingId( + provider_host->process_id(), provider_host->frame_id())); } return provider_host_ids;
diff --git a/content/browser/service_worker/service_worker_context_wrapper.h b/content/browser/service_worker/service_worker_context_wrapper.h index f897d4f..7766bd23 100644 --- a/content/browser/service_worker/service_worker_context_wrapper.h +++ b/content/browser/service_worker/service_worker_context_wrapper.h
@@ -19,6 +19,7 @@ #include "content/browser/service_worker/service_worker_context_core.h" #include "content/browser/service_worker/service_worker_context_core_observer.h" #include "content/common/content_export.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/service_worker_context.h" namespace base { @@ -151,10 +152,9 @@ void HasMainFrameProviderHost(const GURL& origin, BoolCallback callback) const; - // Returns all render process ids and frame ids for the given |origin|. - std::unique_ptr< - std::vector<std::pair<int /* render process id */, int /* frame id */>>> - GetProviderHostIds(const GURL& origin) const; + // Returns all frame ids for the given |origin|. + std::unique_ptr<std::vector<GlobalFrameRoutingId>> GetProviderHostIds( + const GURL& origin) const; // Returns the registration whose scope longest matches |document_url|. It is // guaranteed that the returned registration has the activated worker.
diff --git a/content/browser/shared_worker/shared_worker_host.cc b/content/browser/shared_worker/shared_worker_host.cc index 993b59f..ba80bf1 100644 --- a/content/browser/shared_worker/shared_worker_host.cc +++ b/content/browser/shared_worker/shared_worker_host.cc
@@ -41,7 +41,7 @@ void AllowFileSystemOnIOThread(const GURL& url, ResourceContext* resource_context, - std::vector<std::pair<int, int>> render_frames, + std::vector<GlobalFrameRoutingId> render_frames, base::OnceCallback<void(bool)> callback) { DCHECK_CURRENTLY_ON(BrowserThread::IO); GetContentClient()->browser()->AllowWorkerFileSystem( @@ -52,7 +52,7 @@ bool AllowIndexedDBOnIOThread(const GURL& url, const base::string16& name, ResourceContext* resource_context, - std::vector<std::pair<int, int>> render_frames) { + std::vector<GlobalFrameRoutingId> render_frames) { DCHECK_CURRENTLY_ON(BrowserThread::IO); return GetContentClient()->browser()->AllowWorkerIndexedDB( url, name, resource_context, render_frames); @@ -372,11 +372,12 @@ info.client->OnFeatureUsed(feature); } -std::vector<std::pair<int, int>> +std::vector<GlobalFrameRoutingId> SharedWorkerHost::GetRenderFrameIDsForWorker() { - std::vector<std::pair<int, int>> result; + std::vector<GlobalFrameRoutingId> result; + result.reserve(clients_.size()); for (const ClientInfo& info : clients_) - result.push_back(std::make_pair(info.process_id, info.frame_id)); + result.push_back(GlobalFrameRoutingId(info.process_id, info.frame_id)); return result; }
diff --git a/content/browser/shared_worker/shared_worker_host.h b/content/browser/shared_worker/shared_worker_host.h index d8c7382..8947786 100644 --- a/content/browser/shared_worker/shared_worker_host.h +++ b/content/browser/shared_worker/shared_worker_host.h
@@ -21,6 +21,7 @@ #include "content/common/shared_worker/shared_worker_client.mojom.h" #include "content/common/shared_worker/shared_worker_factory.mojom.h" #include "content/common/shared_worker/shared_worker_host.mojom.h" +#include "content/public/browser/global_routing_id.h" #include "mojo/public/cpp/bindings/binding.h" #include "services/network/public/mojom/url_loader_factory.mojom.h" #include "services/service_manager/public/mojom/interface_provider.mojom.h" @@ -132,8 +133,8 @@ void OnScriptLoadFailed() override; void OnFeatureUsed(blink::mojom::WebFeature feature) override; - // Return a vector of all the render process/render frame IDs. - std::vector<std::pair<int, int>> GetRenderFrameIDsForWorker(); + // Returns the frame ids of this worker's clients. + std::vector<GlobalFrameRoutingId> GetRenderFrameIDsForWorker(); void AllowFileSystemResponse(base::OnceCallback<void(bool)> callback, bool allowed);
diff --git a/content/browser/site_per_process_browsertest.cc b/content/browser/site_per_process_browsertest.cc index 48bd9c4..1497e843 100644 --- a/content/browser/site_per_process_browsertest.cc +++ b/content/browser/site_per_process_browsertest.cc
@@ -375,23 +375,6 @@ focus_observer.Wait(); } -// A BrowserMessageFilter that drops SwapOut ACK messages. -class SwapoutACKMessageFilter : public BrowserMessageFilter { - public: - SwapoutACKMessageFilter() : BrowserMessageFilter(FrameMsgStart) {} - - protected: - ~SwapoutACKMessageFilter() override {} - - private: - // BrowserMessageFilter: - bool OnMessageReceived(const IPC::Message& message) override { - return message.type() == FrameHostMsg_SwapOut_ACK::ID; - } - - DISALLOW_COPY_AND_ASSIGN(SwapoutACKMessageFilter); -}; - class RenderWidgetHostVisibilityObserver : public RenderWidgetHostObserver { public: explicit RenderWidgetHostVisibilityObserver(RenderWidgetHostImpl* rwhi, @@ -7800,10 +7783,10 @@ // At this point, we should have two pending WebContents. EXPECT_TRUE(base::ContainsKey( web_contents()->pending_contents_, - std::make_pair(process1->GetID(), filter1->routing_id()))); + GlobalRoutingID(process1->GetID(), filter1->routing_id()))); EXPECT_TRUE(base::ContainsKey( web_contents()->pending_contents_, - std::make_pair(process2->GetID(), filter2->routing_id()))); + GlobalRoutingID(process2->GetID(), filter2->routing_id()))); // Both subframes were set up in the same way, so the next routing ID for the // new popup windows should match up (this led to the collision in the @@ -7878,10 +7861,10 @@ // At this point, we should have two pending widgets. EXPECT_TRUE(base::ContainsKey( web_contents()->pending_widget_views_, - std::make_pair(process1->GetID(), filter1->routing_id()))); + GlobalRoutingID(process1->GetID(), filter1->routing_id()))); EXPECT_TRUE(base::ContainsKey( web_contents()->pending_widget_views_, - std::make_pair(process2->GetID(), filter2->routing_id()))); + GlobalRoutingID(process2->GetID(), filter2->routing_id()))); // Both subframes were set up in the same way, so the next routing ID for the // new popup widgets should match up (this led to the collision in the @@ -7895,10 +7878,10 @@ false, gfx::Rect()); EXPECT_FALSE(base::ContainsKey( web_contents()->pending_widget_views_, - std::make_pair(process1->GetID(), filter1->routing_id()))); + GlobalRoutingID(process1->GetID(), filter1->routing_id()))); EXPECT_FALSE(base::ContainsKey( web_contents()->pending_widget_views_, - std::make_pair(process2->GetID(), filter2->routing_id()))); + GlobalRoutingID(process2->GetID(), filter2->routing_id()))); } #endif
diff --git a/content/browser/site_per_process_hit_test_browsertest.cc b/content/browser/site_per_process_hit_test_browsertest.cc index 06d9651..7e4cb96 100644 --- a/content/browser/site_per_process_hit_test_browsertest.cc +++ b/content/browser/site_per_process_hit_test_browsertest.cc
@@ -217,7 +217,10 @@ RouteMouseEventAndWaitUntilDispatch(router, root_view, expected_target, &down_event); EXPECT_TRUE(monitor.EventWasReceived()); - EXPECT_NEAR(expected_location.x(), monitor.event().PositionInWidget().x, 2); + EXPECT_NEAR(expected_location.x(), monitor.event().PositionInWidget().x, 2) + << " & original location was " << location.x() << ", " << location.y() + << " & root_location was " << root_location.x() << ", " + << root_location.y(); EXPECT_NEAR(expected_location.y(), monitor.event().PositionInWidget().y, 2); } @@ -318,6 +321,44 @@ gfx::PointF(5, 5)); } +void PerspectiveTransformedSurfaceHitTestHelper( + Shell* shell, + net::test_server::EmbeddedTestServer* embedded_test_server) { + GURL main_url(embedded_test_server->GetURL( + "/frame_tree/page_with_perspective_transformed_frame.html")); + EXPECT_TRUE(NavigateToURL(shell, main_url)); + auto* web_contents = static_cast<WebContentsImpl*>(shell->web_contents()); + + RenderFrameSubmissionObserver render_frame_submission_observer(web_contents); + + FrameTreeNode* root = web_contents->GetFrameTree()->root(); + ASSERT_EQ(1U, root->child_count()); + + FrameTreeNode* child_node = root->child_at(0); + GURL site_url(embedded_test_server->GetURL("baz.com", "/title1.html")); + EXPECT_EQ(site_url, child_node->current_url()); + EXPECT_NE(shell->web_contents()->GetSiteInstance(), + child_node->current_frame_host()->GetSiteInstance()); + + RenderWidgetHostViewBase* rwhv_root = static_cast<RenderWidgetHostViewBase*>( + root->current_frame_host()->GetRenderWidgetHost()->GetView()); + RenderWidgetHostViewBase* rwhv_child = static_cast<RenderWidgetHostViewBase*>( + child_node->current_frame_host()->GetRenderWidgetHost()->GetView()); + + WaitForHitTestDataOrChildSurfaceReady(child_node->current_frame_host()); + + // (90, 75) hit tests into the child frame that is positioned at (50, 50). + // Without other transformations this should result in a translated point + // of (40, 25), but the 45 degree 3-dimensional rotation of the frame about + // a vertical axis skews it. + // We can't allow DispatchMouseEventAndWaitUntilDispatch to compute the + // coordinates in the root space unless browser conversions with + // perspective transforms are first fixed. See https://crbug.com/854257. + DispatchMouseEventAndWaitUntilDispatch(web_contents, rwhv_root, + gfx::PointF(90, 75), rwhv_child, + gfx::PointF(33, 23)); +} + // Helper function that performs a surface hittest in nested frame. void NestedSurfaceHitTestTestHelper( Shell* shell, @@ -1872,6 +1913,27 @@ NonFlatTransformedSurfaceHitTestHelper(shell(), embedded_test_server()); } +// TODO(kenrb): Running this test on Android bots has slight discrepancies in +// transformed event coordinates when we do manual calculation of expected +// values. We can't rely on browser side transformation because it is broken +// for perspective transforms. See https://crbug.com/854247. +#if defined(OS_ANDROID) +#define MAYBE_PerspectiveTransformedSurfaceHitTestTest \ + DISABLED_PerspectiveTransformedSurfaceHitTestTest +#else +#define MAYBE_PerspectiveTransformedSurfaceHitTestTest \ + PerspectiveTransformedSurfaceHitTestTest +#endif +IN_PROC_BROWSER_TEST_P(SitePerProcessHitTestBrowserTest, + MAYBE_PerspectiveTransformedSurfaceHitTestTest) { + PerspectiveTransformedSurfaceHitTestHelper(shell(), embedded_test_server()); +} + +IN_PROC_BROWSER_TEST_P(SitePerProcessHighDPIHitTestBrowserTest, + MAYBE_PerspectiveTransformedSurfaceHitTestTest) { + PerspectiveTransformedSurfaceHitTestHelper(shell(), embedded_test_server()); +} + #if defined(OS_LINUX) // Flaky timeouts and failures: https://crbug.com/833380 #define MAYBE_OverlapSurfaceHitTestTest DISABLED_OverlapSurfaceHitTestTest @@ -4583,37 +4645,46 @@ { base::RunLoop run_loop; viz::FrameSinkId received_frame_sink_id; + gfx::PointF returned_point; base::Closure quit_closure = content::GetDeferredQuitTaskForRunLoop(&run_loop); DCHECK_NE(child_node->current_frame_host()->GetInputTargetClient(), nullptr); child_node->current_frame_host()->GetInputTargetClient()->FrameSinkIdAt( point_in_child, - base::BindLambdaForTesting([&](const viz::FrameSinkId& id) { - received_frame_sink_id = id; - quit_closure.Run(); - })); + base::BindLambdaForTesting( + [&](const viz::FrameSinkId& id, const gfx::PointF& point) { + received_frame_sink_id = id; + returned_point = point; + quit_closure.Run(); + })); content::RunThisRunLoop(&run_loop); // |point_in_child| should hit test to the view for |child_node|. ASSERT_EQ(rwhv_child->GetFrameSinkId(), received_frame_sink_id); + ASSERT_EQ(gfx::PointF(1, 1), returned_point); } { base::RunLoop run_loop; viz::FrameSinkId received_frame_sink_id; + gfx::PointF returned_point; base::Closure quit_closure = content::GetDeferredQuitTaskForRunLoop(&run_loop); DCHECK_NE(child_node->current_frame_host()->GetInputTargetClient(), nullptr); child_node->current_frame_host()->GetInputTargetClient()->FrameSinkIdAt( gfx::ToCeiledPoint(point_in_nested_child), - base::BindLambdaForTesting([&](const viz::FrameSinkId& id) { - received_frame_sink_id = id; - quit_closure.Run(); - })); + base::BindLambdaForTesting( + [&](const viz::FrameSinkId& id, const gfx::PointF& point) { + received_frame_sink_id = id; + returned_point = point; + quit_closure.Run(); + })); content::RunThisRunLoop(&run_loop); // |point_in_nested_child| should hit test to |rwhv_grandchild|. ASSERT_EQ(rwhv_grandchild->GetFrameSinkId(), received_frame_sink_id); + EXPECT_NEAR(returned_point.x(), 5, 2); + EXPECT_NEAR(returned_point.y(), 5, 2); } }
diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc index f806c32..51d4ce1e 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc
@@ -2670,8 +2670,8 @@ // FrameTreeNode id instead of the routing id of the Widget for the main // frame. https://crbug.com/545684 DCHECK_NE(MSG_ROUTING_NONE, main_frame_widget_route_id); - pending_contents_[std::make_pair(render_process_id, - main_frame_widget_route_id)] = + pending_contents_[GlobalRoutingID(render_process_id, + main_frame_widget_route_id)] = std::move(new_contents); AddDestructionObserver(raw_new_contents); } @@ -2773,7 +2773,7 @@ widget_view->SetPopupType(popup_type); } // Save the created widget associated with the route so we can show it later. - pending_widget_views_[std::make_pair(render_process_id, route_id)] = + pending_widget_views_[GlobalRoutingID(render_process_id, route_id)] = widget_view; } @@ -2866,7 +2866,7 @@ std::unique_ptr<WebContents> WebContentsImpl::GetCreatedWindow( int process_id, int main_frame_widget_route_id) { - auto key = std::make_pair(process_id, main_frame_widget_route_id); + auto key = GlobalRoutingID(process_id, main_frame_widget_route_id); auto iter = pending_contents_.find(key); // Certain systems can block the creation of new windows. If we didn't succeed @@ -2894,14 +2894,14 @@ RenderWidgetHostView* WebContentsImpl::GetCreatedWidget(int process_id, int route_id) { - auto iter = pending_widget_views_.find(std::make_pair(process_id, route_id)); + auto iter = pending_widget_views_.find(GlobalRoutingID(process_id, route_id)); if (iter == pending_widget_views_.end()) { DCHECK(false); return nullptr; } RenderWidgetHostView* widget_host_view = iter->second; - pending_widget_views_.erase(std::make_pair(process_id, route_id)); + pending_widget_views_.erase(GlobalRoutingID(process_id, route_id)); RenderWidgetHost* widget_host = widget_host_view->GetRenderWidgetHost(); if (!widget_host->GetProcess()->IsInitializedAndNotDead()) {
diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h index dc1b991d..96a42c8 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h
@@ -41,6 +41,7 @@ #include "content/browser/wake_lock/wake_lock_context_host.h" #include "content/common/content_export.h" #include "content/public/browser/color_chooser.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/notification_observer.h" #include "content/public/browser/notification_registrar.h" #include "content/public/browser/web_contents.h" @@ -1005,6 +1006,8 @@ NotifyFullscreenAcquired_Navigate); FRIEND_TEST_ALL_PREFIXES(WebContentsImplBrowserTest, NotifyFullscreenAcquired_SameOrigin); + FRIEND_TEST_ALL_PREFIXES(WebContentsImplBrowserTest, + FullscreenAfterFrameSwap); FRIEND_TEST_ALL_PREFIXES(FormStructureBrowserTest, HTMLFiles); FRIEND_TEST_ALL_PREFIXES(NavigationControllerTest, HistoryNavigate); FRIEND_TEST_ALL_PREFIXES(RenderFrameHostManagerTest, PageDoesBackAndReload); @@ -1410,13 +1413,11 @@ // Tracks created WebContentsImpl objects that have not been shown yet. They // are identified by the process ID and routing ID passed to CreateNewWindow. - typedef std::pair<int, int> ProcessRoutingIdPair; - std::map<ProcessRoutingIdPair, std::unique_ptr<WebContents>> - pending_contents_; + std::map<GlobalRoutingID, std::unique_ptr<WebContents>> pending_contents_; // This map holds widgets that were created on behalf of the renderer but // haven't been shown yet. - std::map<ProcessRoutingIdPair, RenderWidgetHostView*> pending_widget_views_; + std::map<GlobalRoutingID, RenderWidgetHostView*> pending_widget_views_; std::map<WebContentsImpl*, std::unique_ptr<DestructionObserver>> destruction_observers_;
diff --git a/content/browser/web_contents/web_contents_impl_browsertest.cc b/content/browser/web_contents/web_contents_impl_browsertest.cc index 367e29c..f631913 100644 --- a/content/browser/web_contents/web_contents_impl_browsertest.cc +++ b/content/browser/web_contents/web_contents_impl_browsertest.cc
@@ -2696,15 +2696,42 @@ } } -// TODO(beccahughes@): This test is flaking on Android. https://crbug.com/855018 -#if defined(OS_ANDROID) -#define MAYBE_NotifyFullscreenAcquired_Navigate \ - DISABLED_NotifyFullscreenAcquired_Navigate -#else -#define MAYBE_NotifyFullscreenAcquired_Navigate NotifyFullscreenAcquired_Navigate -#endif +// Regression test for https://crbug.com/855018. +// RenderFrameHostImpls exit fullscreen as soon as they are swapped out. +IN_PROC_BROWSER_TEST_F(WebContentsImplBrowserTest, FullscreenAfterFrameSwap) { + ASSERT_TRUE(embedded_test_server()->Start()); + WebContentsImpl* web_contents = + static_cast<WebContentsImpl*>(shell()->web_contents()); + + GURL url_a = embedded_test_server()->GetURL("a.com", "/title1.html"); + GURL url_b = embedded_test_server()->GetURL("b.com", "/title1.html"); + + // 1) Navigate. There is initially no fullscreen frame. + EXPECT_TRUE(NavigateToURL(shell(), url_a)); + RenderFrameHostImpl* main_frame = + static_cast<RenderFrameHostImpl*>(web_contents->GetMainFrame()); + EXPECT_EQ(0u, web_contents->fullscreen_frame_tree_nodes_.size()); + + // 2) Make it fullscreen. + FullscreenWebContentsObserver observer(web_contents, main_frame); + EXPECT_TRUE( + ExecuteScript(main_frame, "document.body.webkitRequestFullscreen();")); + observer.Wait(); + EXPECT_EQ(1u, web_contents->fullscreen_frame_tree_nodes_.size()); + + // 3) Navigate cross origin. Act as if the old frame was very slow delivering + // the swapout ack and stayed in pending deletion for a while. Even if the + // frame is still present, it must be removed from the list of frame in + // fullscreen immediately. + auto filter = base::MakeRefCounted<SwapoutACKMessageFilter>(); + main_frame->GetProcess()->AddFilter(filter.get()); + main_frame->DisableSwapOutTimerForTesting(); + EXPECT_TRUE(NavigateToURL(shell(), url_b)); + EXPECT_EQ(0u, web_contents->fullscreen_frame_tree_nodes_.size()); +} + IN_PROC_BROWSER_TEST_F(WebContentsImplBrowserTest, - MAYBE_NotifyFullscreenAcquired_Navigate) { + NotifyFullscreenAcquired_Navigate) { ASSERT_TRUE(embedded_test_server()->Start()); WebContentsImpl* web_contents = static_cast<WebContentsImpl*>(shell()->web_contents());
diff --git a/content/browser/web_contents/web_contents_view_aura.h b/content/browser/web_contents/web_contents_view_aura.h index 058f3e0..5c8f8a76 100644 --- a/content/browser/web_contents/web_contents_view_aura.h +++ b/content/browser/web_contents/web_contents_view_aura.h
@@ -12,12 +12,12 @@ #include "base/macros.h" #include "base/memory/ref_counted.h" #include "base/memory/weak_ptr.h" -#include "content/browser/loader/global_routing_id.h" #include "content/browser/renderer_host/overscroll_controller_delegate.h" #include "content/browser/renderer_host/render_view_host_delegate_view.h" #include "content/browser/web_contents/web_contents_view.h" #include "content/common/buildflags.h" #include "content/common/content_export.h" +#include "content/public/browser/global_routing_id.h" #include "ui/aura/client/drag_drop_delegate.h" #include "ui/aura/window.h" #include "ui/aura/window_delegate.h"
diff --git a/content/browser/web_contents/web_drag_dest_mac.h b/content/browser/web_contents/web_drag_dest_mac.h index c81c2a89..6d6ae69 100644 --- a/content/browser/web_contents/web_drag_dest_mac.h +++ b/content/browser/web_contents/web_drag_dest_mac.h
@@ -10,8 +10,8 @@ #include <memory> #include "base/strings/string16.h" -#include "content/browser/loader/global_routing_id.h" #include "content/common/content_export.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/common/drop_data.h" #include "ui/gfx/geometry/point_f.h"
diff --git a/content/child/runtime_features.cc b/content/child/runtime_features.cc index 9fbd8bb..65229dd8 100644 --- a/content/child/runtime_features.cc +++ b/content/child/runtime_features.cc
@@ -444,9 +444,11 @@ WebRuntimeFeatures::EnableIsolatedCodeCache( base::FeatureList::IsEnabled(features::kIsolatedCodeCache)); - // Make srcset on link rel=preload work with SignedHTTPExchange flag too. - if (base::FeatureList::IsEnabled(features::kSignedHTTPExchange)) + if (base::FeatureList::IsEnabled(features::kSignedHTTPExchange)) { + WebRuntimeFeatures::EnableSignedHTTPExchange(true); + // Make srcset on link rel=preload work with SignedHTTPExchange flag too. WebRuntimeFeatures::EnablePreloadImageSrcSetEnabled(true); + } WebRuntimeFeatures::EnableNestedWorkers( base::FeatureList::IsEnabled(blink::features::kNestedWorkers));
diff --git a/content/common/background_fetch/background_fetch_struct_traits.cc b/content/common/background_fetch/background_fetch_struct_traits.cc index aa1d30fd..a8bde81 100644 --- a/content/common/background_fetch/background_fetch_struct_traits.cc +++ b/content/common/background_fetch/background_fetch_struct_traits.cc
@@ -39,6 +39,7 @@ registration->uploaded = data.uploaded(); registration->download_total = data.download_total(); registration->downloaded = data.downloaded(); + registration->state = data.state(); return true; }
diff --git a/content/common/background_fetch/background_fetch_struct_traits.h b/content/common/background_fetch/background_fetch_struct_traits.h index 512f74b..3a3a6e1e 100644 --- a/content/common/background_fetch/background_fetch_struct_traits.h +++ b/content/common/background_fetch/background_fetch_struct_traits.h
@@ -64,6 +64,10 @@ const content::BackgroundFetchRegistration& registration) { return registration.downloaded; } + static blink::mojom::BackgroundFetchState state( + const content::BackgroundFetchRegistration& registration) { + return registration.state; + } static bool Read(blink::mojom::BackgroundFetchRegistrationDataView data, content::BackgroundFetchRegistration* registration);
diff --git a/content/common/background_fetch/background_fetch_struct_traits_unittest.cc b/content/common/background_fetch/background_fetch_struct_traits_unittest.cc index d990a54..615ec52 100644 --- a/content/common/background_fetch/background_fetch_struct_traits_unittest.cc +++ b/content/common/background_fetch/background_fetch_struct_traits_unittest.cc
@@ -59,6 +59,7 @@ registration.developer_id = "my_id"; registration.unique_id = "7e57ab1e-c0de-a150-ca75-1e75f005ba11"; registration.download_total = 9001; + registration.state = blink::mojom::BackgroundFetchState::FAILURE; BackgroundFetchRegistration roundtrip_registration; ASSERT_TRUE(blink::mojom::BackgroundFetchRegistration::Deserialize( @@ -69,6 +70,7 @@ EXPECT_EQ(roundtrip_registration.unique_id, registration.unique_id); EXPECT_EQ(roundtrip_registration.download_total, registration.download_total); + EXPECT_EQ(roundtrip_registration.state, registration.state); } TEST(BackgroundFetchStructTraitsTest, ImageResourceRoundtrip) {
diff --git a/content/common/background_fetch/background_fetch_types.cc b/content/common/background_fetch/background_fetch_types.cc index a1e3ac23..e57a1a38 100644 --- a/content/common/background_fetch/background_fetch_types.cc +++ b/content/common/background_fetch/background_fetch_types.cc
@@ -3,6 +3,7 @@ // found in the LICENSE file. #include "content/common/background_fetch/background_fetch_types.h" +#include "third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom.h" namespace { @@ -27,7 +28,24 @@ BackgroundFetchOptions::~BackgroundFetchOptions() = default; -BackgroundFetchRegistration::BackgroundFetchRegistration() = default; +BackgroundFetchRegistration::BackgroundFetchRegistration() + : state(blink::mojom::BackgroundFetchState::PENDING) {} + +BackgroundFetchRegistration::BackgroundFetchRegistration( + const std::string& developer_id, + const std::string& unique_id, + uint64_t upload_total, + uint64_t uploaded, + uint64_t download_total, + uint64_t downloaded, + blink::mojom::BackgroundFetchState state) + : developer_id(developer_id), + unique_id(unique_id), + upload_total(upload_total), + uploaded(uploaded), + download_total(download_total), + downloaded(downloaded), + state(state) {} BackgroundFetchRegistration::BackgroundFetchRegistration( const BackgroundFetchRegistration& other) = default;
diff --git a/content/common/background_fetch/background_fetch_types.h b/content/common/background_fetch/background_fetch_types.h index 193820e..7fd22c1b 100644 --- a/content/common/background_fetch/background_fetch_types.h +++ b/content/common/background_fetch/background_fetch_types.h
@@ -14,6 +14,12 @@ #include "third_party/blink/public/common/manifest/manifest.h" #include "third_party/blink/public/mojom/fetch/fetch_api_response.mojom.h" +namespace blink { +namespace mojom { +enum class BackgroundFetchState; +} // namespace mojom +} // namespace blink + namespace content { // Represents the optional options a developer can provide when starting a new @@ -34,6 +40,13 @@ // https://wicg.github.io/background-fetch/#background-fetch-registration struct CONTENT_EXPORT BackgroundFetchRegistration { BackgroundFetchRegistration(); + BackgroundFetchRegistration(const std::string& developer_id, + const std::string& unique_id, + uint64_t upload_total, + uint64_t uploaded, + uint64_t download_total, + uint64_t downloaded, + blink::mojom::BackgroundFetchState state); BackgroundFetchRegistration(const BackgroundFetchRegistration& other); ~BackgroundFetchRegistration(); @@ -49,7 +62,7 @@ uint64_t uploaded = 0; uint64_t download_total = 0; uint64_t downloaded = 0; - // TODO(crbug.com/699957): Support the `activeFetches` member. + blink::mojom::BackgroundFetchState state; }; // Represents a request/response pair for a settled Background Fetch fetch.
diff --git a/content/common/service_worker/service_worker.mojom b/content/common/service_worker/service_worker.mojom index 21642ace..3f63a4a 100644 --- a/content/common/service_worker/service_worker.mojom +++ b/content/common/service_worker/service_worker.mojom
@@ -20,6 +20,7 @@ import "third_party/blink/public/mojom/service_worker/service_worker_fetch_response_callback.mojom"; import "third_party/blink/public/mojom/service_worker/service_worker_object.mojom"; import "third_party/blink/public/mojom/service_worker/service_worker_registration.mojom"; +import "third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom"; import "url/mojom/origin.mojom"; import "url/mojom/url.mojom"; @@ -86,26 +87,21 @@ // The callbacks are called once the event handler has run and waitUntil() // promise has settled. |developer_id| and |unique_id| are documented in // content::BackgroundFetchRegistrationId. - DispatchBackgroundFetchAbortEvent(string developer_id, - string unique_id, - blink.mojom.BackgroundFetchState state) + DispatchBackgroundFetchAbortEvent( + blink.mojom.BackgroundFetchRegistration registration) => (blink.mojom.ServiceWorkerEventStatus status, mojo_base.mojom.Time dispatch_event_time); - DispatchBackgroundFetchClickEvent(string developer_id, - string unique_id, - blink.mojom.BackgroundFetchState state) + DispatchBackgroundFetchClickEvent( + blink.mojom.BackgroundFetchRegistration registration) => (blink.mojom.ServiceWorkerEventStatus status, mojo_base.mojom.Time dispatch_event_time); - DispatchBackgroundFetchFailEvent(string developer_id, - string unique_id, - blink.mojom.BackgroundFetchState state, - array<blink.mojom.BackgroundFetchSettledFetch> fetches) + DispatchBackgroundFetchFailEvent( + blink.mojom.BackgroundFetchRegistration registration, + array<blink.mojom.BackgroundFetchSettledFetch> fetches) => (blink.mojom.ServiceWorkerEventStatus status, mojo_base.mojom.Time dispatch_event_time); DispatchBackgroundFetchSuccessEvent( - string developer_id, - string unique_id, - blink.mojom.BackgroundFetchState state, + blink.mojom.BackgroundFetchRegistration registration, array<blink.mojom.BackgroundFetchSettledFetch> fetches) => (blink.mojom.ServiceWorkerEventStatus status, mojo_base.mojom.Time dispatch_event_time);
diff --git a/content/public/browser/BUILD.gn b/content/public/browser/BUILD.gn index d0f74db..09d5e0a 100644 --- a/content/public/browser/BUILD.gn +++ b/content/public/browser/BUILD.gn
@@ -133,6 +133,7 @@ "font_list_async.h", "frame_service_base.h", "global_request_id.h", + "global_routing_id.h", "gpu_client.h", "gpu_data_manager.h", "gpu_data_manager_observer.h",
diff --git a/content/public/browser/background_fetch_delegate.h b/content/public/browser/background_fetch_delegate.h index 1113426..bff9eb6 100644 --- a/content/public/browser/background_fetch_delegate.h +++ b/content/public/browser/background_fetch_delegate.h
@@ -15,6 +15,7 @@ #include "base/memory/weak_ptr.h" #include "base/optional.h" #include "content/common/content_export.h" +#include "content/public/browser/resource_request_info.h" #include "third_party/skia/include/core/SkBitmap.h" class GURL; @@ -28,6 +29,10 @@ struct NetworkTrafficAnnotationTag; } // namespace net +namespace url { +class Origin; +} // namespace url + namespace content { struct BackgroundFetchResponse; struct BackgroundFetchResult; @@ -50,6 +55,7 @@ class CONTENT_EXPORT BackgroundFetchDelegate { public: using GetIconDisplaySizeCallback = base::OnceCallback<void(const gfx::Size&)>; + using GetPermissionForOriginCallback = base::OnceCallback<void(bool)>; // Client interface that a BackgroundFetchDelegate would use to signal the // progress of a background fetch. @@ -98,6 +104,13 @@ // Gets size of the icon to display with the Background Fetch UI. virtual void GetIconDisplaySize(GetIconDisplaySizeCallback callback) = 0; + // Checks whether |origin| has permission to start a Background Fetch. + // |wc_getter| can be null, which means this is running from a worker context. + virtual void GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) = 0; + // Creates a new download grouping identified by |job_unique_id|. Further // downloads started by DownloadUrl will also use this |job_unique_id| so that // a notification can be updated with the current status. If the download was
diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc index ba41da2..9098a79 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc
@@ -327,7 +327,7 @@ void ContentBrowserClient::AllowWorkerFileSystem( const GURL& url, ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback) { std::move(callback).Run(true); } @@ -336,7 +336,7 @@ const GURL& url, const base::string16& name, ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames) { + const std::vector<GlobalFrameRoutingId>& render_frames) { return true; }
diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h index e9ce260..2c51c82 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h
@@ -22,6 +22,7 @@ #include "build/build_config.h" #include "content/public/browser/certificate_request_result_type.h" #include "content/public/browser/global_request_id.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/navigation_throttle.h" #include "content/public/browser/overlay_window.h" #include "content/public/browser/resource_request_info.h" @@ -570,7 +571,7 @@ virtual void AllowWorkerFileSystem( const GURL& url, ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames, + const std::vector<GlobalFrameRoutingId>& render_frames, base::Callback<void(bool)> callback); // Allow the embedder to control if access to IndexedDB by a shared worker @@ -580,7 +581,7 @@ const GURL& url, const base::string16& name, ResourceContext* context, - const std::vector<std::pair<int, int> >& render_frames); + const std::vector<GlobalFrameRoutingId>& render_frames); // Allow the embedder to control whether we can use Web Bluetooth. // TODO(crbug.com/589228): Replace this with a use of the permission system.
diff --git a/content/public/browser/global_routing_id.h b/content/public/browser/global_routing_id.h new file mode 100644 index 0000000..bf6a9d8 --- /dev/null +++ b/content/public/browser/global_routing_id.h
@@ -0,0 +1,82 @@ +// Copyright (c) 2018 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_GLOBAL_ROUTING_ID_H_ +#define CONTENT_PUBLIC_BROWSER_GLOBAL_ROUTING_ID_H_ + +#include <tuple> + +#include "base/hash.h" +#include "ipc/ipc_message.h" + +namespace content { + +// Uniquely identifies a target that legacy IPCs can be routed to. +struct GlobalRoutingID { + GlobalRoutingID() : child_id(-1), route_id(-1) {} + + GlobalRoutingID(int child_id, int route_id) + : child_id(child_id), route_id(route_id) {} + + // The unique ID of the child process (this is different from OS's PID / this + // should come from RenderProcessHost::GetID()). + int child_id; + + // The route ID. + int route_id; + + bool operator<(const GlobalRoutingID& other) const { + return std::tie(child_id, route_id) < + std::tie(other.child_id, other.route_id); + } + bool operator==(const GlobalRoutingID& other) const { + return child_id == other.child_id && route_id == other.route_id; + } + bool operator!=(const GlobalRoutingID& other) const { + return !(*this == other); + } +}; + +// Same as GlobalRoutingID except the route_id must be a RenderFrameHost routing +// id. +struct GlobalFrameRoutingId { + GlobalFrameRoutingId() : child_id(0), frame_routing_id(MSG_ROUTING_NONE) {} + + GlobalFrameRoutingId(int child_id, int frame_routing_id) + : child_id(child_id), frame_routing_id(frame_routing_id) {} + + // GlobalFrameRoutingId is copyable. + GlobalFrameRoutingId(const GlobalFrameRoutingId&) = default; + GlobalFrameRoutingId& operator=(const GlobalFrameRoutingId&) = default; + + // The unique ID of the child process (this is different from OS's PID / this + // should come from RenderProcessHost::GetID()). + int child_id; + + // The route ID of a RenderFrame - should come from + // RenderFrameHost::GetRoutingID(). + int frame_routing_id; + + bool operator<(const GlobalFrameRoutingId& other) const { + return std::tie(child_id, frame_routing_id) < + std::tie(other.child_id, other.frame_routing_id); + } + bool operator==(const GlobalFrameRoutingId& other) const { + return child_id == other.child_id && + frame_routing_id == other.frame_routing_id; + } + bool operator!=(const GlobalFrameRoutingId& other) const { + return !(*this == other); + } +}; + +struct GlobalFrameRoutingIdHasher { + std::size_t operator()(const GlobalFrameRoutingId& id) const { + return base::HashInts(id.child_id, id.frame_routing_id); + } +}; + +} // namespace content + +#endif // CONTENT_PUBLIC_BROWSER_GLOBAL_ROUTING_ID_H_
diff --git a/content/public/browser/presentation_request.cc b/content/public/browser/presentation_request.cc index d3a1dccd..b8df3bc 100644 --- a/content/public/browser/presentation_request.cc +++ b/content/public/browser/presentation_request.cc
@@ -7,7 +7,7 @@ namespace content { PresentationRequest::PresentationRequest( - const std::pair<int, int>& render_frame_host_id, + const GlobalFrameRoutingId& render_frame_host_id, const std::vector<GURL>& presentation_urls, const url::Origin& frame_origin) : render_frame_host_id(render_frame_host_id),
diff --git a/content/public/browser/presentation_request.h b/content/public/browser/presentation_request.h index e2a1a5b1..224095a 100644 --- a/content/public/browser/presentation_request.h +++ b/content/public/browser/presentation_request.h
@@ -9,6 +9,7 @@ #include <vector> #include "content/common/content_export.h" +#include "content/public/browser/global_routing_id.h" #include "url/gurl.h" #include "url/origin.h" @@ -19,7 +20,7 @@ // frame. struct CONTENT_EXPORT PresentationRequest { public: - PresentationRequest(const std::pair<int, int>& render_frame_host_id, + PresentationRequest(const GlobalFrameRoutingId& render_frame_host_id, const std::vector<GURL>& presentation_urls, const url::Origin& frame_origin); ~PresentationRequest(); @@ -28,7 +29,7 @@ PresentationRequest& operator=(const PresentationRequest& other); // ID of RenderFrameHost that initiated the request. - std::pair<int, int> render_frame_host_id; + GlobalFrameRoutingId render_frame_host_id; // URLs of presentation. std::vector<GURL> presentation_urls;
diff --git a/content/renderer/input/input_target_client_impl.cc b/content/renderer/input/input_target_client_impl.cc index db8a81e..b8ee18d5 100644 --- a/content/renderer/input/input_target_client_impl.cc +++ b/content/renderer/input/input_target_client_impl.cc
@@ -24,8 +24,10 @@ void InputTargetClientImpl::FrameSinkIdAt(const gfx::Point& point, FrameSinkIdAtCallback callback) { - std::move(callback).Run( - render_frame_->GetRenderWidget()->GetFrameSinkIdAtPoint(point)); + gfx::PointF local_point; + viz::FrameSinkId id = render_frame_->GetRenderWidget()->GetFrameSinkIdAtPoint( + point, &local_point); + std::move(callback).Run(id, local_point); } } // namespace content
diff --git a/content/renderer/input/render_widget_input_handler.cc b/content/renderer/input/render_widget_input_handler.cc index e463640..3299f34 100644 --- a/content/renderer/input/render_widget_input_handler.cc +++ b/content/renderer/input/render_widget_input_handler.cc
@@ -191,16 +191,18 @@ RenderWidgetInputHandler::~RenderWidgetInputHandler() {} viz::FrameSinkId RenderWidgetInputHandler::GetFrameSinkIdAtPoint( - const gfx::Point& point) { + const gfx::Point& point, + gfx::PointF* local_point) { gfx::PointF point_in_pixel(point); if (widget_->compositor_deps()->IsUseZoomForDSFEnabled()) { point_in_pixel = gfx::ConvertPointToPixel( widget_->GetOriginalScreenInfo().device_scale_factor, point_in_pixel); } - blink::WebNode result_node = widget_->GetWebWidget() - ->HitTestResultAt(blink::WebPoint( - point_in_pixel.x(), point_in_pixel.y())) - .GetNode(); + blink::WebHitTestResult result = widget_->GetWebWidget()->HitTestResultAt( + blink::WebPoint(point_in_pixel.x(), point_in_pixel.y())); + + blink::WebNode result_node = result.GetNode(); + *local_point = gfx::PointF(point); // TODO(crbug.com/797828): When the node is null the caller may // need to do extra checks. Like maybe update the layout and then @@ -217,6 +219,11 @@ viz::FrameSinkId frame_sink_id = RenderFrameProxy::FromWebFrame(result_frame->ToWebRemoteFrame()) ->frame_sink_id(); + *local_point = gfx::PointF(result.LocalPointWithoutContentBoxOffset()); + if (widget_->compositor_deps()->IsUseZoomForDSFEnabled()) { + *local_point = gfx::ConvertPointToDIP( + widget_->GetOriginalScreenInfo().device_scale_factor, *local_point); + } if (frame_sink_id.is_valid()) return frame_sink_id; }
diff --git a/content/renderer/input/render_widget_input_handler.h b/content/renderer/input/render_widget_input_handler.h index 4ebdb4f..e3884c4 100644 --- a/content/renderer/input/render_widget_input_handler.h +++ b/content/renderer/input/render_widget_input_handler.h
@@ -47,8 +47,10 @@ virtual ~RenderWidgetInputHandler(); // Hit test the given point to find out the frame underneath and - // returns the FrameSinkId for that frame. - viz::FrameSinkId GetFrameSinkIdAtPoint(const gfx::Point& point); + // returns the FrameSinkId for that frame. |local_point| returns the point + // in the coordinate space of the FrameSinkId that was hit. + viz::FrameSinkId GetFrameSinkIdAtPoint(const gfx::Point& point, + gfx::PointF* local_point); // Handle input events from the input event provider. virtual void HandleInputEvent(
diff --git a/content/renderer/media/webrtc/rtc_video_encoder.cc b/content/renderer/media/webrtc/rtc_video_encoder.cc index 3ecf311..5df15b2 100644 --- a/content/renderer/media/webrtc/rtc_video_encoder.cc +++ b/content/renderer/media/webrtc/rtc_video_encoder.cc
@@ -63,7 +63,7 @@ return webrtc::kVideoCodecH264; } NOTREACHED() << "Invalid profile " << GetProfileName(profile); - return webrtc::kVideoCodecUnknown; + return webrtc::kVideoCodecGeneric; } // Populates struct webrtc::RTPFragmentationHeader for H264 codec.
diff --git a/content/renderer/render_widget.cc b/content/renderer/render_widget.cc index 3f35799..59e99c72 100644 --- a/content/renderer/render_widget.cc +++ b/content/renderer/render_widget.cc
@@ -942,8 +942,9 @@ Send(new ViewHostMsg_ForceRedrawComplete(routing_id(), snapshot_id)); } -viz::FrameSinkId RenderWidget::GetFrameSinkIdAtPoint(const gfx::Point& point) { - return input_handler_->GetFrameSinkIdAtPoint(point); +viz::FrameSinkId RenderWidget::GetFrameSinkIdAtPoint(const gfx::Point& point, + gfx::PointF* local_point) { + return input_handler_->GetFrameSinkIdAtPoint(point, local_point); } void RenderWidget::HandleInputEvent(
diff --git a/content/renderer/render_widget.h b/content/renderer/render_widget.h index b1ff3bd8..4b3297ba 100644 --- a/content/renderer/render_widget.h +++ b/content/renderer/render_widget.h
@@ -467,7 +467,8 @@ // Requests a BeginMainFrame callback from the compositor. void SetNeedsMainFrame() override; - viz::FrameSinkId GetFrameSinkIdAtPoint(const gfx::Point& point); + viz::FrameSinkId GetFrameSinkIdAtPoint(const gfx::Point& point, + gfx::PointF* local_point); void HandleInputEvent(const blink::WebCoalescedInputEvent& input_event, const ui::LatencyInfo& latency_info,
diff --git a/content/renderer/render_widget_browsertest.cc b/content/renderer/render_widget_browsertest.cc index 56fcf0c..8082956 100644 --- a/content/renderer/render_widget_browsertest.cc +++ b/content/renderer/render_widget_browsertest.cc
@@ -121,20 +121,23 @@ "<iframe style='width: 200px; height: 100px;'" "srcdoc='<body style=\"margin: 0px; height: 100px; width: 200px;\">" "</body>'></iframe><div></body>"); + gfx::PointF point; viz::FrameSinkId main_frame_sink_id = - widget()->GetFrameSinkIdAtPoint(gfx::Point(10, 10)); + widget()->GetFrameSinkIdAtPoint(gfx::Point(10, 10), &point); EXPECT_EQ(static_cast<uint32_t>(widget()->routing_id()), main_frame_sink_id.sink_id()); EXPECT_EQ(static_cast<uint32_t>(RenderThreadImpl::Get()->GetClientId()), main_frame_sink_id.client_id()); + EXPECT_EQ(gfx::PointF(10, 10), point); // Targeting a child frame should also return the FrameSinkId for the main // widget. viz::FrameSinkId frame_sink_id = - widget()->GetFrameSinkIdAtPoint(gfx::Point(150, 150)); + widget()->GetFrameSinkIdAtPoint(gfx::Point(150, 150), &point); EXPECT_EQ(static_cast<uint32_t>(widget()->routing_id()), frame_sink_id.sink_id()); EXPECT_EQ(main_frame_sink_id.client_id(), frame_sink_id.client_id()); + EXPECT_EQ(gfx::PointF(150, 150), point); } TEST_F(RenderWidgetTest, GetCompositionRangeValidComposition) {
diff --git a/content/renderer/service_worker/service_worker_context_client.cc b/content/renderer/service_worker/service_worker_context_client.cc index a437bebd..67a5d18 100644 --- a/content/renderer/service_worker/service_worker_context_client.cc +++ b/content/renderer/service_worker/service_worker_context_client.cc
@@ -65,6 +65,8 @@ #include "third_party/blink/public/mojom/service_worker/service_worker_object.mojom.h" #include "third_party/blink/public/mojom/service_worker/service_worker_registration.mojom.h" #include "third_party/blink/public/platform/interface_provider.h" +#include "third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom.h" +#include "third_party/blink/public/platform/modules/background_fetch/web_background_fetch_registration.h" #include "third_party/blink/public/platform/modules/background_fetch/web_background_fetch_settled_fetch.h" #include "third_party/blink/public/platform/modules/notifications/web_notification_data.h" #include "third_party/blink/public/platform/modules/payments/web_payment_handler_response.h" @@ -191,6 +193,17 @@ return web_client_info; } +// Converts a content::BackgroundFetchRegistration object to +// a blink::WebBackgroundFetchRegistration object. +blink::WebBackgroundFetchRegistration ToWebBackgroundFetchRegistration( + const BackgroundFetchRegistration& registration) { + return blink::WebBackgroundFetchRegistration( + blink::WebString::FromUTF8(registration.developer_id), + blink::WebString::FromUTF8(registration.unique_id), + registration.upload_total, registration.uploaded, + registration.download_total, registration.downloaded, registration.state); +} + // If |is_for_fetch_event| is true, some headers may be omitted according // to the embedder. It's always true now, but it might change with // more Onion Souping, and future callsites like Background Fetch probably don't @@ -1594,9 +1607,7 @@ } void ServiceWorkerContextClient::DispatchBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, DispatchBackgroundFetchAbortEventCallback callback) { int request_id = context_->timeout_timer->StartEvent( CreateAbortCallback(&context_->background_fetch_abort_event_callbacks)); @@ -1610,14 +1621,11 @@ TRACE_EVENT_FLAG_FLOW_OUT); proxy_->DispatchBackgroundFetchAbortEvent( - request_id, blink::WebString::FromUTF8(developer_id), - blink::WebString::FromUTF8(unique_id), state); + request_id, ToWebBackgroundFetchRegistration(registration)); } void ServiceWorkerContextClient::DispatchBackgroundFetchClickEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, DispatchBackgroundFetchClickEventCallback callback) { int request_id = context_->timeout_timer->StartEvent( CreateAbortCallback(&context_->background_fetch_click_event_callbacks)); @@ -1631,14 +1639,11 @@ TRACE_EVENT_FLAG_FLOW_OUT); proxy_->DispatchBackgroundFetchClickEvent( - request_id, blink::WebString::FromUTF8(developer_id), - blink::WebString::FromUTF8(unique_id), state); + request_id, ToWebBackgroundFetchRegistration(registration)); } void ServiceWorkerContextClient::DispatchBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, DispatchBackgroundFetchFailEventCallback callback) { int request_id = context_->timeout_timer->StartEvent( @@ -1661,14 +1666,11 @@ } proxy_->DispatchBackgroundFetchFailEvent( - request_id, blink::WebString::FromUTF8(developer_id), - blink::WebString::FromUTF8(unique_id), state, web_fetches); + request_id, ToWebBackgroundFetchRegistration(registration), web_fetches); } void ServiceWorkerContextClient::DispatchBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, DispatchBackgroundFetchSuccessEventCallback callback) { int request_id = context_->timeout_timer->StartEvent( @@ -1691,8 +1693,7 @@ } proxy_->DispatchBackgroundFetchSuccessEvent( - request_id, blink::WebString::FromUTF8(developer_id), - blink::WebString::FromUTF8(unique_id), state, web_fetches); + request_id, ToWebBackgroundFetchRegistration(registration), web_fetches); } void ServiceWorkerContextClient::InitializeGlobalScope(
diff --git a/content/renderer/service_worker/service_worker_context_client.h b/content/renderer/service_worker/service_worker_context_client.h index 4d1688d9..fb9518d 100644 --- a/content/renderer/service_worker/service_worker_context_client.h +++ b/content/renderer/service_worker/service_worker_context_client.h
@@ -284,25 +284,17 @@ DispatchInstallEventCallback callback) override; void DispatchActivateEvent(DispatchActivateEventCallback callback) override; void DispatchBackgroundFetchAbortEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, DispatchBackgroundFetchAbortEventCallback callback) override; void DispatchBackgroundFetchClickEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, DispatchBackgroundFetchClickEventCallback callback) override; void DispatchBackgroundFetchFailEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, DispatchBackgroundFetchFailEventCallback callback) override; void DispatchBackgroundFetchSuccessEvent( - const std::string& developer_id, - const std::string& unique_id, - blink::mojom::BackgroundFetchState state, + const BackgroundFetchRegistration& registration, const std::vector<BackgroundFetchSettledFetch>& fetches, DispatchBackgroundFetchSuccessEventCallback callback) override; void DispatchExtendableMessageEvent(
diff --git a/content/renderer/service_worker/service_worker_context_client_unittest.cc b/content/renderer/service_worker/service_worker_context_client_unittest.cc index 783f7f5..efd620e 100644 --- a/content/renderer/service_worker/service_worker_context_client_unittest.cc +++ b/content/renderer/service_worker/service_worker_context_client_unittest.cc
@@ -83,32 +83,24 @@ void DispatchActivateEvent(int event_id) override { NOTREACHED(); } void DispatchBackgroundFetchAbortEvent( int event_id, - const blink::WebString& developer_id, - const blink::WebString& unique_id, - blink::mojom::BackgroundFetchState state) override { + const blink::WebBackgroundFetchRegistration& registration) override { NOTREACHED(); } void DispatchBackgroundFetchClickEvent( int event_id, - const blink::WebString& developer_id, - const blink::WebString& unique_id, - blink::mojom::BackgroundFetchState state) override { + const blink::WebBackgroundFetchRegistration& registration) override { NOTREACHED(); } void DispatchBackgroundFetchFailEvent( int event_id, - const blink::WebString& developer_id, - const blink::WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const blink::WebBackgroundFetchRegistration& registration, const blink::WebVector<blink::WebBackgroundFetchSettledFetch>& fetches) override { NOTREACHED(); } void DispatchBackgroundFetchSuccessEvent( int event_id, - const blink::WebString& developer_id, - const blink::WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const blink::WebBackgroundFetchRegistration& registration, const blink::WebVector<blink::WebBackgroundFetchSettledFetch>& fetches) override { NOTREACHED();
diff --git a/content/shell/browser/layout_test/blink_test_controller.cc b/content/shell/browser/layout_test/blink_test_controller.cc index 3db1eb8..669d296 100644 --- a/content/shell/browser/layout_test/blink_test_controller.cc +++ b/content/shell/browser/layout_test/blink_test_controller.cc
@@ -1261,8 +1261,7 @@ mojom::LayoutTestControl* BlinkTestController::GetLayoutTestControlPtr( RenderFrameHost* frame) { - auto key = std::make_pair<int, int>(frame->GetProcess()->GetID(), - frame->GetRoutingID()); + GlobalFrameRoutingId key(frame->GetProcess()->GetID(), frame->GetRoutingID()); if (layout_test_control_map_.find(key) == layout_test_control_map_.end()) { mojom::LayoutTestControlAssociatedPtr& new_ptr = layout_test_control_map_[key]; @@ -1276,7 +1275,7 @@ } void BlinkTestController::HandleLayoutTestControlError( - const std::pair<int, int>& key) { + const GlobalFrameRoutingId& key) { layout_test_control_map_.erase(key); }
diff --git a/content/shell/browser/layout_test/blink_test_controller.h b/content/shell/browser/layout_test/blink_test_controller.h index be5df38..56f898b 100644 --- a/content/shell/browser/layout_test/blink_test_controller.h +++ b/content/shell/browser/layout_test/blink_test_controller.h
@@ -11,6 +11,7 @@ #include <set> #include <string> #include <utility> +#include <vector> #include "base/cancelable_callback.h" #include "base/files/file_path.h" @@ -22,6 +23,7 @@ #include "base/values.h" #include "build/build_config.h" #include "content/public/browser/bluetooth_chooser.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/gpu_data_manager_observer.h" #include "content/public/browser/notification_observer.h" #include "content/public/browser/notification_registrar.h" @@ -242,7 +244,7 @@ const std::string& argument); void OnBlockThirdPartyCookies(bool block); mojom::LayoutTestControl* GetLayoutTestControlPtr(RenderFrameHost* frame); - void HandleLayoutTestControlError(const std::pair<int, int>& key); + void HandleLayoutTestControlError(const GlobalFrameRoutingId& key); void OnCleanupFinished(); void OnCaptureDumpCompleted(mojom::LayoutTestDumpPtr dump); @@ -328,11 +330,7 @@ bool waiting_for_main_frame_dump_ = false; // Map from one frame to one mojo pipe. - // - // The key is a pair of (process id, frame routing id). - // TODO(lukasza): Use content::GlobalFrameRoutingID instead of std::pair<...> - // once it is exposed via content/public/browser API. - std::map<std::pair<int, int>, mojom::LayoutTestControlAssociatedPtr> + std::map<GlobalFrameRoutingId, mojom::LayoutTestControlAssociatedPtr> layout_test_control_map_; #if defined(OS_ANDROID) // Because of the nested message pump implementation, Android needs to allow
diff --git a/content/shell/browser/layout_test/layout_test_background_fetch_delegate.cc b/content/shell/browser/layout_test/layout_test_background_fetch_delegate.cc index 4aa72c2..1f4baf4 100644 --- a/content/shell/browser/layout_test/layout_test_background_fetch_delegate.cc +++ b/content/shell/browser/layout_test/layout_test_background_fetch_delegate.cc
@@ -173,6 +173,14 @@ std::move(callback).Run(gfx::Size(192, 192)); } +void LayoutTestBackgroundFetchDelegate::GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) { + DCHECK_CURRENTLY_ON(BrowserThread::UI); + std::move(callback).Run(true /* has_permission */); +} + void LayoutTestBackgroundFetchDelegate::CreateDownloadJob( std::unique_ptr<BackgroundFetchDescription> fetch_description) {}
diff --git a/content/shell/browser/layout_test/layout_test_background_fetch_delegate.h b/content/shell/browser/layout_test/layout_test_background_fetch_delegate.h index a960a7f..6ed853f 100644 --- a/content/shell/browser/layout_test/layout_test_background_fetch_delegate.h +++ b/content/shell/browser/layout_test/layout_test_background_fetch_delegate.h
@@ -27,6 +27,10 @@ // BackgroundFetchDelegate implementation: void GetIconDisplaySize(GetIconDisplaySizeCallback callback) override; + void GetPermissionForOrigin( + const url::Origin& origin, + const ResourceRequestInfo::WebContentsGetter& wc_getter, + GetPermissionForOriginCallback callback) override; void CreateDownloadJob( std::unique_ptr<BackgroundFetchDescription> fetch_description) override; void DownloadUrl(const std::string& job_unique_id,
diff --git a/content/test/content_browser_test_utils_internal.cc b/content/test/content_browser_test_utils_internal.cc index 3639a77..b02e0a5 100644 --- a/content/test/content_browser_test_utils_internal.cc +++ b/content/test/content_browser_test_utils_internal.cc
@@ -456,4 +456,13 @@ message_loop_runner_->Quit(); } +SwapoutACKMessageFilter::SwapoutACKMessageFilter() + : BrowserMessageFilter(FrameMsgStart) {} + +SwapoutACKMessageFilter::~SwapoutACKMessageFilter() {} + +bool SwapoutACKMessageFilter::OnMessageReceived(const IPC::Message& message) { + return message.type() == FrameHostMsg_SwapOut_ACK::ID; +} + } // namespace content
diff --git a/content/test/content_browser_test_utils_internal.h b/content/test/content_browser_test_utils_internal.h index 7834ba1..e6fe4c0 100644 --- a/content/test/content_browser_test_utils_internal.h +++ b/content/test/content_browser_test_utils_internal.h
@@ -252,6 +252,20 @@ DISALLOW_COPY_AND_ASSIGN(ShowWidgetMessageFilter); }; +// A BrowserMessageFilter that drops SwapOut ACK messages. +class SwapoutACKMessageFilter : public BrowserMessageFilter { + public: + SwapoutACKMessageFilter(); + + protected: + ~SwapoutACKMessageFilter() override; + + private: + // BrowserMessageFilter: + bool OnMessageReceived(const IPC::Message& message) override; + DISALLOW_COPY_AND_ASSIGN(SwapoutACKMessageFilter); +}; + } // namespace content #endif // CONTENT_TEST_CONTENT_BROWSER_TEST_UTILS_INTERNAL_H_
diff --git a/content/test/data/frame_tree/page_with_perspective_transformed_frame.html b/content/test/data/frame_tree/page_with_perspective_transformed_frame.html new file mode 100644 index 0000000..1866a1d --- /dev/null +++ b/content/test/data/frame_tree/page_with_perspective_transformed_frame.html
@@ -0,0 +1,18 @@ +<!DOCTYPE html> +<style> +iframe { + position:absolute; + top: 50px; + left: 50px; + width: 100px; + height: 100px; + transform: perspective(50em) rotateY(45deg); +} + +</style> +<html> +<body> +<iframe src="/cross-site/baz.com/title1.html"></iframe> +This page contains a cross-origin iframe with 45 degree perspective. +</body> +</html>
diff --git a/content/test/gpu/gpu_tests/webgl2_conformance_expectations.py b/content/test/gpu/gpu_tests/webgl2_conformance_expectations.py index ff1e41c..91c4afb 100644 --- a/content/test/gpu/gpu_tests/webgl2_conformance_expectations.py +++ b/content/test/gpu/gpu_tests/webgl2_conformance_expectations.py
@@ -34,6 +34,9 @@ # The multiview extension is only expected to be supported through ANGLE. self.Skip('WebglExtension_WEBGL_multiview', ['win', 'no_passthrough'], bug=864524) + # # ANGLE's OpenGL backend supports multiview only on NVIDIA. + self.Skip('WebglExtension_WEBGL_multiview', + ['win', 'passthrough', 'opengl', 'intel'], bug=864524) self.Skip('WebglExtension_EXT_disjoint_timer_query_webgl2', ['android'], bug=808744) self.Fail('WebglExtension_EXT_disjoint_timer_query_webgl2', @@ -403,6 +406,27 @@ self.Fail('conformance/renderbuffers/framebuffer-state-restoration.html', ['passthrough', 'opengl', 'intel'], bug=602688) + # Passthrough command decoder / Windows / OpenGL / Intel + self.Fail('conformance2/textures/misc/copy-texture-image-same-texture.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=809594) + self.Fail('conformance2/renderbuffers/' + + 'multisampled-depth-renderbuffer-initialization.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=2760) # ANGLE bug + self.Fail('conformance/uniforms/' + + 'no-over-optimization-on-uniform-array-16.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=602688) + self.Fail('conformance/glsl/constructors/glsl-construct-mat2.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=602688) + self.Fail('conformance2/textures/misc/texture-npot.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=602688) + self.Fail('conformance2/textures/misc/npot-video-sizing.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=602688) + self.Fail('conformance2/glsl3/' + + 'vector-dynamic-indexing-swizzled-lvalue.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=602688) + self.Fail('conformance2/glsl3/vector-dynamic-indexing.html', + ['win', 'passthrough', 'opengl', 'intel'], bug=602688) + # Passthrough command decoder / Linux / OpenGL / NVIDIA self.Fail('conformance/textures/image_bitmap_from_video/' + 'tex-2d-luminance_alpha-luminance_alpha-unsigned_byte.html', @@ -968,9 +992,6 @@ ['linux', ('nvidia', 0x1cb3), 'opengl'], bug=703779) # Linux Intel - self.Fail('conformance2/extensions/ext-color-buffer-float.html', - ['linux', 'intel'], bug=640389) - # See https://bugs.freedesktop.org/show_bug.cgi?id=94477 self.Skip('conformance/glsl/bugs/temp-expressions-should-not-crash.html', ['linux', 'intel'], bug=540543) # GPU timeout
diff --git a/content/test/test_web_contents.cc b/content/test/test_web_contents.cc index 92260a4..6511a0a 100644 --- a/content/test/test_web_contents.cc +++ b/content/test/test_web_contents.cc
@@ -368,7 +368,7 @@ void TestWebContents::AddPendingContents( std::unique_ptr<WebContents> contents) { // This is normally only done in WebContentsImpl::CreateNewWindow. - ProcessRoutingIdPair key( + GlobalRoutingID key( contents->GetRenderViewHost()->GetProcess()->GetID(), contents->GetRenderViewHost()->GetWidget()->GetRoutingID()); WebContentsImpl* raw_contents = static_cast<WebContentsImpl*>(contents.get());
diff --git a/content/test/web_contents_observer_sanity_checker.h b/content/test/web_contents_observer_sanity_checker.h index e9794e0d3..942396e2 100644 --- a/content/test/web_contents_observer_sanity_checker.h +++ b/content/test/web_contents_observer_sanity_checker.h
@@ -5,12 +5,14 @@ #ifndef CONTENT_TEST_WEB_CONTENTS_OBSERVER_SANITY_CHECKER_H_ #define CONTENT_TEST_WEB_CONTENTS_OBSERVER_SANITY_CHECKER_H_ +#include <map> #include <set> #include <string> +#include <vector> #include "base/macros.h" #include "base/supports_user_data.h" -#include "content/browser/loader/global_routing_id.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/web_contents_observer.h" namespace content {
diff --git a/docs/chromedriver_status.md b/docs/chromedriver_status.md index dbfc1874..349568662 100644 --- a/docs/chromedriver_status.md +++ b/docs/chromedriver_status.md
@@ -2,9 +2,12 @@ Below is a list of all WebDriver commands and their current support in ChromeDriver based on what is in the [WebDriver Specification](https://w3c.github.io/webdriver/webdriver-spec.html). +Notes: + - Currently some error strings returned by ChromeDriver are incorrect. This is tracked by bug [2552](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2552). + | Method | URL | Command | Status | Bug | --- | --- | --- | --- | --- | -| POST | /session | New Session | Partially Complete | [1997](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1997) +| POST | /session | New Session | Partially Complete | [1997](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1997) [2537](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2537) | DELETE | /session/{session id} | Delete Status | Complete | | GET | /status | Status | Complete | | GET | /session/{session id}/timeouts | Get Timeouts | Complete | @@ -16,7 +19,7 @@ | POST | /session/{session id}/refresh | Refresh | Partially Complete | [1988](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1988) | GET | /session/{session id}/title | Get Title | Complete | | GET | /session/{session id}/window | Get Window Handle | Complete | -| DELETE | /session/{session id}/window | Close Window | Partially Complete | [1990](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1990) +| DELETE | /session/{session id}/window | Close Window | Complete | | POST | /session/{session id}/window | Switch To Window | Complete | | GET | /session/{session id}/window/handles | Get Window Handles | Complete | | POST | /session/{session id}/frame | Switch To Frame | Partially Complete | [1992](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1992) @@ -43,8 +46,8 @@ | POST | /session/{session id}/element/{element id}/clear | Element Clear | Partially Complete | [1998](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1998) | POST | /session/{session id}/element/{element id}/value | Element Send Keys | Partially Complete | [1999](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1999) | GET | /session/{session id}/source | Get Page Source | | -| POST | /session/{session id}/execute/sync | Execute Script | Partially Complete | [2000](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2000) -| POST | /session/{session id}/execute/async | Execute Async Script | Partially Complete | [2001](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2001) +| POST | /session/{session id}/execute/sync | Execute Script | Partially Complete | [2000](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2000) [2398](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2398) [2556](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2556) +| POST | /session/{session id}/execute/async | Execute Async Script | Partially Complete | [2001](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2001) [2398](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2398) [2556](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2556) | GET | /session/{session id}/cookie | Get All Cookies | Complete | | GET | /session/{session id}/cookie/{name} | Get Named Cookie | Complete | | POST | /session/{session id}/cookie | Add Cookie | Partially Complete | [2002](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2002) @@ -52,8 +55,8 @@ | DELETE | /session/{session id)/cookie | Delete All Cookies | Complete | | POST | /session/{session id}/actions | Perform Actions | Incomplete | [1897](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1897) | DELETE | /session/{session id}/actions | Release Actions | Incomplete | [1897](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1897) -| POST | /session/{session id}/alert/dismiss | Dismiss Alert | Partially Complete | [1500](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1500) -| POST | /session/{session id}/alert/accept | Accept Alert | Partially Complete | [1500](https://bugs.chromium.org/p/chromedriver/issues/detail?id=1500) +| POST | /session/{session id}/alert/dismiss | Dismiss Alert | Complete | +| POST | /session/{session id}/alert/accept | Accept Alert | Complete | | GET | /session/{session id}/alert/text | Get Alert Text | Complete | | POST | /session/{session id}/alert/text | Send Alert Text | Partially Complete | [2003](https://bugs.chromium.org/p/chromedriver/issues/detail?id=2003) | GET | /session/{session id}/screenshot | Take Screenshot | |
diff --git a/extensions/browser/api/declarative_net_request/rules_monitor_service.cc b/extensions/browser/api/declarative_net_request/rules_monitor_service.cc index 6d2148ef..81304f8 100644 --- a/extensions/browser/api/declarative_net_request/rules_monitor_service.cc +++ b/extensions/browser/api/declarative_net_request/rules_monitor_service.cc
@@ -104,6 +104,11 @@ int expected_ruleset_checksum; URLPatternSet allowed_pages; + // True in case the checksum of the indexed ruleset changed. If true, + // |expected_ruleset_checksum| contains the updated checksum. This can only + // happen in case of an incorrect indexed ruleset format version. + bool checksum_updated_due_to_version_mismatch = false; + DISALLOW_COPY_AND_ASSIGN(LoadRulesetInfo); }; @@ -179,23 +184,34 @@ // be called on this sequence itself. IndexAndPersistRulesCallback ruleset_reindexed_callback = base::BindOnce( &FileSequenceState::OnRulesetReindexed, weak_factory_.GetWeakPtr(), - std::move(info), std::move(ui_callback)); + std::move(info), result, std::move(ui_callback)); IndexAndPersistRules(connector_.get(), nullptr /*identity*/, *extension, std::move(ruleset_reindexed_callback)); } // Callback invoked when the JSON ruleset is reindexed. - void OnRulesetReindexed(LoadRulesetInfo info, - LoadRulesetUICallback ui_callback, - IndexAndPersistRulesResult result) const { + void OnRulesetReindexed( + LoadRulesetInfo info, + RulesetMatcher::LoadRulesetResult initial_failure_reason, + LoadRulesetUICallback ui_callback, + IndexAndPersistRulesResult result) const { DCHECK(GetExtensionFileTaskRunner()->RunsTasksInCurrentSequence()); + // In case of updates to the ruleset version, the ruleset checksum can + // change. + if (result.success && + initial_failure_reason == + RulesetMatcher::LoadRulesetResult::kLoadErrorVersionMismatch) { + info.expected_ruleset_checksum = result.ruleset_checksum; + info.checksum_updated_due_to_version_mismatch = true; + } + // The checksum of the reindexed ruleset should have been the same as the - // expected checksum obtained from prefs. If this is not the case, then - // there is some other issue (like the JSON rules file has been modified - // from the one used during installation or preferences are corrupted). But - // taking care of these is beyond our scope here, so simply signal a - // failure. + // expected checksum obtained from prefs, in all cases except when the + // ruleset version changes. If this is not the case, then there is some + // other issue (like the JSON rules file has been modified from the one used + // during installation or preferences are corrupted). But taking care of + // these is beyond our scope here, so simply signal a failure. bool reindexing_success = result.success && info.expected_ruleset_checksum == result.ruleset_checksum; @@ -325,6 +341,12 @@ void RulesMonitorService::OnRulesetLoaded( LoadRulesetInfo info, std::unique_ptr<RulesetMatcher> matcher) { + // Update the ruleset checksum if needed. + if (info.checksum_updated_due_to_version_mismatch) { + prefs_->SetDNRRulesetChecksum(info.extension->id(), + info.expected_ruleset_checksum); + } + if (!matcher) { // The ruleset failed to load. Notify the user. warning_service_->AddWarnings(
diff --git a/extensions/browser/api/declarative_net_request/rules_monitor_service.h b/extensions/browser/api/declarative_net_request/rules_monitor_service.h index 5d018f1d..76196378 100644 --- a/extensions/browser/api/declarative_net_request/rules_monitor_service.h +++ b/extensions/browser/api/declarative_net_request/rules_monitor_service.h
@@ -98,7 +98,7 @@ // Guaranteed to be valid through-out the lifetime of this instance. InfoMap* const info_map_; - const ExtensionPrefs* const prefs_; + ExtensionPrefs* const prefs_; ExtensionRegistry* const extension_registry_; WarningService* const warning_service_;
diff --git a/extensions/browser/api/declarative_net_request/ruleset_matcher.cc b/extensions/browser/api/declarative_net_request/ruleset_matcher.cc index 414fe13..bab9700 100644 --- a/extensions/browser/api/declarative_net_request/ruleset_matcher.cc +++ b/extensions/browser/api/declarative_net_request/ruleset_matcher.cc
@@ -47,6 +47,9 @@ if (!base::ReadFileToString(indexed_ruleset_path, &ruleset_data)) return kLoadErrorFileRead; + if (!StripVersionHeaderAndParseVersion(&ruleset_data)) + return kLoadErrorVersionMismatch; + // This guarantees that no memory access will end up outside the buffer. if (!IsValidRulesetData( base::make_span(reinterpret_cast<const uint8_t*>(ruleset_data.data()),
diff --git a/extensions/browser/api/declarative_net_request/ruleset_matcher.h b/extensions/browser/api/declarative_net_request/ruleset_matcher.h index 9e3561a..e3b4838 100644 --- a/extensions/browser/api/declarative_net_request/ruleset_matcher.h +++ b/extensions/browser/api/declarative_net_request/ruleset_matcher.h
@@ -39,10 +39,22 @@ // This is logged as part of UMA. Hence existing values should not be re- // numbered or deleted. New values should be added before kLoadRulesetMax. enum LoadRulesetResult { + // Ruleset loading succeeded. kLoadSuccess = 0, + + // Ruleset loading failed since the provided path did not exist. kLoadErrorInvalidPath = 1, + + // Ruleset loading failed due to a file read error. kLoadErrorFileRead = 2, + + // Ruleset loading failed due to a checksum mismatch. + // TODO(karandeepb): Rename this to kLoadErrorChecksumMismatch. kLoadErrorRulesetVerification = 3, + + // Ruleset loading failed due to version header mismatch. + kLoadErrorVersionMismatch = 4, + kLoadResultMax };
diff --git a/extensions/browser/api/declarative_net_request/utils.cc b/extensions/browser/api/declarative_net_request/utils.cc index 753b23b..fb838b3f 100644 --- a/extensions/browser/api/declarative_net_request/utils.cc +++ b/extensions/browser/api/declarative_net_request/utils.cc
@@ -10,11 +10,13 @@ #include "base/callback.h" #include "base/callback_helpers.h" +#include "base/files/file.h" #include "base/files/file_path.h" #include "base/files/file_util.h" #include "base/hash.h" #include "base/json/json_file_value_serializer.h" #include "base/metrics/histogram_macros.h" +#include "base/strings/stringprintf.h" #include "base/threading/thread_restrictions.h" #include "base/timer/elapsed_timer.h" #include "base/values.h" @@ -39,7 +41,36 @@ namespace dnr_api = extensions::api::declarative_net_request; -// Returns the checksum of the given serialized |data|. +// The ruleset format version of the flatbuffer schema. Increment this whenever +// making an incompatible change to the schema at extension_ruleset.fbs or +// url_pattern_index.fbs. Whenever an extension with an indexed ruleset format +// version different from the one currently used by Chrome is loaded, the +// extension ruleset will be reindexed. +// TODO(crbug.com/755717): Add checks to ensure that we increment this when +// necessary. +constexpr int kIndexedRulesetFormatVersion = 1; + +constexpr int kInvalidIndexedRulesetFormatVersion = -1; + +int g_indexed_ruleset_format_version_for_testing = + kInvalidIndexedRulesetFormatVersion; + +int GetIndexedRulesetFormatVersion() { + return g_indexed_ruleset_format_version_for_testing == + kInvalidIndexedRulesetFormatVersion + ? kIndexedRulesetFormatVersion + : g_indexed_ruleset_format_version_for_testing; +} + +// Returns the header to be used for indexed rulesets. This depends on the +// current ruleset format version. +std::string GetVersionHeader() { + return base::StringPrintf("---------Version=%d", + GetIndexedRulesetFormatVersion()); +} + +// Returns the checksum of the given serialized |data|. |data| must not include +// the version header. int GetChecksum(base::span<const uint8_t> data) { uint32_t hash = base::PersistentHash(data.data(), data.size()); @@ -48,7 +79,10 @@ return static_cast<int>(hash & 0x7fffffff); } -// Helper function to persist the indexed ruleset |data| for |extension|. +// Helper function to persist the indexed ruleset |data| for |extension|. The +// ruleset is composed of a version header corresponding to the current ruleset +// format version, followed by the actual ruleset data. Note: The checksum only +// corresponds to this ruleset data and does not include the version header. bool PersistRuleset(const Extension& extension, base::span<const uint8_t> data, int* ruleset_checksum) { @@ -57,20 +91,34 @@ const base::FilePath path = file_util::GetIndexedRulesetPath(extension.path()); - // Create the directory corresponding to |path| if it does not exist and then - // persist the ruleset. + // Create the directory corresponding to |path| if it does not exist. + if (!base::CreateDirectory(path.DirName())) + return false; + + base::File ruleset_file( + path, base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE); + if (!ruleset_file.IsValid()) + return false; + + // Write the version header. + std::string version_header = GetVersionHeader(); + int version_header_size = static_cast<int>(version_header.size()); + if (ruleset_file.WriteAtCurrentPos( + version_header.data(), version_header_size) != version_header_size) { + return false; + } + + // Write the flatbuffer ruleset. if (!base::IsValueInRangeForNumericType<int>(data.size())) return false; - const int data_size = static_cast<int>(data.size()); - const bool success = - base::CreateDirectory(path.DirName()) && - base::WriteFile(path, reinterpret_cast<const char*>(data.data()), - data_size) == data_size; + int data_size = static_cast<int>(data.size()); + if (ruleset_file.WriteAtCurrentPos(reinterpret_cast<const char*>(data.data()), + data_size) != data_size) { + return false; + } - if (success) - *ruleset_checksum = GetChecksum(data); - - return success; + *ruleset_checksum = GetChecksum(data); + return true; } // Helper to retrieve the ruleset ExtensionResource for |extension|. @@ -274,5 +322,28 @@ flat::VerifyExtensionIndexedRulesetBuffer(verifier); } +std::string GetVersionHeaderForTesting() { + return GetVersionHeader(); +} + +void SetIndexedRulesetFormatVersionForTesting(int version) { + DCHECK_NE(kInvalidIndexedRulesetFormatVersion, version); + g_indexed_ruleset_format_version_for_testing = version; +} + +bool StripVersionHeaderAndParseVersion(std::string* ruleset_data) { + DCHECK(ruleset_data); + const std::string version_header = GetVersionHeader(); + + if (!base::StartsWith(*ruleset_data, version_header, + base::CompareCase::SENSITIVE)) { + return false; + } + + // Strip the header from |ruleset_data|. + ruleset_data->erase(0, version_header.size()); + return true; +} + } // namespace declarative_net_request } // namespace extensions
diff --git a/extensions/browser/api/declarative_net_request/utils.h b/extensions/browser/api/declarative_net_request/utils.h index 629d038..1a7650f 100644 --- a/extensions/browser/api/declarative_net_request/utils.h +++ b/extensions/browser/api/declarative_net_request/utils.h
@@ -81,6 +81,17 @@ // ruleset data with |expected_checksum|. bool IsValidRulesetData(base::span<const uint8_t> data, int expected_checksum); +// Returns the version header used for indexed ruleset files. Only exposed for +// testing. +std::string GetVersionHeaderForTesting(); + +// Override the ruleset format version for testing. +void SetIndexedRulesetFormatVersionForTesting(int version); + +// Strips the version header from |ruleset_data|. Returns false on version +// mismatch. +bool StripVersionHeaderAndParseVersion(std::string* ruleset_data); + } // namespace declarative_net_request } // namespace extensions
diff --git a/extensions/browser/app_window/app_web_contents_helper.cc b/extensions/browser/app_window/app_web_contents_helper.cc index 21d676e9..158d1a2 100644 --- a/extensions/browser/app_window/app_web_contents_helper.cc +++ b/extensions/browser/app_window/app_web_contents_helper.cc
@@ -32,8 +32,18 @@ // static bool AppWebContentsHelper::ShouldSuppressGestureEvent( const blink::WebGestureEvent& event) { + // Disable "smart zoom" (double-tap with two fingers on Mac trackpad). + if (event.GetType() == blink::WebInputEvent::kGestureDoubleTap) + return true; + // Disable pinch zooming in app windows. - return blink::WebInputEvent::IsPinchGestureEventType(event.GetType()); + if (blink::WebInputEvent::IsPinchGestureEventType(event.GetType())) { + // Only suppress pinch events that cause a scale change. We still + // allow synthetic wheel events for touchpad pinch to go to the page. + return !event.NeedsWheelEvent(); + } + + return false; } content::WebContents* AppWebContentsHelper::OpenURLFromTab(
diff --git a/extensions/browser/extension_prefs.cc b/extensions/browser/extension_prefs.cc index 42fec16..e6d8dd4 100644 --- a/extensions/browser/extension_prefs.cc +++ b/extensions/browser/extension_prefs.cc
@@ -1740,9 +1740,8 @@ dnr_ruleset_checksum); } -void ExtensionPrefs::SetDNRRulesetChecksumForTesting( - const ExtensionId& extension_id, - int dnr_ruleset_checksum) { +void ExtensionPrefs::SetDNRRulesetChecksum(const ExtensionId& extension_id, + int dnr_ruleset_checksum) { UpdateExtensionPref(extension_id, kPrefDNRRulesetChecksum, std::make_unique<base::Value>(dnr_ruleset_checksum)); }
diff --git a/extensions/browser/extension_prefs.h b/extensions/browser/extension_prefs.h index e55793d..9fbdcea 100644 --- a/extensions/browser/extension_prefs.h +++ b/extensions/browser/extension_prefs.h
@@ -573,8 +573,8 @@ // |dnr_ruleset_checksum|. bool GetDNRRulesetChecksum(const ExtensionId& extension_id, int* dnr_ruleset_checksum) const; - void SetDNRRulesetChecksumForTesting(const ExtensionId& extension_id, - int dnr_ruleset_checksum); + void SetDNRRulesetChecksum(const ExtensionId& extension_id, + int dnr_ruleset_checksum); // Sets the set of allowed pages for the given |extension_id|. void SetDNRAllowedPages(const ExtensionId& extension_id, URLPatternSet set);
diff --git a/extensions/browser/guest_view/web_view/web_view_renderer_state.cc b/extensions/browser/guest_view/web_view/web_view_renderer_state.cc index c95fac9..e6a6e6b 100644 --- a/extensions/browser/guest_view/web_view/web_view_renderer_state.cc +++ b/extensions/browser/guest_view/web_view/web_view_renderer_state.cc
@@ -95,7 +95,7 @@ // TODO(fsamuel): Store per-process info in WebViewPartitionInfo instead of in // WebViewInfo. for (const auto& info : web_view_info_map_) { - if (info.first.first == guest_process_id) { + if (info.first.child_id == guest_process_id) { if (owner_process_id) *owner_process_id = info.second.embedder_process_id; if (owner_host)
diff --git a/extensions/browser/guest_view/web_view/web_view_renderer_state.h b/extensions/browser/guest_view/web_view/web_view_renderer_state.h index c1c9242..28f4031 100644 --- a/extensions/browser/guest_view/web_view/web_view_renderer_state.h +++ b/extensions/browser/guest_view/web_view/web_view_renderer_state.h
@@ -20,6 +20,7 @@ #include "base/macros.h" #include "base/memory/singleton.h" +#include "content/public/browser/global_routing_id.h" namespace extensions { @@ -76,7 +77,7 @@ friend class WebViewGuest; friend struct base::DefaultSingletonTraits<WebViewRendererState>; - using RenderId = std::pair<int, int>; + using RenderId = content::GlobalRoutingID; using WebViewInfoMap = std::map<RenderId, WebViewInfo>; struct WebViewPartitionInfo {
diff --git a/extensions/renderer/bindings/api_binding_test.cc b/extensions/renderer/bindings/api_binding_test.cc index 38f0ec4..fb6d022 100644 --- a/extensions/renderer/bindings/api_binding_test.cc +++ b/extensions/renderer/bindings/api_binding_test.cc
@@ -33,8 +33,9 @@ gin::IsolateHolder::kStableV8Extras, gin::ArrayBufferAllocator::SharedInstance()); - isolate_holder_ = - std::make_unique<gin::IsolateHolder>(base::ThreadTaskRunnerHandle::Get()); + isolate_holder_ = std::make_unique<gin::IsolateHolder>( + base::ThreadTaskRunnerHandle::Get(), + gin::IsolateHolder::IsolateType::kTest); isolate()->Enter(); v8::HandleScope handle_scope(isolate());
diff --git a/gin/isolate_holder.cc b/gin/isolate_holder.cc index e3a23cf3..4491b39 100644 --- a/gin/isolate_holder.cc +++ b/gin/isolate_holder.cc
@@ -31,23 +31,29 @@ } // namespace IsolateHolder::IsolateHolder( - scoped_refptr<base::SingleThreadTaskRunner> task_runner) - : IsolateHolder(std::move(task_runner), AccessMode::kSingleThread) {} + scoped_refptr<base::SingleThreadTaskRunner> task_runner, + IsolateType isolate_type) + : IsolateHolder(std::move(task_runner), + AccessMode::kSingleThread, + isolate_type) {} IsolateHolder::IsolateHolder( scoped_refptr<base::SingleThreadTaskRunner> task_runner, - AccessMode access_mode) + AccessMode access_mode, + IsolateType isolate_type) : IsolateHolder(std::move(task_runner), access_mode, kAllowAtomicsWait, + isolate_type, IsolateCreationMode::kNormal) {} IsolateHolder::IsolateHolder( scoped_refptr<base::SingleThreadTaskRunner> task_runner, AccessMode access_mode, AllowAtomicsWaitMode atomics_wait_mode, + IsolateType isolate_type, IsolateCreationMode isolate_creation_mode) - : access_mode_(access_mode) { + : access_mode_(access_mode), isolate_type_(isolate_type) { DCHECK(task_runner); DCHECK(task_runner->BelongsToCurrentThread());
diff --git a/gin/public/isolate_holder.h b/gin/public/isolate_holder.h index a70ad1ce5..6945a601 100644 --- a/gin/public/isolate_holder.h +++ b/gin/public/isolate_holder.h
@@ -58,14 +58,28 @@ kCreateSnapshot, }; - explicit IsolateHolder( - scoped_refptr<base::SingleThreadTaskRunner> task_runner); + // Isolate type used for UMA/UKM reporting: + // - kBlinkMainThread: the main isolate of Blink. + // - kBlinkWorkerThread: the isolate of a Blink worker. + // - kTest: used only in tests. + // - kUtility: the isolate of PDFium and ProxyResolver. + enum class IsolateType { + kBlinkMainThread, + kBlinkWorkerThread, + kTest, + kUtility + }; + IsolateHolder(scoped_refptr<base::SingleThreadTaskRunner> task_runner, - AccessMode access_mode); + IsolateType isolate_type); + IsolateHolder(scoped_refptr<base::SingleThreadTaskRunner> task_runner, + AccessMode access_mode, + IsolateType isolate_type); IsolateHolder( scoped_refptr<base::SingleThreadTaskRunner> task_runner, AccessMode access_mode, AllowAtomicsWaitMode atomics_wait_mode, + IsolateType isolate_type, IsolateCreationMode isolate_creation_mode = IsolateCreationMode::kNormal); ~IsolateHolder(); @@ -90,6 +104,8 @@ // This method returns if v8::Locker is needed to access isolate. AccessMode access_mode() const { return access_mode_; } + IsolateType isolate_type() const { return isolate_type_; } + v8::SnapshotCreator* snapshot_creator() const { return snapshot_creator_.get(); } @@ -111,6 +127,7 @@ std::unique_ptr<PerIsolateData> isolate_data_; std::unique_ptr<V8IsolateMemoryDumpProvider> isolate_memory_dump_provider_; AccessMode access_mode_; + IsolateType isolate_type_; DISALLOW_COPY_AND_ASSIGN(IsolateHolder); };
diff --git a/gin/shell/gin_main.cc b/gin/shell/gin_main.cc index 304c9da..eb0c686 100644 --- a/gin/shell/gin_main.cc +++ b/gin/shell/gin_main.cc
@@ -84,7 +84,9 @@ gin::IsolateHolder::Initialize(gin::IsolateHolder::kStrictMode, gin::IsolateHolder::kStableV8Extras, gin::ArrayBufferAllocator::SharedInstance()); - gin::IsolateHolder instance(base::ThreadTaskRunnerHandle::Get()); + gin::IsolateHolder instance( + base::ThreadTaskRunnerHandle::Get(), + gin::IsolateHolder::IsolateType::kBlinkMainThread); gin::GinShellRunnerDelegate delegate; gin::ShellRunner runner(&delegate, instance.isolate());
diff --git a/gin/shell_runner_unittest.cc b/gin/shell_runner_unittest.cc index 02e6835..1a5ad6b 100644 --- a/gin/shell_runner_unittest.cc +++ b/gin/shell_runner_unittest.cc
@@ -36,7 +36,8 @@ gin::IsolateHolder::Initialize(gin::IsolateHolder::kStrictMode, gin::IsolateHolder::kStableV8Extras, gin::ArrayBufferAllocator::SharedInstance()); - gin::IsolateHolder instance(base::ThreadTaskRunnerHandle::Get()); + gin::IsolateHolder instance(base::ThreadTaskRunnerHandle::Get(), + gin::IsolateHolder::IsolateType::kTest); ShellRunnerDelegate delegate; Isolate* isolate = instance.isolate();
diff --git a/gin/test/v8_test.cc b/gin/test/v8_test.cc index 88009dd..4a68091 100644 --- a/gin/test/v8_test.cc +++ b/gin/test/v8_test.cc
@@ -28,7 +28,9 @@ gin::IsolateHolder::kStableV8Extras, gin::ArrayBufferAllocator::SharedInstance()); - instance_.reset(new gin::IsolateHolder(base::ThreadTaskRunnerHandle::Get())); + instance_.reset(new gin::IsolateHolder( + base::ThreadTaskRunnerHandle::Get(), + gin::IsolateHolder::IsolateType::kBlinkMainThread)); instance_->isolate()->Enter(); HandleScope handle_scope(instance_->isolate()); context_.Reset(instance_->isolate(), Context::New(instance_->isolate()));
diff --git a/headless/lib/browser/headless_browser_context_impl.cc b/headless/lib/browser/headless_browser_context_impl.cc index 565a640..0e59b9c 100644 --- a/headless/lib/browser/headless_browser_context_impl.cc +++ b/headless/lib/browser/headless_browser_context_impl.cc
@@ -151,7 +151,7 @@ const base::UnguessableToken& devtools_frame_token, int frame_tree_node_id) { base::AutoLock lock(devtools_frame_token_map_lock_); - devtools_frame_token_map_[std::make_pair( + devtools_frame_token_map_[content::GlobalFrameRoutingId( render_process_id, render_frame_routing_id)] = devtools_frame_token; frame_tree_node_id_to_devtools_frame_token_map_[frame_tree_node_id] = devtools_frame_token; @@ -162,8 +162,8 @@ int render_frame_routing_id, int frame_tree_node_id) { base::AutoLock lock(devtools_frame_token_map_lock_); - devtools_frame_token_map_.erase( - std::make_pair(render_process_id, render_frame_routing_id)); + devtools_frame_token_map_.erase(content::GlobalFrameRoutingId( + render_process_id, render_frame_routing_id)); frame_tree_node_id_to_devtools_frame_token_map_.erase(frame_tree_node_id); } @@ -172,7 +172,7 @@ int render_frame_id) const { base::AutoLock lock(devtools_frame_token_map_lock_); const auto& find_it = devtools_frame_token_map_.find( - std::make_pair(render_process_id, render_frame_id)); + content::GlobalFrameRoutingId(render_process_id, render_frame_id)); if (find_it == devtools_frame_token_map_.end()) return nullptr; return &find_it->second;
diff --git a/headless/lib/browser/headless_browser_context_impl.h b/headless/lib/browser/headless_browser_context_impl.h index b4b2f1a5..d192b10 100644 --- a/headless/lib/browser/headless_browser_context_impl.h +++ b/headless/lib/browser/headless_browser_context_impl.h
@@ -13,6 +13,7 @@ #include "base/files/file_path.h" #include "base/unguessable_token.h" #include "content/public/browser/browser_context.h" +#include "content/public/browser/global_routing_id.h" #include "content/public/browser/resource_context.h" #include "headless/lib/browser/headless_browser_context_options.h" #include "headless/lib/browser/headless_network_conditions.h" @@ -139,7 +140,7 @@ // TODO(alexclarke): Remove if we can add DevTools frame token ID to // ResourceRequestInfo. See https://crbug.com/715541 mutable base::Lock devtools_frame_token_map_lock_; - base::flat_map<std::pair<int, int>, base::UnguessableToken> + base::flat_map<content::GlobalFrameRoutingId, base::UnguessableToken> devtools_frame_token_map_; base::flat_map<int, base::UnguessableToken> frame_tree_node_id_to_devtools_frame_token_map_;
diff --git a/ios/chrome/app/strings/ios_strings.grd b/ios/chrome/app/strings/ios_strings.grd index fe8c9032..e10ca3e3 100644 --- a/ios/chrome/app/strings/ios_strings.grd +++ b/ios/chrome/app/strings/ios_strings.grd
@@ -777,6 +777,9 @@ <message name="IDS_IOS_GOOGLE_SERVICES_SETTINGS_READING_LIST_TEXT" desc="Feature in the settings for the user to enable/disable, to sync reading list links between devices. [iOS only]"> Reading List </message> + <message name="IDS_IOS_GOOGLE_SERVICES_SETTINGS_AUTOCOMPLETE_WALLET" desc="Label for the checkbox that controls the Autofill/Payments integration feature. 'Google Pay' should not be translated as it is the product name. [iOS only]"> + Payment methods and addresses using Google Pay + </message> <message name="IDS_IOS_GOOGLE_SERVICES_SETTINGS_SETTINGS_TEXT" desc="Feature in the settings for the user to enable/disable, to sync settings data between devices. [iOS only]"> Settings </message>
diff --git a/ios/chrome/browser/BUILD.gn b/ios/chrome/browser/BUILD.gn index 549c2e02..a906447c 100644 --- a/ios/chrome/browser/BUILD.gn +++ b/ios/chrome/browser/BUILD.gn
@@ -210,7 +210,6 @@ "//ios/web/public/app", "//net", "//rlz/buildflags", - "//services/network:network_service", "//ui/base", ]
diff --git a/ios/chrome/browser/DEPS b/ios/chrome/browser/DEPS index c732355..6c856b1 100644 --- a/ios/chrome/browser/DEPS +++ b/ios/chrome/browser/DEPS
@@ -106,7 +106,6 @@ "+rlz/buildflags", "+services/identity/public", "+services/metrics/public", - "+services/network/network_change_manager.h", "+services/network/public/mojom", "+services/network/public/cpp", "+services/service_manager/public",
diff --git a/ios/chrome/browser/application_context.h b/ios/chrome/browser/application_context.h index 37b4000..bfdcf5e 100644 --- a/ios/chrome/browser/application_context.h +++ b/ios/chrome/browser/application_context.h
@@ -39,7 +39,6 @@ } namespace network { -class NetworkConnectionTracker; class SharedURLLoaderFactory; namespace mojom { class NetworkContext; @@ -140,9 +139,6 @@ virtual component_updater::ComponentUpdateService* GetComponentUpdateService() = 0; - // Returns the NetworkConnectionTracker instance for this ApplicationContext. - virtual network::NetworkConnectionTracker* GetNetworkConnectionTracker() = 0; - protected: // Sets the global ApplicationContext instance. static void SetApplicationContext(ApplicationContext* context);
diff --git a/ios/chrome/browser/application_context_impl.cc b/ios/chrome/browser/application_context_impl.cc index 359def6..b7db100 100644 --- a/ios/chrome/browser/application_context_impl.cc +++ b/ios/chrome/browser/application_context_impl.cc
@@ -55,8 +55,6 @@ #include "net/socket/client_socket_pool_manager.h" #include "net/url_request/url_request_context_getter.h" #include "services/metrics/public/cpp/ukm_recorder.h" -#include "services/network/network_change_manager.h" -#include "services/network/public/cpp/network_connection_tracker.h" #include "services/network/public/cpp/weak_wrapper_shared_url_loader_factory.h" namespace { @@ -81,13 +79,6 @@ app_context, std::move(request))); } -// Passed to NetworkConnectionTracker to bind a NetworkChangeManagerRequest. -void BindNetworkChangeManagerRequest( - network::NetworkChangeManager* network_change_manager, - network::mojom::NetworkChangeManagerRequest request) { - network_change_manager->AddRequest(std::move(request)); -} - } // namespace ApplicationContextImpl::ApplicationContextImpl( @@ -354,21 +345,6 @@ return component_updater_.get(); } -network::NetworkConnectionTracker* -ApplicationContextImpl::GetNetworkConnectionTracker() { - if (!network_connection_tracker_) { - if (!network_change_manager_) { - network_change_manager_ = - std::make_unique<network::NetworkChangeManager>(nullptr); - } - network_connection_tracker_ = - std::make_unique<network::NetworkConnectionTracker>(base::BindRepeating( - &BindNetworkChangeManagerRequest, - base::Unretained(network_change_manager_.get()))); - } - return network_connection_tracker_.get(); -} - void ApplicationContextImpl::SetApplicationLocale(const std::string& locale) { DCHECK(thread_checker_.CalledOnValidThread()); application_locale_ = locale;
diff --git a/ios/chrome/browser/application_context_impl.h b/ios/chrome/browser/application_context_impl.h index 76bbed4..b868ba5 100644 --- a/ios/chrome/browser/application_context_impl.h +++ b/ios/chrome/browser/application_context_impl.h
@@ -21,7 +21,6 @@ } namespace network { -class NetworkChangeManager; class WeakWrapperSharedURLLoaderFactory; } @@ -69,7 +68,6 @@ gcm::GCMDriver* GetGCMDriver() override; component_updater::ComponentUpdateService* GetComponentUpdateService() override; - network::NetworkConnectionTracker* GetNetworkConnectionTracker() override; private: // Sets the locale used by the application. @@ -104,10 +102,6 @@ // Created on the UI thread, destroyed on the IO thread. std::unique_ptr<web::NetworkContextOwner> network_context_owner_; - std::unique_ptr<network::NetworkChangeManager> network_change_manager_; - std::unique_ptr<network::NetworkConnectionTracker> - network_connection_tracker_; - bool was_last_shutdown_clean_; DISALLOW_COPY_AND_ASSIGN(ApplicationContextImpl);
diff --git a/ios/chrome/browser/autofill/form_suggestion_view.mm b/ios/chrome/browser/autofill/form_suggestion_view.mm index 9b22780..02abb037 100644 --- a/ios/chrome/browser/autofill/form_suggestion_view.mm +++ b/ios/chrome/browser/autofill/form_suggestion_view.mm
@@ -69,7 +69,6 @@ - (void)setupSubviews { self.showsVerticalScrollIndicator = NO; self.showsHorizontalScrollIndicator = NO; - self.bounces = NO; self.canCancelContentTouches = YES; UIStackView* stackView = [[UIStackView alloc] initWithArrangedSubviews:@[]];
diff --git a/ios/chrome/browser/google/BUILD.gn b/ios/chrome/browser/google/BUILD.gn index b805688..b629ee4 100644 --- a/ios/chrome/browser/google/BUILD.gn +++ b/ios/chrome/browser/google/BUILD.gn
@@ -17,7 +17,6 @@ "//components/google/core/browser", "//components/keyed_service/ios", "//components/prefs", - "//ios/chrome/browser", "//ios/chrome/browser/browser_state", "//ios/public/provider/chrome/browser", "//ios/public/provider/chrome/browser/distribution",
diff --git a/ios/chrome/browser/google/google_url_tracker_factory.cc b/ios/chrome/browser/google/google_url_tracker_factory.cc index f62da15..1f3081c 100644 --- a/ios/chrome/browser/google/google_url_tracker_factory.cc +++ b/ios/chrome/browser/google/google_url_tracker_factory.cc
@@ -10,7 +10,6 @@ #include "components/google/core/browser/google_url_tracker.h" #include "components/keyed_service/ios/browser_state_dependency_manager.h" #include "components/prefs/pref_service.h" -#include "ios/chrome/browser/application_context.h" #include "ios/chrome/browser/browser_state/browser_state_otr_helper.h" #include "ios/chrome/browser/browser_state/chrome_browser_state.h" #include "ios/chrome/browser/google/google_url_tracker_client_impl.h" @@ -50,8 +49,7 @@ return std::make_unique<GoogleURLTracker>( base::WrapUnique(new GoogleURLTrackerClientImpl(browser_state)), - GoogleURLTracker::NORMAL_MODE, - GetApplicationContext()->GetNetworkConnectionTracker()); + GoogleURLTracker::NORMAL_MODE, context->GetNetworkConnectionTracker()); } web::BrowserState* GoogleURLTrackerFactory::GetBrowserStateToUse(
diff --git a/ios/chrome/browser/metrics/ios_chrome_metrics_services_manager_client.mm b/ios/chrome/browser/metrics/ios_chrome_metrics_services_manager_client.mm index bb9527b..ac381d9 100644 --- a/ios/chrome/browser/metrics/ios_chrome_metrics_services_manager_client.mm +++ b/ios/chrome/browser/metrics/ios_chrome_metrics_services_manager_client.mm
@@ -76,9 +76,7 @@ return variations::VariationsService::Create( std::make_unique<IOSChromeVariationsServiceClient>(), local_state_, GetMetricsStateManager(), "dummy-disable-background-switch", - ::CreateUIStringOverrider(), - base::BindOnce(&ApplicationContext::GetNetworkConnectionTracker, - base::Unretained(GetApplicationContext()))); + ::CreateUIStringOverrider()); } std::unique_ptr<metrics::MetricsServiceClient>
diff --git a/ios/chrome/browser/signin/account_tracker_service_factory.cc b/ios/chrome/browser/signin/account_tracker_service_factory.cc index a8ad4ea..cadccbbfa 100644 --- a/ios/chrome/browser/signin/account_tracker_service_factory.cc +++ b/ios/chrome/browser/signin/account_tracker_service_factory.cc
@@ -10,7 +10,6 @@ #include "components/keyed_service/ios/browser_state_dependency_manager.h" #include "components/signin/core/browser/account_tracker_service.h" #include "ios/chrome/browser/browser_state/chrome_browser_state.h" -#include "ios/chrome/browser/signin/signin_client_factory.h" namespace ios { @@ -18,7 +17,6 @@ : BrowserStateKeyedServiceFactory( "AccountTrackerService", BrowserStateDependencyManager::GetInstance()) { - DependsOn(SigninClientFactory::GetInstance()); } AccountTrackerServiceFactory::~AccountTrackerServiceFactory() {} @@ -46,8 +44,7 @@ ios::ChromeBrowserState* chrome_browser_state = ios::ChromeBrowserState::FromBrowserState(context); std::unique_ptr<AccountTrackerService> service(new AccountTrackerService()); - service->Initialize( - SigninClientFactory::GetForBrowserState(chrome_browser_state)); + service->Initialize(chrome_browser_state->GetPrefs(), base::FilePath()); return service; }
diff --git a/ios/chrome/browser/signin/authentication_service_unittest.mm b/ios/chrome/browser/signin/authentication_service_unittest.mm index 62cae6f..fa6fc8b09 100644 --- a/ios/chrome/browser/signin/authentication_service_unittest.mm +++ b/ios/chrome/browser/signin/authentication_service_unittest.mm
@@ -565,8 +565,7 @@ // Migrate the accounts (this actually requires a shutdown and re-initialize // of the account tracker). account_tracker->Shutdown(); - account_tracker->Initialize( - SigninClientFactory::GetForBrowserState(browser_state_.get())); + account_tracker->Initialize(browser_state_->GetPrefs(), base::FilePath()); account_tracker->SetMigrationDone(); // Actually migrate the accounts in prefs.
diff --git a/ios/chrome/browser/translate/translate_service_ios.cc b/ios/chrome/browser/translate/translate_service_ios.cc index 9a9c93f..2df8f01 100644 --- a/ios/chrome/browser/translate/translate_service_ios.cc +++ b/ios/chrome/browser/translate/translate_service_ios.cc
@@ -19,10 +19,8 @@ TranslateServiceIOS::TranslateServiceIOS() : resource_request_allowed_notifier_( GetApplicationContext()->GetLocalState(), - nullptr, - base::BindOnce(&ApplicationContext::GetNetworkConnectionTracker, - base::Unretained(GetApplicationContext()))) { - resource_request_allowed_notifier_.Init(this, false /* leaky */); + nullptr) { + resource_request_allowed_notifier_.Init(this); } TranslateServiceIOS::~TranslateServiceIOS() {
diff --git a/ios/chrome/browser/ui/content_suggestions/content_suggestions_header_view_controller.mm b/ios/chrome/browser/ui/content_suggestions/content_suggestions_header_view_controller.mm index d282cf33..942fc82 100644 --- a/ios/chrome/browser/ui/content_suggestions/content_suggestions_header_view_controller.mm +++ b/ios/chrome/browser/ui/content_suggestions/content_suggestions_header_view_controller.mm
@@ -459,8 +459,6 @@ !content_suggestions::IsRegularXRegularSizeClass(self.view))) { [self.dispatcher onFakeboxBlur]; } - self.fakeOmnibox.hidden = NO; - [self.collectionSynchronizer shiftTilesDown]; [self.commandHandler dismissModals]; @@ -476,7 +474,6 @@ !content_suggestions::IsRegularXRegularSizeClass(self.view))) { [self.dispatcher onFakeboxAnimationComplete]; [self.headerView fadeOutShadow]; - [self.fakeOmnibox setHidden:YES]; } }; [self.collectionSynchronizer shiftTilesUpWithCompletionBlock:completionBlock];
diff --git a/ios/chrome/browser/ui/settings/google_services_settings_consumer.h b/ios/chrome/browser/ui/settings/google_services_settings_consumer.h index 9fb8ccc..def7367 100644 --- a/ios/chrome/browser/ui/settings/google_services_settings_consumer.h +++ b/ios/chrome/browser/ui/settings/google_services_settings_consumer.h
@@ -19,6 +19,9 @@ // Reloads |sections|. - (void)reloadSections:(NSIndexSet*)sections; +// Reloads only a specific |item|. +- (void)reloadItem:(CollectionViewItem*)item; + @end #endif // IOS_CHROME_BROWSER_UI_SETTINGS_GOOGLE_SERVICES_SETTINGS_CONSUMER_H_
diff --git a/ios/chrome/browser/ui/settings/google_services_settings_mediator.mm b/ios/chrome/browser/ui/settings/google_services_settings_mediator.mm index 3fb4be20..d32e3b4 100644 --- a/ios/chrome/browser/ui/settings/google_services_settings_mediator.mm +++ b/ios/chrome/browser/ui/settings/google_services_settings_mediator.mm
@@ -6,6 +6,7 @@ #include "base/auto_reset.h" #include "base/mac/foundation_util.h" +#include "components/autofill/core/common/autofill_prefs.h" #include "components/browser_sync/profile_sync_service.h" #include "components/metrics/metrics_pref_names.h" #import "components/prefs/ios/pref_observer_bridge.h" @@ -66,6 +67,7 @@ SyncAutofillItemType, SyncSettingsItemType, SyncReadingListItemType, + AutocompleteWalletItemType, SyncActivityAndInteractionsItemType, SyncGoogleActivityControlsItemType, EncryptionItemType, @@ -99,6 +101,9 @@ @property(nonatomic, assign, readonly) BOOL isConsentGiven; // Sync setup service. @property(nonatomic, assign, readonly) SyncSetupService* syncSetupService; +// Preference value for the autocomplete wallet feature. +@property(nonatomic, strong, readonly) + PrefBackedBoolean* autocompleteWalletPreference; // Preference value for the "Autocomplete searches and URLs" feature. @property(nonatomic, strong, readonly) PrefBackedBoolean* autocompleteSearchPreference; @@ -135,6 +140,8 @@ SettingsCollapsibleItem* syncPersonalizationItem; // All the items for the personalized section. @property(nonatomic, strong, readonly) ItemArray personalizedItems; +// Item for the autocomplete wallet feature. +@property(nonatomic, strong, readonly) SyncSwitchItem* autocompleteWalletItem; // Collapsible item for the non-personalized section. @property(nonatomic, strong, readonly) SettingsCollapsibleItem* nonPersonalizedServicesItem; @@ -149,6 +156,7 @@ @synthesize consumer = _consumer; @synthesize authService = _authService; @synthesize syncSetupService = _syncSetupService; +@synthesize autocompleteWalletPreference = _autocompleteWalletPreference; @synthesize autocompleteSearchPreference = _autocompleteSearchPreference; @synthesize preloadPagesPreference = _preloadPagesPreference; @synthesize preloadPagesWifiOnlyPreference = _preloadPagesWifiOnlyPreference; @@ -163,6 +171,7 @@ @synthesize syncEverythingItem = _syncEverythingItem; @synthesize syncPersonalizationItem = _syncPersonalizationItem; @synthesize personalizedItems = _personalizedItems; +@synthesize autocompleteWalletItem = _autocompleteWalletItem; @synthesize nonPersonalizedServicesItem = _nonPersonalizedServicesItem; @synthesize nonPersonalizedItems = _nonPersonalizedItems; @@ -189,21 +198,25 @@ prefChangeRegistrar_.Init(userPrefService); prefObserverBridge_->ObserveChangesForPreference(kUnifiedConsentGiven, &prefChangeRegistrar_); + _autocompleteWalletPreference = [[PrefBackedBoolean alloc] + initWithPrefService:userPrefService + prefName:autofill::prefs::kAutofillWalletImportEnabled]; + _autocompleteWalletPreference.observer = self; _autocompleteSearchPreference = [[PrefBackedBoolean alloc] initWithPrefService:userPrefService prefName:prefs::kSearchSuggestEnabled]; - [_autocompleteSearchPreference setObserver:self]; + _autocompleteSearchPreference.observer = self; _preloadPagesPreference = [[PrefBackedBoolean alloc] initWithPrefService:userPrefService prefName:prefs::kNetworkPredictionEnabled]; - [_preloadPagesPreference setObserver:self]; + _preloadPagesPreference.observer = self; _preloadPagesWifiOnlyPreference = [[PrefBackedBoolean alloc] initWithPrefService:userPrefService prefName:prefs::kNetworkPredictionWifiOnly]; _sendDataUsagePreference = [[PrefBackedBoolean alloc] initWithPrefService:localPrefService prefName:metrics::prefs::kMetricsReportingEnabled]; - [_sendDataUsagePreference setObserver:self]; + _sendDataUsagePreference.observer = self; _sendDataUsageWifiOnlyPreference = [[PrefBackedBoolean alloc] initWithPrefService:localPrefService prefName:prefs::kMetricsReportingWifiOnly]; @@ -211,7 +224,7 @@ initWithPrefService:userPrefService prefName:unified_consent::prefs:: kUrlKeyedAnonymizedDataCollectionEnabled]; - [_anonymizedDataCollectionPreference setObserver:self]; + _anonymizedDataCollectionPreference.observer = self; } return self; } @@ -379,13 +392,27 @@ _personalizedItems = @[ syncBookmarksItem, syncHistoryItem, syncPasswordsItem, syncOpenTabsItem, syncAutofillItem, syncSettingsItem, syncReadingListItem, - syncActivityAndInteractionsItem, syncGoogleActivityControlsItem, - encryptionItem, manageSyncedDataItem + self.autocompleteWalletItem, syncActivityAndInteractionsItem, + syncGoogleActivityControlsItem, encryptionItem, manageSyncedDataItem ]; } return _personalizedItems; } +- (SyncSwitchItem*)autocompleteWalletItem { + if (!_autocompleteWalletItem) { + _autocompleteWalletItem = [self + switchItemWithItemType:AutocompleteWalletItemType + textStringID: + IDS_IOS_GOOGLE_SERVICES_SETTINGS_AUTOCOMPLETE_WALLET + detailStringID:0 + commandID: + GoogleServicesSettingsCommandIDAutocompleteWalletService + dataType:0]; + } + return _autocompleteWalletItem; +} + - (SettingsCollapsibleItem*)nonPersonalizedServicesItem { if (!_nonPersonalizedServicesItem) { _nonPersonalizedServicesItem = [self @@ -497,6 +524,14 @@ [self updateSectionWithCollapsibleItem:self.syncPersonalizationItem items:self.personalizedItems enabled:enabled]; + syncer::ModelType autofillModelType = + _syncSetupService->GetModelType(SyncSetupService::kSyncAutofill); + BOOL isAutofillOn = _syncSetupService->IsDataTypePreferred(autofillModelType); + self.autocompleteWalletItem.enabled = enabled && isAutofillOn; + if (!isAutofillOn) { + // Autocomplete wallet item should be disabled when autofill is off. + self.autocompleteWalletItem.on = false; + } } // Updates the non-personalized section according to the user consent. @@ -528,6 +563,9 @@ switchItem.on = self.syncSetupService->IsDataTypePreferred(modelType); break; } + case GoogleServicesSettingsCommandIDAutocompleteWalletService: + switchItem.on = self.autocompleteWalletPreference.value; + break; case GoogleServicesSettingsCommandIDToggleAutocompleteSearchesService: switchItem.on = self.autocompleteSearchPreference.value; break; @@ -588,6 +626,10 @@ self.syncSetupService->SetDataTypeEnabled(modelType, value); } +- (void)toggleAutocompleteWalletServiceWithValue:(BOOL)value { + self.autocompleteWalletPreference.value = value; +} + - (void)toggleAutocompleteSearchesServiceWithValue:(BOOL)value { self.autocompleteSearchPreference.value = value; } @@ -653,10 +695,15 @@ - (void)onSyncStateChanged { [self updatePersonalizedSection]; if (!self.personalizedSectionBeingAnimated) { + CollectionViewModel* model = self.consumer.collectionViewModel; NSMutableIndexSet* sectionIndexToReload = [NSMutableIndexSet indexSet]; - [sectionIndexToReload - addIndex:PersonalizedSectionIdentifier - kSectionIdentifierEnumZero]; + [sectionIndexToReload addIndex:[model sectionForSectionIdentifier: + PersonalizedSectionIdentifier]]; [self.consumer reloadSections:sectionIndexToReload]; + } else { + // Needs to reload only the autocomplete wallet item (which is part of the + // personalized section), if the autofill feature changed state. + [self.consumer reloadItem:self.autocompleteWalletItem]; } }
diff --git a/ios/chrome/browser/ui/settings/google_services_settings_service_delegate.h b/ios/chrome/browser/ui/settings/google_services_settings_service_delegate.h index fb7bcd16..e20b7448 100644 --- a/ios/chrome/browser/ui/settings/google_services_settings_service_delegate.h +++ b/ios/chrome/browser/ui/settings/google_services_settings_service_delegate.h
@@ -15,6 +15,8 @@ // Personalized section. // Enable/disabble bookmark sync. GoogleServicesSettingsCommandIDToggleDataTypeSync, + // Enable/disable autocomplete wallet for Google Pay. + GoogleServicesSettingsCommandIDAutocompleteWalletService, // Opens the Google activity controls dialog. GoogleServicesSettingsCommandIDOpenGoogleActivityControlsDialog, // Opens the encryption dialog. @@ -42,6 +44,9 @@ // Personalized section. // Called when GoogleServicesSettingsCommandIDToggleDataTypeSync is triggered. - (void)toggleSyncDataSync:(NSInteger)dataType withValue:(BOOL)value; +// Called when GoogleServicesSettingsCommandIDAutocompleteWalletService is +// triggered. +- (void)toggleAutocompleteWalletServiceWithValue:(BOOL)value; // Non-personalized section. // Called when GoogleServicesSettingsCommandIDToggleAutocompleteSearchesService
diff --git a/ios/chrome/browser/ui/settings/google_services_settings_view_controller.mm b/ios/chrome/browser/ui/settings/google_services_settings_view_controller.mm index cef94c6..c6dee0a 100644 --- a/ios/chrome/browser/ui/settings/google_services_settings_view_controller.mm +++ b/ios/chrome/browser/ui/settings/google_services_settings_view_controller.mm
@@ -110,6 +110,9 @@ [self.serviceDelegate toggleSyncDataSync:syncSwitchItem.dataType withValue:isOn]; break; + case GoogleServicesSettingsCommandIDAutocompleteWalletService: + [self.serviceDelegate toggleAutocompleteWalletServiceWithValue:isOn]; + break; case GoogleServicesSettingsCommandIDToggleAutocompleteSearchesService: [self.serviceDelegate toggleAutocompleteSearchesServiceWithValue:isOn]; break; @@ -152,6 +155,11 @@ [self.collectionView reloadSections:sections]; } +- (void)reloadItem:(CollectionViewItem*)item { + NSIndexPath* indexPath = [self.collectionViewModel indexPathForItem:item]; + [self.collectionView reloadItemsAtIndexPaths:@[ indexPath ]]; +} + #pragma mark - CollectionViewController - (void)loadModel { @@ -235,6 +243,7 @@ case GoogleServicesSettingsCommandIDNoOp: case GoogleServicesSettingsCommandIDToggleSyncEverything: case GoogleServicesSettingsCommandIDToggleDataTypeSync: + case GoogleServicesSettingsCommandIDAutocompleteWalletService: case GoogleServicesSettingsCommandIDToggleAutocompleteSearchesService: case GoogleServicesSettingsCommandIDTogglePreloadPagesService: case GoogleServicesSettingsCommandIDToggleImproveChromeService:
diff --git a/ios/chrome/test/testing_application_context.h b/ios/chrome/test/testing_application_context.h index e9f99ec..ea8b4d2 100644 --- a/ios/chrome/test/testing_application_context.h +++ b/ios/chrome/test/testing_application_context.h
@@ -59,7 +59,6 @@ gcm::GCMDriver* GetGCMDriver() override; component_updater::ComponentUpdateService* GetComponentUpdateService() override; - network::NetworkConnectionTracker* GetNetworkConnectionTracker() override; private: base::ThreadChecker thread_checker_;
diff --git a/ios/chrome/test/testing_application_context.mm b/ios/chrome/test/testing_application_context.mm index 9922836..85c7afd 100644 --- a/ios/chrome/test/testing_application_context.mm +++ b/ios/chrome/test/testing_application_context.mm
@@ -179,9 +179,3 @@ DCHECK(thread_checker_.CalledOnValidThread()); return nullptr; } - -network::NetworkConnectionTracker* -TestingApplicationContext::GetNetworkConnectionTracker() { - DCHECK(thread_checker_.CalledOnValidThread()); - return nullptr; -}
diff --git a/ios/web/DEPS b/ios/web/DEPS index 7f2767d7..375657e 100644 --- a/ios/web/DEPS +++ b/ios/web/DEPS
@@ -5,6 +5,7 @@ "+ios/web", "+mojo/public", "+net", + "+services/network/network_change_manager.h", "+services/network/network_context.h", "+services/network/public/cpp", "+services/network/public/mojom",
diff --git a/ios/web/browser_state.mm b/ios/web/browser_state.mm index 37c8d2e..df3dcaf 100644 --- a/ios/web/browser_state.mm +++ b/ios/web/browser_state.mm
@@ -23,7 +23,9 @@ #include "mojo/public/cpp/bindings/interface_request.h" #include "net/url_request/url_request_context_getter.h" #include "net/url_request/url_request_context_getter_observer.h" +#include "services/network/network_change_manager.h" #include "services/network/network_context.h" +#include "services/network/public/cpp/network_connection_tracker.h" #include "services/network/public/cpp/weak_wrapper_shared_url_loader_factory.h" #include "services/service_manager/public/cpp/connector.h" #include "services/service_manager/public/mojom/service.mojom.h" @@ -107,6 +109,13 @@ DISALLOW_COPY_AND_ASSIGN(BrowserStateServiceManagerConnectionHolder); }; +// Passed to NetworkConnectionTracker to bind a NetworkChangeManagerRequest. +void BindNetworkChangeManagerRequest( + network::NetworkChangeManager* network_change_manager, + network::mojom::NetworkChangeManagerRequest request) { + network_change_manager->AddRequest(std::move(request)); +} + } // namespace // static @@ -189,6 +198,19 @@ return cookie_manager_.get(); } +network::NetworkConnectionTracker* BrowserState::GetNetworkConnectionTracker() { + if (!network_connection_tracker_) { + DCHECK(!network_change_manager_); + network_change_manager_ = + std::make_unique<network::NetworkChangeManager>(nullptr); + network_connection_tracker_ = + std::make_unique<network::NetworkConnectionTracker>(base::BindRepeating( + &BindNetworkChangeManagerRequest, + base::Unretained(network_change_manager_.get()))); + } + return network_connection_tracker_.get(); +} + void BrowserState::GetProxyResolvingSocketFactory( network::mojom::ProxyResolvingSocketFactoryRequest request) { CreateNetworkContextIfNecessary();
diff --git a/ios/web/public/browser_state.h b/ios/web/public/browser_state.h index 878d5507..535b5174 100644 --- a/ios/web/public/browser_state.h +++ b/ios/web/public/browser_state.h
@@ -23,6 +23,8 @@ } namespace network { +class NetworkChangeManager; +class NetworkConnectionTracker; class SharedURLLoaderFactory; class WeakWrapperSharedURLLoaderFactory; } // namespace network @@ -68,6 +70,9 @@ // Returns a CookieManager that is backed by GetRequestContext. network::mojom::CookieManager* GetCookieManager(); + // Returns the NetworkConnectionTracker instance for this BrowserState. + network::NetworkConnectionTracker* GetNetworkConnectionTracker(); + // Binds a ProxyResolvingSocketFactory request to NetworkContext. void GetProxyResolvingSocketFactory( network::mojom::ProxyResolvingSocketFactoryRequest request); @@ -129,6 +134,12 @@ shared_url_loader_factory_; network::mojom::NetworkContextPtr network_context_; + // Acts as a proxy between the NetworkChangeNotifier and + // NetworkConnectionTracker. + std::unique_ptr<network::NetworkChangeManager> network_change_manager_; + std::unique_ptr<network::NetworkConnectionTracker> + network_connection_tracker_; + // Owns the network::NetworkContext that backs |url_loader_factory_|. Created // on the UI thread, destroyed on the IO thread. std::unique_ptr<NetworkContextOwner> network_context_owner_;
diff --git a/ios/web/public/web_state/web_frames_manager.h b/ios/web/public/web_state/web_frames_manager.h index 441a385..770cbbb 100644 --- a/ios/web/public/web_state/web_frames_manager.h +++ b/ios/web/public/web_state/web_frames_manager.h
@@ -5,10 +5,11 @@ #ifndef IOS_WEB_PUBLIC_WEB_STATE_WEB_FRAMES_MANAGER_H_ #define IOS_WEB_PUBLIC_WEB_STATE_WEB_FRAMES_MANAGER_H_ +#include <set> #include <string> -#include <vector> #include "base/macros.h" +#import "ios/web/public/web_state/web_state_user_data.h" namespace web { @@ -19,19 +20,24 @@ // NOTE: WebFrame objects should be used directly from this manager and not // stored elsewhere for later use becase WebFrames are frequently replaced. // For example, a navigation will invalidate the WebFrame object for that frame. -class WebFramesManager { +class WebFramesManager : public web::WebStateUserData<WebFramesManager> { public: // Returns a list of all the web frames associated with WebState. // NOTE: Due to the asynchronous nature of renderer, this list may be // outdated. - virtual const std::vector<WebFrame*>& GetAllWebFrames() = 0; + virtual std::set<WebFrame*> GetAllWebFrames() = 0; // Returns the web frame for the main frame associated with WebState or null // if unknown. // NOTE: Due to the asynchronous nature of JavaScript to native messsaging, // this object may be outdated. virtual WebFrame* GetMainWebFrame() = 0; + // Returns the web frame with |frame_id|, if one exists. + // NOTE: Due to the asynchronous nature of JavaScript to native messsaging, + // this object may be outdated and the WebFrame returned by this method may + // not back a real frame in the web page. + virtual WebFrame* GetFrameWithId(const std::string& frame_id) = 0; - virtual ~WebFramesManager() {} + ~WebFramesManager() override {} protected: WebFramesManager() {}
diff --git a/ios/web/web_state/web_frames_manager_impl.h b/ios/web/web_state/web_frames_manager_impl.h index bef7fe3..0f316a1 100644 --- a/ios/web/web_state/web_frames_manager_impl.h +++ b/ios/web/web_state/web_frames_manager_impl.h
@@ -6,19 +6,19 @@ #define IOS_WEB_WEB_STATE_WEB_FRAMES_MANAGER_IMPL_H_ #include "ios/web/public/web_state/web_frames_manager.h" -#include "ios/web/public/web_state/web_state_user_data.h" namespace web { class WebFrame; -class WebFramesManagerImpl - : public WebFramesManager, - public web::WebStateUserData<WebFramesManagerImpl> { +class WebFramesManagerImpl : public WebFramesManager { public: ~WebFramesManagerImpl() override; explicit WebFramesManagerImpl(web::WebState* web_state); + static void CreateForWebState(WebState* web_state); + static WebFramesManagerImpl* FromWebState(WebState* web_state); + // Adds |frame| to the list of web frames associated with WebState. void AddFrame(std::unique_ptr<WebFrame> frame); // Removes the web frame with |frame_id|, if one exists, from the list of @@ -30,21 +30,16 @@ // and keys of existing frames. void RegisterExistingFrames(); - // Returns the web frame with |frame_id|, if one exisits, from the list of - // associated web frames. - WebFrame* GetFrameWithId(const std::string& frame_id); - // WebFramesManager overrides - const std::vector<WebFrame*>& GetAllWebFrames() override; + std::set<WebFrame*> GetAllWebFrames() override; WebFrame* GetMainWebFrame() override; + WebFrame* GetFrameWithId(const std::string& frame_id) override; private: friend class web::WebStateUserData<WebFramesManagerImpl>; - // List of all web frames associated with WebState. - std::vector<std::unique_ptr<WebFrame>> web_frames_; // List of pointers to all web frames associated with WebState. - std::vector<WebFrame*> web_frame_ptrs_; + std::map<std::string, std::unique_ptr<WebFrame>> web_frames_; // Reference to the current main web frame. WebFrame* main_web_frame_ = nullptr;
diff --git a/ios/web/web_state/web_frames_manager_impl.mm b/ios/web/web_state/web_frames_manager_impl.mm index 0d83ba1..5b902e5 100644 --- a/ios/web/web_state/web_frames_manager_impl.mm +++ b/ios/web/web_state/web_frames_manager_impl.mm
@@ -31,7 +31,19 @@ namespace web { -DEFINE_WEB_STATE_USER_DATA_KEY(WebFramesManagerImpl); +// static +void WebFramesManagerImpl::CreateForWebState(WebState* web_state) { + DCHECK(web_state); + if (!FromWebState(web_state)) + web_state->SetUserData( + UserDataKey(), base::WrapUnique(new WebFramesManagerImpl(web_state))); +} + +// static +WebFramesManagerImpl* WebFramesManagerImpl::FromWebState(WebState* web_state) { + return static_cast<WebFramesManagerImpl*>( + WebFramesManager::FromWebState(web_state)); +} WebFramesManagerImpl::~WebFramesManagerImpl() = default; @@ -42,39 +54,35 @@ if (frame->IsMainFrame()) { main_web_frame_ = frame.get(); } - web_frame_ptrs_.push_back(frame.get()); - web_frames_.push_back(std::move(frame)); + DCHECK(web_frames_.count(frame->GetFrameId()) == 0); + web_frames_[frame->GetFrameId()] = std::move(frame); } void WebFramesManagerImpl::RemoveFrameWithId(const std::string& frame_id) { if (main_web_frame_ && main_web_frame_->GetFrameId() == frame_id) { main_web_frame_ = nullptr; } - - auto web_frame_ptrs_it = std::find_if( - web_frame_ptrs_.begin(), web_frame_ptrs_.end(), FrameIdMatcher(frame_id)); - if (web_frame_ptrs_it != web_frame_ptrs_.end()) { - web_frame_ptrs_.erase(web_frame_ptrs_it); - web_frames_.erase(web_frames_.begin() + - (web_frame_ptrs_it - web_frame_ptrs_.begin())); - } + web_frames_.erase(frame_id); } void WebFramesManagerImpl::RemoveAllWebFrames() { main_web_frame_ = nullptr; web_frames_.clear(); - web_frame_ptrs_.clear(); } WebFrame* WebFramesManagerImpl::GetFrameWithId(const std::string& frame_id) { - auto web_frame_ptrs_it = std::find_if( - web_frame_ptrs_.begin(), web_frame_ptrs_.end(), FrameIdMatcher(frame_id)); - return web_frame_ptrs_it == web_frame_ptrs_.end() ? nullptr - : *web_frame_ptrs_it; + DCHECK(!frame_id.empty()); + auto web_frames_it = web_frames_.find(frame_id); + return web_frames_it == web_frames_.end() ? nullptr + : web_frames_it->second.get(); } -const std::vector<WebFrame*>& WebFramesManagerImpl::GetAllWebFrames() { - return web_frame_ptrs_; +std::set<WebFrame*> WebFramesManagerImpl::GetAllWebFrames() { + std::set<WebFrame*> frames; + for (const auto& it : web_frames_) { + frames.insert(it.second.get()); + } + return frames; } WebFrame* WebFramesManagerImpl::GetMainWebFrame() {
diff --git a/ios/web/web_state/web_frames_manager_impl_unittest.mm b/ios/web/web_state/web_frames_manager_impl_unittest.mm index 6baf7af..ccd0fbe 100644 --- a/ios/web/web_state/web_frames_manager_impl_unittest.mm +++ b/ios/web/web_state/web_frames_manager_impl_unittest.mm
@@ -22,7 +22,7 @@ const char kFrameKey[] = "d1uJzdvOFIUT5kEpK4o+x5JCaSlYT/a45ISU7S9EzTo="; // Returns true if |web_frame| is contained in |frames|. -bool ContainsWebFrame(std::vector<web::WebFrame*> frames, +bool ContainsWebFrame(std::set<web::WebFrame*> frames, web::WebFrame* web_frame) { return frames.end() != std::find(frames.begin(), frames.end(), web_frame); }
diff --git a/ios/web_view/BUILD.gn b/ios/web_view/BUILD.gn index 90f015b..5bf710c 100644 --- a/ios/web_view/BUILD.gn +++ b/ios/web_view/BUILD.gn
@@ -246,7 +246,6 @@ "//components/language/core/browser", "//components/language/core/common", "//components/net_log", - "//services/network:network_service", "//components/password_manager/core/browser", "//components/password_manager/core/browser/form_parsing:form_parsing", "//components/password_manager/core/common",
diff --git a/ios/web_view/internal/DEPS b/ios/web_view/internal/DEPS index 57946d6..560a264 100644 --- a/ios/web_view/internal/DEPS +++ b/ios/web_view/internal/DEPS
@@ -34,7 +34,6 @@ "+ios/web_view", "+net", "+services/identity/public/cpp", - "+services/network/network_change_manager.h", "+services/network/public/cpp", "+services/network/public/mojom", "+third_party/ocmock",
diff --git a/ios/web_view/internal/app/application_context.cc b/ios/web_view/internal/app/application_context.cc index ca0468b..593402e32 100644 --- a/ios/web_view/internal/app/application_context.cc +++ b/ios/web_view/internal/app/application_context.cc
@@ -20,22 +20,10 @@ #include "ios/web_view/cwv_web_view_features.h" #include "ios/web_view/internal/app/web_view_io_thread.h" #include "net/socket/client_socket_pool_manager.h" -#include "services/network/network_change_manager.h" -#include "services/network/public/cpp/network_connection_tracker.h" #include "services/network/public/cpp/weak_wrapper_shared_url_loader_factory.h" #include "ui/base/l10n/l10n_util_mac.h" namespace ios_web_view { -namespace { - -// Passed to NetworkConnectionTracker to bind a NetworkChangeManagerRequest. -void BindNetworkChangeManagerRequest( - network::NetworkChangeManager* network_change_manager, - network::mojom::NetworkChangeManagerRequest request) { - network_change_manager->AddRequest(std::move(request)); -} - -} // namespace ApplicationContext* ApplicationContext::GetInstance() { return base::Singleton<ApplicationContext>::get(); @@ -149,21 +137,6 @@ return network_context_.get(); } -network::NetworkConnectionTracker* -ApplicationContext::GetNetworkConnectionTracker() { - if (!network_connection_tracker_) { - if (!network_change_manager_) { - network_change_manager_ = - std::make_unique<network::NetworkChangeManager>(nullptr); - } - network_connection_tracker_ = - std::make_unique<network::NetworkConnectionTracker>(base::BindRepeating( - &BindNetworkChangeManagerRequest, - base::Unretained(network_change_manager_.get()))); - } - return network_connection_tracker_.get(); -} - const std::string& ApplicationContext::GetApplicationLocale() { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); DCHECK(!application_locale_.empty());
diff --git a/ios/web_view/internal/app/application_context.h b/ios/web_view/internal/app/application_context.h index 19f242d..5e94d37 100644 --- a/ios/web_view/internal/app/application_context.h +++ b/ios/web_view/internal/app/application_context.h
@@ -23,8 +23,6 @@ } namespace network { -class NetworkChangeManager; -class NetworkConnectionTracker; class SharedURLLoaderFactory; class WeakWrapperSharedURLLoaderFactory; namespace mojom { @@ -56,9 +54,6 @@ scoped_refptr<network::SharedURLLoaderFactory> GetSharedURLLoaderFactory(); network::mojom::NetworkContext* GetSystemNetworkContext(); - // Returns the NetworkConnectionTracker instance for this ApplicationContext. - network::NetworkConnectionTracker* GetNetworkConnectionTracker(); - // Gets the locale used by the application. const std::string& GetApplicationLocale(); @@ -103,10 +98,6 @@ // Created on the UI thread, destroyed on the IO thread. std::unique_ptr<web::NetworkContextOwner> network_context_owner_; - std::unique_ptr<network::NetworkChangeManager> network_change_manager_; - std::unique_ptr<network::NetworkConnectionTracker> - network_connection_tracker_; - DISALLOW_COPY_AND_ASSIGN(ApplicationContext); };
diff --git a/ios/web_view/internal/signin/web_view_account_tracker_service_factory.mm b/ios/web_view/internal/signin/web_view_account_tracker_service_factory.mm index 1ec93fdc9..27b3e5d 100644 --- a/ios/web_view/internal/signin/web_view_account_tracker_service_factory.mm +++ b/ios/web_view/internal/signin/web_view_account_tracker_service_factory.mm
@@ -9,8 +9,6 @@ #include "base/memory/singleton.h" #include "components/keyed_service/ios/browser_state_dependency_manager.h" #include "components/signin/core/browser/account_tracker_service.h" -#include "ios/web_view/internal/signin/ios_web_view_signin_client.h" -#include "ios/web_view/internal/signin/web_view_signin_client_factory.h" #include "ios/web_view/internal/web_view_browser_state.h" #if !defined(__has_feature) || !__has_feature(objc_arc) @@ -23,7 +21,6 @@ : BrowserStateKeyedServiceFactory( "AccountTrackerService", BrowserStateDependencyManager::GetInstance()) { - DependsOn(WebViewSigninClientFactory::GetInstance()); } // static @@ -51,8 +48,7 @@ WebViewBrowserState::FromBrowserState(context); std::unique_ptr<AccountTrackerService> service = std::make_unique<AccountTrackerService>(); - service->Initialize( - WebViewSigninClientFactory::GetForBrowserState(browser_state)); + service->Initialize(browser_state->GetPrefs(), base::FilePath()); return service; }
diff --git a/ios/web_view/internal/translate/web_view_translate_service.cc b/ios/web_view/internal/translate/web_view_translate_service.cc index fbe15c8..f9e06a7 100644 --- a/ios/web_view/internal/translate/web_view_translate_service.cc +++ b/ios/web_view/internal/translate/web_view_translate_service.cc
@@ -15,10 +15,8 @@ TranslateRequestsAllowedListener() : resource_request_allowed_notifier_( ios_web_view::ApplicationContext::GetInstance()->GetLocalState(), - /*disable_network_switch=*/nullptr, - base::BindOnce(&ApplicationContext::GetNetworkConnectionTracker, - base::Unretained(ApplicationContext::GetInstance()))) { - resource_request_allowed_notifier_.Init(this, /*leaky=*/false); + /*disable_network_switch=*/nullptr) { + resource_request_allowed_notifier_.Init(this); } WebViewTranslateService::TranslateRequestsAllowedListener::
diff --git a/net/base/net_error_list.h b/net/base/net_error_list.h index 9617a472..786ad95 100644 --- a/net/base/net_error_list.h +++ b/net/base/net_error_list.h
@@ -424,8 +424,7 @@ // received before any data is returned from the socket. The request should be // retried with early data disabled. // -// See https://tools.ietf.org/html/draft-ietf-tls-tls13-28#appendix-D.3 for -// details. +// See https://tools.ietf.org/html/rfc8446#appendix-D.3 for details. NET_ERROR(WRONG_VERSION_ON_EARLY_DATA, -179) // Certificate error codes
diff --git a/net/cert/nss_cert_database.cc b/net/cert/nss_cert_database.cc index ef6d740..a6f3aabb 100644 --- a/net/cert/nss_cert_database.cc +++ b/net/cert/nss_cert_database.cc
@@ -347,6 +347,26 @@ return false; } +bool NSSCertDatabase::IsWebTrustAnchor(const CERTCertificate* cert) const { + CERTCertTrust nsstrust; + SECStatus rv = CERT_GetCertTrust(cert, &nsstrust); + if (rv != SECSuccess) { + LOG(ERROR) << "CERT_GetCertTrust failed with error " << PORT_GetError(); + return false; + } + + // Note: This should return true iff a net::TrustStoreNSS instantiated with + // SECTrustType trustSSL would classify |cert| as a trust anchor. + const unsigned int ssl_trust_flags = nsstrust.sslFlags; + + // Determine if the certificate is a trust anchor. + if ((ssl_trust_flags & CERTDB_TRUSTED_CA) == CERTDB_TRUSTED_CA) { + return true; + } + + return false; +} + bool NSSCertDatabase::SetCertTrust(CERTCertificate* cert, CertType type, TrustBits trust_bits) {
diff --git a/net/cert/nss_cert_database.h b/net/cert/nss_cert_database.h index d2baedd..b2fe081c 100644 --- a/net/cert/nss_cert_database.h +++ b/net/cert/nss_cert_database.h
@@ -211,6 +211,10 @@ // rejecting them. bool IsUntrusted(const CERTCertificate* cert) const; + // IsWebTrustAnchor returns true if |cert| is explicitly trusted for web + // navigations according to the trust bits stored in the database. + bool IsWebTrustAnchor(const CERTCertificate* cert) const; + // Set trust values for certificate. // Returns true on success or false on failure. bool SetCertTrust(CERTCertificate* cert, CertType type, TrustBits trust_bits);
diff --git a/net/proxy_resolution/proxy_resolver_v8.cc b/net/proxy_resolution/proxy_resolver_v8.cc index 5b46b99..c77fcc8 100644 --- a/net/proxy_resolution/proxy_resolver_v8.cc +++ b/net/proxy_resolution/proxy_resolver_v8.cc
@@ -393,8 +393,9 @@ has_initialized_v8_ = true; } - holder_.reset(new gin::IsolateHolder(base::ThreadTaskRunnerHandle::Get(), - gin::IsolateHolder::kUseLocker)); + holder_.reset(new gin::IsolateHolder( + base::ThreadTaskRunnerHandle::Get(), gin::IsolateHolder::kUseLocker, + gin::IsolateHolder::IsolateType::kUtility)); } return holder_->isolate();
diff --git a/pdf/pdfium/pdfium_engine.cc b/pdf/pdfium/pdfium_engine.cc index c87110e..5e47623b 100644 --- a/pdf/pdfium/pdfium_engine.cc +++ b/pdf/pdfium/pdfium_engine.cc
@@ -542,8 +542,9 @@ gin::IsolateHolder::kStableV8Extras, gin::ArrayBufferAllocator::SharedInstance()); DCHECK(!g_isolate_holder); - g_isolate_holder = new gin::IsolateHolder(base::ThreadTaskRunnerHandle::Get(), - gin::IsolateHolder::kSingleThread); + g_isolate_holder = new gin::IsolateHolder( + base::ThreadTaskRunnerHandle::Get(), gin::IsolateHolder::kSingleThread, + gin::IsolateHolder::IsolateType::kUtility); g_isolate_holder->isolate()->Enter(); }
diff --git a/services/identity/identity_manager_impl_unittest.cc b/services/identity/identity_manager_impl_unittest.cc index 7ffbb7d4..0e9bb8923 100644 --- a/services/identity/identity_manager_impl_unittest.cc +++ b/services/identity/identity_manager_impl_unittest.cc
@@ -104,7 +104,7 @@ SigninManagerBase::RegisterProfilePrefs(pref_service_.registry()); SigninManagerBase::RegisterPrefs(pref_service_.registry()); - account_tracker_.Initialize(&signin_client_); + account_tracker_.Initialize(&pref_service_, base::FilePath()); } void TearDown() override {
diff --git a/services/identity/public/cpp/access_token_fetcher_unittest.cc b/services/identity/public/cpp/access_token_fetcher_unittest.cc index 095255f..9862f533 100644 --- a/services/identity/public/cpp/access_token_fetcher_unittest.cc +++ b/services/identity/public/cpp/access_token_fetcher_unittest.cc
@@ -49,7 +49,7 @@ AccountTrackerService::RegisterPrefs(pref_service_.registry()); account_tracker_ = std::make_unique<AccountTrackerService>(); - account_tracker_->Initialize(&signin_client_); + account_tracker_->Initialize(&pref_service_, base::FilePath()); token_service_.AddDiagnosticsObserver(this); }
diff --git a/services/identity/public/cpp/identity_manager_unittest.cc b/services/identity/public/cpp/identity_manager_unittest.cc index 67540ea9..256a2dd9 100644 --- a/services/identity/public/cpp/identity_manager_unittest.cc +++ b/services/identity/public/cpp/identity_manager_unittest.cc
@@ -360,7 +360,7 @@ SigninManagerBase::RegisterProfilePrefs(pref_service_.registry()); SigninManagerBase::RegisterPrefs(pref_service_.registry()); - account_tracker_.Initialize(&signin_client_); + account_tracker_.Initialize(&pref_service_, base::FilePath()); RecreateSigninAndIdentityManager( signin::AccountConsistencyMethod::kDisabled,
diff --git a/services/identity/public/cpp/identity_test_environment.cc b/services/identity/public/cpp/identity_test_environment.cc index b878334..bcb23901 100644 --- a/services/identity/public/cpp/identity_test_environment.cc +++ b/services/identity/public/cpp/identity_test_environment.cc
@@ -79,7 +79,7 @@ SigninManagerBase::RegisterProfilePrefs(pref_service_.registry()); SigninManagerBase::RegisterPrefs(pref_service_.registry()); - account_tracker_.Initialize(&signin_client_); + account_tracker_.Initialize(&pref_service_, base::FilePath()); identity_manager_.reset(new IdentityManager(&signin_manager_, &token_service_, &account_tracker_,
diff --git a/services/network/public/cpp/BUILD.gn b/services/network/public/cpp/BUILD.gn index ccf815a..7ff247f 100644 --- a/services/network/public/cpp/BUILD.gn +++ b/services/network/public/cpp/BUILD.gn
@@ -10,6 +10,8 @@ sources = [ "cors/cors.cc", "cors/cors.h", + "cors/origin_access_entry.cc", + "cors/origin_access_entry.h", "cors/preflight_cache.cc", "cors/preflight_cache.h", "cors/preflight_result.cc", @@ -140,6 +142,7 @@ sources = [ "cors/cors_unittest.cc", + "cors/origin_access_entry_unittest.cc", "cors/preflight_cache_unittest.cc", "cors/preflight_result_unittest.cc", "cross_thread_shared_url_loader_factory_info_unittest.cc",
diff --git a/services/network/public/cpp/cors/origin_access_entry.cc b/services/network/public/cpp/cors/origin_access_entry.cc new file mode 100644 index 0000000..6b7400d --- /dev/null +++ b/services/network/public/cpp/cors/origin_access_entry.cc
@@ -0,0 +1,124 @@ +// Copyright 2018 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 "services/network/public/cpp/cors/origin_access_entry.h" + +#include "base/strings/string_util.h" +#include "net/base/registry_controlled_domains/registry_controlled_domain.h" +#include "url/origin.h" +#include "url/url_util.h" + +namespace network { + +namespace cors { + +namespace { + +bool IsSubdomainOfHost(const std::string& subdomain, const std::string& host) { + if (subdomain.length() <= host.length()) + return false; + + if (subdomain[subdomain.length() - host.length() - 1] != '.') + return false; + + if (!base::EndsWith(subdomain, host, base::CompareCase::SENSITIVE)) + return false; + + return true; +} + +} // namespace + +OriginAccessEntry::OriginAccessEntry(const std::string& protocol, + const std::string& host, + MatchMode match_mode) + : protocol_(protocol), + host_(host), + match_mode_(match_mode), + host_is_ip_address_(url::HostIsIPAddress(host)), + host_is_public_suffix_(false) { + if (host_is_ip_address_) + return; + + // Look for top-level domains, either with or without an additional dot. + // Call sites in Blink passes some things that aren't technically hosts like + // "*.foo", so use the permissive variant. + size_t public_suffix_length = + net::registry_controlled_domains::PermissiveGetHostRegistryLength( + host_, net::registry_controlled_domains::INCLUDE_UNKNOWN_REGISTRIES, + net::registry_controlled_domains::INCLUDE_PRIVATE_REGISTRIES); + if (public_suffix_length == 0) + public_suffix_length = host_.length(); + + if (host_.length() <= public_suffix_length + 1) { + host_is_public_suffix_ = true; + } else if (match_mode_ == kAllowRegisterableDomains && public_suffix_length) { + // The "2" in the next line is 1 for the '.', plus a 1-char minimum label + // length. + const size_t dot = + host_.rfind('.', host_.length() - public_suffix_length - 2); + if (dot == std::string::npos) + registerable_domain_ = host_; + else + registerable_domain_ = host_.substr(dot + 1); + } +} + +OriginAccessEntry::OriginAccessEntry(OriginAccessEntry&& from) = default; + +OriginAccessEntry::MatchResult OriginAccessEntry::MatchesOrigin( + const url::Origin& origin) const { + if (protocol_ != origin.scheme()) + return kDoesNotMatchOrigin; + + return MatchesDomain(origin); +} + +OriginAccessEntry::MatchResult OriginAccessEntry::MatchesDomain( + const url::Origin& origin) const { + // Special case: Include subdomains and empty host means "all hosts, including + // ip addresses". + if (match_mode_ != kDisallowSubdomains && host_.empty()) + return kMatchesOrigin; + + // Exact match. + if (host_ == origin.host()) + return kMatchesOrigin; + + // Don't try to do subdomain matching on IP addresses. + if (host_is_ip_address_) + return kDoesNotMatchOrigin; + + // Match subdomains. + switch (match_mode_) { + case kDisallowSubdomains: + return kDoesNotMatchOrigin; + + case kAllowSubdomains: + if (!IsSubdomainOfHost(origin.host(), host_)) + return kDoesNotMatchOrigin; + break; + + case kAllowRegisterableDomains: + // Fall back to a simple subdomain check if no registerable domain could + // be found: + if (registerable_domain_.empty()) { + if (!IsSubdomainOfHost(origin.host(), host_)) + return kDoesNotMatchOrigin; + } else if (registerable_domain_ != origin.host() && + !IsSubdomainOfHost(origin.host(), registerable_domain_)) { + return kDoesNotMatchOrigin; + } + break; + }; + + if (host_is_public_suffix_) + return kMatchesOriginButIsPublicSuffix; + + return kMatchesOrigin; +} + +} // namespace cors + +} // namespace network
diff --git a/services/network/public/cpp/cors/origin_access_entry.h b/services/network/public/cpp/cors/origin_access_entry.h new file mode 100644 index 0000000..46a35c2 --- /dev/null +++ b/services/network/public/cpp/cors/origin_access_entry.h
@@ -0,0 +1,80 @@ +// Copyright 2018 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 SERVICES_NETWORK_PUBLIC_CPP_CORS_ORIGIN_ACCESS_ENTRY_H_ +#define SERVICES_NETWORK_PUBLIC_CPP_CORS_ORIGIN_ACCESS_ENTRY_H_ + +#include <string> + +#include "base/component_export.h" +#include "base/macros.h" + +namespace url { +class Origin; +} // namespace url + +namespace network { + +namespace cors { + +// A class to hold a protocol and host pair and to provide methods to determine +// if a given origin or domain matches to the pair. The class can have a setting +// to control if the matching methods accept a partial match. +class COMPONENT_EXPORT(NETWORK_CPP) OriginAccessEntry final { + public: + // A enum to represent a mode if matching functions can accept a partial match + // for sub-domains, or for registerable domains. + enum MatchMode { + // 'www.example.com' matches an OriginAccessEntry for 'example.com' + kAllowSubdomains, + + // 'www.example.com' matches an OriginAccessEntry for 'not-www.example.com' + kAllowRegisterableDomains, + + // 'www.example.com' does not match an OriginAccessEntry for 'example.com' + kDisallowSubdomains, + }; + + enum MatchResult { + kMatchesOrigin, + kMatchesOriginButIsPublicSuffix, + kDoesNotMatchOrigin + }; + + // If host is empty string and MatchMode is not DisallowSubdomains, the entry + // will match all domains in the specified protocol. + // IPv6 addresses must include brackets (e.g. + // '[2001:db8:85a3::8a2e:370:7334]', not '2001:db8:85a3::8a2e:370:7334'). + OriginAccessEntry(const std::string& protocol, + const std::string& host, + MatchMode match_mode); + OriginAccessEntry(OriginAccessEntry&& from); + + // 'matchesOrigin' requires a protocol match (e.g. 'http' != 'https'). + // 'matchesDomain' relaxes this constraint. + MatchResult MatchesOrigin(const url::Origin& origin) const; + MatchResult MatchesDomain(const url::Origin& domain) const; + + bool host_is_ip_address() const { return host_is_ip_address_; } + const std::string& registerable_domain() const { + return registerable_domain_; + } + + private: + const std::string protocol_; + const std::string host_; + const MatchMode match_mode_; + const bool host_is_ip_address_; + + std::string registerable_domain_; + bool host_is_public_suffix_; + + DISALLOW_COPY_AND_ASSIGN(OriginAccessEntry); +}; + +} // namespace cors + +} // namespace network + +#endif // SERVICES_NETWORK_PUBLIC_CPP_CORS_ORIGIN_ACCESS_ENTRY_H_
diff --git a/third_party/blink/renderer/platform/weborigin/origin_access_entry_test.cc b/services/network/public/cpp/cors/origin_access_entry_unittest.cc similarity index 73% rename from third_party/blink/renderer/platform/weborigin/origin_access_entry_test.cc rename to services/network/public/cpp/cors/origin_access_entry_unittest.cc index 9bfe180..d814028c 100644 --- a/third_party/blink/renderer/platform/weborigin/origin_access_entry_test.cc +++ b/services/network/public/cpp/cors/origin_access_entry_unittest.cc
@@ -1,63 +1,38 @@ -/* - * Copyright (C) 2013 Google Inc. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are - * met: - * - * * Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * * Redistributions in binary form must reproduce the above - * copyright notice, this list of conditions and the following disclaimer - * in the documentation and/or other materials provided with the - * distribution. - * * Neither the name of Google Inc. nor the names of its - * contributors may be used to endorse or promote products derived from - * this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, - * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT - * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, - * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY - * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE - * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ +// Copyright 2018 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 "third_party/blink/renderer/platform/weborigin/origin_access_entry.h" +#include "services/network/public/cpp/cors/origin_access_entry.h" #include "testing/gtest/include/gtest/gtest.h" -#include "third_party/blink/public/platform/platform.h" -#include "third_party/blink/renderer/platform/testing/testing_platform_support.h" -#include "third_party/blink/renderer/platform/weborigin/kurl.h" -#include "third_party/blink/renderer/platform/weborigin/security_origin.h" +#include "url/gurl.h" +#include "url/origin.h" -namespace blink { +namespace network { + +namespace cors { + +namespace { TEST(OriginAccessEntryTest, PublicSuffixListTest) { - scoped_refptr<const SecurityOrigin> origin = - SecurityOrigin::CreateFromString("http://www.google.com"); + url::Origin origin = url::Origin::Create(GURL("http://www.google.com")); OriginAccessEntry entry1("http", "google.com", OriginAccessEntry::kAllowSubdomains); OriginAccessEntry entry2("http", "hamster.com", OriginAccessEntry::kAllowSubdomains); OriginAccessEntry entry3("http", "com", OriginAccessEntry::kAllowSubdomains); - EXPECT_EQ(OriginAccessEntry::kMatchesOrigin, entry1.MatchesOrigin(*origin)); + EXPECT_EQ(OriginAccessEntry::kMatchesOrigin, entry1.MatchesOrigin(origin)); EXPECT_EQ(OriginAccessEntry::kDoesNotMatchOrigin, - entry2.MatchesOrigin(*origin)); + entry2.MatchesOrigin(origin)); EXPECT_EQ(OriginAccessEntry::kMatchesOriginButIsPublicSuffix, - entry3.MatchesOrigin(*origin)); + entry3.MatchesOrigin(origin)); } TEST(OriginAccessEntryTest, AllowSubdomainsTest) { struct TestCase { - const char* protocol; - const char* host; - const char* origin; + const std::string protocol; + const std::string host; + const std::string origin; OriginAccessEntry::MatchResult expected_origin; OriginAccessEntry::MatchResult expected_domain; } inputs[] = { @@ -110,20 +85,19 @@ for (const auto& test : inputs) { SCOPED_TRACE(testing::Message() << "Host: " << test.host << ", Origin: " << test.origin); - scoped_refptr<const SecurityOrigin> origin_to_test = - SecurityOrigin::CreateFromString(test.origin); + url::Origin origin_to_test = url::Origin::Create(GURL(test.origin)); OriginAccessEntry entry1(test.protocol, test.host, OriginAccessEntry::kAllowSubdomains); - EXPECT_EQ(test.expected_origin, entry1.MatchesOrigin(*origin_to_test)); - EXPECT_EQ(test.expected_domain, entry1.MatchesDomain(*origin_to_test)); + EXPECT_EQ(test.expected_origin, entry1.MatchesOrigin(origin_to_test)); + EXPECT_EQ(test.expected_domain, entry1.MatchesDomain(origin_to_test)); } } TEST(OriginAccessEntryTest, AllowRegisterableDomainsTest) { struct TestCase { - const char* protocol; - const char* host; - const char* origin; + const std::string protocol; + const std::string host; + const std::string origin; OriginAccessEntry::MatchResult expected; } inputs[] = { {"http", "example.com", "http://example.com/", @@ -159,23 +133,22 @@ }; for (const auto& test : inputs) { - scoped_refptr<const SecurityOrigin> origin_to_test = - SecurityOrigin::CreateFromString(test.origin); + url::Origin origin_to_test = url::Origin::Create(GURL(test.origin)); OriginAccessEntry entry1(test.protocol, test.host, OriginAccessEntry::kAllowRegisterableDomains); SCOPED_TRACE(testing::Message() << "Host: " << test.host << ", Origin: " << test.origin - << ", Domain: " << entry1.Registerable().Utf8().data()); - EXPECT_EQ(test.expected, entry1.MatchesOrigin(*origin_to_test)); + << ", Domain: " << entry1.registerable_domain()); + EXPECT_EQ(test.expected, entry1.MatchesOrigin(origin_to_test)); } } TEST(OriginAccessEntryTest, AllowRegisterableDomainsTestWithDottedSuffix) { struct TestCase { - const char* protocol; - const char* host; - const char* origin; + const std::string protocol; + const std::string host; + const std::string origin; OriginAccessEntry::MatchResult expected; } inputs[] = { {"http", "example.appspot.com", "http://example.appspot.com/", @@ -212,23 +185,22 @@ }; for (const auto& test : inputs) { - scoped_refptr<const SecurityOrigin> origin_to_test = - SecurityOrigin::CreateFromString(test.origin); + url::Origin origin_to_test = url::Origin::Create(GURL(test.origin)); OriginAccessEntry entry1(test.protocol, test.host, OriginAccessEntry::kAllowRegisterableDomains); SCOPED_TRACE(testing::Message() << "Host: " << test.host << ", Origin: " << test.origin - << ", Domain: " << entry1.Registerable().Utf8().data()); - EXPECT_EQ(test.expected, entry1.MatchesOrigin(*origin_to_test)); + << ", Domain: " << entry1.registerable_domain()); + EXPECT_EQ(test.expected, entry1.MatchesOrigin(origin_to_test)); } } TEST(OriginAccessEntryTest, DisallowSubdomainsTest) { struct TestCase { - const char* protocol; - const char* host; - const char* origin; + const std::string protocol; + const std::string host; + const std::string origin; OriginAccessEntry::MatchResult expected; } inputs[] = { {"http", "example.com", "http://example.com/", @@ -262,18 +234,17 @@ for (const auto& test : inputs) { SCOPED_TRACE(testing::Message() << "Host: " << test.host << ", Origin: " << test.origin); - scoped_refptr<const SecurityOrigin> origin_to_test = - SecurityOrigin::CreateFromString(test.origin); + url::Origin origin_to_test = url::Origin::Create(GURL(test.origin)); OriginAccessEntry entry1(test.protocol, test.host, OriginAccessEntry::kDisallowSubdomains); - EXPECT_EQ(test.expected, entry1.MatchesOrigin(*origin_to_test)); + EXPECT_EQ(test.expected, entry1.MatchesOrigin(origin_to_test)); } } TEST(OriginAccessEntryTest, IPAddressTest) { struct TestCase { - const char* protocol; - const char* host; + const std::string protocol; + const std::string host; bool is_ip_address; } inputs[] = { {"http", "1.1.1.1", true}, @@ -291,15 +262,15 @@ SCOPED_TRACE(testing::Message() << "Host: " << test.host); OriginAccessEntry entry(test.protocol, test.host, OriginAccessEntry::kDisallowSubdomains); - EXPECT_EQ(test.is_ip_address, entry.HostIsIPAddress()) << test.host; + EXPECT_EQ(test.is_ip_address, entry.host_is_ip_address()) << test.host; } } TEST(OriginAccessEntryTest, IPAddressMatchingTest) { struct TestCase { - const char* protocol; - const char* host; - const char* origin; + const std::string protocol; + const std::string host; + const std::string origin; OriginAccessEntry::MatchResult expected; } inputs[] = { {"http", "192.0.0.123", "http://192.0.0.123/", @@ -315,16 +286,19 @@ for (const auto& test : inputs) { SCOPED_TRACE(testing::Message() << "Host: " << test.host << ", Origin: " << test.origin); - scoped_refptr<const SecurityOrigin> origin_to_test = - SecurityOrigin::CreateFromString(test.origin); + url::Origin origin_to_test = url::Origin::Create(GURL(test.origin)); OriginAccessEntry entry1(test.protocol, test.host, OriginAccessEntry::kAllowSubdomains); - EXPECT_EQ(test.expected, entry1.MatchesOrigin(*origin_to_test)); + EXPECT_EQ(test.expected, entry1.MatchesOrigin(origin_to_test)); OriginAccessEntry entry2(test.protocol, test.host, OriginAccessEntry::kDisallowSubdomains); - EXPECT_EQ(test.expected, entry2.MatchesOrigin(*origin_to_test)); + EXPECT_EQ(test.expected, entry2.MatchesOrigin(origin_to_test)); } } -} // namespace blink +} // namespace + +} // namespace cors + +} // namespace network
diff --git a/services/network/public/cpp/simple_url_loader.cc b/services/network/public/cpp/simple_url_loader.cc index 668b0f0..10a89108 100644 --- a/services/network/public/cpp/simple_url_loader.cc +++ b/services/network/public/cpp/simple_url_loader.cc
@@ -9,6 +9,7 @@ #include <algorithm> #include "base/bind.h" +#include "base/debug/alias.h" #include "base/files/file_path.h" #include "base/files/file_util.h" #include "base/location.h" @@ -489,6 +490,19 @@ mojo::ScopedDataPipeConsumerHandle body_data_pipe = std::move(body_data_pipe_); + // TODO(mmenke): Remove this once https://crbug.com/875253 is understood + // and fixed. + int total_bytes_read = total_bytes_read_; + int max_body_size = max_body_size_; + base::debug::Alias(&body_data); + base::debug::Alias(&max_body_size); + base::debug::Alias(&total_bytes_read); + base::debug::Alias(&read_size); + base::debug::Alias(©_size); + // This is just to make sure the first byte of body_data is accessible. + char first_read_byte = static_cast<const char*>(body_data)[0]; + base::debug::Alias(&first_read_byte); + // This call may delete the BodyReader. net::Error error = delegate_->OnDataRead(copy_size, static_cast<const char*>(body_data)); @@ -632,6 +646,11 @@ // BodyReader::Delegate implementation. net::Error OnDataRead(uint32_t length, const char* data) override { + // TODO(mmenke): Remove this once https://crbug.com/875253 is understood and + // fixed. + std::string* body = body_.get(); + base::debug::Alias(&body); + body_->append(data, length); ReportProgress(body_reader_->total_bytes_read()); return net::OK;
diff --git a/services/ui/ime/test_ime_driver/test_ime_driver.cc b/services/ui/ime/test_ime_driver/test_ime_driver.cc index d7c83d3..59250e6 100644 --- a/services/ui/ime/test_ime_driver/test_ime_driver.cc +++ b/services/ui/ime/test_ime_driver/test_ime_driver.cc
@@ -20,8 +20,12 @@ private: // mojom::InputMethod: - void OnTextInputTypeChanged(TextInputType text_input_type) override {} - void OnCaretBoundsChanged(const gfx::Rect& caret_bounds) override {} + void OnTextInputTypeChanged(TextInputType text_input_type) override { + NOTIMPLEMENTED(); + } + void OnCaretBoundsChanged(const gfx::Rect& caret_bounds) override { + NOTIMPLEMENTED(); + } void ProcessKeyEvent(std::unique_ptr<Event> key_event, ProcessKeyEventCallback callback) override { DCHECK(key_event->IsKeyEvent()); @@ -35,7 +39,8 @@ base::Unretained(this), std::move(cloned_event), std::move(callback))); } - void CancelComposition() override {} + void CancelComposition() override { NOTIMPLEMENTED(); } + void ShowVirtualKeyboardIfEnabled() override { NOTIMPLEMENTED(); } void PostProcssKeyEvent(std::unique_ptr<Event> key_event, ProcessKeyEventCallback callback,
diff --git a/services/ui/public/interfaces/ime/ime.mojom b/services/ui/public/interfaces/ime/ime.mojom index 0157f71..8dfa142 100644 --- a/services/ui/public/interfaces/ime/ime.mojom +++ b/services/ui/public/interfaces/ime/ime.mojom
@@ -155,6 +155,9 @@ ProcessKeyEvent(ui.mojom.Event key_event) => (bool handled); CancelComposition(); + + // Plumbs requests to show the virtual keyboard. + ShowVirtualKeyboardIfEnabled(); }; // IME drivers send updates to clients using the TextInputClient interface.
diff --git a/services/viz/public/interfaces/hit_test/input_target_client.mojom b/services/viz/public/interfaces/hit_test/input_target_client.mojom index 32d4b2c..1ec376a 100644 --- a/services/viz/public/interfaces/hit_test/input_target_client.mojom +++ b/services/viz/public/interfaces/hit_test/input_target_client.mojom
@@ -1,3 +1,7 @@ +// 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. + module viz.mojom; import "services/viz/public/interfaces/compositing/frame_sink_id.mojom"; @@ -12,5 +16,8 @@ // RenderWidget containing the point, which is either the widget that was // asked to perform the hit test or an immediately embedded widget (i.e. an // out-of-process iframe). - FrameSinkIdAt(gfx.mojom.Point point) => (FrameSinkId id); + // |local_point| is the point in the coordinate space of the RenderWidget + // indicated by the FrameSinkId. + FrameSinkIdAt(gfx.mojom.Point point) => (FrameSinkId id, + gfx.mojom.PointF local_point); };
diff --git a/third_party/WebKit/LayoutTests/TestExpectations b/third_party/WebKit/LayoutTests/TestExpectations index 154e3e12..aaf70a7 100644 --- a/third_party/WebKit/LayoutTests/TestExpectations +++ b/third_party/WebKit/LayoutTests/TestExpectations
@@ -365,8 +365,6 @@ crbug.com/635619 virtual/layout_ng/fast/block/float/floats-do-not-overhang-from-block-formatting-context.html [ Failure ] crbug.com/635619 [ Mac ] virtual/layout_ng/fast/block/float/intruding-painted-twice.html [ Failure ] crbug.com/635619 virtual/layout_ng/fast/block/float/line-break-after-white-space-crash.html [ Pass Crash Timeout ] -crbug.com/635619 virtual/layout_ng/fast/block/float/negative-margin-on-element-avoiding-floats-with-margin-on-parent.html [ Failure ] -crbug.com/635619 virtual/layout_ng/fast/block/float/negative-margin-on-element-avoiding-floats.html [ Failure ] crbug.com/635619 virtual/layout_ng/fast/block/float/nopaint-after-layer-destruction.html [ Failure ] crbug.com/635619 virtual/layout_ng/fast/block/float/nopaint-after-layer-destruction2.html [ Failure ] crbug.com/810370 virtual/layout_ng/fast/block/float/overhanging-float-remove-from-fixed-position-block.html [ Failure ] @@ -401,9 +399,6 @@ # Maybe a Mac-specific rebaselining issue. crbug.com/846557 [ Mac ] virtual/layout_ng_experimental/css3/flexbox/button.html [ Skip ] -### Crash site: ContainerNode.cpp -crbug.com/714962 virtual/layout_ng/fast/inline/inline-with-empty-inline-children.html [ Crash Failure ] - ### Crash site: layout_ng_block_flow.cc crbug.com/714962 virtual/layout_ng/fast/inline/inline-offsetLeft-relpos.html [ Crash Failure ] @@ -414,9 +409,7 @@ ### Image/text failures #crbug.com/714962 virtual/layout_ng/fast/inline/001.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/inline/absolute-positioned-block-in-centred-block.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/inline/continuation-outlines-with-layers-2.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/inline/drawStyledEmptyInlinesWithWS.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/inline/emptyInlinesWithinLists.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/inline/inline-box-background-long-image.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/inline/inline-box-background-repeat-x.html [ Failure ] @@ -427,6 +420,8 @@ crbug.com/714962 virtual/layout_ng/fast/inline/outline-offset.html [ Failure ] crbug.com/714962 [ Mac ] virtual/layout_ng/fast/inline/br-text-decoration.html [ Failure ] crbug.com/714962 [ Mac ] virtual/layout_ng/fast/inline/drawStyledEmptyInlines.html [ Failure ] +crbug.com/714962 [ Mac ] virtual/layout_ng/fast/inline/drawStyledEmptyInlinesWithWS.html [ Failure ] + ### Image/text failures also on LayoutNG crbug.com/714962 virtual/layout_ng/fast/inline/absolute-positioned-inline-in-centred-block.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/inline/continuation-outlines-with-layers.html [ Failure ] @@ -454,13 +449,10 @@ ### virtual/layout_ng/fast/writing-mode/ crbug.com/714962 virtual/layout_ng/fast/writing-mode/auto-sizing-orthogonal-flows.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/background-vertical-lr.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/writing-mode/background-vertical-rl.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/basic-vertical-line.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/border-image-vertical-lr.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/writing-mode/border-image-vertical-rl.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/border-radius-clipping-vertical-lr.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/border-styles-vertical-lr.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/writing-mode/border-styles-vertical-rl.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/box-shadow-vertical-lr.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/box-shadow-vertical-rl.html [ Failure ] crbug.com/714962 [ Mac ] virtual/layout_ng/fast/writing-mode/broken-ideograph-small-caps.html [ Failure ] @@ -474,9 +466,6 @@ crbug.com/714962 [ Mac ] virtual/layout_ng/fast/writing-mode/orthogonal-inline-block.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/orthogonal-writing-modes-available-width-absolute-crash.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/percentage-height-orthogonal-writing-modes.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/writing-mode/text-combine-justify.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/writing-mode/text-combine-line-break.html [ Failure ] -crbug.com/714962 virtual/layout_ng/fast/writing-mode/text-combine-various-fonts.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/vertical-align-table-baseline.html [ Failure ] crbug.com/714962 virtual/layout_ng/fast/writing-mode/vertical-baseline-alignment.html [ Failure ] crbug.com/714962 [ Mac ] virtual/layout_ng/fast/writing-mode/vertical-font-fallback.html [ Failure ] @@ -1930,7 +1919,6 @@ crbug.com/652964 [ Linux Win ] fast/text/hyphens/midword-break-priority.html [ Skip ] crbug.com/405389 external/wpt/css/css-shapes/shape-outside/supported-shapes/polygon/shape-outside-polygon-017.html [ Failure ] -crbug.com/424365 external/wpt/css/css-shapes/shape-outside/shape-image/shape-image-010.html [ Failure ] crbug.com/424365 external/wpt/css/css-shapes/shape-outside/shape-image/shape-image-024.html [ Failure ] crbug.com/441840 [ Win ] external/wpt/css/css-shapes/shape-outside/values/shape-margin-001.html [ Failure ] crbug.com/441840 external/wpt/css/css-shapes/shape-outside/values/shape-outside-circle-004.html [ Failure ] @@ -2880,7 +2868,6 @@ crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-polygon-024.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-ellipse-048.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-inset-026.html [ Failure ] -crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-polygon-020.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-circle-055.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-ellipse-051.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-circle-037.html [ Failure ] @@ -2889,7 +2876,6 @@ crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-margin-box-border-radius-003.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-border-box-border-radius-009.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-margin-box-border-radius-008.html [ Failure ] -crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-inset-021.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-circle-050.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-ellipse-050.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-border-box-border-radius-012.html [ Failure ] @@ -2905,8 +2891,6 @@ crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-polygon-021.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-polygon-025.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-inset-027.html [ Failure ] -crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-polygon-022.html [ Failure ] -crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-inset-020.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-ellipse-046.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-circle-042.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-ellipse-039.html [ Failure ] @@ -2917,7 +2901,6 @@ crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-border-box-border-radius-008.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-circle-054.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-border-box-border-radius-004.html [ Failure ] -crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-circle-048.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-inset-022.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-inset-025.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/shapes1/shape-outside-border-box-border-radius-007.html [ Failure ] @@ -3203,7 +3186,6 @@ crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/counter-styles-3/descriptor-symbols.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/counter-styles-3/system-extends-invalid.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/counter-styles-3/redefine-builtin.html [ Failure ] -crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/flexbox/flexbox-intrinsic-ratio-003v.html [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/flexbox/flexbox-intrinsic-ratio-006v.html [ Failure ] crbug.com/626703 external/wpt/css/css-fonts/font-variant-06.xht [ Failure ] crbug.com/626703 external/wpt/css/vendor-imports/mozilla/mozilla-central-reftests/flexbox/flexbox-intrinsic-ratio-001v.html [ Failure ] @@ -4983,9 +4965,6 @@ # Test frequently times out on Mac CQ bots. crbug.com/874703 [ Mac ] http/tests/devtools/extensions/extensions-panel.js [ Timeout Pass ] -# This won't pass until the bug fixed. -crbug.com/875287 fast/frames/crash-frameset-CSS-content-property.html [ Crash ] - # Wake Lock api test timeouts crbug.com/872530 external/wpt/wake-lock/wakelock-applicability-manual.https.html [ Pass Timeout ] crbug.com/872530 external/wpt/wake-lock/wakelock-document-hidden.https.html [ Pass Timeout ]
diff --git a/third_party/WebKit/LayoutTests/fast/events/touch/gesture/gesture-tap-frame-removed.html b/third_party/WebKit/LayoutTests/fast/events/touch/gesture/gesture-tap-frame-removed.html index 80d0e394..ad49d6f 100644 --- a/third_party/WebKit/LayoutTests/fast/events/touch/gesture/gesture-tap-frame-removed.html +++ b/third_party/WebKit/LayoutTests/fast/events/touch/gesture/gesture-tap-frame-removed.html
@@ -16,7 +16,7 @@ if (e.type == removalEventType) { debug('Removing iframe'); target.parentNode.removeChild(target); - internals.gc(); + gc(); } }
diff --git a/third_party/WebKit/LayoutTests/http/tests/devtools/tracing/timeline-gpu-tasks-expected.txt b/third_party/WebKit/LayoutTests/http/tests/devtools/tracing/timeline-gpu-tasks-expected.txt deleted file mode 100644 index c4d9058..0000000 --- a/third_party/WebKit/LayoutTests/http/tests/devtools/tracing/timeline-gpu-tasks-expected.txt +++ /dev/null
@@ -1,4 +0,0 @@ -Tests the Timeline events for GPUTask - -Found GPUTask events: true -
diff --git a/third_party/WebKit/LayoutTests/http/tests/devtools/tracing/timeline-gpu-tasks.js b/third_party/WebKit/LayoutTests/http/tests/devtools/tracing/timeline-gpu-tasks.js deleted file mode 100644 index 7b2a7aa..0000000 --- a/third_party/WebKit/LayoutTests/http/tests/devtools/tracing/timeline-gpu-tasks.js +++ /dev/null
@@ -1,24 +0,0 @@ -// Copyright 2018 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. - -(async function() { - TestRunner.addResult(`Tests the Timeline events for GPUTask\n`); - await TestRunner.loadModule('performance_test_runner'); - await TestRunner.showPanel('timeline'); - await TestRunner.evaluateInPagePromise(` - async function performActions() { - const gl = document.createElement('canvas').getContext('webgl'); - return gl.getParameter(gl.MAX_VIEWPORT_DIMS); - } - `); - - await PerformanceTestRunner.invokeAsyncWithTimeline('performActions'); - - const tracingModel = PerformanceTestRunner.tracingModel(); - const hasGPUTasks = tracingModel.sortedProcesses().some(p => p.sortedThreads().some(t => t.events().some( - event => event.name === TimelineModel.TimelineModel.RecordType.GPUTask))); - TestRunner.addResult(`Found GPUTask events: ${hasGPUTasks}`); - - TestRunner.completeTest(); -})();
diff --git a/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter-expected.txt b/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter-expected.txt index 76ab560..6f0712c 100644 --- a/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter-expected.txt +++ b/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter-expected.txt
@@ -2,5 +2,5 @@ Recording started Another page Tracing complete -There should be just 3 processes (browser, GPU, and renderer): 3 +There should be just 2 processes (browser and renderer): 2
diff --git a/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter.js b/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter.js index c43f871..f81444e 100644 --- a/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter.js +++ b/third_party/WebKit/LayoutTests/inspector-protocol/timeline/tracing-process-filter.js
@@ -16,7 +16,7 @@ const pids = new Set(); for (const event of events) pids.add(event.pid); - testRunner.log(`There should be just 3 processes (browser, GPU, and renderer): ${pids.size}`); + testRunner.log(`There should be just 2 processes (browser and renderer): ${pids.size}`); testRunner.completeTest(); })
diff --git a/third_party/WebKit/LayoutTests/reporting-observer/intervention.html b/third_party/WebKit/LayoutTests/reporting-observer/intervention.html index d71074a..8e12d888 100644 --- a/third_party/WebKit/LayoutTests/reporting-observer/intervention.html +++ b/third_party/WebKit/LayoutTests/reporting-observer/intervention.html
@@ -9,9 +9,12 @@ <script> async_test(function(test) { + var kInterventionReport = 2531; // From web_feature.mojom. + var observer = new ReportingObserver(function(reports, observer) { test.step(function() { assert_equals(reports.length, 1); + assert_true(internals.isUseCounted(document, kInterventionReport)); // Ensure that the contents of the report are valid. assert_equals(reports[0].type, "intervention"); @@ -29,6 +32,7 @@ }); observer.observe(); + assert_false(internals.isUseCounted(document, kInterventionReport)); causeIntervention(); }, "Intervention report"); </script>
diff --git a/third_party/WebKit/LayoutTests/reporting-observer/resources/deprecation.js b/third_party/WebKit/LayoutTests/reporting-observer/resources/deprecation.js index e86b736f..5078e75 100644 --- a/third_party/WebKit/LayoutTests/reporting-observer/resources/deprecation.js +++ b/third_party/WebKit/LayoutTests/reporting-observer/resources/deprecation.js
@@ -1,7 +1,12 @@ async_test(function(test) { + // UseCounter feature IDs, from web_feature.mojom. + var kReportingObserver = 2529; + var kDeprecationReport = 2530; + var observer = new ReportingObserver(function(reports, observer) { test.step(function() { assert_equals(reports.length, 2); + assert_true(internals.isUseCounted(document, kDeprecationReport)); // Ensure that the contents of the reports are valid. for(let report of reports) { @@ -21,7 +26,11 @@ test.done(); }); + assert_false(internals.isUseCounted(document, kReportingObserver)); observer.observe(); + assert_true(internals.isUseCounted(document, kReportingObserver)); + + assert_false(internals.isUseCounted(document, kDeprecationReport)); // This ensures that ReportingObserver is traced properly. This will cause the // test to fail otherwise.
diff --git a/third_party/WebKit/LayoutTests/shadow-dom/crashes/imperative-api.html b/third_party/WebKit/LayoutTests/shadow-dom/crashes/imperative-api.html new file mode 100644 index 0000000..3b44667 --- /dev/null +++ b/third_party/WebKit/LayoutTests/shadow-dom/crashes/imperative-api.html
@@ -0,0 +1,28 @@ +<!DOCTYPE html> +<!-- +CrashTests for Imperative Shadow DOM Distribution API. +See https://crbug.com/869308 +--> +<script src="../../resources/testharness.js"></script> +<script src="../../resources/testharnessreport.js"></script> +<div id="host"> + <div id="child1"></div> +</div> + +<script> +const host = document.querySelector("#host"); +const child1 = document.querySelector("#child1"); +const shadow_root = host.attachShadow({ mode: "open", slotting: "manual" }); +const slot1 = document.createElement("slot"); +const slot2 = document.createElement("slot"); +shadow_root.appendChild(slot1); +shadow_root.appendChild(slot2); + +test(() => { + slot2.assign([child1]); + slot1.assign([child1]); + + slot1.remove(); + slot2.remove(); +}, "slot.remove after slot\'s removal should not crash"); +</script>
diff --git a/third_party/android_async_task/java/src/org/chromium/base/AsyncTask.java b/third_party/android_async_task/java/src/org/chromium/base/AsyncTask.java index b977e20..31c3601f4 100644 --- a/third_party/android_async_task/java/src/org/chromium/base/AsyncTask.java +++ b/third_party/android_async_task/java/src/org/chromium/base/AsyncTask.java
@@ -143,7 +143,7 @@ * <li>The AsyncTask class must be loaded on the UI thread. This is done * automatically as of {@link android.os.Build.VERSION_CODES#JELLY_BEAN}.</li> * <li>The task instance must be created on the UI thread.</li> - * <li>{@link #execute} must be invoked on the UI thread.</li> + * <li>{@link #executeOnExecutor(Executor)} must be invoked on the UI thread.</li> * <li>Do not call {@link #onPreExecute()}, {@link #onPostExecute}, * {@link #doInBackground} manually.</li> * <li>The task can be executed only once (an exception will be thrown if @@ -207,8 +207,6 @@ private static final int MESSAGE_POST_RESULT = 0x1; private static final int MESSAGE_POST_PROGRESS = 0x2; - private static volatile Executor sDefaultExecutor = SERIAL_EXECUTOR; - private static final StealRunnableHandler STEAL_RUNNABLE_HANDLER = new StealRunnableHandler(); private final Callable<Result> mWorker; @@ -409,9 +407,7 @@ } /** - * Override this method to perform a computation on a background thread. The - * specified parameters are the parameters passed to {@link #execute} - * by the caller of this task. + * Override this method to perform a computation on a background thread. * * @return A result, defined by the subclass of this task. * @@ -568,37 +564,6 @@ * Executes the task with the specified parameters. The task returns * itself (this) so that the caller can keep a reference to it. * - * <p>Note: this function schedules the task on a queue for a single background - * thread or pool of threads depending on the platform version. When first - * introduced, AsyncTasks were executed serially on a single background thread. - * Starting with {@link android.os.Build.VERSION_CODES#DONUT}, this was changed - * to a pool of threads allowing multiple tasks to operate in parallel. Starting - * {@link android.os.Build.VERSION_CODES#HONEYCOMB}, tasks are back to being - * executed on a single thread to avoid common application errors caused - * by parallel execution. If you truly want parallel execution, you can use - * the {@link #executeOnExecutor} version of this method - * with {@link #THREAD_POOL_EXECUTOR}; however, see commentary there for warnings - * on its use. - * - * <p>This method must be invoked on the UI thread. - * - * @return This instance of AsyncTask. - * - * @throws IllegalStateException If {@link #getStatus()} returns either - * {@link AsyncTask.Status#RUNNING} or {@link AsyncTask.Status#FINISHED}. - * - * @see #executeOnExecutor(java.util.concurrent.Executor) - * @see #execute(Runnable) - */ - @MainThread - public final AsyncTask<Result> execute() { - return executeOnExecutor(sDefaultExecutor); - } - - /** - * Executes the task with the specified parameters. The task returns - * itself (this) so that the caller can keep a reference to it. - * * <p>This method is typically used with {@link #THREAD_POOL_EXECUTOR} to * allow multiple tasks to run in parallel on a pool of threads managed by * AsyncTask, however you can also use your own {@link Executor} for custom @@ -624,8 +589,6 @@ * * @throws IllegalStateException If {@link #getStatus()} returns either * {@link AsyncTask.Status#RUNNING} or {@link AsyncTask.Status#FINISHED}. - * - * @see #execute() */ @SuppressWarnings({"MissingCasesInEnumSwitch"}) @MainThread @@ -651,19 +614,6 @@ return this; } - /** - * Convenience version of {@link #execute()} for use with - * a simple Runnable object. See {@link #execute()} for more - * information on the order of execution. - * - * @see #execute() - * @see #executeOnExecutor(java.util.concurrent.Executor) - */ - @MainThread - public static void execute(Runnable runnable) { - sDefaultExecutor.execute(runnable); - } - private void finish(Result result) { if (isCancelled()) { onCancelled(result);
diff --git a/third_party/blink/public/BUILD.gn b/third_party/blink/public/BUILD.gn index 50d29a0..df91be1c 100644 --- a/third_party/blink/public/BUILD.gn +++ b/third_party/blink/public/BUILD.gn
@@ -126,6 +126,7 @@ "platform/linux/web_sandbox_support.h", "platform/mac/web_sandbox_support.h", "platform/mac/web_scrollbar_theme.h", + "platform/modules/background_fetch/web_background_fetch_registration.h", "platform/modules/background_fetch/web_background_fetch_settled_fetch.h", "platform/modules/indexeddb/web_idb_callbacks.h", "platform/modules/indexeddb/web_idb_cursor.h",
diff --git a/third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom b/third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom index 550260d..3a4b0b9 100644 --- a/third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom +++ b/third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom
@@ -18,7 +18,8 @@ INVALID_ID, STORAGE_ERROR, SERVICE_WORKER_UNAVAILABLE, - QUOTA_EXCEEDED + QUOTA_EXCEEDED, + PERMISSION_DENIED }; // Struct representing completed Background Fetch requests, along with their @@ -59,6 +60,7 @@ uint64 uploaded; uint64 download_total; uint64 downloaded; + BackgroundFetchState state; }; interface BackgroundFetchRegistrationObserver {
diff --git a/third_party/blink/public/platform/modules/background_fetch/web_background_fetch_registration.h b/third_party/blink/public/platform/modules/background_fetch/web_background_fetch_registration.h new file mode 100644 index 0000000..fb8a54d --- /dev/null +++ b/third_party/blink/public/platform/modules/background_fetch/web_background_fetch_registration.h
@@ -0,0 +1,46 @@ +// Copyright 2018 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 THIRD_PARTY_BLINK_PUBLIC_PLATFORM_MODULES_BACKGROUND_FETCH_WEB_BACKGROUND_FETCH_REGISTRATION_H_ +#define THIRD_PARTY_BLINK_PUBLIC_PLATFORM_MODULES_BACKGROUND_FETCH_WEB_BACKGROUND_FETCH_REGISTRATION_H_ + +#include "third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom-shared.h" +#include "third_party/blink/public/platform/web_common.h" +#include "third_party/blink/public/platform/web_string.h" + +namespace blink { + +// Represents a BackgroundFetchRegistration object, added mainly for layering. +// Analogous to the following structure in the spec: +// https://wicg.github.io/background-fetch/#background-fetch-registration +struct WebBackgroundFetchRegistration { + WebBackgroundFetchRegistration(const WebString& developer_id, + const WebString& unique_id, + uint64_t upload_total, + uint64_t uploaded, + uint64_t download_total, + uint64_t downloaded, + mojom::BackgroundFetchState state) + : developer_id(developer_id), + unique_id(unique_id), + upload_total(upload_total), + uploaded(uploaded), + download_total(download_total), + downloaded(downloaded), + state(state) {} + + ~WebBackgroundFetchRegistration() = default; + + WebString developer_id; + WebString unique_id; + uint64_t upload_total; + uint64_t uploaded; + uint64_t download_total; + uint64_t downloaded; + mojom::BackgroundFetchState state; +}; + +} // namespace blink + +#endif // THIRD_PARTY_BLINK_PUBLIC_PLATFORM_MODULES_BACKGROUND_FETCH_WEB_BACKGROUND_FETCH_REGISTRATION_H_
diff --git a/third_party/blink/public/platform/web_feature.mojom b/third_party/blink/public/platform/web_feature.mojom index 1beafa7..4f1beb4 100644 --- a/third_party/blink/public/platform/web_feature.mojom +++ b/third_party/blink/public/platform/web_feature.mojom
@@ -1981,6 +1981,10 @@ kV8MediaStreamTrack_ContentHint_AttributeGetter = 2525, kV8MediaStreamTrack_ContentHint_AttributeSetter = 2526, kV8IDBFactory_Open_Method = 2527, + kEvaluateScriptMovedBetweenDocuments = 2528, + kReportingObserver = 2529, + kDeprecationReport = 2530, + kInterventionReport = 2531, // Add new features immediately above this line. Don't change assigned // numbers of any item, and don't reuse removed slots.
diff --git a/third_party/blink/public/platform/web_runtime_features.h b/third_party/blink/public/platform/web_runtime_features.h index e78a4d4..23c12c8 100644 --- a/third_party/blink/public/platform/web_runtime_features.h +++ b/third_party/blink/public/platform/web_runtime_features.h
@@ -150,6 +150,7 @@ bool); BLINK_PLATFORM_EXPORT static void EnableSharedArrayBuffer(bool); BLINK_PLATFORM_EXPORT static void EnableSharedWorker(bool); + BLINK_PLATFORM_EXPORT static void EnableSignedHTTPExchange(bool); BLINK_PLATFORM_EXPORT static void EnableSlimmingPaintV2(bool); BLINK_PLATFORM_EXPORT static void EnableTouchEventFeatureDetection(bool); BLINK_PLATFORM_EXPORT static void EnableUserActivationV2(bool);
diff --git a/third_party/blink/public/web/modules/service_worker/web_service_worker_context_proxy.h b/third_party/blink/public/web/modules/service_worker/web_service_worker_context_proxy.h index 0d21f81..923f0a2 100644 --- a/third_party/blink/public/web/modules/service_worker/web_service_worker_context_proxy.h +++ b/third_party/blink/public/web/modules/service_worker/web_service_worker_context_proxy.h
@@ -34,6 +34,7 @@ #include "base/time/time.h" #include "third_party/blink/public/common/message_port/transferable_message.h" #include "third_party/blink/public/platform/modules/background_fetch/background_fetch.mojom-shared.h" +#include "third_party/blink/public/platform/modules/background_fetch/web_background_fetch_registration.h" #include "third_party/blink/public/platform/modules/service_worker/web_service_worker.h" #include "third_party/blink/public/platform/modules/service_worker/web_service_worker_registration.h" #include "third_party/blink/public/platform/web_canonical_cookie.h" @@ -70,25 +71,17 @@ virtual void DispatchBackgroundFetchAbortEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state) = 0; + const WebBackgroundFetchRegistration& registration) = 0; virtual void DispatchBackgroundFetchClickEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state) = 0; + const WebBackgroundFetchRegistration& registration) = 0; virtual void DispatchBackgroundFetchFailEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const WebBackgroundFetchRegistration& registration, const WebVector<WebBackgroundFetchSettledFetch>& fetches) = 0; virtual void DispatchBackgroundFetchSuccessEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const WebBackgroundFetchRegistration& registration, const WebVector<WebBackgroundFetchSettledFetch>& fetches) = 0; virtual void DispatchCookieChangeEvent( int event_id,
diff --git a/third_party/blink/public/web/web_hit_test_result.h b/third_party/blink/public/web/web_hit_test_result.h index c88ba06..72645e2c 100644 --- a/third_party/blink/public/web/web_hit_test_result.h +++ b/third_party/blink/public/web/web_hit_test_result.h
@@ -56,6 +56,10 @@ // Coordinates of the point that was hit. Relative to the node. BLINK_EXPORT WebPoint LocalPoint() const; + // Coordinates of the point that was hit. Relative to the node, but with + // ContentBoxOffset removed if the node has box layout. + BLINK_EXPORT WebPoint LocalPointWithoutContentBoxOffset() const; + // If a link (eg. anchor or area tag) is hit, return the element. // Return null otheriwse. BLINK_EXPORT WebElement UrlElement() const;
diff --git a/third_party/blink/renderer/bindings/core/v8/generated_code_helper.cc b/third_party/blink/renderer/bindings/core/v8/generated_code_helper.cc index 55f9850..ead42a8 100644 --- a/third_party/blink/renderer/bindings/core/v8/generated_code_helper.cc +++ b/third_party/blink/renderer/bindings/core/v8/generated_code_helper.cc
@@ -58,10 +58,14 @@ // the incumbent context which originally schedules the currently-running // callback to see whether the script setting is disabled before invoking // the callback. + // TODO(crbug.com/608641): move IsMainWorld check into + // ExecutionContext::CanExecuteScripts() return incumbent_execution_context && !incumbent_execution_context->IsContextPaused() && !incumbent_execution_context->IsContextDestroyed() && - incumbent_execution_context->CanExecuteScripts(kAboutToExecuteScript); + (!incumbent_script_state->World().IsMainWorld() || + incumbent_execution_context->CanExecuteScripts( + kAboutToExecuteScript)); } } // namespace blink
diff --git a/third_party/blink/renderer/bindings/templates/interface.cpp.tmpl b/third_party/blink/renderer/bindings/templates/interface.cpp.tmpl index 00aa053..a6844bb 100644 --- a/third_party/blink/renderer/bindings/templates/interface.cpp.tmpl +++ b/third_party/blink/renderer/bindings/templates/interface.cpp.tmpl
@@ -1045,12 +1045,16 @@ default: NOTREACHED(); }; + // TODO(v8:8073): Use specific deallocator per mode once v8 provides information. WTF::ArrayBufferContents::DataHandle data(v8Contents.AllocationBase(), v8Contents.AllocationLength(), v8Contents.Data(), v8Contents.ByteLength(), kind, - WTF::ArrayBufferContents::FreeMemory); + [](void* buffer, size_t length, void* alloc_data) { + WTF::ArrayBufferContents::FreeMemory(buffer); + }, + nullptr); WTF::ArrayBufferContents contents(std::move(data), WTF::ArrayBufferContents::k{% if interface_name == 'ArrayBuffer' %}Not{% endif %}Shared); {{cpp_class}}* buffer = {{cpp_class}}::Create(contents); v8::Local<v8::Object> associatedWrapper = buffer->AssociateWithWrapper(v8::Isolate::GetCurrent(), buffer->GetWrapperTypeInfo(), object);
diff --git a/third_party/blink/renderer/bindings/templates/methods.cpp.tmpl b/third_party/blink/renderer/bindings/templates/methods.cpp.tmpl index 8b8f8929..ec8eaaa 100644 --- a/third_party/blink/renderer/bindings/templates/methods.cpp.tmpl +++ b/third_party/blink/renderer/bindings/templates/methods.cpp.tmpl
@@ -212,6 +212,20 @@ if (!info[{{argument.index}}]->IsNullOrUndefined()) { {{v8_value_to_local_cpp_value(argument) | trim | indent(2)}} } +{% elif argument.idl_type == 'object' %} +if (info[{{argument.index}}]->IsObject()) { + {{v8_value_to_local_cpp_value(argument)}} +{% if argument.is_nullable %} +} else if (info[{{argument.index}}]->IsNullOrUndefined()) { + {{argument.name}} = ScriptValue(ScriptState::Current(info.GetIsolate()), v8::Null(info.GetIsolate())); +{% elif argument.is_optional %} +} else if (info[{{argument.index}}]->IsUndefined()) { + {{argument.name}} = ScriptValue(ScriptState::Current(info.GetIsolate()), v8::Undefined(info.GetIsolate())); +{% endif %} +} else { + {{throw_argument_error(method, argument, "parameter %(index)d ('%(name)s') is not an object.")}} + return; +} {% else %}{# argument is something else #} {{v8_value_to_local_cpp_value(argument)}} {% endif %}{# end of the dispatch by the argument type #}
diff --git a/third_party/blink/renderer/bindings/tests/idls/core/test_interface.idl b/third_party/blink/renderer/bindings/tests/idls/core/test_interface.idl index 747e0e9..b3262e53 100644 --- a/third_party/blink/renderer/bindings/tests/idls/core/test_interface.idl +++ b/third_party/blink/renderer/bindings/tests/idls/core/test_interface.idl
@@ -72,6 +72,7 @@ void voidMethodTestInterfaceEmptyArg(TestInterfaceEmpty testInterfaceEmptyArg); void voidMethodDoubleArgFloatArg(double doubleArg, float floatArg); + void voidMethodNullableAndOptionalObjectArgs(object objectArg, optional object optionalObjectArg, object? nullableObjectArg); void voidMethodUnrestrictedDoubleArgUnrestrictedFloatArg(unrestricted double unrestrictedDoubleArg, unrestricted float unrestrictedFloatArg); void voidMethodTestEnumArg(TestEnum testEnumArg); [PerWorldBindings] void voidMethod();
diff --git a/third_party/blink/renderer/bindings/tests/results/core/v8_array_buffer.cc b/third_party/blink/renderer/bindings/tests/results/core/v8_array_buffer.cc index f9eab4d..aeec0af 100644 --- a/third_party/blink/renderer/bindings/tests/results/core/v8_array_buffer.cc +++ b/third_party/blink/renderer/bindings/tests/results/core/v8_array_buffer.cc
@@ -87,12 +87,16 @@ default: NOTREACHED(); }; + // TODO(v8:8073): Use specific deallocator per mode once v8 provides information. WTF::ArrayBufferContents::DataHandle data(v8Contents.AllocationBase(), v8Contents.AllocationLength(), v8Contents.Data(), v8Contents.ByteLength(), kind, - WTF::ArrayBufferContents::FreeMemory); + [](void* buffer, size_t length, void* alloc_data) { + WTF::ArrayBufferContents::FreeMemory(buffer); + }, + nullptr); WTF::ArrayBufferContents contents(std::move(data), WTF::ArrayBufferContents::kNotShared); TestArrayBuffer* buffer = TestArrayBuffer::Create(contents); v8::Local<v8::Object> associatedWrapper = buffer->AssociateWithWrapper(v8::Isolate::GetCurrent(), buffer->GetWrapperTypeInfo(), object);
diff --git a/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.cc b/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.cc index e1b3c85..67da698 100644 --- a/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.cc +++ b/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.cc
@@ -1555,6 +1555,55 @@ impl->voidMethodDoubleArgFloatArg(doubleArg, floatArg); } +static void voidMethodNullableAndOptionalObjectArgsMethod(const v8::FunctionCallbackInfo<v8::Value>& info) { + TestInterfaceImplementation* impl = V8TestInterface::ToImpl(info.Holder()); + + if (UNLIKELY(info.Length() < 2)) { + V8ThrowException::ThrowTypeError(info.GetIsolate(), ExceptionMessages::FailedToExecute("voidMethodNullableAndOptionalObjectArgs", "TestInterface", ExceptionMessages::NotEnoughArguments(2, info.Length()))); + return; + } + + ScriptValue objectArg; + ScriptValue optionalObjectArg; + ScriptValue nullableObjectArg; + int numArgsPassed = info.Length(); + while (numArgsPassed > 0) { + if (!info[numArgsPassed - 1]->IsUndefined()) + break; + --numArgsPassed; + } + if (info[0]->IsObject()) { + objectArg = ScriptValue(ScriptState::Current(info.GetIsolate()), info[0]); + } else { + V8ThrowException::ThrowTypeError(info.GetIsolate(), ExceptionMessages::FailedToExecute("voidMethodNullableAndOptionalObjectArgs", "TestInterface", "parameter 1 ('objectArg') is not an object.")); + return; + } + + if (UNLIKELY(numArgsPassed <= 1)) { + impl->voidMethodNullableAndOptionalObjectArgs(objectArg); + return; + } + if (info[1]->IsObject()) { + optionalObjectArg = ScriptValue(ScriptState::Current(info.GetIsolate()), info[1]); + } else if (info[1]->IsUndefined()) { + optionalObjectArg = ScriptValue(ScriptState::Current(info.GetIsolate()), v8::Undefined(info.GetIsolate())); + } else { + V8ThrowException::ThrowTypeError(info.GetIsolate(), ExceptionMessages::FailedToExecute("voidMethodNullableAndOptionalObjectArgs", "TestInterface", "parameter 2 ('optionalObjectArg') is not an object.")); + return; + } + + if (info[2]->IsObject()) { + nullableObjectArg = ScriptValue(ScriptState::Current(info.GetIsolate()), info[2]); + } else if (info[2]->IsNullOrUndefined()) { + nullableObjectArg = ScriptValue(ScriptState::Current(info.GetIsolate()), v8::Null(info.GetIsolate())); + } else { + V8ThrowException::ThrowTypeError(info.GetIsolate(), ExceptionMessages::FailedToExecute("voidMethodNullableAndOptionalObjectArgs", "TestInterface", "parameter 3 ('nullableObjectArg') is not an object.")); + return; + } + + impl->voidMethodNullableAndOptionalObjectArgs(objectArg, optionalObjectArg, nullableObjectArg); +} + static void voidMethodUnrestrictedDoubleArgUnrestrictedFloatArgMethod(const v8::FunctionCallbackInfo<v8::Value>& info) { ExceptionState exceptionState(info.GetIsolate(), ExceptionState::kExecutionContext, "TestInterface", "voidMethodUnrestrictedDoubleArgUnrestrictedFloatArg"); @@ -3202,6 +3251,12 @@ TestInterfaceImplementationV8Internal::voidMethodDoubleArgFloatArgMethod(info); } +void V8TestInterface::voidMethodNullableAndOptionalObjectArgsMethodCallback(const v8::FunctionCallbackInfo<v8::Value>& info) { + RUNTIME_CALL_TIMER_SCOPE_DISABLED_BY_DEFAULT(info.GetIsolate(), "Blink_TestInterfaceImplementation_voidMethodNullableAndOptionalObjectArgs"); + + TestInterfaceImplementationV8Internal::voidMethodNullableAndOptionalObjectArgsMethod(info); +} + void V8TestInterface::voidMethodUnrestrictedDoubleArgUnrestrictedFloatArgMethodCallback(const v8::FunctionCallbackInfo<v8::Value>& info) { RUNTIME_CALL_TIMER_SCOPE_DISABLED_BY_DEFAULT(info.GetIsolate(), "Blink_TestInterfaceImplementation_voidMethodUnrestrictedDoubleArgUnrestrictedFloatArg"); @@ -3677,6 +3732,7 @@ static const V8DOMConfiguration::MethodConfiguration V8TestInterfaceMethods[] = { {"voidMethodTestInterfaceEmptyArg", V8TestInterface::voidMethodTestInterfaceEmptyArgMethodCallback, 1, v8::None, V8DOMConfiguration::kOnPrototype, V8DOMConfiguration::kCheckHolder, V8DOMConfiguration::kDoNotCheckAccess, V8DOMConfiguration::kHasSideEffect, V8DOMConfiguration::kAllWorlds}, {"voidMethodDoubleArgFloatArg", V8TestInterface::voidMethodDoubleArgFloatArgMethodCallback, 2, v8::None, V8DOMConfiguration::kOnPrototype, V8DOMConfiguration::kCheckHolder, V8DOMConfiguration::kDoNotCheckAccess, V8DOMConfiguration::kHasSideEffect, V8DOMConfiguration::kAllWorlds}, + {"voidMethodNullableAndOptionalObjectArgs", V8TestInterface::voidMethodNullableAndOptionalObjectArgsMethodCallback, 2, v8::None, V8DOMConfiguration::kOnPrototype, V8DOMConfiguration::kCheckHolder, V8DOMConfiguration::kDoNotCheckAccess, V8DOMConfiguration::kHasSideEffect, V8DOMConfiguration::kAllWorlds}, {"voidMethodUnrestrictedDoubleArgUnrestrictedFloatArg", V8TestInterface::voidMethodUnrestrictedDoubleArgUnrestrictedFloatArgMethodCallback, 2, v8::None, V8DOMConfiguration::kOnPrototype, V8DOMConfiguration::kCheckHolder, V8DOMConfiguration::kDoNotCheckAccess, V8DOMConfiguration::kHasSideEffect, V8DOMConfiguration::kAllWorlds}, {"voidMethodTestEnumArg", V8TestInterface::voidMethodTestEnumArgMethodCallback, 1, v8::None, V8DOMConfiguration::kOnPrototype, V8DOMConfiguration::kCheckHolder, V8DOMConfiguration::kDoNotCheckAccess, V8DOMConfiguration::kHasSideEffect, V8DOMConfiguration::kAllWorlds}, {"voidMethod", V8TestInterface::voidMethodMethodCallbackForMainWorld, 0, v8::None, V8DOMConfiguration::kOnPrototype, V8DOMConfiguration::kCheckHolder, V8DOMConfiguration::kDoNotCheckAccess, V8DOMConfiguration::kHasSideEffect, V8DOMConfiguration::kMainWorld},
diff --git a/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.h b/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.h index e3ac903..4d87362 100644 --- a/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.h +++ b/third_party/blink/renderer/bindings/tests/results/core/v8_test_interface.h
@@ -179,6 +179,7 @@ CORE_EXPORT static void voidMethodTestInterfaceEmptyArgMethodCallback(const v8::FunctionCallbackInfo<v8::Value>&); CORE_EXPORT static void voidMethodDoubleArgFloatArgMethodCallback(const v8::FunctionCallbackInfo<v8::Value>&); + CORE_EXPORT static void voidMethodNullableAndOptionalObjectArgsMethodCallback(const v8::FunctionCallbackInfo<v8::Value>&); CORE_EXPORT static void voidMethodUnrestrictedDoubleArgUnrestrictedFloatArgMethodCallback(const v8::FunctionCallbackInfo<v8::Value>&); CORE_EXPORT static void voidMethodTestEnumArgMethodCallback(const v8::FunctionCallbackInfo<v8::Value>&); CORE_EXPORT static void voidMethodMethodCallback(const v8::FunctionCallbackInfo<v8::Value>&);
diff --git a/third_party/blink/renderer/core/dom/document.cc b/third_party/blink/renderer/core/dom/document.cc index 5913d45..40226dd 100644 --- a/third_party/blink/renderer/core/dom/document.cc +++ b/third_party/blink/renderer/core/dom/document.cc
@@ -32,6 +32,7 @@ #include <memory> #include "base/auto_reset.h" +#include "base/optional.h" #include "services/metrics/public/cpp/mojo_ukm_recorder.h" #include "services/metrics/public/cpp/ukm_builders.h" #include "services/metrics/public/cpp/ukm_source_id.h" @@ -5059,7 +5060,7 @@ if (!access_entry_from_url_) { access_entry_from_url_ = std::make_unique<OriginAccessEntry>( Url().Protocol(), Url().Host(), - OriginAccessEntry::kAllowRegisterableDomains); + network::cors::OriginAccessEntry::kAllowRegisterableDomains); } return *access_entry_from_url_; } @@ -5347,17 +5348,19 @@ // string "null". https://crbug.com/733150 if (!RuntimeEnabledFeatures::NullableDocumentDomainEnabled() || new_domain != "null") { - OriginAccessEntry access_entry(GetSecurityOrigin()->Protocol(), new_domain, - OriginAccessEntry::kAllowSubdomains); - OriginAccessEntry::MatchResult result = + OriginAccessEntry access_entry( + GetSecurityOrigin()->Protocol(), new_domain, + network::cors::OriginAccessEntry::kAllowSubdomains); + network::cors::OriginAccessEntry::MatchResult result = access_entry.MatchesOrigin(*GetSecurityOrigin()); - if (result == OriginAccessEntry::kDoesNotMatchOrigin) { + if (result == network::cors::OriginAccessEntry::kDoesNotMatchOrigin) { exception_state.ThrowSecurityError( "'" + new_domain + "' is not a suffix of '" + domain() + "'."); return; } - if (result == OriginAccessEntry::kMatchesOriginButIsPublicSuffix) { + if (result == + network::cors::OriginAccessEntry::kMatchesOriginButIsPublicSuffix) { exception_state.ThrowSecurityError("'" + new_domain + "' is a top-level domain."); return; @@ -5442,12 +5445,16 @@ // document's SecurityOrigin. A sandboxed document has a unique opaque // origin, but that shouldn't affect first-/third-party status for cookies // and site data. + base::Optional<OriginAccessEntry> remote_entry; + if (!top.IsLocalFrame()) { + remote_entry.emplace( + top_document_url.Protocol(), top_document_url.Host(), + network::cors::OriginAccessEntry::kAllowRegisterableDomains); + } const OriginAccessEntry& access_entry = - top.IsLocalFrame() - ? ToLocalFrame(top).GetDocument()->AccessEntryFromURL() - : OriginAccessEntry(top_document_url.Protocol(), - top_document_url.Host(), - OriginAccessEntry::kAllowRegisterableDomains); + remote_entry ? *remote_entry + : ToLocalFrame(top).GetDocument()->AccessEntryFromURL(); + const Frame* current_frame = GetFrame(); while (current_frame) { // Skip over srcdoc documents, as they are always same-origin with their @@ -5458,11 +5465,10 @@ DCHECK(current_frame); // We use 'matchesDomain' here, as it turns out that some folks embed HTTPS - // login forms - // into HTTP pages; we should allow this kind of upgrade. + // login forms into HTTP pages; we should allow this kind of upgrade. if (access_entry.MatchesDomain( *current_frame->GetSecurityContext()->GetSecurityOrigin()) == - OriginAccessEntry::kDoesNotMatchOrigin) + network::cors::OriginAccessEntry::kDoesNotMatchOrigin) return SecurityOrigin::UrlWithUniqueOpaqueOrigin(); current_frame = current_frame->Tree().Parent();
diff --git a/third_party/blink/renderer/core/exported/web_hit_test_result.cc b/third_party/blink/renderer/core/exported/web_hit_test_result.cc index c13ddd7..763fb423 100644 --- a/third_party/blink/renderer/core/exported/web_hit_test_result.cc +++ b/third_party/blink/renderer/core/exported/web_hit_test_result.cc
@@ -32,6 +32,7 @@ #include "third_party/blink/renderer/core/dom/element.h" #include "third_party/blink/renderer/core/dom/node.h" #include "third_party/blink/renderer/core/layout/hit_test_result.h" +#include "third_party/blink/renderer/core/layout/layout_box.h" #include "third_party/blink/renderer/platform/weborigin/kurl.h" namespace blink { @@ -77,6 +78,16 @@ return RoundedIntPoint(private_->Result().LocalPoint()); } +WebPoint WebHitTestResult::LocalPointWithoutContentBoxOffset() const { + IntPoint local_point = RoundedIntPoint(private_->Result().LocalPoint()); + LayoutObject* object = private_->Result().GetLayoutObject(); + if (object->IsBox()) { + LayoutBox* box = ToLayoutBox(object); + local_point.Move(-RoundedIntSize(box->ContentBoxOffset())); + } + return local_point; +} + WebElement WebHitTestResult::UrlElement() const { return WebElement(private_->Result().URLElement()); }
diff --git a/third_party/blink/renderer/core/fetch/data_consumer_handle_test_util.cc b/third_party/blink/renderer/core/fetch/data_consumer_handle_test_util.cc index 45fc96c..808341e 100644 --- a/third_party/blink/renderer/core/fetch/data_consumer_handle_test_util.cc +++ b/third_party/blink/renderer/core/fetch/data_consumer_handle_test_util.cc
@@ -61,7 +61,8 @@ DCHECK(thread_->IsCurrentThread()); if (initialization_policy_ >= kScriptExecution) { isolate_holder_ = std::make_unique<gin::IsolateHolder>( - scheduler::GetSingleThreadTaskRunnerForTesting()); + scheduler::GetSingleThreadTaskRunnerForTesting(), + gin::IsolateHolder::IsolateType::kTest); GetIsolate()->Enter(); } thread_->InitializeOnThread();
diff --git a/third_party/blink/renderer/core/frame/link_highlights.cc b/third_party/blink/renderer/core/frame/link_highlights.cc index 1f1bc64..1f4cc617 100644 --- a/third_party/blink/renderer/core/frame/link_highlights.cc +++ b/third_party/blink/renderer/core/frame/link_highlights.cc
@@ -58,7 +58,7 @@ continue; Color highlight_color = - node->GetLayoutObject()->Style()->TapHighlightColor(); + node->GetLayoutObject()->StyleRef().TapHighlightColor(); // Safari documentation for -webkit-tap-highlight-color says if the // specified color has 0 alpha, then tap highlighting is disabled. // http://developer.apple.com/library/safari/#documentation/appleapplications/reference/safaricssref/articles/standardcssproperties.html
diff --git a/third_party/blink/renderer/core/frame/local_frame_view.cc b/third_party/blink/renderer/core/frame/local_frame_view.cc index 3ea304f..7e427825 100644 --- a/third_party/blink/renderer/core/frame/local_frame_view.cc +++ b/third_party/blink/renderer/core/frame/local_frame_view.cc
@@ -888,7 +888,7 @@ if (first_layout_) { first_layout_ = false; last_viewport_size_ = GetLayoutSize(); - last_zoom_factor_ = GetLayoutView()->Style()->Zoom(); + last_zoom_factor_ = GetLayoutView()->StyleRef().Zoom(); ScrollbarMode h_mode; ScrollbarMode v_mode; @@ -1264,7 +1264,7 @@ if (GetLayoutView() && frame_->IsMainFrame() && frame_->GetPage()->GetBrowserControls().TotalHeight()) { - if (GetLayoutView()->Style()->HasFixedBackgroundImage()) { + if (GetLayoutView()->StyleRef().HasFixedBackgroundImage()) { // We've already issued a full invalidation above. GetLayoutView()->SetShouldDoFullPaintInvalidationOnResizeIfNeeded( width_changed, height_changed); @@ -1380,8 +1380,8 @@ for (auto* const viewport_constrained_object : *viewport_constrained_objects_) { LayoutObject* layout_object = viewport_constrained_object; - DCHECK(layout_object->Style()->HasViewportConstrainedPosition() || - layout_object->Style()->HasStickyConstrainedPosition()); + DCHECK(layout_object->StyleRef().HasViewportConstrainedPosition() || + layout_object->StyleRef().HasStickyConstrainedPosition()); DCHECK(layout_object->HasLayer()); PaintLayer* layer = ToLayoutBoxModelObject(layout_object)->Layer(); @@ -3055,12 +3055,12 @@ // Dumping externalRepresentation(m_frame->layoutObject()).ascii() is a good // trick to see the state of things before and after the layout if (LayoutView* layout_view = this->GetLayoutView()) { - float page_logical_width = layout_view->Style()->IsHorizontalWritingMode() + float page_logical_width = layout_view->StyleRef().IsHorizontalWritingMode() ? page_size.Width() : page_size.Height(); - float page_logical_height = layout_view->Style()->IsHorizontalWritingMode() - ? page_size.Height() - : page_size.Width(); + float page_logical_height = + layout_view->StyleRef().IsHorizontalWritingMode() ? page_size.Height() + : page_size.Width(); LayoutUnit floored_page_logical_width = static_cast<LayoutUnit>(page_logical_width); @@ -3078,7 +3078,7 @@ // FIXME: We are assuming a shrink-to-fit printing implementation. A // cropping implementation should not do this! bool horizontal_writing_mode = - layout_view->Style()->IsHorizontalWritingMode(); + layout_view->StyleRef().IsHorizontalWritingMode(); const LayoutRect& document_rect = LayoutRect(layout_view->DocumentRect()); LayoutUnit doc_logical_width = horizontal_writing_mode ? document_rect.Width() @@ -3118,7 +3118,7 @@ ? updated_document_rect.MaxX() : updated_document_rect.MaxY(); LayoutUnit clipped_logical_left; - if (!layout_view->Style()->IsLeftToRightDirection()) { + if (!layout_view->StyleRef().IsLeftToRightDirection()) { clipped_logical_left = LayoutUnit(doc_logical_right - page_logical_width); } @@ -4239,8 +4239,8 @@ return false; for (const LayoutObject* layout_object : *ViewportConstrainedObjects()) { DCHECK(layout_object->IsBoxModelObject() && layout_object->HasLayer()); - DCHECK(layout_object->Style()->GetPosition() == EPosition::kFixed || - layout_object->Style()->GetPosition() == EPosition::kSticky); + DCHECK(layout_object->StyleRef().GetPosition() == EPosition::kFixed || + layout_object->StyleRef().GetPosition() == EPosition::kSticky); if (ToLayoutBoxModelObject(layout_object)->IsSlowRepaintConstrainedObject()) return true; } @@ -4310,7 +4310,7 @@ // smooth-scroll animations. For this reason, we use HasOverflow instead of // ScrollsOverflow (which is false for overflow: hidden). if (LayoutViewport()->HasOverflow() && - GetLayoutView()->Style()->VisibleToHitTesting() && + GetLayoutView()->StyleRef().VisibleToHitTesting() && HasVisibleSlowRepaintViewportConstrainedObjects()) { reasons |= MainThreadScrollingReason::kHasNonLayerViewportConstrainedObjects;
diff --git a/third_party/blink/renderer/core/frame/reporting_context.cc b/third_party/blink/renderer/core/frame/reporting_context.cc index b8c64581..549ab18 100644 --- a/third_party/blink/renderer/core/frame/reporting_context.cc +++ b/third_party/blink/renderer/core/frame/reporting_context.cc
@@ -9,6 +9,7 @@ #include "third_party/blink/renderer/core/frame/local_frame.h" #include "third_party/blink/renderer/core/frame/report.h" #include "third_party/blink/renderer/core/frame/reporting_observer.h" +#include "third_party/blink/renderer/core/frame/use_counter.h" #include "third_party/blink/renderer/platform/bindings/script_state.h" namespace blink { @@ -31,10 +32,11 @@ } void ReportingContext::QueueReport(Report* report) { + CountReport(report); report_buffer_.insert(report); // Only the most recent 100 reports will remain buffered. - // https://wicg.github.io/reporting/#notify-observers + // https://w3c.github.io/reporting/#notify-observers if (report_buffer_.size() > 100) report_buffer_.RemoveFirst(); @@ -42,7 +44,25 @@ observer->QueueReport(report); } +void ReportingContext::CountReport(Report* report) { + const String& type = report->type(); + WebFeature feature; + + if (type == "deprecation") { + feature = WebFeature::kDeprecationReport; + } else if (type == "intervention") { + feature = WebFeature::kInterventionReport; + } else { + NOTREACHED(); + return; + } + + UseCounter::Count(execution_context_, feature); +} + void ReportingContext::RegisterObserver(ReportingObserver* observer) { + UseCounter::Count(execution_context_, WebFeature::kReportingObserver); + observers_.insert(observer); if (!observer->Buffered()) return;
diff --git a/third_party/blink/renderer/core/frame/reporting_context.h b/third_party/blink/renderer/core/frame/reporting_context.h index f75fbdef8..c60b9d77 100644 --- a/third_party/blink/renderer/core/frame/reporting_context.h +++ b/third_party/blink/renderer/core/frame/reporting_context.h
@@ -33,6 +33,9 @@ // Queues a report in all registered observers. void QueueReport(Report*); + // Counts the use of a report type via UseCounter. + void CountReport(Report*); + void RegisterObserver(ReportingObserver*); void UnregisterObserver(ReportingObserver*);
diff --git a/third_party/blink/renderer/core/frame/root_frame_viewport.cc b/third_party/blink/renderer/core/frame/root_frame_viewport.cc index 171d036..7292b06 100644 --- a/third_party/blink/renderer/core/frame/root_frame_viewport.cc +++ b/third_party/blink/renderer/core/frame/root_frame_viewport.cc
@@ -297,9 +297,9 @@ if (params.is_for_scroll_sequence) { DCHECK(params.GetScrollType() == kProgrammaticScroll || params.GetScrollType() == kUserScroll); - ScrollBehavior behavior = - DetermineScrollBehavior(params.GetScrollBehavior(), - GetLayoutBox()->Style()->GetScrollBehavior()); + ScrollBehavior behavior = DetermineScrollBehavior( + params.GetScrollBehavior(), + GetLayoutBox()->StyleRef().GetScrollBehavior()); GetSmoothScrollSequencer()->QueueAnimation(this, new_scroll_offset, behavior); } else {
diff --git a/third_party/blink/renderer/core/frame/smart_clip.cc b/third_party/blink/renderer/core/frame/smart_clip.cc index b0887aa..60a0b403 100644 --- a/third_party/blink/renderer/core/frame/smart_clip.cc +++ b/third_party/blink/renderer/core/frame/smart_clip.cc
@@ -173,7 +173,7 @@ if (layout_object && !node_rect.IsEmpty()) { if (layout_object->IsText() || layout_object->IsLayoutImage() || node->IsFrameOwnerElement() || - (layout_object->Style()->HasBackgroundImage() && + (layout_object->StyleRef().HasBackgroundImage() && !ShouldSkipBackgroundImage(node))) { if (resized_crop_rect.Intersects(node_rect)) { min_node = MinNodeContainsNodes(min_node, node); @@ -203,8 +203,8 @@ // or a width. On the other hand, if we've got a legit background image, // it's very likely the height or the width will be set to auto. LayoutObject* layout_object = node->GetLayoutObject(); - if (layout_object && (layout_object->Style()->LogicalHeight().IsAuto() || - layout_object->Style()->LogicalWidth().IsAuto())) + if (layout_object && (layout_object->StyleRef().LogicalHeight().IsAuto() || + layout_object->StyleRef().LogicalWidth().IsAuto())) return true; return false;
diff --git a/third_party/blink/renderer/core/layout/api/line_layout_item.h b/third_party/blink/renderer/core/layout/api/line_layout_item.h index fcc3467..d4d92293 100644 --- a/third_party/blink/renderer/core/layout/api/line_layout_item.h +++ b/third_party/blink/renderer/core/layout/api/line_layout_item.h
@@ -121,7 +121,7 @@ if (IsSVGInlineText()) return false; - return Style()->PreserveNewline(); + return StyleRef().PreserveNewline(); } unsigned length() const { return layout_object_->length(); }
diff --git a/third_party/blink/renderer/core/layout/bidi_run_for_line.cc b/third_party/blink/renderer/core/layout/bidi_run_for_line.cc index 59a9901..d304a550 100644 --- a/third_party/blink/renderer/core/layout/bidi_run_for_line.cc +++ b/third_party/blink/renderer/core/layout/bidi_run_for_line.cc
@@ -83,8 +83,8 @@ InlineIterator iter(LineLayoutItem(root), first_layout_object, first_layout_object == current ? pos : 0); InlineBidiResolver observer; - observer.SetStatus(BidiStatus(root.Style()->Direction(), - IsOverride(root.Style()->GetUnicodeBidi()))); + observer.SetStatus(BidiStatus(root.StyleRef().Direction(), + IsOverride(root.StyleRef().GetUnicodeBidi()))); observer.SetPositionIgnoringNestedIsolates(iter); return observer.DetermineParagraphDirectionality(); } @@ -138,7 +138,7 @@ isolated_resolver.GetMidpointState(); isolated_line_midpoint_state = top_resolver.MidpointStateForIsolatedRun(isolated_run.run_to_replace); - UnicodeBidi unicode_bidi = isolated_inline.Style()->GetUnicodeBidi(); + UnicodeBidi unicode_bidi = isolated_inline.StyleRef().GetUnicodeBidi(); TextDirection direction; if (unicode_bidi == UnicodeBidi::kPlaintext) { direction = DeterminePlaintextDirectionality( @@ -146,7 +146,7 @@ } else { DCHECK(unicode_bidi == UnicodeBidi::kIsolate || unicode_bidi == UnicodeBidi::kIsolateOverride); - direction = isolated_inline.Style()->Direction(); + direction = isolated_inline.StyleRef().Direction(); } isolated_resolver.SetStatus(BidiStatus::CreateForIsolate( direction, IsOverride(unicode_bidi), isolated_run.level));
diff --git a/third_party/blink/renderer/core/layout/flexible_box_algorithm.cc b/third_party/blink/renderer/core/layout/flexible_box_algorithm.cc index 50501fd..f070bde 100644 --- a/third_party/blink/renderer/core/layout/flexible_box_algorithm.cc +++ b/third_party/blink/renderer/core/layout/flexible_box_algorithm.cc
@@ -111,11 +111,11 @@ bool FlexItem::HasAutoMarginsInCrossAxis() const { if (algorithm->IsHorizontalFlow()) { - return box->Style()->MarginTop().IsAuto() || - box->Style()->MarginBottom().IsAuto(); + return box->StyleRef().MarginTop().IsAuto() || + box->StyleRef().MarginBottom().IsAuto(); } - return box->Style()->MarginLeft().IsAuto() || - box->Style()->MarginRight().IsAuto(); + return box->StyleRef().MarginLeft().IsAuto() || + box->StyleRef().MarginRight().IsAuto(); } ItemPosition FlexItem::Alignment() const { @@ -127,14 +127,14 @@ DCHECK_GE(auto_margin_offset, LayoutUnit()); if (algorithm->IsHorizontalFlow()) { - if (box->Style()->MarginLeft().IsAuto()) + if (box->StyleRef().MarginLeft().IsAuto()) box->SetMarginLeft(auto_margin_offset); - if (box->Style()->MarginRight().IsAuto()) + if (box->StyleRef().MarginRight().IsAuto()) box->SetMarginRight(auto_margin_offset); } else { - if (box->Style()->MarginTop().IsAuto()) + if (box->StyleRef().MarginTop().IsAuto()) box->SetMarginTop(auto_margin_offset); - if (box->Style()->MarginBottom().IsAuto()) + if (box->StyleRef().MarginBottom().IsAuto()) box->SetMarginBottom(auto_margin_offset); } } @@ -145,10 +145,10 @@ LayoutBox* child = violations[i]->box; LayoutUnit child_size = violations[i]->flexed_content_size; remaining_free_space -= child_size - violations[i]->flex_base_content_size; - total_flex_grow -= child->Style()->FlexGrow(); - total_flex_shrink -= child->Style()->FlexShrink(); + total_flex_grow -= child->StyleRef().FlexGrow(); + total_flex_shrink -= child->StyleRef().FlexShrink(); total_weighted_flex_shrink -= - child->Style()->FlexShrink() * violations[i]->flex_base_content_size; + child->StyleRef().FlexShrink() * violations[i]->flex_base_content_size; // totalWeightedFlexShrink can be negative when we exceed the precision of // a double when we initially calcuate totalWeightedFlexShrink. We then // subtract each child's weighted flex shrink with full precision, now @@ -173,8 +173,8 @@ DCHECK(!flex_item.box->IsOutOfFlowPositioned()); DCHECK(!flex_item.frozen) << i; float flex_factor = (flex_sign == kPositiveFlexibility) - ? child->Style()->FlexGrow() - : child->Style()->FlexShrink(); + ? child->StyleRef().FlexGrow() + : child->StyleRef().FlexShrink(); if (flex_factor == 0 || (flex_sign == kPositiveFlexibility && flex_item.flex_base_content_size > @@ -218,12 +218,12 @@ if (remaining_free_space > 0 && total_flex_grow > 0 && flex_sign == kPositiveFlexibility && std::isfinite(total_flex_grow)) { extra_space = - remaining_free_space * child->Style()->FlexGrow() / total_flex_grow; + remaining_free_space * child->StyleRef().FlexGrow() / total_flex_grow; } else if (remaining_free_space < 0 && total_weighted_flex_shrink > 0 && flex_sign == kNegativeFlexibility && std::isfinite(total_weighted_flex_shrink) && - child->Style()->FlexShrink()) { - extra_space = remaining_free_space * child->Style()->FlexShrink() * + child->StyleRef().FlexShrink()) { + extra_space = remaining_free_space * child->StyleRef().FlexShrink() * flex_item.flex_base_content_size / total_weighted_flex_shrink; } @@ -262,14 +262,14 @@ LayoutBox* child = line_items[i].box; DCHECK(!child->IsOutOfFlowPositioned()); if (is_horizontal) { - if (child->Style()->MarginLeft().IsAuto()) + if (child->StyleRef().MarginLeft().IsAuto()) ++number_of_auto_margins; - if (child->Style()->MarginRight().IsAuto()) + if (child->StyleRef().MarginRight().IsAuto()) ++number_of_auto_margins; } else { - if (child->Style()->MarginTop().IsAuto()) + if (child->StyleRef().MarginTop().IsAuto()) ++number_of_auto_margins; - if (child->Style()->MarginBottom().IsAuto()) + if (child->StyleRef().MarginBottom().IsAuto()) ++number_of_auto_margins; } } @@ -302,7 +302,7 @@ available_free_space, justify_content, line_items.size()); LayoutUnit max_descent; // Used when align-items: baseline. LayoutUnit max_child_cross_axis_extent; - bool should_flip_main_axis = !algorithm->Style()->IsColumnFlexDirection() && + bool should_flip_main_axis = !algorithm->StyleRef().IsColumnFlexDirection() && !algorithm->IsLeftToRightFlow(); for (size_t i = 0; i < line_items.size(); ++i) { FlexItem& flex_item = line_items[i]; @@ -392,10 +392,10 @@ line_items.push_back(flex_item); line_has_in_flow_item = true; sum_flex_base_size += flex_item.FlexBaseMarginBoxSize(); - total_flex_grow += flex_item.box->Style()->FlexGrow(); - total_flex_shrink += flex_item.box->Style()->FlexShrink(); - total_weighted_flex_shrink += - flex_item.box->Style()->FlexShrink() * flex_item.flex_base_content_size; + total_flex_grow += flex_item.box->StyleRef().FlexGrow(); + total_flex_shrink += flex_item.box->StyleRef().FlexShrink(); + total_weighted_flex_shrink += flex_item.box->StyleRef().FlexShrink() * + flex_item.flex_base_content_size; sum_hypothetical_main_size += flex_item.HypotheticalMainAxisMarginBoxSize(); } DCHECK(line_items.size() > 0 || next_item_index_ == all_items_.size());
diff --git a/third_party/blink/renderer/core/layout/flexible_box_algorithm.h b/third_party/blink/renderer/core/layout/flexible_box_algorithm.h index f7aae55..ea5bf0f 100644 --- a/third_party/blink/renderer/core/layout/flexible_box_algorithm.h +++ b/third_party/blink/renderer/core/layout/flexible_box_algorithm.h
@@ -242,6 +242,7 @@ Vector<FlexItem>& all_items); const ComputedStyle* Style() const { return style_; } + const ComputedStyle& StyleRef() const { return *style_; } Vector<FlexLine>& FlexLines() { return flex_lines_; }
diff --git a/third_party/blink/renderer/core/layout/floating_objects.cc b/third_party/blink/renderer/core/layout/floating_objects.cc index 9e58504..befe3dd 100644 --- a/third_party/blink/renderer/core/layout/floating_objects.cc +++ b/third_party/blink/renderer/core/layout/floating_objects.cc
@@ -59,7 +59,7 @@ is_in_placed_tree_(false) #endif { - EFloat type = layout_object->Style()->Floating(); + EFloat type = layout_object->StyleRef().Floating(); DCHECK_NE(type, EFloat::kNone); if (type == EFloat::kLeft) type_ = kFloatLeft;
diff --git a/third_party/blink/renderer/core/layout/hit_test_result.cc b/third_party/blink/renderer/core/layout/hit_test_result.cc index e930b724..b9b95b5 100644 --- a/third_party/blink/renderer/core/layout/hit_test_result.cc +++ b/third_party/blink/renderer/core/layout/hit_test_result.cc
@@ -238,7 +238,7 @@ String title = ToElement(title_node)->title(); if (!title.IsNull()) { if (LayoutObject* layout_object = title_node->GetLayoutObject()) - dir = layout_object->Style()->Direction(); + dir = layout_object->StyleRef().Direction(); return title; } }
diff --git a/third_party/blink/renderer/core/layout/layout_analyzer.cc b/third_party/blink/renderer/core/layout/layout_analyzer.cc index e5b6ef7..92ae9e1b 100644 --- a/third_party/blink/renderer/core/layout/layout_analyzer.cc +++ b/third_party/blink/renderer/core/layout/layout_analyzer.cc
@@ -68,7 +68,7 @@ Increment(kLayoutObjectsThatAreTableCells); if (o.IsFloating()) Increment(kLayoutObjectsThatAreFloating); - if (o.Style()->SpecifiesColumns()) + if (o.StyleRef().SpecifiesColumns()) Increment(kLayoutObjectsThatSpecifyColumns); if (o.HasLayer()) Increment(kLayoutObjectsThatHaveALayer);
diff --git a/third_party/blink/renderer/core/layout/layout_block.cc b/third_party/blink/renderer/core/layout/layout_block.cc index 252aef8..75b3e60 100644 --- a/third_party/blink/renderer/core/layout/layout_block.cc +++ b/third_party/blink/renderer/core/layout/layout_block.cc
@@ -463,7 +463,7 @@ // if we have percentage padding, which is rather non-obvious. That method // returns true in other cases as well. width_available_to_children_has_changed |= - Style()->BoxSizing() == EBoxSizing::kBorderBox && + StyleRef().BoxSizing() == EBoxSizing::kBorderBox && NeedsPreferredWidthsRecalculation() && View()->GetLayoutState()->ContainingBlockLogicalWidthChanged(); @@ -552,14 +552,14 @@ for (auto* positioned_object : *positioned_descendants) { // Fixed positioned elements don't contribute to layout overflow, since they // don't scroll with the content. - if (positioned_object->Style()->GetPosition() != EPosition::kFixed) + if (positioned_object->StyleRef().GetPosition() != EPosition::kFixed) AddOverflowFromChild(*positioned_object, ToLayoutSize(positioned_object->Location())); } } void LayoutBlock::AddVisualOverflowFromTheme() { - if (!Style()->HasAppearance()) + if (!StyleRef().HasAppearance()) return; IntRect inflated_rect = PixelSnappedBorderBoxRect(); @@ -571,10 +571,10 @@ static inline bool ChangeInAvailableLogicalHeightAffectsChild( LayoutBlock* parent, LayoutBox& child) { - if (parent->Style()->BoxSizing() != EBoxSizing::kBorderBox) + if (parent->StyleRef().BoxSizing() != EBoxSizing::kBorderBox) return false; - return parent->Style()->IsHorizontalWritingMode() && - !child.Style()->IsHorizontalWritingMode(); + return parent->StyleRef().IsHorizontalWritingMode() && + !child.StyleRef().IsHorizontalWritingMode(); } void LayoutBlock::UpdateBlockChildDirtyBitsBeforeLayout(bool relayout_children, @@ -696,19 +696,19 @@ void LayoutBlock::MarkFixedPositionObjectForLayoutIfNeeded( LayoutObject* child, SubtreeLayoutScope& layout_scope) { - if (child->Style()->GetPosition() != EPosition::kFixed) + if (child->StyleRef().GetPosition() != EPosition::kFixed) return; bool has_static_block_position = - child->Style()->HasStaticBlockPosition(IsHorizontalWritingMode()); + child->StyleRef().HasStaticBlockPosition(IsHorizontalWritingMode()); bool has_static_inline_position = - child->Style()->HasStaticInlinePosition(IsHorizontalWritingMode()); + child->StyleRef().HasStaticInlinePosition(IsHorizontalWritingMode()); if (!has_static_block_position && !has_static_inline_position) return; LayoutObject* o = child->Parent(); while (!o->IsLayoutView() && - o->Style()->GetPosition() != EPosition::kAbsolute) + o->StyleRef().GetPosition() != EPosition::kAbsolute) o = o->Parent(); // The LayoutView is absolute-positioned, but does not move. if (o->IsLayoutView()) @@ -1076,9 +1076,9 @@ LayoutUnit LayoutBlock::TextIndentOffset() const { LayoutUnit cw; - if (Style()->TextIndent().IsPercentOrCalc()) + if (StyleRef().TextIndent().IsPercentOrCalc()) cw = ContainingBlock()->AvailableLogicalWidth(); - return MinimumValueForLength(Style()->TextIndent(), cw); + return MinimumValueForLength(StyleRef().TextIndent(), cw); } bool LayoutBlock::IsPointInOverflowControl( @@ -1242,7 +1242,7 @@ static inline bool IsChildHitTestCandidate(LayoutBox* box) { return box->Size().Height() && - box->Style()->Visibility() == EVisibility::kVisible && + box->StyleRef().Visibility() == EVisibility::kVisible && !box->IsOutOfFlowPositioned() && !box->IsLayoutFlowThread(); } @@ -1270,7 +1270,7 @@ while (last_candidate_box && !IsChildHitTestCandidate(last_candidate_box)) last_candidate_box = last_candidate_box->PreviousSiblingBox(); - bool blocks_are_flipped = Style()->IsFlippedBlocksWritingMode(); + bool blocks_are_flipped = StyleRef().IsFlippedBlocksWritingMode(); if (last_candidate_box) { if (point_in_logical_contents.Y() > LogicalTopForChild(*last_candidate_box) || @@ -1494,7 +1494,7 @@ // will attempt to overlap the float if the negative margin is smaller // than the float width. bool ltr = containing_block - ? containing_block->Style()->IsLeftToRightDirection() + ? containing_block->StyleRef().IsLeftToRightDirection() : style_to_use.IsLeftToRightDirection(); LayoutUnit margin_logical_left = ltr ? margin_start : margin_end; LayoutUnit margin_logical_right = ltr ? margin_end : margin_start; @@ -1621,8 +1621,8 @@ // the theme is turned off, checkboxes/radios will still have decent // baselines. // FIXME: Need to patch form controls to deal with vertical lines. - if (Style()->HasAppearance() && - !LayoutTheme::GetTheme().IsControlContainer(Style()->Appearance())) { + if (StyleRef().HasAppearance() && + !LayoutTheme::GetTheme().IsControlContainer(StyleRef().Appearance())) { return Size().Height() + MarginTop() + LayoutTheme::GetTheme().BaselinePositionAdjustment(StyleRef()); } @@ -1716,7 +1716,7 @@ // We likewise avoid using the last line box in the case of size containment, // where the block's contents shouldn't be considered when laying out its // ancestors or siblings. - return (!Style()->IsOverflowVisible() && + return (!StyleRef().IsOverflowVisible() && !ShouldIgnoreOverflowPropertyForInlineBlockBaseline()) || ShouldApplySizeContainment(); } @@ -1765,7 +1765,8 @@ const LayoutBlock* first_line_block = this; bool has_pseudo = false; while (true) { - has_pseudo = first_line_block->Style()->HasPseudoStyle(kPseudoIdFirstLine); + has_pseudo = + first_line_block->StyleRef().HasPseudoStyle(kPseudoIdFirstLine); if (has_pseudo) break; LayoutObject* parent_block = first_line_block->Parent(); @@ -1853,7 +1854,7 @@ LayoutBox* LayoutBlock::CreateAnonymousBoxWithSameTypeAs( const LayoutObject* parent) const { - return CreateAnonymousWithParentAndDisplay(parent, Style()->Display()); + return CreateAnonymousWithParentAndDisplay(parent, StyleRef().Display()); } void LayoutBlock::PaginatedContentWasLaidOut( @@ -1904,15 +1905,17 @@ bool LayoutBlock::HasMarginBeforeQuirk(const LayoutBox* child) const { // If the child has the same directionality as we do, then we can just return // its margin quirk. - if (!child->IsWritingModeRoot()) + if (!child->IsWritingModeRoot()) { return child->IsLayoutBlock() ? ToLayoutBlock(child)->HasMarginBeforeQuirk() - : child->Style()->HasMarginBeforeQuirk(); + : child->StyleRef().HasMarginBeforeQuirk(); + } // The child has a different directionality. If the child is parallel, then // it's just flipped relative to us. We can use the opposite edge. - if (child->IsHorizontalWritingMode() == IsHorizontalWritingMode()) + if (child->IsHorizontalWritingMode() == IsHorizontalWritingMode()) { return child->IsLayoutBlock() ? ToLayoutBlock(child)->HasMarginAfterQuirk() - : child->Style()->HasMarginAfterQuirk(); + : child->StyleRef().HasMarginAfterQuirk(); + } // The child is perpendicular to us and box sides are never quirky in // html.css, and we don't really care about whether or not authors specified @@ -1923,15 +1926,17 @@ bool LayoutBlock::HasMarginAfterQuirk(const LayoutBox* child) const { // If the child has the same directionality as we do, then we can just return // its margin quirk. - if (!child->IsWritingModeRoot()) + if (!child->IsWritingModeRoot()) { return child->IsLayoutBlock() ? ToLayoutBlock(child)->HasMarginAfterQuirk() - : child->Style()->HasMarginAfterQuirk(); + : child->StyleRef().HasMarginAfterQuirk(); + } // The child has a different directionality. If the child is parallel, then // it's just flipped relative to us. We can use the opposite edge. - if (child->IsHorizontalWritingMode() == IsHorizontalWritingMode()) + if (child->IsHorizontalWritingMode() == IsHorizontalWritingMode()) { return child->IsLayoutBlock() ? ToLayoutBlock(child)->HasMarginBeforeQuirk() - : child->Style()->HasMarginBeforeQuirk(); + : child->StyleRef().HasMarginBeforeQuirk(); + } // The child is perpendicular to us and box sides are never quirky in // html.css, and we don't really care about whether or not authors specified @@ -2173,7 +2178,7 @@ } bool LayoutBlock::NeedsPreferredWidthsRecalculation() const { - return (HasRelativeLogicalHeight() && Style()->LogicalWidth().IsAuto()) || + return (HasRelativeLogicalHeight() && StyleRef().LogicalWidth().IsAuto()) || LayoutBox::NeedsPreferredWidthsRecalculation(); }
diff --git a/third_party/blink/renderer/core/layout/layout_block.h b/third_party/blink/renderer/core/layout/layout_block.h index e7cd22d..9588bfc0 100644 --- a/third_party/blink/renderer/core/layout/layout_block.h +++ b/third_party/blink/renderer/core/layout/layout_block.h
@@ -290,12 +290,12 @@ return LogicalLeftOffsetForContent() + AvailableLogicalWidth(); } LayoutUnit StartOffsetForContent() const { - return Style()->IsLeftToRightDirection() + return StyleRef().IsLeftToRightDirection() ? LogicalLeftOffsetForContent() : LogicalWidth() - LogicalRightOffsetForContent(); } LayoutUnit EndOffsetForContent() const { - return !Style()->IsLeftToRightDirection() + return !StyleRef().IsLeftToRightDirection() ? LogicalLeftOffsetForContent() : LogicalWidth() - LogicalRightOffsetForContent(); }
diff --git a/third_party/blink/renderer/core/layout/layout_block_flow.cc b/third_party/blink/renderer/core/layout/layout_block_flow.cc index ff86543f..c7724a31 100644 --- a/third_party/blink/renderer/core/layout/layout_block_flow.cc +++ b/third_party/blink/renderer/core/layout/layout_block_flow.cc
@@ -384,19 +384,19 @@ "-webkit-input-placeholder")); if (LogicalHeight() > LayoutUnit() || BorderAndPaddingLogicalHeight() || - Style()->LogicalMinHeight().IsPositive() || - Style()->MarginBeforeCollapse() == EMarginCollapse::kSeparate || - Style()->MarginAfterCollapse() == EMarginCollapse::kSeparate) + StyleRef().LogicalMinHeight().IsPositive() || + StyleRef().MarginBeforeCollapse() == EMarginCollapse::kSeparate || + StyleRef().MarginAfterCollapse() == EMarginCollapse::kSeparate) return false; - Length logical_height_length = Style()->LogicalHeight(); + Length logical_height_length = StyleRef().LogicalHeight(); bool has_auto_height = logical_height_length.IsAuto(); if (logical_height_length.IsPercentOrCalc() && !GetDocument().InQuirksMode()) { has_auto_height = true; for (LayoutBlock* cb = ContainingBlock(); !cb->IsLayoutView(); cb = cb->ContainingBlock()) { - if (cb->Style()->LogicalHeight().IsFixed() || cb->IsTableCell()) + if (cb->StyleRef().LogicalHeight().IsFixed() || cb->IsTableCell()) has_auto_height = false; } } @@ -568,8 +568,8 @@ // have no margins, so we don't fill in the values for table cells. if (!IsTableCell()) { InitMaxMarginValues(); - SetHasMarginBeforeQuirk(Style()->HasMarginBeforeQuirk()); - SetHasMarginAfterQuirk(Style()->HasMarginAfterQuirk()); + SetHasMarginBeforeQuirk(StyleRef().HasMarginBeforeQuirk()); + SetHasMarginAfterQuirk(StyleRef().HasMarginAfterQuirk()); } if (View()->GetLayoutState()->IsPaginated()) { @@ -689,14 +689,14 @@ // If the child is being centred then the margin calculated to do that has // factored in any offset required to avoid floats, so use it if necessary. if (StyleRef().GetTextAlign() == ETextAlign::kWebkitCenter || - child.Style()->MarginStartUsing(StyleRef()).IsAuto()) + child.StyleRef().MarginStartUsing(StyleRef()).IsAuto()) new_position = std::max(new_position, position_to_avoid_floats + child_margin_start); else if (position_to_avoid_floats > initial_start_position) new_position = std::max(new_position, position_to_avoid_floats); } - SetLogicalLeftForChild(child, Style()->IsLeftToRightDirection() + SetLogicalLeftForChild(child, StyleRef().IsLeftToRightDirection() ? new_position : total_available_logical_width - new_position - @@ -1147,7 +1147,7 @@ if (total_logical_height > page_logical_height) return false; } else { - if (line_index > block.Style()->Orphans()) + if (line_index > block.StyleRef().Orphans()) return false; // Not enough orphans here. Push the entire block to the next column / page @@ -2047,7 +2047,7 @@ // In case the child discarded the before margin of the block we need to // reset the mustDiscardMarginBefore flag to the initial value. - SetMustDiscardMarginBefore(Style()->MarginBeforeCollapse() == + SetMustDiscardMarginBefore(StyleRef().MarginBeforeCollapse() == EMarginCollapse::kDiscard); } @@ -2096,13 +2096,13 @@ // FIXME: Use writing mode independent accessor for marginBeforeCollapse. if ((GetDocument().InQuirksMode() && HasMarginBeforeQuirk(&child) && (IsTableCell() || IsBody())) || - child.Style()->MarginBeforeCollapse() == EMarginCollapse::kSeparate) + child.StyleRef().MarginBeforeCollapse() == EMarginCollapse::kSeparate) return; // The margins are discarded by a child that specified // -webkit-margin-collapse: discard. // FIXME: Use writing mode independent accessor for marginBeforeCollapse. - if (child.Style()->MarginBeforeCollapse() == EMarginCollapse::kDiscard) { + if (child.StyleRef().MarginBeforeCollapse() == EMarginCollapse::kDiscard) { positive_margin_before = LayoutUnit(); negative_margin_before = LayoutUnit(); discard_margin_before = true; @@ -2147,9 +2147,9 @@ if (grandchild_box->IsLayoutBlock()) { LayoutBlock* grandchild_block = ToLayoutBlock(grandchild_box); grandchild_block->SetHasMarginBeforeQuirk( - grandchild_box->Style()->HasMarginBeforeQuirk()); + grandchild_box->StyleRef().HasMarginBeforeQuirk()); grandchild_block->SetHasMarginAfterQuirk( - grandchild_box->Style()->HasMarginAfterQuirk()); + grandchild_box->StyleRef().HasMarginAfterQuirk()); } } @@ -2157,7 +2157,7 @@ // require clearance to move past any floats. If that's the case we want to be // sure we estimate the correct position including margins after any floats // rather than use 'clearance' later which could give us the wrong position. - if (grandchild_box->Style()->Clear() != EClear::kNone && + if (grandchild_box->StyleRef().Clear() != EClear::kNone && child_block_flow->MarginBeforeForChild(*grandchild_box) == 0) return; @@ -2317,7 +2317,7 @@ } void LayoutBlockFlow::SetMustDiscardMarginBefore(bool value) { - if (Style()->MarginBeforeCollapse() == EMarginCollapse::kDiscard) { + if (StyleRef().MarginBeforeCollapse() == EMarginCollapse::kDiscard) { DCHECK(value); return; } @@ -2332,7 +2332,7 @@ } void LayoutBlockFlow::SetMustDiscardMarginAfter(bool value) { - if (Style()->MarginAfterCollapse() == EMarginCollapse::kDiscard) { + if (StyleRef().MarginAfterCollapse() == EMarginCollapse::kDiscard) { DCHECK(value); return; } @@ -2347,12 +2347,12 @@ } bool LayoutBlockFlow::MustDiscardMarginBefore() const { - return Style()->MarginBeforeCollapse() == EMarginCollapse::kDiscard || + return StyleRef().MarginBeforeCollapse() == EMarginCollapse::kDiscard || (rare_data_ && rare_data_->discard_margin_before_); } bool LayoutBlockFlow::MustDiscardMarginAfter() const { - return Style()->MarginAfterCollapse() == EMarginCollapse::kDiscard || + return StyleRef().MarginAfterCollapse() == EMarginCollapse::kDiscard || (rare_data_ && rare_data_->discard_margin_after_); } @@ -2362,13 +2362,13 @@ if (!child.IsWritingModeRoot()) { return child.IsLayoutBlockFlow() ? ToLayoutBlockFlow(&child)->MustDiscardMarginBefore() - : (child.Style()->MarginBeforeCollapse() == + : (child.StyleRef().MarginBeforeCollapse() == EMarginCollapse::kDiscard); } if (child.IsHorizontalWritingMode() == IsHorizontalWritingMode()) { return child.IsLayoutBlockFlow() ? ToLayoutBlockFlow(&child)->MustDiscardMarginAfter() - : (child.Style()->MarginAfterCollapse() == + : (child.StyleRef().MarginAfterCollapse() == EMarginCollapse::kDiscard); } @@ -2385,13 +2385,13 @@ if (!child.IsWritingModeRoot()) { return child.IsLayoutBlockFlow() ? ToLayoutBlockFlow(&child)->MustDiscardMarginAfter() - : (child.Style()->MarginAfterCollapse() == + : (child.StyleRef().MarginAfterCollapse() == EMarginCollapse::kDiscard); } if (child.IsHorizontalWritingMode() == IsHorizontalWritingMode()) { return child.IsLayoutBlockFlow() ? ToLayoutBlockFlow(&child)->MustDiscardMarginBefore() - : (child.Style()->MarginBeforeCollapse() == + : (child.StyleRef().MarginBeforeCollapse() == EMarginCollapse::kDiscard); } @@ -2720,7 +2720,7 @@ return LayoutUnit(-1); // InlineFlowBox::placeBoxesInBlockDirection will flip lines in // case of verticalLR mode, so we can assume verticalRL for now. - if (Style()->IsFlippedLinesWritingMode()) { + if (StyleRef().IsFlippedLinesWritingMode()) { return LogicalHeight() - LastLineBox()->LogicalBottom() + font_data->GetFontMetrics().Ascent(LastRootBox()->BaselineType()); } @@ -2858,7 +2858,7 @@ // At least one float is present. We need to perform the clearance // computation. - EClear clear = child->Style()->Clear(); + EClear clear = child->StyleRef().Clear(); LayoutUnit logical_bottom = LowestFloatLogicalBottom(clear); // We also clear floats if we are too big to sit on the same line as a float @@ -3032,7 +3032,7 @@ CreateOrDestroyMultiColumnFlowThreadIfNeeded(old_style); if (old_style) { if (LayoutMultiColumnFlowThread* flow_thread = MultiColumnFlowThread()) { - if (!Style()->ColumnRuleEquivalent(*old_style)) { + if (!StyleRef().ColumnRuleEquivalent(*old_style)) { // Column rules are painted by anonymous column set children of the // multicol container. We need to notify them. flow_thread->ColumnRuleStyleDidChange(); @@ -3054,7 +3054,7 @@ LayoutBox& child, LayoutUnit logical_top, IndentTextOrNot indent_text) { - if (child.Style()->IsOriginalDisplayInlineType()) + if (child.StyleRef().IsOriginalDisplayInlineType()) SetStaticInlinePositionForChild( child, StartAlignedOffsetForLine(logical_top, indent_text)); else @@ -3621,7 +3621,7 @@ LayoutPoint LayoutBlockFlow::FlipFloatForWritingModeForChild( const FloatingObject& child, const LayoutPoint& point) const { - if (!Style()->IsFlippedBlocksWritingMode()) + if (!StyleRef().IsFlippedBlocksWritingMode()) return point; // This is similar to LayoutBox::flipForWritingModeForChild. We have to @@ -3661,7 +3661,7 @@ IndentTextOrNot apply_text_indent) const { LayoutUnit left = offset_from_floats; - if (apply_text_indent == kIndentText && Style()->IsLeftToRightDirection()) + if (apply_text_indent == kIndentText && StyleRef().IsLeftToRightDirection()) left += TextIndentOffset(); return left; @@ -3672,7 +3672,7 @@ IndentTextOrNot apply_text_indent) const { LayoutUnit right = offset_from_floats; - if (apply_text_indent == kIndentText && !Style()->IsLeftToRightDirection()) + if (apply_text_indent == kIndentText && !StyleRef().IsLeftToRightDirection()) right -= TextIndentOffset(); return right; @@ -3693,7 +3693,7 @@ LayoutUnit float_logical_left; - if (child_box->Style()->Floating() == EFloat::kLeft) { + if (child_box->StyleRef().Floating() == EFloat::kLeft) { LayoutUnit height_remaining_left = LayoutUnit(1); LayoutUnit height_remaining_right = LayoutUnit(1); float_logical_left = LogicalLeftOffsetForPositioningFloat( @@ -3880,7 +3880,7 @@ logical_top_margin_edge = std::max(logical_top_margin_edge, - LowestFloatLogicalBottom(child.Style()->Clear())); + LowestFloatLogicalBottom(child.StyleRef().Clear())); bool is_paginated = View()->GetLayoutState()->IsPaginated(); if (is_paginated && !ChildrenInline()) { @@ -3981,7 +3981,7 @@ } LayoutUnit child_logical_left_margin = - Style()->IsLeftToRightDirection() ? margin_start : margin_end; + StyleRef().IsLeftToRightDirection() ? margin_start : margin_end; SetLogicalLeftForChild( child, float_logical_location.X() + child_logical_left_margin); SetLogicalLeftForFloat(floating_object, float_logical_location.X()); @@ -4431,10 +4431,10 @@ if (IsInline() || IsFloatingOrOutOfFlowPositioned() || HasOverflowClip() || IsFlexItemIncludingDeprecated() || IsTableCell() || IsTableCaption() || IsFieldset() || IsCustomItem() || IsDocumentElement() || IsGridItem() || - IsWritingModeRoot() || Style()->Display() == EDisplay::kFlowRoot || + IsWritingModeRoot() || StyleRef().Display() == EDisplay::kFlowRoot || ShouldApplyPaintContainment() || ShouldApplyLayoutContainment() || - Style()->SpecifiesColumns() || - Style()->GetColumnSpan() == EColumnSpan::kAll) { + StyleRef().SpecifiesColumns() || + StyleRef().GetColumnSpan() == EColumnSpan::kAll) { // The specs require this object to establish a new formatting context. return true; } @@ -4675,8 +4675,8 @@ if (!FirstRootBox()) return CreatePositionWithAffinity(0); - bool lines_are_flipped = Style()->IsFlippedLinesWritingMode(); - bool blocks_are_flipped = Style()->IsFlippedBlocksWritingMode(); + bool lines_are_flipped = StyleRef().IsFlippedLinesWritingMode(); + bool blocks_are_flipped = StyleRef().IsFlippedBlocksWritingMode(); // look for the closest line box in the root box which is at the passed-in y // coordinate
diff --git a/third_party/blink/renderer/core/layout/layout_block_flow.h b/third_party/blink/renderer/core/layout/layout_block_flow.h index ce749445..89d863fe 100644 --- a/third_party/blink/renderer/core/layout/layout_block_flow.h +++ b/third_party/blink/renderer/core/layout/layout_block_flow.h
@@ -143,7 +143,7 @@ LayoutUnit position, IndentTextOrNot indent_text, LayoutUnit logical_height = LayoutUnit()) const { - return Style()->IsLeftToRightDirection() + return StyleRef().IsLeftToRightDirection() ? LogicalLeftOffsetForLine(position, indent_text, logical_height) : LogicalWidth() - LogicalRightOffsetForLine( position, indent_text, logical_height); @@ -171,7 +171,7 @@ LayoutUnit StartOffsetForAvoidingFloats( LayoutUnit position, LayoutUnit logical_height = LayoutUnit()) const { - return Style()->IsLeftToRightDirection() + return StyleRef().IsLeftToRightDirection() ? LogicalLeftOffsetForAvoidingFloats(position, logical_height) : LogicalWidth() - LogicalRightOffsetForAvoidingFloats( position, logical_height); @@ -179,7 +179,7 @@ LayoutUnit EndOffsetForAvoidingFloats( LayoutUnit position, LayoutUnit logical_height = LayoutUnit()) const { - return !Style()->IsLeftToRightDirection() + return !StyleRef().IsLeftToRightDirection() ? LogicalLeftOffsetForAvoidingFloats(position, logical_height) : LogicalWidth() - LogicalRightOffsetForAvoidingFloats( position, logical_height); @@ -305,7 +305,7 @@ static bool ShouldSkipCreatingRunsForObject(LineLayoutItem obj) { return obj.IsFloating() || (obj.IsOutOfFlowPositioned() && - !obj.Style()->IsOriginalDisplayInlineType() && + !obj.StyleRef().IsOriginalDisplayInlineType() && !obj.Container().IsLayoutInline()); }
diff --git a/third_party/blink/renderer/core/layout/layout_block_flow_line.cc b/third_party/blink/renderer/core/layout/layout_block_flow_line.cc index 527f2e5..4697ac5 100644 --- a/third_party/blink/renderer/core/layout/layout_block_flow_line.cc +++ b/third_party/blink/renderer/core/layout/layout_block_flow_line.cc
@@ -101,7 +101,7 @@ CHECK_LE(opportunities_in_run, total_opportunities_); // Don't justify for white-space: pre. - if (r->line_layout_item_.Style()->WhiteSpace() != EWhiteSpace::kPre) { + if (r->line_layout_item_.StyleRef().WhiteSpace() != EWhiteSpace::kPre) { InlineTextBox* text_box = ToInlineTextBox(r->box_); CHECK(total_opportunities_); int expansion = ((available_logical_width - total_logical_width) * @@ -150,7 +150,7 @@ if (text.IsBR()) text_box->SetIsText(is_only_run || text.GetDocument().InNoQuirksMode()); text_box->SetDirOverride( - run.DirOverride(text.Style()->RtlOrdering() == EOrder::kVisual)); + run.DirOverride(text.StyleRef().RtlOrdering() == EOrder::kVisual)); if (run.has_hyphen_) text_box->SetHasHyphen(true); return text_box; @@ -291,10 +291,12 @@ for (BidiRun* r = bidi_runs.FirstRun(); r; r = r->Next()) { // Create a box for our object. bool is_only_run = (run_count == 1); - if (run_count == 2 && !r->line_layout_item_.IsListMarker()) - is_only_run = (!Style()->IsLeftToRightDirection() ? bidi_runs.LastRun() - : bidi_runs.FirstRun()) - ->line_layout_item_.IsListMarker(); + if (run_count == 2 && !r->line_layout_item_.IsListMarker()) { + is_only_run = + (!StyleRef().IsLeftToRightDirection() ? bidi_runs.LastRun() + : bidi_runs.FirstRun()) + ->line_layout_item_.IsListMarker(); + } if (line_info.IsEmpty()) continue; @@ -361,7 +363,7 @@ ETextAlign LayoutBlockFlow::TextAlignmentForLine( bool ends_with_soft_break) const { - return Style()->GetTextAlign(!ends_with_soft_break); + return StyleRef().GetTextAlign(!ends_with_soft_break); } static bool TextAlignmentNeedsTrailingSpace(ETextAlign text_align, @@ -482,10 +484,10 @@ } layout_ruby_run->GetOverhang( line_info.IsFirstLine(), - layout_ruby_run->Style()->IsLeftToRightDirection() ? previous_object - : next_object, - layout_ruby_run->Style()->IsLeftToRightDirection() ? next_object - : previous_object, + layout_ruby_run->StyleRef().IsLeftToRightDirection() ? previous_object + : next_object, + layout_ruby_run->StyleRef().IsLeftToRightDirection() ? next_object + : previous_object, start_overhang, end_overhang); SetMarginStartForChild(*layout_ruby_run, LayoutUnit(-start_overhang)); SetMarginEndForChild(*layout_ruby_run, LayoutUnit(-end_overhang)); @@ -582,7 +584,7 @@ run->Direction(), line_info.IsFirstLine()); if (i > 0 && word_length == 1 && layout_text.CharacterAt(word_measurement.start_offset) == ' ') - measured_width += layout_text.Style()->WordSpacing(); + measured_width += layout_text.StyleRef().WordSpacing(); } else { FloatRect word_glyph_bounds = word_measurement.glyph_bounds; word_glyph_bounds.Move(measured_width, 0); @@ -658,11 +660,11 @@ unsigned expansion_opportunity_count) { TextDirection direction; if (root_inline_box && - root_inline_box->GetLineLayoutItem().Style()->GetUnicodeBidi() == + root_inline_box->GetLineLayoutItem().StyleRef().GetUnicodeBidi() == UnicodeBidi::kPlaintext) direction = root_inline_box->Direction(); else - direction = Style()->Direction(); + direction = StyleRef().Direction(); // Armed with the total width of the line (without justification), // we now examine our text-align property in order to determine where to @@ -672,19 +674,19 @@ case ETextAlign::kLeft: case ETextAlign::kWebkitLeft: UpdateLogicalWidthForLeftAlignedBlock( - Style()->IsLeftToRightDirection(), trailing_space_run, logical_left, + StyleRef().IsLeftToRightDirection(), trailing_space_run, logical_left, total_logical_width, available_logical_width); break; case ETextAlign::kRight: case ETextAlign::kWebkitRight: UpdateLogicalWidthForRightAlignedBlock( - Style()->IsLeftToRightDirection(), trailing_space_run, logical_left, + StyleRef().IsLeftToRightDirection(), trailing_space_run, logical_left, total_logical_width, available_logical_width); break; case ETextAlign::kCenter: case ETextAlign::kWebkitCenter: UpdateLogicalWidthForCenterAlignedBlock( - Style()->IsLeftToRightDirection(), trailing_space_run, logical_left, + StyleRef().IsLeftToRightDirection(), trailing_space_run, logical_left, total_logical_width, available_logical_width); break; case ETextAlign::kJustify: @@ -699,24 +701,26 @@ } FALLTHROUGH; case ETextAlign::kStart: - if (direction == TextDirection::kLtr) + if (direction == TextDirection::kLtr) { UpdateLogicalWidthForLeftAlignedBlock( - Style()->IsLeftToRightDirection(), trailing_space_run, logical_left, - total_logical_width, available_logical_width); - else + StyleRef().IsLeftToRightDirection(), trailing_space_run, + logical_left, total_logical_width, available_logical_width); + } else { UpdateLogicalWidthForRightAlignedBlock( - Style()->IsLeftToRightDirection(), trailing_space_run, logical_left, - total_logical_width, available_logical_width); + StyleRef().IsLeftToRightDirection(), trailing_space_run, + logical_left, total_logical_width, available_logical_width); + } break; case ETextAlign::kEnd: - if (direction == TextDirection::kLtr) + if (direction == TextDirection::kLtr) { UpdateLogicalWidthForRightAlignedBlock( - Style()->IsLeftToRightDirection(), trailing_space_run, logical_left, - total_logical_width, available_logical_width); - else + StyleRef().IsLeftToRightDirection(), trailing_space_run, + logical_left, total_logical_width, available_logical_width); + } else { UpdateLogicalWidthForLeftAlignedBlock( - Style()->IsLeftToRightDirection(), trailing_space_run, logical_left, - total_logical_width, available_logical_width); + StyleRef().IsLeftToRightDirection(), trailing_space_run, + logical_left, total_logical_width, available_logical_width); + } break; } if (ShouldPlaceBlockDirectionScrollbarOnLogicalLeft()) @@ -803,7 +807,7 @@ ExpansionOpportunities expansions; LayoutObject* previous_object = nullptr; ETextAlign text_align = line_info.GetTextAlign(); - TextJustify text_justify = Style()->GetTextJustify(); + TextJustify text_justify = StyleRef().GetTextJustify(); BidiRun* r = first_run; size_t word_measurements_index = 0; @@ -1255,7 +1259,7 @@ if (!pagination_strut_from_deleted_line) { for (const auto& positioned_object : line_breaker.PositionedObjects()) { - if (positioned_object.Style()->IsOriginalDisplayInlineType()) { + if (positioned_object.StyleRef().IsOriginalDisplayInlineType()) { // Auto-positioned "inline" out-of-flow objects have already been // positioned, but if we're paginated, or just ceased to be so, we // need to update their position now, since the line they "belong" to @@ -1295,7 +1299,7 @@ // widows then we need to ignore the possibility of having a new widows // situation. Otherwise, we risk leaving empty containers which is against the // block fragmentation principles. - if (paginated && Style()->Widows() > 1 && !DidBreakAtLineToAvoidWidow()) { + if (paginated && StyleRef().Widows() > 1 && !DidBreakAtLineToAvoidWidow()) { // Check the line boxes to make sure we didn't create unacceptable widows. // However, we'll prioritize orphans - so nothing we do here should create // a new orphan. @@ -1317,11 +1321,11 @@ line_box == first_line_in_block) return; - if (num_lines_hanging < Style()->Widows()) { + if (num_lines_hanging < StyleRef().Widows()) { // We have detected a widow. Now we need to work out how many // lines there are on the previous page, and how many we need // to steal. - int num_lines_needed = Style()->Widows() - num_lines_hanging; + int num_lines_needed = StyleRef().Widows() - num_lines_hanging; RootInlineBox* current_first_line_of_new_page = line_box; // Count the number of lines in the previous page. @@ -1339,7 +1343,7 @@ // about orphans, but given the specification says the initial orphan // value is non-zero, this is ok. The author is always free to set orphans // explicitly as well. - int orphans = Style()->Orphans(); + int orphans = StyleRef().Orphans(); int num_lines_available = num_lines_in_previous_page - orphans; if (num_lines_available <= 0) return; @@ -1531,10 +1535,10 @@ } // FIXME: This ignores first-line. - const Font& font = text->Style()->GetFont(); + const Font& font = text->StyleRef().GetFont(); TextRun run = ConstructTextRun(font, &trailing_whitespace_char, 1, text->StyleRef(), - text->Style()->Direction()); + text->StyleRef().Direction()); float space_width = font.Width(run); inline_max -= LayoutUnit::FromFloatCeil( space_width + font.GetFontDescription().WordSpacing()); @@ -1623,8 +1627,8 @@ bool should_break_line_after_text = false; while (LayoutObject* child = child_iterator.Next()) { auto_wrap = child->IsAtomicInlineLevel() - ? child->Parent()->Style()->AutoWrap() - : child->Style()->AutoWrap(); + ? child->Parent()->StyleRef().AutoWrap() + : child->StyleRef().AutoWrap(); if (!child->IsBR()) { // Step One: determine whether or not we need to go ahead and @@ -1915,7 +1919,7 @@ object_to_check = parent; } return object_to_check->HasOverflowClip() && - object_to_check->Style()->TextOverflow() != ETextOverflow::kClip; + object_to_check->StyleRef().TextOverflow() != ETextOverflow::kClip; } DISABLE_CFI_PERF @@ -1997,7 +2001,7 @@ if (LastRootBox()) { LayoutUnit lowest_allowed_position = std::max(LastRootBox()->LineBottom(), LogicalHeight() + PaddingAfter()); - if (!Style()->IsFlippedLinesWritingMode()) + if (!StyleRef().IsFlippedLinesWritingMode()) last_line_annotations_adjustment = LastRootBox() ->ComputeUnderAnnotationAdjustment(lowest_allowed_position) @@ -2144,11 +2148,11 @@ resolver.SetPosition(iter, NumberOfIsolateAncestors(iter)); resolver.SetStatus(last->LineBreakBidiStatus()); } else { - TextDirection direction = Style()->Direction(); - if (Style()->GetUnicodeBidi() == UnicodeBidi::kPlaintext) + TextDirection direction = StyleRef().Direction(); + if (StyleRef().GetUnicodeBidi() == UnicodeBidi::kPlaintext) direction = DeterminePlaintextDirectionality(LineLayoutItem(this)); resolver.SetStatus( - BidiStatus(direction, IsOverride(Style()->GetUnicodeBidi()))); + BidiStatus(direction, IsOverride(StyleRef().GetUnicodeBidi()))); InlineIterator iter = InlineIterator( LineLayoutBlockFlow(this), BidiFirstSkippingEmptyInlines(LineLayoutBlockFlow(this), @@ -2165,11 +2169,11 @@ // difficulty. if (!curr->EndsWithBreak()) return false; - InlineBox* last_box = Style()->IsLeftToRightDirection() + InlineBox* last_box = StyleRef().IsLeftToRightDirection() ? curr->LastLeafChild() : curr->FirstLeafChild(); return last_box && last_box->GetLineLayoutItem().IsBR() && - last_box->GetLineLayoutItem().Style()->Clear() != EClear::kNone; + last_box->GetLineLayoutItem().StyleRef().Clear() != EClear::kNone; } void LayoutBlockFlow::DetermineEndPosition(LineLayoutState& layout_state, @@ -2316,7 +2320,7 @@ // FIXME: Need to find another way to do this, since scrollbars could show // when we don't want them to. if (HasOverflowClip() && !end_padding && GetNode() && - IsRootEditableElement(*GetNode()) && Style()->IsLeftToRightDirection()) + IsRootEditableElement(*GetNode()) && StyleRef().IsLeftToRightDirection()) end_padding = LayoutUnit(1); for (RootInlineBox* curr = FirstRootBox(); curr; curr = curr->NextRootBox()) { AddLayoutOverflow(curr->PaddedLayoutOverflowRect(end_padding)); @@ -2351,7 +2355,7 @@ } void LayoutBlockFlow::DeleteEllipsisLineBoxes() { - ETextAlign text_align = Style()->GetTextAlign(); + ETextAlign text_align = StyleRef().GetTextAlign(); IndentTextOrNot indent_text = kIndentText; for (RootInlineBox* curr = FirstRootBox(); curr; curr = curr->NextRootBox()) { if (curr->HasEllipsisBox()) { @@ -2377,7 +2381,7 @@ } void LayoutBlockFlow::ClearTruncationOnAtomicInlines(RootInlineBox* root) { - bool ltr = Style()->IsLeftToRightDirection(); + bool ltr = StyleRef().IsLeftToRightDirection(); InlineBox* first_child = ltr ? root->LastChild() : root->FirstChild(); for (InlineBox* box = first_child; box; box = ltr ? box->PrevOnLine() : box->NextOnLine()) { @@ -2394,7 +2398,7 @@ void LayoutBlockFlow::CheckLinesForTextOverflow() { // Determine the width of the ellipsis using the current font. - const Font& font = Style()->GetFont(); + const Font& font = StyleRef().GetFont(); const size_t kFullStopStringLength = 3; const UChar kFullStopString[] = {kFullstopCharacter, kFullstopCharacter, @@ -2447,8 +2451,8 @@ // For RTL, we use the left edge of the padding box and check the left edge of // the line box to see if it is less Include the scrollbar for overflow // blocks, which means we want to use "contentWidth()". - bool ltr = Style()->IsLeftToRightDirection(); - ETextAlign text_align = Style()->GetTextAlign(); + bool ltr = StyleRef().IsLeftToRightDirection(); + ETextAlign text_align = StyleRef().GetTextAlign(); IndentTextOrNot indent_text = kIndentText; for (RootInlineBox* curr = FirstRootBox(); curr; curr = curr->NextRootBox()) { LayoutUnit block_right_edge = @@ -2503,7 +2507,7 @@ const AtomicString& selected_ellipsis_str, InlineBox* box_truncation_starts_at) { bool found_box = box_truncation_starts_at ? true : false; - bool ltr = Style()->IsLeftToRightDirection(); + bool ltr = StyleRef().IsLeftToRightDirection(); LayoutUnit logical_left_offset = block_left_edge; // Each atomic inline block (e.g. a <span>) inside a blockflow is managed by @@ -2603,17 +2607,17 @@ LayoutUnit LayoutBlockFlow::StartAlignedOffsetForLine( LayoutUnit position, IndentTextOrNot indent_text) { - ETextAlign text_align = Style()->GetTextAlign(); + ETextAlign text_align = StyleRef().GetTextAlign(); bool apply_indent_text; switch (text_align) { // FIXME: Handle TAEND here case ETextAlign::kLeft: case ETextAlign::kWebkitLeft: - apply_indent_text = Style()->IsLeftToRightDirection(); + apply_indent_text = StyleRef().IsLeftToRightDirection(); break; case ETextAlign::kRight: case ETextAlign::kWebkitRight: - apply_indent_text = !Style()->IsLeftToRightDirection(); + apply_indent_text = !StyleRef().IsLeftToRightDirection(); break; case ETextAlign::kStart: apply_indent_text = true; @@ -2637,7 +2641,7 @@ total_logical_width, available_logical_width, 0); - if (!Style()->IsLeftToRightDirection()) + if (!StyleRef().IsLeftToRightDirection()) return LogicalWidth() - logical_left; return logical_left; }
diff --git a/third_party/blink/renderer/core/layout/layout_box.cc b/third_party/blink/renderer/core/layout/layout_box.cc index 5815cfbe..9251606 100644 --- a/third_party/blink/renderer/core/layout/layout_box.cc +++ b/third_party/blink/renderer/core/layout/layout_box.cc
@@ -115,9 +115,9 @@ // since position:static elements that are not flex-items get their z-index // coerced to auto. if (IsPositioned() || CreatesGroup() || HasTransformRelatedProperty() || - HasHiddenBackface() || HasReflection() || Style()->SpecifiesColumns() || - Style()->IsStackingContext() || - Style()->ShouldCompositeForCurrentAnimations() || + HasHiddenBackface() || HasReflection() || StyleRef().SpecifiesColumns() || + StyleRef().IsStackingContext() || + StyleRef().ShouldCompositeForCurrentAnimations() || IsEffectiveRootScroller()) return kNormalPaintLayer; @@ -428,17 +428,17 @@ if (!old_style || !Parent() || !Parent()->IsLayoutGrid()) return; - if (old_style->GridColumnStart() == Style()->GridColumnStart() && - old_style->GridColumnEnd() == Style()->GridColumnEnd() && - old_style->GridRowStart() == Style()->GridRowStart() && - old_style->GridRowEnd() == Style()->GridRowEnd() && - old_style->Order() == Style()->Order() && - old_style->HasOutOfFlowPosition() == Style()->HasOutOfFlowPosition()) + if (old_style->GridColumnStart() == StyleRef().GridColumnStart() && + old_style->GridColumnEnd() == StyleRef().GridColumnEnd() && + old_style->GridRowStart() == StyleRef().GridRowStart() && + old_style->GridRowEnd() == StyleRef().GridRowEnd() && + old_style->Order() == StyleRef().Order() && + old_style->HasOutOfFlowPosition() == StyleRef().HasOutOfFlowPosition()) return; // Positioned items don't participate on the layout of the grid, // so we don't need to mark the grid as dirty if they change positions. - if (old_style->HasOutOfFlowPosition() && Style()->HasOutOfFlowPosition()) + if (old_style->HasOutOfFlowPosition() && StyleRef().HasOutOfFlowPosition()) return; // It should be possible to not dirty the grid in some cases (like moving an @@ -559,7 +559,7 @@ return GetScrollableArea()->ScrollWidth(); // For objects with visible overflow, this matches IE. // FIXME: Need to work right with writing modes. - if (Style()->IsLeftToRightDirection()) + if (StyleRef().IsLeftToRightDirection()) return std::max(ClientWidth(), LayoutOverflowRect().MaxX() - BorderLeft()); return ClientWidth() - std::min(LayoutUnit(), LayoutOverflowRect().X() - BorderLeft()); @@ -704,7 +704,7 @@ // If we are fixed-position and stick to the viewport, it is useless to // scroll the parent. - if (Style()->GetPosition() == EPosition::kFixed && Container() == View()) + if (StyleRef().GetPosition() == EPosition::kFixed && Container() == View()) return absolute_rect_for_parent; if (parent_box) { @@ -764,7 +764,7 @@ if (!overflow_ || HasOverflowClip()) return LogicalHeight(); LayoutRect overflow = LayoutOverflowRect(); - if (Style()->IsHorizontalWritingMode()) + if (StyleRef().IsHorizontalWritingMode()) return overflow.MaxY(); return overflow.MaxX(); } @@ -878,7 +878,7 @@ LayoutRect LayoutBox::BackgroundRect(BackgroundRectType rect_type) const { EFillBox background_box = EFillBox::kText; // Find the largest background rect of the given opaqueness. - if (const FillLayer* current = &(Style()->BackgroundLayers())) { + if (const FillLayer* current = &(StyleRef().BackgroundLayers())) { do { const FillLayer* cur = current; current = current->Next(); @@ -955,7 +955,7 @@ // hasOverflowClip(). However, they do "implicitly" clip their contents, so // we want to allow resizing them also. return (HasOverflowClip() || IsLayoutIFrame()) && - Style()->Resize() != EResize::kNone; + StyleRef().Resize() != EResize::kNone; } void LayoutBox::AddLayerHitTestRects( @@ -978,14 +978,14 @@ } int LayoutBox::VerticalScrollbarWidth() const { - if (!HasOverflowClip() || Style()->OverflowY() == EOverflow::kOverlay) + if (!HasOverflowClip() || StyleRef().OverflowY() == EOverflow::kOverlay) return 0; return GetScrollableArea()->VerticalScrollbarWidth(); } int LayoutBox::HorizontalScrollbarHeight() const { - if (!HasOverflowClip() || Style()->OverflowX() == EOverflow::kOverlay) + if (!HasOverflowClip() || StyleRef().OverflowX() == EOverflow::kOverlay) return 0; return GetScrollableArea()->HorizontalScrollbarHeight(); @@ -1144,8 +1144,8 @@ } bool LayoutBox::NeedsPreferredWidthsRecalculation() const { - return Style()->PaddingStart().IsPercentOrCalc() || - Style()->PaddingEnd().IsPercentOrCalc(); + return StyleRef().PaddingStart().IsPercentOrCalc() || + StyleRef().PaddingEnd().IsPercentOrCalc(); } IntSize LayoutBox::OriginAdjustmentForScrollbars() const { @@ -1188,7 +1188,7 @@ const LayoutObject* ancestor, VisualRectFlags visual_rect_flags, TransformState& transform_state) const { - bool container_preserve_3d = container_object->Style()->Preserves3D(); + bool container_preserve_3d = container_object->StyleRef().Preserves3D(); TransformState::TransformAccumulation accumulation = container_preserve_3d ? TransformState::kAccumulateTransform @@ -1247,7 +1247,7 @@ // d) Perspective applied by container. if (container_object && container_object->HasLayer() && - container_object->Style()->HasPerspective()) { + container_object->StyleRef().HasPerspective()) { // Perspective on the container affects us, so we have to factor it in here. DCHECK(container_object->HasLayer()); FloatPoint perspective_origin = @@ -1255,7 +1255,7 @@ TransformationMatrix perspective_matrix; perspective_matrix.ApplyPerspective( - container_object->Style()->Perspective()); + container_object->StyleRef().Perspective()); perspective_matrix.ApplyTransformOrigin(perspective_origin.X(), perspective_origin.Y(), 0); @@ -1477,7 +1477,7 @@ float width) const { LayoutUnit borders_plus_padding = CollapsedBorderAndCSSPaddingLogicalWidth(); LayoutUnit result(width); - if (Style()->BoxSizing() == EBoxSizing::kContentBox) + if (StyleRef().BoxSizing() == EBoxSizing::kContentBox) return result + borders_plus_padding; return std::max(result, borders_plus_padding); } @@ -1486,7 +1486,7 @@ float height) const { LayoutUnit borders_plus_padding = CollapsedBorderAndCSSPaddingLogicalHeight(); LayoutUnit result(height); - if (Style()->BoxSizing() == EBoxSizing::kContentBox) + if (StyleRef().BoxSizing() == EBoxSizing::kContentBox) return result + borders_plus_padding; return std::max(result, borders_plus_padding); } @@ -1494,7 +1494,7 @@ LayoutUnit LayoutBox::AdjustContentBoxLogicalWidthForBoxSizing( float width) const { LayoutUnit result(width); - if (Style()->BoxSizing() == EBoxSizing::kBorderBox) + if (StyleRef().BoxSizing() == EBoxSizing::kBorderBox) result -= CollapsedBorderAndCSSPaddingLogicalWidth(); return std::max(LayoutUnit(), result); } @@ -1502,7 +1502,7 @@ LayoutUnit LayoutBox::AdjustContentBoxLogicalHeightForBoxSizing( float height) const { LayoutUnit result(height); - if (Style()->BoxSizing() == EBoxSizing::kBorderBox) + if (StyleRef().BoxSizing() == EBoxSizing::kBorderBox) result -= CollapsedBorderAndCSSPaddingLogicalHeight(); return std::max(LayoutUnit(), result); } @@ -1552,10 +1552,10 @@ adjusted_location, kExcludeOverlayScrollbarSizeForHitTesting))) { skip_children = true; } - if (!skip_children && Style()->HasBorderRadius()) { + if (!skip_children && StyleRef().HasBorderRadius()) { LayoutRect bounds_rect(adjusted_location, Size()); skip_children = !location_in_container.Intersects( - Style()->GetRoundedInnerBorderFor(bounds_rect)); + StyleRef().GetRoundedInnerBorderFor(bounds_rect)); } } @@ -1564,7 +1564,7 @@ return true; } - if (Style()->HasBorderRadius() && + if (StyleRef().HasBorderRadius() && HitTestClippedOutByBorder(location_in_container, adjusted_location)) return false; @@ -1608,7 +1608,7 @@ LayoutRect border_rect = BorderBoxRect(); border_rect.MoveBy(border_box_location); return !location_in_container.Intersects( - Style()->GetRoundedBorderFor(border_rect)); + StyleRef().GetRoundedBorderFor(border_rect)); } void LayoutBox::Paint(const PaintInfo& paint_info) const { @@ -1636,8 +1636,8 @@ return true; } - if (!Style()->BackgroundLayers().GetImage() || - Style()->BackgroundLayers().Next()) { + if (!StyleRef().BackgroundLayers().GetImage() || + StyleRef().BackgroundLayers().Next()) { painted_extent = background_rect; return true; } @@ -1647,7 +1647,7 @@ // and outside of the paint phase. Potentially returning different results at // different phases. crbug.com/732934 geometry.Calculate(nullptr, PaintPhase::kBlockBackground, - kGlobalPaintNormalPhase, Style()->BackgroundLayers(), + kGlobalPaintNormalPhase, StyleRef().BackgroundLayers(), background_rect); if (geometry.HasNonLocalGeometry()) return false; @@ -1664,16 +1664,16 @@ // We cannot be sure if theme paints the background opaque. // In this case it is safe to not assume opaqueness. // FIXME: May be ask theme if it paints opaque. - if (Style()->HasAppearance()) + if (StyleRef().HasAppearance()) return false; // FIXME: Check the opaqueness of background images. // FIXME: Use rounded rect if border radius is present. - if (Style()->HasBorderRadius()) + if (StyleRef().HasBorderRadius()) return false; if (HasClipPath()) return false; - if (Style()->HasBlendMode()) + if (StyleRef().HasBlendMode()) return false; return BackgroundRect(kBackgroundKnownOpaqueRect).Contains(local_rect); } @@ -1755,7 +1755,7 @@ if (IsLayoutView()) return false; // FIXME: box-shadow is painted while background painting. - if (Style()->BoxShadow()) + if (StyleRef().BoxShadow()) return false; LayoutRect background_rect; if (!GetBackgroundPaintedExtent(background_rect)) @@ -1822,7 +1822,7 @@ } } - ShapeValue* shape_outside_value = Style()->ShapeOutside(); + ShapeValue* shape_outside_value = StyleRef().ShapeOutside(); if (!GetFrameView()->IsInPerformLayout() && IsFloating() && shape_outside_value && shape_outside_value->GetImage() && shape_outside_value->GetImage()->Data() == image) { @@ -1966,26 +1966,28 @@ LayoutRect clip_rect = LayoutRect(border_box_rect.Location() + location, border_box_rect.Size()); - if (!Style()->ClipLeft().IsAuto()) { - LayoutUnit c = ValueForLength(Style()->ClipLeft(), border_box_rect.Width()); + if (!StyleRef().ClipLeft().IsAuto()) { + LayoutUnit c = + ValueForLength(StyleRef().ClipLeft(), border_box_rect.Width()); clip_rect.Move(c, LayoutUnit()); clip_rect.Contract(c, LayoutUnit()); } - if (!Style()->ClipRight().IsAuto()) + if (!StyleRef().ClipRight().IsAuto()) clip_rect.Contract( - Size().Width() - ValueForLength(Style()->ClipRight(), Size().Width()), + Size().Width() - ValueForLength(StyleRef().ClipRight(), Size().Width()), LayoutUnit()); - if (!Style()->ClipTop().IsAuto()) { - LayoutUnit c = ValueForLength(Style()->ClipTop(), border_box_rect.Height()); + if (!StyleRef().ClipTop().IsAuto()) { + LayoutUnit c = + ValueForLength(StyleRef().ClipTop(), border_box_rect.Height()); clip_rect.Move(LayoutUnit(), c); clip_rect.Contract(LayoutUnit(), c); } - if (!Style()->ClipBottom().IsAuto()) { + if (!StyleRef().ClipBottom().IsAuto()) { clip_rect.Contract(LayoutUnit(), - Size().Height() - ValueForLength(Style()->ClipBottom(), + Size().Height() - ValueForLength(StyleRef().ClipBottom(), Size().Height())); } @@ -2123,7 +2125,7 @@ void LayoutBox::MapLocalToAncestor(const LayoutBoxModelObject* ancestor, TransformState& transform_state, MapCoordinatesFlags mode) const { - bool is_fixed_pos = Style()->GetPosition() == EPosition::kFixed; + bool is_fixed_pos = StyleRef().GetPosition() == EPosition::kFixed; // If this box has a transform or contains paint, it acts as a fixed position // container for fixed descendants, and may itself also be fixed position. So @@ -2142,7 +2144,7 @@ if (this == ancestor) return; - bool is_fixed_pos = Style()->GetPosition() == EPosition::kFixed; + bool is_fixed_pos = StyleRef().GetPosition() == EPosition::kFixed; // If this box has a transform or contains paint, it acts as a fixed position // container for fixed descendants, and may itself also be fixed position. So @@ -2170,7 +2172,7 @@ offset += OffsetFromScrollableContainer(o, ignore_scroll_offset); if (IsOutOfFlowPositioned() && o->IsLayoutInline() && - o->CanContainOutOfFlowPositionedElement(Style()->GetPosition())) { + o->CanContainOutOfFlowPositionedElement(StyleRef().GetPosition())) { offset += ToLayoutInline(o)->OffsetForInFlowPositionedInline(*this); } @@ -2210,7 +2212,7 @@ void LayoutBox::PositionLineBox(InlineBox* box) { if (IsOutOfFlowPositioned()) { // Cache the x position only if we were an INLINE type originally. - bool originally_inline = Style()->IsOriginalDisplayInlineType(); + bool originally_inline = StyleRef().IsOriginalDisplayInlineType(); if (originally_inline) { // The value is cached in the xPos of the box. We only need this value if // our object was inline originally, since otherwise it would have ended @@ -2242,7 +2244,7 @@ DCHECK(IsOutOfFlowPositioned()); DCHECK(Container()->IsLayoutInline()); DCHECK(Container()->CanContainOutOfFlowPositionedElement( - Style()->GetPosition())); + StyleRef().GetPosition())); // If this object is inside a relative positioned inline and its inline // position is an explicit offset from the edge of its container then it will // need to move if its inline container has changed width. We do not track if @@ -2250,7 +2252,7 @@ // inside it, so it probably has - mark our object for layout so that it can // move to the new offset created by the new width. if (!NormalChildNeedsLayout() && - !Style()->HasStaticInlinePosition(is_horizontal)) + !StyleRef().HasStaticInlinePosition(is_horizontal)) SetChildNeedsLayout(kMarkOnlyThis); } @@ -2354,7 +2356,7 @@ } EBreakBetween LayoutBox::BreakAfter() const { - EBreakBetween break_value = Style()->BreakAfter(); + EBreakBetween break_value = StyleRef().BreakAfter(); if (break_value == EBreakBetween::kAuto || IsBreakBetweenControllable(break_value)) return break_value; @@ -2362,7 +2364,7 @@ } EBreakBetween LayoutBox::BreakBefore() const { - EBreakBetween break_value = Style()->BreakBefore(); + EBreakBetween break_value = StyleRef().BreakBefore(); if (break_value == EBreakBetween::kAuto || IsBreakBetweenControllable(break_value)) return break_value; @@ -2370,7 +2372,7 @@ } EBreakInside LayoutBox::BreakInside() const { - EBreakInside break_value = Style()->BreakInside(); + EBreakInside break_value = StyleRef().BreakInside(); if (break_value == EBreakInside::kAuto || IsBreakInsideControllable(break_value)) return break_value; @@ -2522,7 +2524,7 @@ return false; if (skip_info.AncestorSkipped()) { - bool preserve3D = container->Style()->Preserves3D(); + bool preserve3D = container->StyleRef().Preserves3D(); TransformState::TransformAccumulation accumulation = preserve3D ? TransformState::kAccumulateTransform : TransformState::kFlattenTransform; @@ -2615,7 +2617,7 @@ Node* parent_node = layout_object->GeneratingNode(); DCHECK(parent_node); DCHECK(IsHTMLOListElement(parent_node) || IsHTMLUListElement(parent_node)); - DCHECK_NE(layout_object->Style()->TextAutosizingMultiplier(), 1); + DCHECK_NE(layout_object->StyleRef().TextAutosizingMultiplier(), 1); #endif float max_width = 0; for (LayoutObject* child = layout_object->SlowFirstChild(); child; @@ -2666,8 +2668,9 @@ // https://bugs.webkit.org/show_bug.cgi?id=46418 bool in_vertical_box = Parent()->IsDeprecatedFlexibleBox() && - (Parent()->Style()->BoxOrient() == EBoxOrient::kVertical); - bool stretching = (Parent()->Style()->BoxAlign() == EBoxAlignment::kStretch); + (Parent()->StyleRef().BoxOrient() == EBoxOrient::kVertical); + bool stretching = + (Parent()->StyleRef().BoxAlign() == EBoxAlignment::kStretch); // TODO (lajava): Stretching is the only reason why we don't want the box to // be treated as a replaced element, so we could perhaps refactor all this // logic, not only for flex and grid since alignment is intended to be applied @@ -2725,7 +2728,7 @@ ComputeMarginsForDirection( kInlineDirection, cb, container_logical_width, computed_values.extent_, computed_values.margins_.start_, computed_values.margins_.end_, - Style()->MarginStart(), Style()->MarginEnd()); + StyleRef().MarginStart(), StyleRef().MarginEnd()); if (!has_perpendicular_containing_block && container_logical_width && container_logical_width != @@ -2735,8 +2738,8 @@ !cb->IsLayoutGrid()) { LayoutUnit new_margin_total = container_logical_width - computed_values.extent_; - bool has_inverted_direction = cb->Style()->IsLeftToRightDirection() != - Style()->IsLeftToRightDirection(); + bool has_inverted_direction = cb->StyleRef().IsLeftToRightDirection() != + StyleRef().IsLeftToRightDirection(); if (has_inverted_direction) { computed_values.margins_.start_ = new_margin_total - computed_values.margins_.end_; @@ -2756,8 +2759,8 @@ const float adjusted_margin = (1 - 1.0 / style_to_use.TextAutosizingMultiplier()) * GetMaxWidthListMarker(this); - bool has_inverted_direction = cb->Style()->IsLeftToRightDirection() != - Style()->IsLeftToRightDirection(); + bool has_inverted_direction = cb->StyleRef().IsLeftToRightDirection() != + StyleRef().IsLeftToRightDirection(); if (has_inverted_direction) computed_values.margins_.end_ += adjusted_margin; else @@ -2784,9 +2787,9 @@ LayoutUnit available_size_for_resolving_margin = isOrthogonalElement ? ContainingBlockLogicalWidthForContent() : available_logical_width; - margin_start = MinimumValueForLength(Style()->MarginStart(), + margin_start = MinimumValueForLength(StyleRef().MarginStart(), available_size_for_resolving_margin); - margin_end = MinimumValueForLength(Style()->MarginEnd(), + margin_end = MinimumValueForLength(StyleRef().MarginEnd(), available_size_for_resolving_margin); LayoutUnit available = available_logical_width - margin_start - margin_end; available = std::max(available, LayoutUnit()); @@ -2892,15 +2895,15 @@ bool LayoutBox::IsStretchingColumnFlexItem() const { LayoutObject* parent = Parent(); if (parent->IsDeprecatedFlexibleBox() && - parent->Style()->BoxOrient() == EBoxOrient::kVertical && - parent->Style()->BoxAlign() == EBoxAlignment::kStretch) + parent->StyleRef().BoxOrient() == EBoxOrient::kVertical && + parent->StyleRef().BoxAlign() == EBoxAlignment::kStretch) return true; // We don't stretch multiline flexboxes because they need to apply line // spacing (align-content) first. if (parent->IsFlexibleBox() && - parent->Style()->FlexWrap() == EFlexWrap::kNowrap && - parent->Style()->IsColumnFlexDirection() && + parent->StyleRef().FlexWrap() == EFlexWrap::kNowrap && + parent->StyleRef().IsColumnFlexDirection() && ColumnFlexItemHasStretchAlignment()) return true; return false; @@ -2948,8 +2951,8 @@ if (Parent()->IsFlexibleBox()) { // For multiline columns, we need to apply align-content first, so we can't // stretch now. - if (!Parent()->Style()->IsColumnFlexDirection() || - Parent()->Style()->FlexWrap() != EFlexWrap::kNowrap) + if (!Parent()->StyleRef().IsColumnFlexDirection() || + Parent()->StyleRef().FlexWrap() != EFlexWrap::kNowrap) return true; if (!ColumnFlexItemHasStretchAlignment()) return true; @@ -2961,8 +2964,8 @@ // FIXME: Think about writing-mode here. // https://bugs.webkit.org/show_bug.cgi?id=46473 if (Parent()->IsDeprecatedFlexibleBox() && - (Parent()->Style()->BoxOrient() == EBoxOrient::kHorizontal || - Parent()->Style()->BoxAlign() != EBoxAlignment::kStretch)) + (Parent()->StyleRef().BoxOrient() == EBoxOrient::kHorizontal || + Parent()->StyleRef().BoxAlign() != EBoxAlignment::kStretch)) return true; // Button, input, select, textarea, and legend treat width value of 'auto' as @@ -3043,7 +3046,7 @@ // width of the containing block, then any 'auto' values for 'margin-left' or // 'margin-right' are, for the following rules, treated as zero. LayoutUnit margin_box_width = - child_width + (!Style()->Width().IsAuto() + child_width + (!StyleRef().Width().IsAuto() ? margin_start_width + margin_end_width : LayoutUnit()); @@ -3119,8 +3122,8 @@ static inline Length HeightForDocumentElement(const Document& document) { return document.documentElement() ->GetLayoutObject() - ->Style() - ->LogicalHeight(); + ->StyleRef() + .LogicalHeight(); } void LayoutBox::ComputeLogicalHeight( @@ -3169,8 +3172,8 @@ ComputeMarginsForDirection( flow_direction, cb, ContainingBlockLogicalWidthForContent(), computed_values.extent_, computed_values.margins_.before_, - computed_values.margins_.after_, Style()->MarginBefore(), - Style()->MarginAfter()); + computed_values.margins_.after_, StyleRef().MarginBefore(), + StyleRef().MarginAfter()); return; } @@ -3178,8 +3181,9 @@ // https://bugs.webkit.org/show_bug.cgi?id=46418 bool in_horizontal_box = Parent()->IsDeprecatedFlexibleBox() && - Parent()->Style()->BoxOrient() == EBoxOrient::kHorizontal; - bool stretching = Parent()->Style()->BoxAlign() == EBoxAlignment::kStretch; + Parent()->StyleRef().BoxOrient() == EBoxOrient::kHorizontal; + bool stretching = + Parent()->StyleRef().BoxAlign() == EBoxAlignment::kStretch; bool treat_as_replaced = ShouldComputeSizeAsReplaced() && (!in_horizontal_box || !stretching); bool check_min_max_height = false; @@ -3193,7 +3197,7 @@ ComputeReplacedLogicalHeight() + BorderAndPaddingLogicalHeight(), kFixed); } else { - h = Style()->LogicalHeight(); + h = StyleRef().LogicalHeight(); check_min_max_height = true; } @@ -3211,7 +3215,7 @@ LayoutUnit height_result; if (check_min_max_height) { height_result = ComputeLogicalHeightUsing( - kMainOrPreferredSize, Style()->LogicalHeight(), + kMainOrPreferredSize, StyleRef().LogicalHeight(), computed_values.extent_ - BorderAndPaddingLogicalHeight()); if (height_result == -1) height_result = computed_values.extent_; @@ -3227,8 +3231,8 @@ ComputeMarginsForDirection( flow_direction, cb, ContainingBlockLogicalWidthForContent(), computed_values.extent_, computed_values.margins_.before_, - computed_values.margins_.after_, Style()->MarginBefore(), - Style()->MarginAfter()); + computed_values.margins_.after_, StyleRef().MarginBefore(), + StyleRef().MarginAfter()); } // WinIE quirk: The <html> block always fills the entire canvas in quirks @@ -3357,7 +3361,7 @@ bool LayoutBox::StretchesToViewportInQuirksMode() const { if (!IsDocumentElement() && !IsBody()) return false; - return Style()->LogicalHeight().IsAuto() && + return StyleRef().LogicalHeight().IsAuto() && !IsFloatingOrOutOfFlowPositioned() && !IsInline() && !FlowThreadContainingBlock(); } @@ -3387,7 +3391,7 @@ return GetDocument().InQuirksMode() && !containing_block->IsTableCell() && !containing_block->IsOutOfFlowPositioned() && !containing_block->IsLayoutGrid() && - containing_block->Style()->LogicalHeight().IsAuto(); + containing_block->StyleRef().LogicalHeight().IsAuto(); } LayoutUnit LayoutBox::ComputePercentageLogicalHeight( @@ -3429,11 +3433,11 @@ // height if they have overflow set to visible or hidden or if // they are replaced elements, and a 0px height if they have not. LayoutTableCell* cell = ToLayoutTableCell(cb); - if (Style()->OverflowY() != EOverflow::kVisible && - Style()->OverflowY() != EOverflow::kHidden && + if (StyleRef().OverflowY() != EOverflow::kVisible && + StyleRef().OverflowY() != EOverflow::kHidden && !ShouldBeConsideredAsReplaced() && - (!cell->Style()->LogicalHeight().IsAuto() || - !cell->Table()->Style()->LogicalHeight().IsAuto())) + (!cell->StyleRef().LogicalHeight().IsAuto() || + !cell->Table()->StyleRef().LogicalHeight().IsAuto())) return LayoutUnit(); return LayoutUnit(-1); } @@ -3464,7 +3468,7 @@ IsTable() || (cb->IsTableCell() && !skipped_auto_height_containing_block && cb->HasOverrideLogicalHeight() && - Style()->BoxSizing() == EBoxSizing::kContentBox); + StyleRef().BoxSizing() == EBoxSizing::kContentBox); if (subtract_border_and_padding) { result -= BorderAndPaddingLogicalHeight(); return std::max(LayoutUnit(), result); @@ -3476,7 +3480,7 @@ ShouldComputePreferred should_compute_preferred) const { return ComputeReplacedLogicalWidthRespectingMinMaxWidth( ComputeReplacedLogicalWidthUsing(kMainOrPreferredSize, - Style()->LogicalWidth()), + StyleRef().LogicalWidth()), should_compute_preferred); } @@ -3485,17 +3489,17 @@ ShouldComputePreferred should_compute_preferred) const { LayoutUnit min_logical_width = (should_compute_preferred == kComputePreferred && - Style()->LogicalMinWidth().IsPercentOrCalc()) + StyleRef().LogicalMinWidth().IsPercentOrCalc()) ? logical_width : ComputeReplacedLogicalWidthUsing(kMinSize, - Style()->LogicalMinWidth()); + StyleRef().LogicalMinWidth()); LayoutUnit max_logical_width = (should_compute_preferred == kComputePreferred && - Style()->LogicalMaxWidth().IsPercentOrCalc()) || - Style()->LogicalMaxWidth().IsMaxSizeNone() + StyleRef().LogicalMaxWidth().IsPercentOrCalc()) || + StyleRef().LogicalMaxWidth().IsMaxSizeNone() ? logical_width : ComputeReplacedLogicalWidthUsing(kMaxSize, - Style()->LogicalMaxWidth()); + StyleRef().LogicalMaxWidth()); return std::max(min_logical_width, std::min(logical_width, max_logical_width)); } @@ -3535,7 +3539,7 @@ : PerpendicularContainingBlockLogicalHeight(); } Length container_logical_width = - ContainingBlock()->Style()->LogicalWidth(); + ContainingBlock()->StyleRef().LogicalWidth(); // FIXME: Handle cases when containing block width is calculated or // viewport percent. https://bugs.webkit.org/show_bug.cgi?id=91071 if (logical_width.IsIntrinsic()) @@ -3564,13 +3568,13 @@ LayoutUnit LayoutBox::ComputeReplacedLogicalHeight(LayoutUnit) const { return ComputeReplacedLogicalHeightRespectingMinMaxHeight( ComputeReplacedLogicalHeightUsing(kMainOrPreferredSize, - Style()->LogicalHeight())); + StyleRef().LogicalHeight())); } bool LayoutBox::LogicalHeightComputesAsNone(SizeType size_type) const { DCHECK(size_type == kMinSize || size_type == kMaxSize); - Length logical_height = size_type == kMinSize ? Style()->LogicalMinHeight() - : Style()->LogicalMaxHeight(); + Length logical_height = size_type == kMinSize ? StyleRef().LogicalMinHeight() + : StyleRef().LogicalMaxHeight(); Length initial_logical_height = size_type == kMinSize ? ComputedStyleInitialValues::InitialMinHeight() : ComputedStyleInitialValues::InitialMaxHeight(); @@ -3590,13 +3594,15 @@ // the percentage value is treated as '0' (for 'min-height') or 'none' (for // 'max-height'). LayoutUnit min_logical_height; - if (!LogicalHeightComputesAsNone(kMinSize)) + if (!LogicalHeightComputesAsNone(kMinSize)) { min_logical_height = ComputeReplacedLogicalHeightUsing( - kMinSize, Style()->LogicalMinHeight()); + kMinSize, StyleRef().LogicalMinHeight()); + } LayoutUnit max_logical_height = logical_height; - if (!LogicalHeightComputesAsNone(kMaxSize)) + if (!LogicalHeightComputesAsNone(kMaxSize)) { max_logical_height = ComputeReplacedLogicalHeightUsing( - kMaxSize, Style()->LogicalMaxHeight()); + kMaxSize, StyleRef().LogicalMaxHeight()); + } return std::max(min_logical_height, std::min(logical_height, max_logical_height)); } @@ -3639,8 +3645,9 @@ } } - if (cb->IsOutOfFlowPositioned() && cb->Style()->Height().IsAuto() && - !(cb->Style()->Top().IsAuto() || cb->Style()->Bottom().IsAuto())) { + if (cb->IsOutOfFlowPositioned() && cb->StyleRef().Height().IsAuto() && + !(cb->StyleRef().Top().IsAuto() || + cb->StyleRef().Bottom().IsAuto())) { SECURITY_DCHECK(cb->IsLayoutBlock()); LayoutBlock* block = ToLayoutBlock(cb); LogicalExtentComputedValues computed_values; @@ -3671,8 +3678,8 @@ // image are perpendicular writing-modes, this isn't right. // https://bugs.webkit.org/show_bug.cgi?id=46997 while (cb && !cb->IsLayoutView() && - (cb->Style()->LogicalHeight().IsAuto() || - cb->Style()->LogicalHeight().IsPercentOrCalc())) { + (cb->StyleRef().LogicalHeight().IsAuto() || + cb->StyleRef().LogicalHeight().IsPercentOrCalc())) { if (cb->IsTableCell()) { // Don't let table cells squeeze percent-height replaced elements // <http://bugs.webkit.org/show_bug.cgi?id=15359> @@ -3713,7 +3720,7 @@ // This code gets executed 740 times in the test case. // https://chromium-review.googlesource.com/c/chromium/src/+/1103289 LayoutUnit height = - AvailableLogicalHeightUsing(Style()->LogicalHeight(), height_type); + AvailableLogicalHeightUsing(StyleRef().LogicalHeight(), height_type); if (UNLIKELY(height == -1)) return height; return ConstrainContentBoxLogicalHeightByMinMax(height, LayoutUnit(-1)); @@ -3722,7 +3729,7 @@ // in the content height. // FIXME: Should we pass intrinsicContentLogicalHeight() instead of -1 here? return ConstrainContentBoxLogicalHeightByMinMax( - AvailableLogicalHeightUsing(Style()->LogicalHeight(), height_type), + AvailableLogicalHeightUsing(StyleRef().LogicalHeight(), height_type), LayoutUnit(-1)); } @@ -3776,8 +3783,8 @@ // writing-mode. // https://bugs.webkit.org/show_bug.cgi?id=46500 if (IsLayoutBlock() && IsOutOfFlowPositioned() && - Style()->Height().IsAuto() && - !(Style()->Top().IsAuto() || Style()->Bottom().IsAuto())) { + StyleRef().Height().IsAuto() && + !(StyleRef().Top().IsAuto() || StyleRef().Bottom().IsAuto())) { LayoutBlock* block = const_cast<LayoutBlock*>(ToLayoutBlock(this)); LogicalExtentComputedValues computed_values; block->ComputeLogicalHeight(block->LogicalHeight(), LayoutUnit(), @@ -3826,7 +3833,7 @@ return ContainingBlockLogicalHeightForPositioned(containing_block, false); // Use viewport as container for top-level fixed-position elements. - if (Style()->GetPosition() == EPosition::kFixed && + if (StyleRef().GetPosition() == EPosition::kFixed && containing_block->IsLayoutView() && !GetDocument().Printing()) { const LayoutView* view = ToLayoutView(containing_block); if (LocalFrameView* frame_view = view->GetFrameView()) { @@ -3856,7 +3863,7 @@ DCHECK(containing_block->IsLayoutInline()); DCHECK(containing_block->CanContainOutOfFlowPositionedElement( - Style()->GetPosition())); + StyleRef().GetPosition())); const LayoutInline* flow = ToLayoutInline(containing_block); InlineFlowBox* first = flow->FirstLineBox(); @@ -3868,7 +3875,7 @@ LayoutUnit from_left; LayoutUnit from_right; - if (containing_block->Style()->IsLeftToRightDirection()) { + if (containing_block->StyleRef().IsLeftToRightDirection()) { from_left = first->LogicalLeft() + first->BorderLogicalLeft(); from_right = last->LogicalLeft() + last->LogicalWidth() - last->BorderLogicalRight(); @@ -3889,7 +3896,7 @@ return ContainingBlockLogicalWidthForPositioned(containing_block, false); // Use viewport as container for top-level fixed-position elements. - if (Style()->GetPosition() == EPosition::kFixed && + if (StyleRef().GetPosition() == EPosition::kFixed && containing_block->IsLayoutView() && !GetDocument().Printing()) { const LayoutView* view = ToLayoutView(containing_block); if (LocalFrameView* frame_view = view->GetFrameView()) { @@ -3911,7 +3918,7 @@ DCHECK(containing_block->IsLayoutInline()); DCHECK(containing_block->CanContainOutOfFlowPositionedElement( - Style()->GetPosition())); + StyleRef().GetPosition())); const LayoutInline* flow = ToLayoutInline(containing_block); InlineFlowBox* first = flow->FirstLineBox(); @@ -3960,7 +3967,7 @@ return; LayoutObject* parent = child->Parent(); - TextDirection parent_direction = parent->Style()->Direction(); + TextDirection parent_direction = parent->StyleRef().Direction(); // This method is using EnclosingBox() which is wrong for absolutely // positioned grid items, as they rely on the grid area. So for grid items if @@ -3995,13 +4002,13 @@ *ToLayoutBox(curr), static_position, static_block_position); } else if (curr->IsInline()) { if (curr->IsInFlowPositioned()) { - if (!curr->Style()->LogicalLeft().IsAuto()) + if (!curr->StyleRef().LogicalLeft().IsAuto()) static_position += - ValueForLength(curr->Style()->LogicalLeft(), + ValueForLength(curr->StyleRef().LogicalLeft(), curr->ContainingBlock()->AvailableWidth()); else static_position -= - ValueForLength(curr->Style()->LogicalRight(), + ValueForLength(curr->StyleRef().LogicalRight(), curr->ContainingBlock()->AvailableWidth()); } } @@ -4033,13 +4040,13 @@ } } else if (curr->IsInline()) { if (curr->IsInFlowPositioned()) { - if (!curr->Style()->LogicalLeft().IsAuto()) + if (!curr->StyleRef().LogicalLeft().IsAuto()) static_position -= - ValueForLength(curr->Style()->LogicalLeft(), + ValueForLength(curr->StyleRef().LogicalLeft(), curr->ContainingBlock()->AvailableWidth()); else static_position += - ValueForLength(curr->Style()->LogicalRight(), + ValueForLength(curr->StyleRef().LogicalRight(), curr->ContainingBlock()->AvailableWidth()); } } @@ -4079,17 +4086,17 @@ // Use the container block's direction except when calculating the static // distance. This conforms with the reference results for // abspos-replaced-width-margin-000.htm of the CSS 2.1 test suite. - TextDirection container_direction = container_block->Style()->Direction(); + TextDirection container_direction = container_block->StyleRef().Direction(); bool is_horizontal = IsHorizontalWritingMode(); const LayoutUnit borders_plus_padding = BorderAndPaddingLogicalWidth(); const Length margin_logical_left = - is_horizontal ? Style()->MarginLeft() : Style()->MarginTop(); + is_horizontal ? StyleRef().MarginLeft() : StyleRef().MarginTop(); const Length margin_logical_right = - is_horizontal ? Style()->MarginRight() : Style()->MarginBottom(); + is_horizontal ? StyleRef().MarginRight() : StyleRef().MarginBottom(); - Length logical_left_length = Style()->LogicalLeft(); - Length logical_right_length = Style()->LogicalRight(); + Length logical_left_length = StyleRef().LogicalLeft(); + Length logical_right_length = StyleRef().LogicalRight(); // --------------------------------------------------------------------------- // For the purposes of this section and the next, the term "static position" // (of an element) refers, roughly, to the position an element would have had @@ -4120,17 +4127,17 @@ // Calculate constraint equation values for 'width' case. ComputePositionedLogicalWidthUsing( - kMainOrPreferredSize, Style()->LogicalWidth(), container_block, + kMainOrPreferredSize, StyleRef().LogicalWidth(), container_block, container_direction, container_logical_width, borders_plus_padding, logical_left_length, logical_right_length, margin_logical_left, margin_logical_right, computed_values); // Calculate constraint equation values for 'max-width' case. - if (!Style()->LogicalMaxWidth().IsMaxSizeNone()) { + if (!StyleRef().LogicalMaxWidth().IsMaxSizeNone()) { LogicalExtentComputedValues max_values; ComputePositionedLogicalWidthUsing( - kMaxSize, Style()->LogicalMaxWidth(), container_block, + kMaxSize, StyleRef().LogicalMaxWidth(), container_block, container_direction, container_logical_width, borders_plus_padding, logical_left_length, logical_right_length, margin_logical_left, margin_logical_right, max_values); @@ -4144,12 +4151,12 @@ } // Calculate constraint equation values for 'min-width' case. - if (!Style()->LogicalMinWidth().IsZero() || - Style()->LogicalMinWidth().IsIntrinsic()) { + if (!StyleRef().LogicalMinWidth().IsZero() || + StyleRef().LogicalMinWidth().IsIntrinsic()) { LogicalExtentComputedValues min_values; ComputePositionedLogicalWidthUsing( - kMinSize, Style()->LogicalMinWidth(), container_block, + kMinSize, StyleRef().LogicalMinWidth(), container_block, container_direction, container_logical_width, borders_plus_padding, logical_left_length, logical_right_length, margin_logical_left, margin_logical_right, min_values); @@ -4177,7 +4184,7 @@ // if the containing block is both a flipped mode and perpendicular to us. if (container_block->IsHorizontalWritingMode() != child->IsHorizontalWritingMode() && - container_block->Style()->IsFlippedBlocksWritingMode()) { + container_block->StyleRef().IsFlippedBlocksWritingMode()) { logical_left_pos = container_logical_width - logical_width_value - logical_left_pos; logical_left_pos += @@ -4246,12 +4253,12 @@ bool logical_width_is_auto = logical_width.IsAuto(); bool logical_left_is_auto = logical_left.IsAuto(); bool logical_right_is_auto = logical_right.IsAuto(); - LayoutUnit& margin_logical_left_value = Style()->IsLeftToRightDirection() + LayoutUnit& margin_logical_left_value = StyleRef().IsLeftToRightDirection() ? computed_values.margins_.start_ : computed_values.margins_.end_; LayoutUnit& margin_logical_right_value = - Style()->IsLeftToRightDirection() ? computed_values.margins_.end_ - : computed_values.margins_.start_; + StyleRef().IsLeftToRightDirection() ? computed_values.margins_.end_ + : computed_values.margins_.start_; if (!logical_left_is_auto && !logical_width_is_auto && !logical_right_is_auto) { // ------------------------------------------------------------------------- @@ -4412,7 +4419,7 @@ // logical left position of the first line box when really it should use the // last line box. When this is fixed elsewhere, this block should be removed. if (container_block->IsLayoutInline() && - !container_block->Style()->IsLeftToRightDirection()) { + !container_block->StyleRef().IsLeftToRightDirection()) { const LayoutInline* flow = ToLayoutInline(container_block); InlineFlowBox* first_line = flow->FirstLineBox(); InlineFlowBox* last_line = flow->LastLineBox(); @@ -4582,11 +4589,11 @@ // containing block's coordinate space. If the containing block is flipped // along this axis, then we need to flip the coordinate. This can only happen // if the containing block is both a flipped mode and perpendicular to us. - if ((child->Style()->IsFlippedBlocksWritingMode() && + if ((child->StyleRef().IsFlippedBlocksWritingMode() && child->IsHorizontalWritingMode() != container_block->IsHorizontalWritingMode()) || - (child->Style()->IsFlippedBlocksWritingMode() != - container_block->Style()->IsFlippedBlocksWritingMode() && + (child->StyleRef().IsFlippedBlocksWritingMode() != + container_block->StyleRef().IsFlippedBlocksWritingMode() && child->IsHorizontalWritingMode() == container_block->IsHorizontalWritingMode())) logical_top_pos = @@ -4594,7 +4601,7 @@ // Our offset is from the logical bottom edge in a flipped environment, e.g., // right for vertical-rl. - if (container_block->Style()->IsFlippedBlocksWritingMode() && + if (container_block->StyleRef().IsFlippedBlocksWritingMode() && child->IsHorizontalWritingMode() == container_block->IsHorizontalWritingMode()) { if (child->IsHorizontalWritingMode()) @@ -4813,7 +4820,7 @@ LayoutUnit caret_width = GetFrameView()->CaretWidth(); LayoutRect rect(Location(), LayoutSize(caret_width, Size().Height())); bool ltr = - box ? box->IsLeftToRightDirection() : Style()->IsLeftToRightDirection(); + box ? box->IsLeftToRightDirection() : StyleRef().IsLeftToRightDirection(); if ((!caret_offset) ^ ltr) rect.Move(LayoutSize(Size().Width() - caret_width, LayoutUnit())); @@ -4834,7 +4841,7 @@ // giant tall-as-window insertion point // // FIXME: ignoring :first-line, missing good reason to take care of - const SimpleFontData* font_data = Style()->GetFont().PrimaryFont(); + const SimpleFontData* font_data = StyleRef().GetFont().PrimaryFont(); LayoutUnit font_height = LayoutUnit(font_data ? font_data->GetFontMetrics().Height() : 0); if (font_height > rect.Height() || (!IsAtomicInlineLevel() && !IsTable())) @@ -4896,7 +4903,7 @@ layout_object = layout_object->NextSibling()) { if ((!layout_object->SlowFirstChild() && !layout_object->IsInline() && !layout_object->IsLayoutBlockFlow()) || - layout_object->Style()->Visibility() != EVisibility::kVisible) + layout_object->StyleRef().Visibility() != EVisibility::kVisible) continue; if (!layout_object->IsBox()) @@ -4971,7 +4978,7 @@ return false; // Only auto width objects can possibly shrink to avoid floats. - if (!Style()->Width().IsAuto()) + if (!StyleRef().Width().IsAuto()) return false; // If the containing block is LayoutNG, we will not let legacy layout deal @@ -5113,7 +5120,7 @@ } void LayoutBox::AddVisualEffectOverflow() { - if (!Style()->HasVisualOverflowingEffect()) + if (!StyleRef().HasVisualOverflowingEffect()) return; // Add in the final overflow with shadows, outsets and outline combined. @@ -5188,11 +5195,11 @@ } bool LayoutBox::HasTopOverflow() const { - return !Style()->IsLeftToRightDirection() && !IsHorizontalWritingMode(); + return !StyleRef().IsLeftToRightDirection() && !IsHorizontalWritingMode(); } bool LayoutBox::HasLeftOverflow() const { - return !Style()->IsLeftToRightDirection() && IsHorizontalWritingMode(); + return !StyleRef().IsLeftToRightDirection() && IsHorizontalWritingMode(); } DISABLE_CFI_PERF @@ -5313,14 +5320,14 @@ // under these conditions, but it should work out to be good enough for common // cases. Paginating overflow with scrollbars present is not the end of the // world and is what we used to do in the old model anyway. - return !Style()->LogicalHeight().IsIntrinsicOrAuto() || - (!Style()->LogicalMaxHeight().IsIntrinsicOrAuto() && - !Style()->LogicalMaxHeight().IsMaxSizeNone() && - (!Style()->LogicalMaxHeight().IsPercentOrCalc() || + return !StyleRef().LogicalHeight().IsIntrinsicOrAuto() || + (!StyleRef().LogicalMaxHeight().IsIntrinsicOrAuto() && + !StyleRef().LogicalMaxHeight().IsMaxSizeNone() && + (!StyleRef().LogicalMaxHeight().IsPercentOrCalc() || PercentageLogicalHeightIsResolvable())) || - (!Style()->LogicalMinHeight().IsIntrinsicOrAuto() && - Style()->LogicalMinHeight().IsPositive() && - (!Style()->LogicalMinHeight().IsPercentOrCalc() || + (!StyleRef().LogicalMinHeight().IsIntrinsicOrAuto() && + StyleRef().LogicalMinHeight().IsPositive() && + (!StyleRef().LogicalMinHeight().IsPercentOrCalc() || PercentageLogicalHeightIsResolvable())); } @@ -5329,7 +5336,8 @@ // actually look for replaced elements. if (IsAtomicInlineLevel() || HasUnsplittableScrollingOverflow() || (Parent() && IsWritingModeRoot()) || - (IsOutOfFlowPositioned() && Style()->GetPosition() == EPosition::kFixed)) + (IsOutOfFlowPositioned() && + StyleRef().GetPosition() == EPosition::kFixed)) return kForbidBreaks; EBreakInside break_value = BreakInside(); @@ -5521,7 +5529,7 @@ LayoutPoint LayoutBox::FlipForWritingModeForChild( const LayoutBox* child, const LayoutPoint& point) const { - if (!Style()->IsFlippedBlocksWritingMode()) + if (!StyleRef().IsFlippedBlocksWritingMode()) return point; // The child is going to add in its x(), so we have to make sure it ends up in @@ -5559,15 +5567,15 @@ } bool LayoutBox::HasRelativeLogicalWidth() const { - return Style()->LogicalWidth().IsPercentOrCalc() || - Style()->LogicalMinWidth().IsPercentOrCalc() || - Style()->LogicalMaxWidth().IsPercentOrCalc(); + return StyleRef().LogicalWidth().IsPercentOrCalc() || + StyleRef().LogicalMinWidth().IsPercentOrCalc() || + StyleRef().LogicalMaxWidth().IsPercentOrCalc(); } bool LayoutBox::HasRelativeLogicalHeight() const { - return Style()->LogicalHeight().IsPercentOrCalc() || - Style()->LogicalMinHeight().IsPercentOrCalc() || - Style()->LogicalMaxHeight().IsPercentOrCalc(); + return StyleRef().LogicalHeight().IsPercentOrCalc() || + StyleRef().LogicalMinHeight().IsPercentOrCalc() || + StyleRef().LogicalMaxHeight().IsPercentOrCalc(); } static void MarkBoxForRelayoutAfterSplit(LayoutBox* box) { @@ -5787,18 +5795,18 @@ bool LayoutBox::MustInvalidateBackgroundOrBorderPaintOnWidthChange() const { if (HasMask() && - MustInvalidateFillLayersPaintOnWidthChange(Style()->MaskLayers())) + MustInvalidateFillLayersPaintOnWidthChange(StyleRef().MaskLayers())) return true; // If we don't have a background/border/mask, then nothing to do. if (!HasBoxDecorationBackground()) return false; - if (MustInvalidateFillLayersPaintOnWidthChange(Style()->BackgroundLayers())) + if (MustInvalidateFillLayersPaintOnWidthChange(StyleRef().BackgroundLayers())) return true; // Our fill layers are ok. Let's check border. - if (Style()->CanRenderBorderImage()) + if (StyleRef().CanRenderBorderImage()) return true; return false; @@ -5806,18 +5814,19 @@ bool LayoutBox::MustInvalidateBackgroundOrBorderPaintOnHeightChange() const { if (HasMask() && - MustInvalidateFillLayersPaintOnHeightChange(Style()->MaskLayers())) + MustInvalidateFillLayersPaintOnHeightChange(StyleRef().MaskLayers())) return true; // If we don't have a background/border/mask, then nothing to do. if (!HasBoxDecorationBackground()) return false; - if (MustInvalidateFillLayersPaintOnHeightChange(Style()->BackgroundLayers())) + if (MustInvalidateFillLayersPaintOnHeightChange( + StyleRef().BackgroundLayers())) return true; // Our fill layers are ok. Let's check border. - if (Style()->CanRenderBorderImage()) + if (StyleRef().CanRenderBorderImage()) return true; return false; @@ -6094,7 +6103,7 @@ if (InlineBoxWrapper()) return InlineBoxWrapper()->Direction(); } - return Style()->Direction(); + return StyleRef().Direction(); } } // namespace blink
diff --git a/third_party/blink/renderer/core/layout/layout_box.h b/third_party/blink/renderer/core/layout/layout_box.h index 0bb8a00..f8e7b716 100644 --- a/third_party/blink/renderer/core/layout/layout_box.h +++ b/third_party/blink/renderer/core/layout/layout_box.h
@@ -262,22 +262,22 @@ } LayoutUnit LogicalLeft() const { - return Style()->IsHorizontalWritingMode() ? frame_rect_.X() - : frame_rect_.Y(); + return StyleRef().IsHorizontalWritingMode() ? frame_rect_.X() + : frame_rect_.Y(); } LayoutUnit LogicalRight() const { return LogicalLeft() + LogicalWidth(); } LayoutUnit LogicalTop() const { - return Style()->IsHorizontalWritingMode() ? frame_rect_.Y() - : frame_rect_.X(); + return StyleRef().IsHorizontalWritingMode() ? frame_rect_.Y() + : frame_rect_.X(); } LayoutUnit LogicalBottom() const { return LogicalTop() + LogicalHeight(); } LayoutUnit LogicalWidth() const { - return Style()->IsHorizontalWritingMode() ? frame_rect_.Width() - : frame_rect_.Height(); + return StyleRef().IsHorizontalWritingMode() ? frame_rect_.Width() + : frame_rect_.Height(); } LayoutUnit LogicalHeight() const { - return Style()->IsHorizontalWritingMode() ? frame_rect_.Height() - : frame_rect_.Width(); + return StyleRef().IsHorizontalWritingMode() ? frame_rect_.Height() + : frame_rect_.Width(); } // Logical height of the object, including content overflowing the @@ -295,12 +295,12 @@ LayoutUnit intrinsic_content_height) const; int PixelSnappedLogicalHeight() const { - return Style()->IsHorizontalWritingMode() ? PixelSnappedHeight() - : PixelSnappedWidth(); + return StyleRef().IsHorizontalWritingMode() ? PixelSnappedHeight() + : PixelSnappedWidth(); } int PixelSnappedLogicalWidth() const { - return Style()->IsHorizontalWritingMode() ? PixelSnappedWidth() - : PixelSnappedHeight(); + return StyleRef().IsHorizontalWritingMode() ? PixelSnappedWidth() + : PixelSnappedHeight(); } LayoutUnit MinimumLogicalHeightForEmptyLine() const { @@ -312,31 +312,31 @@ } void SetLogicalLeft(LayoutUnit left) { - if (Style()->IsHorizontalWritingMode()) + if (StyleRef().IsHorizontalWritingMode()) SetX(left); else SetY(left); } void SetLogicalTop(LayoutUnit top) { - if (Style()->IsHorizontalWritingMode()) + if (StyleRef().IsHorizontalWritingMode()) SetY(top); else SetX(top); } void SetLogicalLocation(const LayoutPoint& location) { - if (Style()->IsHorizontalWritingMode()) + if (StyleRef().IsHorizontalWritingMode()) SetLocation(location); else SetLocation(location.TransposedPoint()); } void SetLogicalWidth(LayoutUnit size) { - if (Style()->IsHorizontalWritingMode()) + if (StyleRef().IsHorizontalWritingMode()) SetWidth(size); else SetHeight(size); } void SetLogicalHeight(LayoutUnit size) { - if (Style()->IsHorizontalWritingMode()) + if (StyleRef().IsHorizontalWritingMode()) SetHeight(size); else SetWidth(size); @@ -479,12 +479,12 @@ return LayoutSize(LayoutOverflowRect().MaxX(), LayoutOverflowRect().MaxY()); } LayoutUnit LogicalLeftLayoutOverflow() const { - return Style()->IsHorizontalWritingMode() ? LayoutOverflowRect().X() - : LayoutOverflowRect().Y(); + return StyleRef().IsHorizontalWritingMode() ? LayoutOverflowRect().X() + : LayoutOverflowRect().Y(); } LayoutUnit LogicalRightLayoutOverflow() const { - return Style()->IsHorizontalWritingMode() ? LayoutOverflowRect().MaxX() - : LayoutOverflowRect().MaxY(); + return StyleRef().IsHorizontalWritingMode() ? LayoutOverflowRect().MaxX() + : LayoutOverflowRect().MaxY(); } LayoutRect VisualOverflowRect() const override; @@ -494,12 +494,12 @@ return overflow_rect; } LayoutUnit LogicalLeftVisualOverflow() const { - return Style()->IsHorizontalWritingMode() ? VisualOverflowRect().X() - : VisualOverflowRect().Y(); + return StyleRef().IsHorizontalWritingMode() ? VisualOverflowRect().X() + : VisualOverflowRect().Y(); } LayoutUnit LogicalRightVisualOverflow() const { - return Style()->IsHorizontalWritingMode() ? VisualOverflowRect().MaxX() - : VisualOverflowRect().MaxY(); + return StyleRef().IsHorizontalWritingMode() ? VisualOverflowRect().MaxX() + : VisualOverflowRect().MaxY(); } LayoutRect SelfVisualOverflowRect() const { @@ -556,12 +556,12 @@ return LayoutSize(ContentWidth(), ContentHeight()); } LayoutUnit ContentLogicalWidth() const { - return Style()->IsHorizontalWritingMode() ? ContentWidth() - : ContentHeight(); + return StyleRef().IsHorizontalWritingMode() ? ContentWidth() + : ContentHeight(); } LayoutUnit ContentLogicalHeight() const { - return Style()->IsHorizontalWritingMode() ? ContentHeight() - : ContentWidth(); + return StyleRef().IsHorizontalWritingMode() ? ContentHeight() + : ContentWidth(); } // IE extensions. Used to calculate offsetWidth/Height. Overridden by inlines @@ -586,10 +586,12 @@ LayoutUnit ClientWidth() const; LayoutUnit ClientHeight() const; DISABLE_CFI_PERF LayoutUnit ClientLogicalWidth() const { - return Style()->IsHorizontalWritingMode() ? ClientWidth() : ClientHeight(); + return StyleRef().IsHorizontalWritingMode() ? ClientWidth() + : ClientHeight(); } DISABLE_CFI_PERF LayoutUnit ClientLogicalHeight() const { - return Style()->IsHorizontalWritingMode() ? ClientHeight() : ClientWidth(); + return StyleRef().IsHorizontalWritingMode() ? ClientHeight() + : ClientWidth(); } DISABLE_CFI_PERF LayoutUnit ClientLogicalBottom() const { return BorderBefore() + ClientLogicalHeight(); @@ -914,12 +916,12 @@ virtual LayoutSize IntrinsicSize() const { return LayoutSize(); } LayoutUnit IntrinsicLogicalWidth() const { - return Style()->IsHorizontalWritingMode() ? IntrinsicSize().Width() - : IntrinsicSize().Height(); + return StyleRef().IsHorizontalWritingMode() ? IntrinsicSize().Width() + : IntrinsicSize().Height(); } LayoutUnit IntrinsicLogicalHeight() const { - return Style()->IsHorizontalWritingMode() ? IntrinsicSize().Height() - : IntrinsicSize().Width(); + return StyleRef().IsHorizontalWritingMode() ? IntrinsicSize().Height() + : IntrinsicSize().Width(); } virtual LayoutUnit IntrinsicContentLogicalHeight() const { return intrinsic_content_logical_height_; @@ -980,12 +982,12 @@ // physical width and available physical height. Relative positioning is one // of those cases, since left/top offsets are physical. LayoutUnit AvailableWidth() const { - return Style()->IsHorizontalWritingMode() + return StyleRef().IsHorizontalWritingMode() ? AvailableLogicalWidth() : AvailableLogicalHeight(kIncludeMarginBorderPadding); } LayoutUnit AvailableHeight() const { - return Style()->IsHorizontalWritingMode() + return StyleRef().IsHorizontalWritingMode() ? AvailableLogicalHeight(kIncludeMarginBorderPadding) : AvailableLogicalWidth(); } @@ -993,12 +995,12 @@ int VerticalScrollbarWidth() const; int HorizontalScrollbarHeight() const; int ScrollbarLogicalWidth() const { - return Style()->IsHorizontalWritingMode() ? VerticalScrollbarWidth() - : HorizontalScrollbarHeight(); + return StyleRef().IsHorizontalWritingMode() ? VerticalScrollbarWidth() + : HorizontalScrollbarHeight(); } int ScrollbarLogicalHeight() const { - return Style()->IsHorizontalWritingMode() ? HorizontalScrollbarHeight() - : VerticalScrollbarWidth(); + return StyleRef().IsHorizontalWritingMode() ? HorizontalScrollbarHeight() + : VerticalScrollbarWidth(); } // Return the width of the vertical scrollbar, unless it's larger than the @@ -1019,16 +1021,16 @@ virtual void DispatchFakeMouseMoveEventSoon(EventHandler&); DISABLE_CFI_PERF bool HasAutoVerticalScrollbar() const { - return HasOverflowClip() && Style()->HasAutoVerticalScroll(); + return HasOverflowClip() && StyleRef().HasAutoVerticalScroll(); } DISABLE_CFI_PERF bool HasAutoHorizontalScrollbar() const { - return HasOverflowClip() && Style()->HasAutoHorizontalScroll(); + return HasOverflowClip() && StyleRef().HasAutoHorizontalScroll(); } DISABLE_CFI_PERF bool ScrollsOverflow() const { - return HasOverflowClip() && Style()->ScrollsOverflow(); + return HasOverflowClip() && StyleRef().ScrollsOverflow(); } virtual bool ShouldPlaceBlockDirectionScrollbarOnLogicalLeft() const { - return Style()->ShouldPlaceBlockDirectionScrollbarOnLogicalLeft(); + return StyleRef().ShouldPlaceBlockDirectionScrollbarOnLogicalLeft(); } bool HasScrollableOverflowX() const { @@ -1040,10 +1042,10 @@ PixelSnappedScrollHeight() != PixelSnappedClientHeight(); } virtual bool ScrollsOverflowX() const { - return HasOverflowClip() && Style()->ScrollsOverflowX(); + return HasOverflowClip() && StyleRef().ScrollsOverflowX(); } virtual bool ScrollsOverflowY() const { - return HasOverflowClip() && Style()->ScrollsOverflowY(); + return HasOverflowClip() && StyleRef().ScrollsOverflowY(); } // Elements such as the <input> field override this to specify that they are @@ -1116,7 +1118,7 @@ bool IsWritingModeRoot() const { return !Parent() || - Parent()->Style()->GetWritingMode() != Style()->GetWritingMode(); + Parent()->StyleRef().GetWritingMode() != StyleRef().GetWritingMode(); } bool IsOrthogonalWritingModeRoot() const { return Parent() && @@ -1315,7 +1317,7 @@ } bool HasSameDirectionAs(const LayoutBox* object) const { - return Style()->Direction() == object->Style()->Direction(); + return StyleRef().Direction() == object->StyleRef().Direction(); } ShapeOutsideInfo* GetShapeOutsideInfo() const;
diff --git a/third_party/blink/renderer/core/layout/layout_box_model_object.cc b/third_party/blink/renderer/core/layout/layout_box_model_object.cc index 63ebb6a..7d802ae 100644 --- a/third_party/blink/renderer/core/layout/layout_box_model_object.cc +++ b/third_party/blink/renderer/core/layout/layout_box_model_object.cc
@@ -49,15 +49,15 @@ inline bool IsOutOfFlowPositionedWithImplicitHeight( const LayoutBoxModelObject* child) { return child->IsOutOfFlowPositioned() && - !child->Style()->LogicalTop().IsAuto() && - !child->Style()->LogicalBottom().IsAuto(); + !child->StyleRef().LogicalTop().IsAuto() && + !child->StyleRef().LogicalBottom().IsAuto(); } // Inclusive of |from|, exclusive of |to|. PaintLayer* FindFirstStickyBetween(LayoutObject* from, LayoutObject* to) { LayoutObject* maybe_sticky_ancestor = from; while (maybe_sticky_ancestor && maybe_sticky_ancestor != to) { - if (maybe_sticky_ancestor->Style()->HasStickyConstrainedPosition()) { + if (maybe_sticky_ancestor->StyleRef().HasStickyConstrainedPosition()) { return ToLayoutBoxModelObject(maybe_sticky_ancestor)->Layer(); } @@ -118,7 +118,7 @@ // TODO(flackr): Remove this when box shadows are still painted correctly when // painting into the composited scrolling contents layer. // https://crbug.com/646464 - if (Style()->BoxShadow()) { + if (StyleRef().BoxShadow()) { if (reasons) *reasons |= MainThreadScrollingReason::kHasBoxShadowFromNonRootLayer; return kBackgroundPaintInGraphicsLayer; @@ -127,7 +127,7 @@ // Assume optimistically that the background can be painted in the scrolling // contents until we find otherwise. BackgroundPaintLocation paint_location = kBackgroundPaintInScrollingContents; - const FillLayer* layer = &(Style()->BackgroundLayers()); + const FillLayer* layer = &(StyleRef().BackgroundLayers()); for (; layer; layer = layer->Next()) { if (layer->Attachment() == EFillAttachment::kLocal) continue; @@ -143,20 +143,20 @@ // there is no border and we don't have custom scrollbars. if (clip == EFillBox::kBorder) { if (!has_custom_scrollbars && - (Style()->BorderTopWidth() == 0 || + (StyleRef().BorderTopWidth() == 0 || !ResolveColor(GetCSSPropertyBorderTopColor()).HasAlpha()) && - (Style()->BorderLeftWidth() == 0 || + (StyleRef().BorderLeftWidth() == 0 || !ResolveColor(GetCSSPropertyBorderLeftColor()).HasAlpha()) && - (Style()->BorderRightWidth() == 0 || + (StyleRef().BorderRightWidth() == 0 || !ResolveColor(GetCSSPropertyBorderRightColor()).HasAlpha()) && - (Style()->BorderBottomWidth() == 0 || + (StyleRef().BorderBottomWidth() == 0 || !ResolveColor(GetCSSPropertyBorderBottomColor()).HasAlpha())) { continue; } // If we have an opaque background color only, we can safely paint it // into both the scrolling contents layer and the graphics layer to // preserve LCD text. - if (layer == (&Style()->BackgroundLayers()) && + if (layer == (&StyleRef().BackgroundLayers()) && ResolveColor(GetCSSPropertyBackgroundColor()).Alpha() < 255) return kBackgroundPaintInGraphicsLayer; paint_location |= kBackgroundPaintInGraphicsLayer; @@ -164,9 +164,10 @@ } // A content fill box can be treated as a padding fill box if there is no // padding. - if (clip == EFillBox::kContent && Style()->PaddingTop().IsZero() && - Style()->PaddingLeft().IsZero() && Style()->PaddingRight().IsZero() && - Style()->PaddingBottom().IsZero()) { + if (clip == EFillBox::kContent && StyleRef().PaddingTop().IsZero() && + StyleRef().PaddingLeft().IsZero() && + StyleRef().PaddingRight().IsZero() && + StyleRef().PaddingBottom().IsZero()) { continue; } } @@ -190,8 +191,8 @@ // 0 during destruction. if (LocalFrame* frame = GetFrame()) { if (LocalFrameView* frame_view = frame->View()) { - if (Style()->HasViewportConstrainedPosition() || - Style()->HasStickyConstrainedPosition()) + if (StyleRef().HasViewportConstrainedPosition() || + StyleRef().HasStickyConstrainedPosition()) frame_view->RemoveViewportConstrainedObject(*this); } } @@ -218,8 +219,8 @@ // invalidate the current compositing container chain which may have painted // cached subsequences containing this object or descendant objects. if (Style() && - (Style()->IsStacked() != new_style.IsStacked() || - Style()->IsStackingContext() != new_style.IsStackingContext()) && + (StyleRef().IsStacked() != new_style.IsStacked() || + StyleRef().IsStackingContext() != new_style.IsStackingContext()) && // ObjectPaintInvalidator requires this. IsRooted()) { if (RuntimeEnabledFeatures::SlimmingPaintV2Enabled()) { @@ -358,7 +359,7 @@ old_style && ToLayoutBoxModelObject(body_layout) ->BackgroundStolenForBeingBody(old_style); if (new_stole_body_background != old_stole_body_background && - body_layout->Style() && body_layout->Style()->HasBackground()) { + body_layout->Style() && body_layout->StyleRef().HasBackground()) { body_layout->SetShouldDoFullPaintInvalidation(); } } @@ -366,10 +367,10 @@ if (LocalFrameView* frame_view = View()->GetFrameView()) { bool new_style_is_viewport_constained = - Style()->GetPosition() == EPosition::kFixed; + StyleRef().GetPosition() == EPosition::kFixed; bool old_style_is_viewport_constrained = old_style && old_style->GetPosition() == EPosition::kFixed; - bool new_style_is_sticky = Style()->HasStickyConstrainedPosition(); + bool new_style_is_sticky = StyleRef().HasStickyConstrainedPosition(); bool old_style_is_sticky = old_style && old_style->HasStickyConstrainedPosition(); @@ -674,7 +675,7 @@ // TODO(rego): Check if we can somehow reuse LayoutBlock:: // availableLogicalHeightForPercentageComputation() (see crbug.com/635655). const LayoutBox* this_box = IsBox() ? ToLayoutBox(this) : nullptr; - Length logical_height_length = Style()->LogicalHeight(); + Length logical_height_length = StyleRef().LogicalHeight(); LayoutBlock* cb = ContainingBlockForAutoHeightDetection(logical_height_length); if (logical_height_length.IsPercentOrCalc() && cb && IsBox()) @@ -715,11 +716,14 @@ // https://drafts.csswg.org/css-position-3/#rel-pos base::Optional<LayoutUnit> left; base::Optional<LayoutUnit> right; - if (!Style()->Left().IsAuto()) - left = ValueForLength(Style()->Left(), containing_block->AvailableWidth()); - if (!Style()->Right().IsAuto()) + if (!StyleRef().Left().IsAuto()) { + left = + ValueForLength(StyleRef().Left(), containing_block->AvailableWidth()); + } + if (!StyleRef().Right().IsAuto()) { right = - ValueForLength(Style()->Right(), containing_block->AvailableWidth()); + ValueForLength(StyleRef().Right(), containing_block->AvailableWidth()); + } if (!left && !right) { left = LayoutUnit(); right = LayoutUnit(); @@ -728,8 +732,8 @@ left = -right.value(); if (!right) right = -left.value(); - bool is_ltr = containing_block->Style()->IsLeftToRightDirection(); - WritingMode writing_mode = containing_block->Style()->GetWritingMode(); + bool is_ltr = containing_block->StyleRef().IsLeftToRightDirection(); + WritingMode writing_mode = containing_block->StyleRef().GetWritingMode(); switch (writing_mode) { case WritingMode::kHorizontalTb: if (is_ltr) @@ -757,18 +761,18 @@ base::Optional<LayoutUnit> top; base::Optional<LayoutUnit> bottom; - if (!Style()->Top().IsAuto() && + if (!StyleRef().Top().IsAuto() && (!containing_block->HasAutoHeightOrContainingBlockWithAutoHeight() || - !Style()->Top().IsPercentOrCalc() || + !StyleRef().Top().IsPercentOrCalc() || containing_block->StretchesToViewport())) { - top = ValueForLength(Style()->Top(), containing_block->AvailableHeight()); + top = ValueForLength(StyleRef().Top(), containing_block->AvailableHeight()); } - if (!Style()->Bottom().IsAuto() && + if (!StyleRef().Bottom().IsAuto() && (!containing_block->HasAutoHeightOrContainingBlockWithAutoHeight() || - !Style()->Bottom().IsPercentOrCalc() || + !StyleRef().Bottom().IsPercentOrCalc() || containing_block->StretchesToViewport())) { - bottom = - ValueForLength(Style()->Bottom(), containing_block->AvailableHeight()); + bottom = ValueForLength(StyleRef().Bottom(), + containing_block->AvailableHeight()); } if (!top && !bottom) { top = LayoutUnit(); @@ -867,18 +871,18 @@ // It is an open issue whether the margin should collapse. // See https://www.w3.org/TR/css-position-3/#sticky-pos scroll_container_relative_containing_block_rect.ContractEdges( - MinimumValueForLength(containing_block->Style()->PaddingTop(), + MinimumValueForLength(containing_block->StyleRef().PaddingTop(), max_container_width) + - MinimumValueForLength(Style()->MarginTop(), max_width), - MinimumValueForLength(containing_block->Style()->PaddingRight(), + MinimumValueForLength(StyleRef().MarginTop(), max_width), + MinimumValueForLength(containing_block->StyleRef().PaddingRight(), max_container_width) + - MinimumValueForLength(Style()->MarginRight(), max_width), - MinimumValueForLength(containing_block->Style()->PaddingBottom(), + MinimumValueForLength(StyleRef().MarginRight(), max_width), + MinimumValueForLength(containing_block->StyleRef().PaddingBottom(), max_container_width) + - MinimumValueForLength(Style()->MarginBottom(), max_width), - MinimumValueForLength(containing_block->Style()->PaddingLeft(), + MinimumValueForLength(StyleRef().MarginBottom(), max_width), + MinimumValueForLength(containing_block->StyleRef().PaddingLeft(), max_container_width) + - MinimumValueForLength(Style()->MarginLeft(), max_width)); + MinimumValueForLength(StyleRef().MarginLeft(), max_width)); constraints.scroll_container_relative_containing_block_rect = FloatRect(scroll_container_relative_containing_block_rect); @@ -923,31 +927,31 @@ // We skip the right or top sticky offset if there is not enough space to // honor both the left/right or top/bottom offsets. LayoutUnit horizontal_offsets = - MinimumValueForLength(Style()->Right(), + MinimumValueForLength(StyleRef().Right(), LayoutUnit(constraining_size.Width())) + - MinimumValueForLength(Style()->Left(), + MinimumValueForLength(StyleRef().Left(), LayoutUnit(constraining_size.Width())); bool skip_right = false; bool skip_left = false; - if (!Style()->Left().IsAuto() && !Style()->Right().IsAuto()) { + if (!StyleRef().Left().IsAuto() && !StyleRef().Right().IsAuto()) { if (horizontal_offsets > scroll_container_relative_containing_block_rect.Width() || horizontal_offsets + sticky_box_rect.Width() > constraining_size.Width()) { - skip_right = Style()->IsLeftToRightDirection(); + skip_right = StyleRef().IsLeftToRightDirection(); skip_left = !skip_right; } } - if (!Style()->Left().IsAuto() && !skip_left) { + if (!StyleRef().Left().IsAuto() && !skip_left) { constraints.left_offset = MinimumValueForLength( - Style()->Left(), LayoutUnit(constraining_size.Width())); + StyleRef().Left(), LayoutUnit(constraining_size.Width())); constraints.is_anchored_left = true; } - if (!Style()->Right().IsAuto() && !skip_right) { + if (!StyleRef().Right().IsAuto() && !skip_right) { constraints.right_offset = MinimumValueForLength( - Style()->Right(), LayoutUnit(constraining_size.Width())); + StyleRef().Right(), LayoutUnit(constraining_size.Width())); constraints.is_anchored_right = true; } @@ -956,11 +960,11 @@ // mode when related sections are fixed in spec. // See http://lists.w3.org/Archives/Public/www-style/2014May/0286.html LayoutUnit vertical_offsets = - MinimumValueForLength(Style()->Top(), + MinimumValueForLength(StyleRef().Top(), LayoutUnit(constraining_size.Height())) + - MinimumValueForLength(Style()->Bottom(), + MinimumValueForLength(StyleRef().Bottom(), LayoutUnit(constraining_size.Height())); - if (!Style()->Top().IsAuto() && !Style()->Bottom().IsAuto()) { + if (!StyleRef().Top().IsAuto() && !StyleRef().Bottom().IsAuto()) { if (vertical_offsets > scroll_container_relative_containing_block_rect.Height() || vertical_offsets + sticky_box_rect.Height() > @@ -969,15 +973,15 @@ } } - if (!Style()->Top().IsAuto()) { + if (!StyleRef().Top().IsAuto()) { constraints.top_offset = MinimumValueForLength( - Style()->Top(), LayoutUnit(constraining_size.Height())); + StyleRef().Top(), LayoutUnit(constraining_size.Height())); constraints.is_anchored_top = true; } - if (!Style()->Bottom().IsAuto() && !skip_bottom) { + if (!StyleRef().Bottom().IsAuto() && !skip_bottom) { constraints.bottom_offset = MinimumValueForLength( - Style()->Bottom(), LayoutUnit(constraining_size.Height())); + StyleRef().Bottom(), LayoutUnit(constraining_size.Height())); constraints.is_anchored_bottom = true; } PaintLayerScrollableArea* scrollable_area = @@ -986,8 +990,8 @@ } bool LayoutBoxModelObject::IsSlowRepaintConstrainedObject() const { - if (!HasLayer() || (Style()->GetPosition() != EPosition::kFixed && - Style()->GetPosition() != EPosition::kSticky)) { + if (!HasLayer() || (StyleRef().GetPosition() != EPosition::kFixed && + StyleRef().GetPosition() != EPosition::kSticky)) { return false; } @@ -1105,7 +1109,7 @@ if (IsBox() && IsOutOfFlowPositioned() && inline_parent->CanContainOutOfFlowPositionedElement( - Style()->GetPosition())) { + StyleRef().GetPosition())) { // Offset for out of flow positioned elements with inline containers is // a special case in the CSS spec reference_point += @@ -1258,7 +1262,7 @@ } x = std::min(x, (max_x - caret_width).ClampNegativeToZero()); - const Font& font = Style()->GetFont(); + const Font& font = StyleRef().GetFont(); const SimpleFontData* font_data = font.PrimaryFont(); LayoutUnit height; // crbug.com/595692 This check should not be needed but sometimes @@ -1288,7 +1292,8 @@ return nullptr; bool is_inline = IsLayoutInline(); - bool is_fixed_pos = !is_inline && Style()->GetPosition() == EPosition::kFixed; + bool is_fixed_pos = + !is_inline && StyleRef().GetPosition() == EPosition::kFixed; bool contains_fixed_position = CanContainFixedPositionObjects(); TransformationMatrix adjustment_for_skipped_ancestor; @@ -1311,10 +1316,12 @@ offset_depends_on_point = true; } else { offset_depends_on_point = - container->Style()->IsFlippedBlocksWritingMode() && container->IsBox(); + container->StyleRef().IsFlippedBlocksWritingMode() && + container->IsBox(); } - bool preserve3d = container->Style()->Preserves3D() || Style()->Preserves3D(); + bool preserve3d = + container->StyleRef().Preserves3D() || StyleRef().Preserves3D(); GeometryInfoFlags flags = 0; if (preserve3d) flags |= kAccumulatingTransform;
diff --git a/third_party/blink/renderer/core/layout/layout_box_model_object.h b/third_party/blink/renderer/core/layout/layout_box_model_object.h index 87a4b950..2d69d72 100644 --- a/third_party/blink/renderer/core/layout/layout_box_model_object.h +++ b/third_party/blink/renderer/core/layout/layout_box_model_object.h
@@ -133,7 +133,7 @@ LayoutSize RelativePositionOffset() const; LayoutSize RelativePositionLogicalOffset() const { - return Style()->IsHorizontalWritingMode() + return StyleRef().IsHorizontalWritingMode() ? RelativePositionOffset() : RelativePositionOffset().TransposedSize(); } @@ -191,34 +191,34 @@ // These return the CSS computed padding values. LayoutUnit ComputedCSSPaddingTop() const { - return ComputedCSSPadding(Style()->PaddingTop()); + return ComputedCSSPadding(StyleRef().PaddingTop()); } LayoutUnit ComputedCSSPaddingBottom() const { - return ComputedCSSPadding(Style()->PaddingBottom()); + return ComputedCSSPadding(StyleRef().PaddingBottom()); } LayoutUnit ComputedCSSPaddingLeft() const { - return ComputedCSSPadding(Style()->PaddingLeft()); + return ComputedCSSPadding(StyleRef().PaddingLeft()); } LayoutUnit ComputedCSSPaddingRight() const { - return ComputedCSSPadding(Style()->PaddingRight()); + return ComputedCSSPadding(StyleRef().PaddingRight()); } LayoutUnit ComputedCSSPaddingBefore() const { - return ComputedCSSPadding(Style()->PaddingBefore()); + return ComputedCSSPadding(StyleRef().PaddingBefore()); } LayoutUnit ComputedCSSPaddingAfter() const { - return ComputedCSSPadding(Style()->PaddingAfter()); + return ComputedCSSPadding(StyleRef().PaddingAfter()); } LayoutUnit ComputedCSSPaddingStart() const { - return ComputedCSSPadding(Style()->PaddingStart()); + return ComputedCSSPadding(StyleRef().PaddingStart()); } LayoutUnit ComputedCSSPaddingEnd() const { - return ComputedCSSPadding(Style()->PaddingEnd()); + return ComputedCSSPadding(StyleRef().PaddingEnd()); } LayoutUnit ComputedCSSPaddingOver() const { - return ComputedCSSPadding(Style()->PaddingOver()); + return ComputedCSSPadding(StyleRef().PaddingOver()); } LayoutUnit ComputedCSSPaddingUnder() const { - return ComputedCSSPadding(Style()->PaddingUnder()); + return ComputedCSSPadding(StyleRef().PaddingUnder()); } // These functions are used during layout. @@ -242,16 +242,16 @@ LayoutUnit PaddingUnder() const { return PhysicalPaddingToLogical().Under(); } virtual LayoutUnit BorderTop() const { - return LayoutUnit(Style()->BorderTopWidth()); + return LayoutUnit(StyleRef().BorderTopWidth()); } virtual LayoutUnit BorderBottom() const { - return LayoutUnit(Style()->BorderBottomWidth()); + return LayoutUnit(StyleRef().BorderBottomWidth()); } virtual LayoutUnit BorderLeft() const { - return LayoutUnit(Style()->BorderLeftWidth()); + return LayoutUnit(StyleRef().BorderLeftWidth()); } virtual LayoutUnit BorderRight() const { - return LayoutUnit(Style()->BorderRightWidth()); + return LayoutUnit(StyleRef().BorderRightWidth()); } LayoutUnit BorderBefore() const { return PhysicalBorderToLogical().Before(); } @@ -281,7 +281,7 @@ } bool HasBorderOrPadding() const { - return Style()->HasBorder() || Style()->HasPadding(); + return StyleRef().HasBorder() || StyleRef().HasPadding(); } LayoutUnit BorderAndPaddingStart() const { @@ -315,17 +315,17 @@ return BorderStart() + BorderEnd() + PaddingStart() + PaddingEnd(); } DISABLE_CFI_PERF LayoutUnit BorderAndPaddingLogicalLeft() const { - return Style()->IsHorizontalWritingMode() ? BorderLeft() + PaddingLeft() - : BorderTop() + PaddingTop(); + return StyleRef().IsHorizontalWritingMode() ? BorderLeft() + PaddingLeft() + : BorderTop() + PaddingTop(); } LayoutUnit BorderLogicalLeft() const { - return LayoutUnit(Style()->IsHorizontalWritingMode() ? BorderLeft() - : BorderTop()); + return LayoutUnit(StyleRef().IsHorizontalWritingMode() ? BorderLeft() + : BorderTop()); } LayoutUnit BorderLogicalRight() const { - return LayoutUnit(Style()->IsHorizontalWritingMode() ? BorderRight() - : BorderBottom()); + return LayoutUnit(StyleRef().IsHorizontalWritingMode() ? BorderRight() + : BorderBottom()); } LayoutUnit PaddingLogicalWidth() const {
diff --git a/third_party/blink/renderer/core/layout/layout_button.cc b/third_party/blink/renderer/core/layout/layout_button.cc index 054433df..b5c23c5 100644 --- a/third_party/blink/renderer/core/layout/layout_button.cc +++ b/third_party/blink/renderer/core/layout/layout_button.cc
@@ -34,7 +34,7 @@ if (!inner_) { // Create an anonymous block. DCHECK(!FirstChild()); - inner_ = CreateAnonymousBlock(Style()->Display()); + inner_ = CreateAnonymousBlock(StyleRef().Display()); LayoutFlexibleBox::AddChild(inner_); } @@ -66,13 +66,13 @@ // when the content overflows, treat it the same as align-items: flex-start. child_style.SetMarginTop(Length()); child_style.SetMarginBottom(Length()); - child_style.SetFlexDirection(Style()->FlexDirection()); - child_style.SetJustifyContent(Style()->JustifyContent()); - child_style.SetFlexWrap(Style()->FlexWrap()); + child_style.SetFlexDirection(StyleRef().FlexDirection()); + child_style.SetJustifyContent(StyleRef().JustifyContent()); + child_style.SetFlexWrap(StyleRef().FlexWrap()); // TODO (lajava): An anonymous box must not be used to resolve children's auto // values. - child_style.SetAlignItems(Style()->AlignItems()); - child_style.SetAlignContent(Style()->AlignContent()); + child_style.SetAlignItems(StyleRef().AlignItems()); + child_style.SetAlignContent(StyleRef().AlignContent()); } LayoutRect LayoutButton::ControlClipRect(
diff --git a/third_party/blink/renderer/core/layout/layout_counter.cc b/third_party/blink/renderer/core/layout/layout_counter.cc index 81eab5fb..afab92ce 100644 --- a/third_party/blink/renderer/core/layout/layout_counter.cc +++ b/third_party/blink/renderer/core/layout/layout_counter.cc
@@ -484,7 +484,7 @@ !before_after_container->IsPseudoElement()) return nullptr; // LayoutCounters are restricted to before and after // pseudo elements - PseudoId container_style = before_after_container->Style()->StyleType(); + PseudoId container_style = before_after_container->StyleRef().StyleType(); if ((container_style == kPseudoIdBefore) || (container_style == kPseudoIdAfter)) break; @@ -602,7 +602,7 @@ static void UpdateCounters(LayoutObject& layout_object) { DCHECK(layout_object.Style()); const CounterDirectiveMap* directive_map = - layout_object.Style()->GetCounterDirectives(); + layout_object.StyleRef().GetCounterDirectives(); if (!directive_map) return; CounterDirectiveMap::const_iterator end = directive_map->end();
diff --git a/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.cc b/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.cc index f7ff1a8a..228b90af 100644 --- a/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.cc +++ b/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.cc
@@ -42,18 +42,18 @@ public: FlexBoxIterator(LayoutDeprecatedFlexibleBox* parent) : box_(parent), largest_ordinal_(1) { - if (box_->Style()->BoxOrient() == EBoxOrient::kHorizontal && - !box_->Style()->IsLeftToRightDirection()) - forward_ = box_->Style()->BoxDirection() != EBoxDirection::kNormal; + if (box_->StyleRef().BoxOrient() == EBoxOrient::kHorizontal && + !box_->StyleRef().IsLeftToRightDirection()) + forward_ = box_->StyleRef().BoxDirection() != EBoxDirection::kNormal; else - forward_ = box_->Style()->BoxDirection() == EBoxDirection::kNormal; + forward_ = box_->StyleRef().BoxDirection() == EBoxDirection::kNormal; if (!forward_) { // No choice, since we're going backwards, we have to find out the highest // ordinal up front. LayoutBox* child = box_->FirstChildBox(); while (child) { - if (child->Style()->BoxOrdinalGroup() > largest_ordinal_) - largest_ordinal_ = child->Style()->BoxOrdinalGroup(); + if (child->StyleRef().BoxOrdinalGroup() > largest_ordinal_) + largest_ordinal_ = child->StyleRef().BoxOrdinalGroup(); child = child->NextSiblingBox(); } } @@ -105,10 +105,10 @@ } if (current_child_ && NotFirstOrdinalValue()) - ordinal_values_.insert(current_child_->Style()->BoxOrdinalGroup()); - } while (!current_child_ || - (!current_child_->IsAnonymous() && - current_child_->Style()->BoxOrdinalGroup() != current_ordinal_)); + ordinal_values_.insert(current_child_->StyleRef().BoxOrdinalGroup()); + } while (!current_child_ || (!current_child_->IsAnonymous() && + current_child_->StyleRef().BoxOrdinalGroup() != + current_ordinal_)); // This peice of code just exists for detecting if this iterator actually // does something other than returning the default order. @@ -129,7 +129,7 @@ bool NotFirstOrdinalValue() { unsigned first_ordinal_value = forward_ ? 1 : largest_ordinal_; return current_ordinal_ == first_ordinal_value && - current_child_->Style()->BoxOrdinalGroup() != first_ordinal_value; + current_child_->StyleRef().BoxOrdinalGroup() != first_ordinal_value; } LayoutDeprecatedFlexibleBox* box_; @@ -148,14 +148,14 @@ // (crawling into blocks). static bool ShouldCheckLines(LayoutBlockFlow* block_flow) { return !block_flow->IsFloatingOrOutOfFlowPositioned() && - block_flow->Style()->Height().IsAuto(); + block_flow->StyleRef().Height().IsAuto(); } static int GetHeightForLineCount(const LayoutBlockFlow* block_flow, int line_count, bool include_bottom, int& count) { - if (block_flow->Style()->Visibility() != EVisibility::kVisible) + if (block_flow->StyleRef().Visibility() != EVisibility::kVisible) return -1; if (block_flow->ChildrenInline()) { for (RootInlineBox* box = block_flow->FirstRootBox(); box; @@ -197,7 +197,7 @@ static RootInlineBox* LineAtIndex(const LayoutBlockFlow* block_flow, int i) { DCHECK_GE(i, 0); - if (block_flow->Style()->Visibility() != EVisibility::kVisible) + if (block_flow->StyleRef().Visibility() != EVisibility::kVisible) return nullptr; if (block_flow->ChildrenInline()) { @@ -225,7 +225,7 @@ static int LineCount(const LayoutBlockFlow* block_flow, const RootInlineBox* stop_root_inline_box = nullptr, bool* found = nullptr) { - if (block_flow->Style()->Visibility() != EVisibility::kVisible) + if (block_flow->StyleRef().Visibility() != EVisibility::kVisible) return 0; int count = 0; if (block_flow->ChildrenInline()) { @@ -260,7 +260,7 @@ } static void ClearTruncation(LayoutBlockFlow* block_flow) { - if (block_flow->Style()->Visibility() != EVisibility::kVisible) + if (block_flow->StyleRef().Visibility() != EVisibility::kVisible) return; if (block_flow->ChildrenInline() && block_flow->HasMarkupTruncation()) { block_flow->SetHasMarkupTruncation(false); @@ -303,8 +303,8 @@ // A margin basically has three types: fixed, percentage, and auto (variable). // Auto and percentage margins simply become 0 when computing min/max width. // Fixed margins can be added in as is. - Length margin_left = child->Style()->MarginLeft(); - Length margin_right = child->Style()->MarginRight(); + Length margin_left = child->StyleRef().MarginLeft(); + Length margin_right = child->StyleRef().MarginRight(); LayoutUnit margin; if (margin_left.IsFixed()) margin += margin_left.Value(); @@ -316,7 +316,7 @@ static bool ChildDoesNotAffectWidthOrFlexing(LayoutObject* child) { // Positioned children and collapsed children don't affect the min/max width. return child->IsOutOfFlowPositioned() || - child->Style()->Visibility() == EVisibility::kCollapse; + child->StyleRef().Visibility() == EVisibility::kCollapse; } static LayoutUnit WidthForChild(LayoutBox* child) { @@ -393,14 +393,14 @@ UseCounter::Count(GetDocument(), WebFeature::kWebkitBoxLayout); - if (Style()->BoxAlign() != ComputedStyleInitialValues::InitialBoxAlign()) + if (StyleRef().BoxAlign() != ComputedStyleInitialValues::InitialBoxAlign()) UseCounter::Count(GetDocument(), WebFeature::kWebkitBoxAlignNotInitial); - if (Style()->BoxDirection() != + if (StyleRef().BoxDirection() != ComputedStyleInitialValues::InitialBoxDirection()) UseCounter::Count(GetDocument(), WebFeature::kWebkitBoxDirectionNotInitial); - if (Style()->BoxPack() != ComputedStyleInitialValues::InitialBoxPack()) + if (StyleRef().BoxPack() != ComputedStyleInitialValues::InitialBoxPack()) UseCounter::Count(GetDocument(), WebFeature::kWebkitBoxPackNotInitial); if (!FirstChildBox()) { @@ -433,8 +433,8 @@ if (previous_size != Size() || (Parent()->IsDeprecatedFlexibleBox() && - Parent()->Style()->BoxOrient() == EBoxOrient::kHorizontal && - Parent()->Style()->BoxAlign() == EBoxAlignment::kStretch)) + Parent()->StyleRef().BoxOrient() == EBoxOrient::kHorizontal && + Parent()->StyleRef().BoxAlign() == EBoxAlignment::kStretch)) relayout_children = true; SetHeight(LayoutUnit()); @@ -471,11 +471,11 @@ bool relayout_children, bool& have_flex) { for (LayoutBox* child = iterator.First(); child; child = iterator.Next()) { - if (child->Style()->BoxFlex() != + if (child->StyleRef().BoxFlex() != ComputedStyleInitialValues::InitialBoxFlex()) UseCounter::Count(document, WebFeature::kWebkitBoxChildFlexNotInitial); - if (child->Style()->BoxOrdinalGroup() != + if (child->StyleRef().BoxOrdinalGroup() != ComputedStyleInitialValues::InitialBoxOrdinalGroup()) { UseCounter::Count(document, WebFeature::kWebkitBoxChildOrdinalGroupNotInitial); @@ -483,7 +483,7 @@ // Check to see if this child flexes. if (!ChildDoesNotAffectWidthOrFlexing(child) && - child->Style()->BoxFlex() > 0.0f) { + child->StyleRef().BoxFlex() > 0.0f) { // We always have to lay out flexible objects again, since the flex // distribution // may have changed, and we need to reallocate space. @@ -534,8 +534,8 @@ // this file. // We probably want to check if the element is replaced. if (relayout_children || (child->IsAtomicInlineLevel() && - (child->Style()->Width().IsPercentOrCalc() || - child->Style()->Height().IsPercentOrCalc()))) + (child->StyleRef().Width().IsPercentOrCalc() || + child->StyleRef().Height().IsPercentOrCalc()))) layout_scope.SetChildNeedsLayout(child); // Compute the child's vertical margins. @@ -548,7 +548,7 @@ child->LayoutIfNeeded(); // Update our height and overflow height. - if (Style()->BoxAlign() == EBoxAlignment::kBaseline) { + if (StyleRef().BoxAlign() == EBoxAlignment::kBaseline) { LayoutUnit ascent(child->FirstLineBoxBaseline()); if (ascent == -1) ascent = child->Size().Height() + child->MarginBottom(); @@ -573,12 +573,14 @@ UpdateFragmentationInfoForChild(*child); } - if (!iterator.First() && HasLineIfEmpty()) - SetHeight(Size().Height() + LineHeight(true, - Style()->IsHorizontalWritingMode() - ? kHorizontalLine - : kVerticalLine, - kPositionOfInteriorLineBoxes)); + if (!iterator.First() && HasLineIfEmpty()) { + SetHeight(Size().Height() + + LineHeight(true, + StyleRef().IsHorizontalWritingMode() + ? kHorizontalLine + : kVerticalLine, + kPositionOfInteriorLineBoxes)); + } SetHeight(Size().Height() + to_add); @@ -590,7 +592,7 @@ height_specified = true; // Now that our height is actually known, we can place our boxes. - stretching_children_ = (Style()->BoxAlign() == EBoxAlignment::kStretch); + stretching_children_ = (StyleRef().BoxAlign() == EBoxAlignment::kStretch); for (LayoutBox* child = iterator.First(); child; child = iterator.Next()) { if (child->IsOutOfFlowPositioned()) { child->ContainingBlock()->InsertPositionedObject(child); @@ -598,14 +600,14 @@ child_layer->SetStaticInlinePosition(x_pos); if (child_layer->StaticBlockPosition() != y_pos) { child_layer->SetStaticBlockPosition(y_pos); - if (child->Style()->HasStaticBlockPosition( - Style()->IsHorizontalWritingMode())) + if (child->StyleRef().HasStaticBlockPosition( + StyleRef().IsHorizontalWritingMode())) child->SetChildNeedsLayout(kMarkOnlyThis); } continue; } - if (child->Style()->Visibility() == EVisibility::kCollapse) { + if (child->StyleRef().Visibility() == EVisibility::kCollapse) { // visibility: collapsed children do not participate in our positioning. // But we need to lay them down. child->LayoutIfNeeded(); @@ -635,7 +637,7 @@ // We can place the child now, using our value of box-align. x_pos += child->MarginLeft(); LayoutUnit child_y = y_pos; - switch (Style()->BoxAlign()) { + switch (StyleRef().BoxAlign()) { case EBoxAlignment::kCenter: child_y += child->MarginTop() + ((ContentHeight() - @@ -691,7 +693,7 @@ for (LayoutBox* child = iterator.First(); child; child = iterator.Next()) { if (AllowedChildFlex(child, expanding)) - total_flex += child->Style()->BoxFlex(); + total_flex += child->StyleRef().BoxFlex(); } LayoutUnit space_available_this_pass = remaining_space; for (LayoutBox* child = iterator.First(); child; @@ -702,7 +704,7 @@ (allowed_flex == LayoutUnit::Max()) ? allowed_flex : LayoutUnit(allowed_flex * - (total_flex / child->Style()->BoxFlex())); + (total_flex / child->StyleRef().BoxFlex())); space_available_this_pass = expanding ? std::min(space_available_this_pass, projected_flex) : std::max(space_available_this_pass, projected_flex); @@ -717,13 +719,13 @@ for (LayoutBox* child = iterator.First(); child && space_available_this_pass && total_flex; child = iterator.Next()) { - if (child->Style()->Visibility() == EVisibility::kCollapse) + if (child->StyleRef().Visibility() == EVisibility::kCollapse) continue; if (AllowedChildFlex(child, expanding)) { LayoutUnit space_add = LayoutUnit(space_available_this_pass * - (child->Style()->BoxFlex() / total_flex)); + (child->StyleRef().BoxFlex() / total_flex)); if (space_add) { child->SetOverrideLogicalWidth(WidthForChild(child) + space_add); flexing_children = true; @@ -733,7 +735,7 @@ space_available_this_pass -= space_add; remaining_space -= space_add; - total_flex -= child->Style()->BoxFlex(); + total_flex -= child->StyleRef().BoxFlex(); } } if (remaining_space == remaining_space_at_beginning) { @@ -758,13 +760,13 @@ } } while (have_flex); - if (remaining_space > 0 && ((Style()->IsLeftToRightDirection() && - Style()->BoxPack() != EBoxPack::kStart) || - (!Style()->IsLeftToRightDirection() && - Style()->BoxPack() != EBoxPack::kEnd))) { + if (remaining_space > 0 && ((StyleRef().IsLeftToRightDirection() && + StyleRef().BoxPack() != EBoxPack::kStart) || + (!StyleRef().IsLeftToRightDirection() && + StyleRef().BoxPack() != EBoxPack::kEnd))) { // Children must be repositioned. LayoutUnit offset; - if (Style()->BoxPack() == EBoxPack::kJustify) { + if (StyleRef().BoxPack() == EBoxPack::kJustify) { // Determine the total number of children. int total_children = 0; for (LayoutBox* child = iterator.First(); child; @@ -798,7 +800,7 @@ } } } else { - if (Style()->BoxPack() == EBoxPack::kCenter) + if (StyleRef().BoxPack() == EBoxPack::kCenter) offset += remaining_space / 2; else // END for LTR, START for RTL offset += remaining_space; @@ -836,7 +838,7 @@ // We confine the line clamp ugliness to vertical flexible boxes (thus keeping // it out of // mainstream block layout); this is not really part of the XUL box model. - if (Style()->HasLineClamp()) + if (StyleRef().HasLineClamp()) ApplyLineClamp(iterator, relayout_children); PaintLayerScrollableArea::DelayScrollOffsetClampScope delay_clamp_scope; @@ -856,21 +858,22 @@ child_layer->SetStaticInlinePosition(BorderStart() + PaddingStart()); if (child_layer->StaticBlockPosition() != Size().Height()) { child_layer->SetStaticBlockPosition(Size().Height()); - if (child->Style()->HasStaticBlockPosition( - Style()->IsHorizontalWritingMode())) + if (child->StyleRef().HasStaticBlockPosition( + StyleRef().IsHorizontalWritingMode())) child->SetChildNeedsLayout(kMarkOnlyThis); } continue; } SubtreeLayoutScope layout_scope(*child); - if (!Style()->HasLineClamp() && - (relayout_children || (child->IsAtomicInlineLevel() && - (child->Style()->Width().IsPercentOrCalc() || - child->Style()->Height().IsPercentOrCalc())))) + if (!StyleRef().HasLineClamp() && + (relayout_children || + (child->IsAtomicInlineLevel() && + (child->StyleRef().Width().IsPercentOrCalc() || + child->StyleRef().Height().IsPercentOrCalc())))) layout_scope.SetChildNeedsLayout(child); - if (child->Style()->Visibility() == EVisibility::kCollapse) { + if (child->StyleRef().Visibility() == EVisibility::kCollapse) { // visibility: collapsed children do not participate in our positioning. // But we need to lay them down. child->LayoutIfNeeded(); @@ -891,7 +894,7 @@ // We can place the child now, using our value of box-align. LayoutUnit child_x = BorderLeft() + PaddingLeft(); - switch (Style()->BoxAlign()) { + switch (StyleRef().BoxAlign()) { case EBoxAlignment::kCenter: case EBoxAlignment::kBaseline: // Baseline just maps to center for // vertical boxes @@ -902,7 +905,7 @@ .ClampNegativeToZero(); break; case EBoxAlignment::kEnd: - if (!Style()->IsLeftToRightDirection()) { + if (!StyleRef().IsLeftToRightDirection()) { child_x += child->MarginLeft(); } else { child_x += @@ -910,7 +913,7 @@ } break; default: // BSTART/BSTRETCH - if (Style()->IsLeftToRightDirection()) { + if (StyleRef().IsLeftToRightDirection()) { child_x += child->MarginLeft(); } else { child_x += @@ -930,12 +933,14 @@ y_pos = Size().Height(); - if (!iterator.First() && HasLineIfEmpty()) - SetHeight(Size().Height() + LineHeight(true, - Style()->IsHorizontalWritingMode() - ? kHorizontalLine - : kVerticalLine, - kPositionOfInteriorLineBoxes)); + if (!iterator.First() && HasLineIfEmpty()) { + SetHeight(Size().Height() + + LineHeight(true, + StyleRef().IsHorizontalWritingMode() + ? kHorizontalLine + : kVerticalLine, + kPositionOfInteriorLineBoxes)); + } SetHeight(Size().Height() + to_add); @@ -977,7 +982,7 @@ for (LayoutBox* child = iterator.First(); child; child = iterator.Next()) { if (AllowedChildFlex(child, expanding)) - total_flex += child->Style()->BoxFlex(); + total_flex += child->StyleRef().BoxFlex(); } LayoutUnit space_available_this_pass = remaining_space; for (LayoutBox* child = iterator.First(); child; @@ -989,7 +994,7 @@ ? allowed_flex : static_cast<LayoutUnit>( allowed_flex * - (total_flex / child->Style()->BoxFlex())); + (total_flex / child->StyleRef().BoxFlex())); space_available_this_pass = expanding ? std::min(space_available_this_pass, projected_flex) : std::max(space_available_this_pass, projected_flex); @@ -1007,7 +1012,7 @@ if (AllowedChildFlex(child, expanding)) { LayoutUnit space_add = static_cast<LayoutUnit>( space_available_this_pass * - (child->Style()->BoxFlex() / total_flex)); + (child->StyleRef().BoxFlex() / total_flex)); if (space_add) { child->SetOverrideLogicalHeight(HeightForChild(child) + space_add); @@ -1018,7 +1023,7 @@ space_available_this_pass -= space_add; remaining_space -= space_add; - total_flex -= child->Style()->BoxFlex(); + total_flex -= child->StyleRef().BoxFlex(); } } if (remaining_space == remaining_space_at_beginning) { @@ -1044,10 +1049,10 @@ } } while (have_flex); - if (Style()->BoxPack() != EBoxPack::kStart && remaining_space > 0) { + if (StyleRef().BoxPack() != EBoxPack::kStart && remaining_space > 0) { // Children must be repositioned. LayoutUnit offset; - if (Style()->BoxPack() == EBoxPack::kJustify) { + if (StyleRef().BoxPack() == EBoxPack::kJustify) { // Determine the total number of children. int total_children = 0; for (LayoutBox* child = iterator.First(); child; @@ -1081,7 +1086,7 @@ } } } else { - if (Style()->BoxPack() == EBoxPack::kCenter) + if (StyleRef().BoxPack() == EBoxPack::kCenter) offset += remaining_space / 2; else // END offset += remaining_space; @@ -1131,9 +1136,9 @@ child->ClearOverrideSize(); if (relayout_children || (child->IsAtomicInlineLevel() && - (child->Style()->Width().IsPercentOrCalc() || - child->Style()->Height().IsPercentOrCalc())) || - (child->Style()->Height().IsAuto() && child->IsLayoutBlock())) { + (child->StyleRef().Width().IsPercentOrCalc() || + child->StyleRef().Height().IsPercentOrCalc())) || + (child->StyleRef().Height().IsAuto() && child->IsLayoutBlock())) { child->SetChildNeedsLayout(kMarkOnlyThis); // Dirty all the positioned objects. @@ -1143,7 +1148,7 @@ } } child->LayoutIfNeeded(); - if (child->Style()->Height().IsAuto() && child->IsLayoutBlockFlow()) + if (child->StyleRef().Height().IsAuto() && child->IsLayoutBlockFlow()) max_line_count = std::max(max_line_count, LineCount(ToLayoutBlockFlow(child))); } @@ -1151,7 +1156,7 @@ // Get the number of lines and then alter all block flow children with auto // height to use the // specified height. We always try to leave room for at least one line. - int num_visible_lines = Style()->LineClamp(); + int num_visible_lines = StyleRef().LineClamp(); DCHECK_GT(num_visible_lines, 0); if (num_visible_lines >= max_line_count) @@ -1159,7 +1164,7 @@ for (LayoutBox* child = iterator.First(); child; child = iterator.Next()) { if (ChildDoesNotAffectWidthOrFlexing(child) || - !child->Style()->Height().IsAuto() || !child->IsLayoutBlockFlow()) + !child->StyleRef().Height().IsAuto() || !child->IsLayoutBlockFlow()) continue; LayoutBlockFlow* block_child = ToLayoutBlockFlow(child); @@ -1177,7 +1182,7 @@ child->ForceChildLayout(); // FIXME: For now don't support RTL. - if (Style()->Direction() != TextDirection::kLtr) + if (StyleRef().Direction() != TextDirection::kLtr) continue; // Get the last line @@ -1195,7 +1200,7 @@ const Font& font = Style(num_visible_lines == 1)->GetFont(); float total_width = font.Width(ConstructTextRun(font, &kHorizontalEllipsisCharacter, 1, - StyleRef(), Style()->Direction())); + StyleRef(), StyleRef().Direction())); // See if this width can be accommodated on the last visible line LineLayoutBlockFlow dest_block = last_visible_line->Block(); @@ -1203,10 +1208,10 @@ // FIXME: Directions of src/destBlock could be different from our direction // and from one another. - if (!src_block.Style()->IsLeftToRightDirection()) + if (!src_block.StyleRef().IsLeftToRightDirection()) continue; - bool left_to_right = dest_block.Style()->IsLeftToRightDirection(); + bool left_to_right = dest_block.StyleRef().IsLeftToRightDirection(); if (!left_to_right) continue; @@ -1243,9 +1248,9 @@ child->ClearOverrideSize(); if ((child->IsAtomicInlineLevel() && - (child->Style()->Width().IsPercentOrCalc() || - child->Style()->Height().IsPercentOrCalc())) || - (child->Style()->Height().IsAuto() && child->IsLayoutBlock())) { + (child->StyleRef().Width().IsPercentOrCalc() || + child->StyleRef().Height().IsPercentOrCalc())) || + (child->StyleRef().Height().IsAuto() && child->IsLayoutBlock())) { child->SetChildNeedsLayout(); if (child->IsLayoutBlockFlow()) { @@ -1269,7 +1274,7 @@ LayoutUnit LayoutDeprecatedFlexibleBox::AllowedChildFlex(LayoutBox* child, bool expanding) { if (ChildDoesNotAffectWidthOrFlexing(child) || - child->Style()->BoxFlex() == 0.0f) + child->StyleRef().BoxFlex() == 0.0f) return LayoutUnit(); if (expanding) { @@ -1277,8 +1282,8 @@ // FIXME: For now just handle fixed values. LayoutUnit max_width = LayoutUnit::Max(); LayoutUnit width = ContentWidthForChild(child); - if (child->Style()->MaxWidth().IsFixed()) - max_width = LayoutUnit(child->Style()->MaxWidth().Value()); + if (child->StyleRef().MaxWidth().IsFixed()) + max_width = LayoutUnit(child->StyleRef().MaxWidth().Value()); if (max_width == LayoutUnit::Max()) return max_width; return (max_width - width).ClampNegativeToZero(); @@ -1286,8 +1291,8 @@ // FIXME: For now just handle fixed values. LayoutUnit max_height = LayoutUnit::Max(); LayoutUnit height = ContentHeightForChild(child); - if (child->Style()->MaxHeight().IsFixed()) - max_height = LayoutUnit(child->Style()->MaxHeight().Value()); + if (child->StyleRef().MaxHeight().IsFixed()) + max_height = LayoutUnit(child->StyleRef().MaxHeight().Value()); if (max_height == LayoutUnit::Max()) return max_height; return (max_height - height).ClampNegativeToZero(); @@ -1297,7 +1302,7 @@ if (IsHorizontal()) { LayoutUnit min_width = child->MinPreferredLogicalWidth(); LayoutUnit width = ContentWidthForChild(child); - const Length& min_width_length = child->Style()->MinWidth(); + const Length& min_width_length = child->StyleRef().MinWidth(); if (min_width_length.IsFixed()) min_width = LayoutUnit(min_width_length.Value()); else if (min_width_length.IsAuto()) @@ -1306,7 +1311,7 @@ LayoutUnit allowed_shrinkage = (min_width - width).ClampPositiveToZero(); return allowed_shrinkage; } - const Length& min_height_length = child->Style()->MinHeight(); + const Length& min_height_length = child->StyleRef().MinHeight(); if (min_height_length.IsFixed() || min_height_length.IsAuto()) { LayoutUnit min_height(min_height_length.Value()); LayoutUnit height = ContentHeightForChild(child);
diff --git a/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.h b/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.h index 5b52ab81..f7000047 100644 --- a/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.h +++ b/third_party/blink/renderer/core/layout/layout_deprecated_flexible_box.h
@@ -56,10 +56,10 @@ LayoutUnit AllowedChildFlex(LayoutBox* child, bool expanding); bool IsVertical() const { - return Style()->BoxOrient() == EBoxOrient::kVertical; + return StyleRef().BoxOrient() == EBoxOrient::kVertical; } bool IsHorizontal() const { - return Style()->BoxOrient() == EBoxOrient::kHorizontal; + return StyleRef().BoxOrient() == EBoxOrient::kHorizontal; } void ApplyLineClamp(FlexBoxIterator&, bool relayout_children);
diff --git a/third_party/blink/renderer/core/layout/layout_details_marker.cc b/third_party/blink/renderer/core/layout/layout_details_marker.cc index b5fdf263..16f354e 100644 --- a/third_party/blink/renderer/core/layout/layout_details_marker.cc +++ b/third_party/blink/renderer/core/layout/layout_details_marker.cc
@@ -33,17 +33,17 @@ : LayoutBlockFlow(element) {} LayoutDetailsMarker::Orientation LayoutDetailsMarker::GetOrientation() const { - switch (Style()->GetWritingMode()) { + switch (StyleRef().GetWritingMode()) { case WritingMode::kHorizontalTb: - if (Style()->IsLeftToRightDirection()) + if (StyleRef().IsLeftToRightDirection()) return IsOpen() ? kDown : kRight; return IsOpen() ? kDown : kLeft; case WritingMode::kVerticalRl: - if (Style()->IsLeftToRightDirection()) + if (StyleRef().IsLeftToRightDirection()) return IsOpen() ? kLeft : kDown; return IsOpen() ? kLeft : kUp; case WritingMode::kVerticalLr: - if (Style()->IsLeftToRightDirection()) + if (StyleRef().IsLeftToRightDirection()) return IsOpen() ? kRight : kDown; return IsOpen() ? kRight : kUp; // TODO(layout-dev): Sideways-lr and sideways-rl are not yet supported.
diff --git a/third_party/blink/renderer/core/layout/layout_embedded_content.cc b/third_party/blink/renderer/core/layout/layout_embedded_content.cc index 0023ca9..6c5b17f 100644 --- a/third_party/blink/renderer/core/layout/layout_embedded_content.cc +++ b/third_party/blink/renderer/core/layout/layout_embedded_content.cc
@@ -258,7 +258,7 @@ if (!embedded_content_view) return; - if (Style()->Visibility() != EVisibility::kVisible) { + if (StyleRef().Visibility() != EVisibility::kVisible) { embedded_content_view->Hide(); } else { embedded_content_view->Show(); @@ -319,7 +319,7 @@ if (!NeedsLayout()) UpdateGeometry(*embedded_content_view); - if (Style()->Visibility() != EVisibility::kVisible) { + if (StyleRef().Visibility() != EVisibility::kVisible) { embedded_content_view->Hide(); } else { embedded_content_view->Show();
diff --git a/third_party/blink/renderer/core/layout/layout_embedded_object.cc b/third_party/blink/renderer/core/layout/layout_embedded_object.cc index a136627..58387dc 100644 --- a/third_party/blink/renderer/core/layout/layout_embedded_object.cc +++ b/third_party/blink/renderer/core/layout/layout_embedded_object.cc
@@ -118,7 +118,7 @@ if (frame_view && frame_view->GetIntrinsicSizingInfo(intrinsic_sizing_info)) { // Handle zoom & vertical writing modes here, as the embedded document // doesn't know about them. - intrinsic_sizing_info.size.Scale(Style()->EffectiveZoom()); + intrinsic_sizing_info.size.Scale(StyleRef().EffectiveZoom()); if (!IsHorizontalWritingMode()) intrinsic_sizing_info.Transpose();
diff --git a/third_party/blink/renderer/core/layout/layout_fieldset.cc b/third_party/blink/renderer/core/layout/layout_fieldset.cc index b872b41..2d661fb 100644 --- a/third_party/blink/renderer/core/layout/layout_fieldset.cc +++ b/third_party/blink/renderer/core/layout/layout_fieldset.cc
@@ -39,8 +39,8 @@ if (LayoutBox* legend = FindInFlowLegend()) { int legend_min_width = legend->MinPreferredLogicalWidth().ToInt(); - Length legend_margin_left = legend->Style()->MarginLeft(); - Length legend_margin_right = legend->Style()->MarginRight(); + Length legend_margin_left = legend->StyleRef().MarginLeft(); + Length legend_margin_right = legend->StyleRef().MarginRight(); if (legend_margin_left.IsFixed()) legend_min_width += legend_margin_left.Value(); @@ -66,8 +66,8 @@ legend->LayoutIfNeeded(); LayoutUnit logical_left; - if (Style()->IsLeftToRightDirection()) { - switch (legend->Style()->GetTextAlign()) { + if (StyleRef().IsLeftToRightDirection()) { + switch (legend->StyleRef().GetTextAlign()) { case ETextAlign::kCenter: logical_left = (LogicalWidth() - LogicalWidthForChild(*legend)) / 2; break; @@ -81,7 +81,7 @@ break; } } else { - switch (legend->Style()->GetTextAlign()) { + switch (legend->StyleRef().GetTextAlign()) { case ETextAlign::kLeft: logical_left = BorderStart() + PaddingStart(); break;
diff --git a/third_party/blink/renderer/core/layout/layout_file_upload_control.cc b/third_party/blink/renderer/core/layout/layout_file_upload_control.cc index ac4ec435..6bdb6aa 100644 --- a/third_party/blink/renderer/core/layout/layout_file_upload_control.cc +++ b/third_party/blink/renderer/core/layout/layout_file_upload_control.cc
@@ -88,7 +88,7 @@ // characters (using "0" as the nominal character). const UChar kCharacter = '0'; const String character_as_string = String(&kCharacter, 1); - const Font& font = Style()->GetFont(); + const Font& font = StyleRef().GetFont(); float min_default_label_width = kDefaultWidthNumChars * font.Width(ConstructTextRun(font, character_as_string, StyleRef(), @@ -106,7 +106,7 @@ max_logical_width = LayoutUnit(ceilf(std::max(min_default_label_width, default_label_width))); - if (!Style()->Width().IsPercentOrCalc()) + if (!StyleRef().Width().IsPercentOrCalc()) min_logical_width = max_logical_width; } @@ -178,7 +178,7 @@ HTMLInputElement* input = ToHTMLInputElement(GetNode()); DCHECK(input->files()); return LayoutTheme::GetTheme().FileListNameForWidth( - input->GetLocale(), input->files(), Style()->GetFont(), + input->GetLocale(), input->files(), StyleRef().GetFont(), MaxFilenameWidth()); }
diff --git a/third_party/blink/renderer/core/layout/layout_flexible_box.cc b/third_party/blink/renderer/core/layout/layout_flexible_box.cc index 9131c71..0791219 100644 --- a/third_party/blink/renderer/core/layout/layout_flexible_box.cc +++ b/third_party/blink/renderer/core/layout/layout_flexible_box.cc
@@ -246,9 +246,9 @@ if (!adjustment_width && !adjustment_height) return size; - EFlexDirection flex_direction = Style()->FlexDirection(); - TextDirection text_direction = Style()->Direction(); - WritingMode writing_mode = Style()->GetWritingMode(); + EFlexDirection flex_direction = StyleRef().FlexDirection(); + TextDirection text_direction = StyleRef().Direction(); + WritingMode writing_mode = StyleRef().GetWritingMode(); if (flex_direction == EFlexDirection::kRow) { if (text_direction == TextDirection::kRtl) { @@ -294,18 +294,18 @@ } bool LayoutFlexibleBox::HasTopOverflow() const { - EFlexDirection flex_direction = Style()->FlexDirection(); + EFlexDirection flex_direction = StyleRef().FlexDirection(); if (IsHorizontalWritingMode()) return flex_direction == EFlexDirection::kColumnReverse; - return flex_direction == (Style()->IsLeftToRightDirection() + return flex_direction == (StyleRef().IsLeftToRightDirection() ? EFlexDirection::kRowReverse : EFlexDirection::kRow); } bool LayoutFlexibleBox::HasLeftOverflow() const { - EFlexDirection flex_direction = Style()->FlexDirection(); + EFlexDirection flex_direction = StyleRef().FlexDirection(); if (IsHorizontalWritingMode()) { - return flex_direction == (Style()->IsLeftToRightDirection() + return flex_direction == (StyleRef().IsLeftToRightDirection() ? EFlexDirection::kRowReverse : EFlexDirection::kRow); } @@ -438,7 +438,7 @@ AlignChildren(line_contexts); - if (Style()->FlexWrap() == EFlexWrap::kWrapReverse) + if (StyleRef().FlexWrap() == EFlexWrap::kWrapReverse) FlipForWrapReverse(line_contexts, cross_axis_start_edge); // direction:rtl + flex-direction:column means the cross-axis direction is @@ -468,7 +468,7 @@ } bool LayoutFlexibleBox::IsColumnFlow() const { - return Style()->IsColumnFlexDirection(); + return StyleRef().IsColumnFlexDirection(); } bool LayoutFlexibleBox::IsHorizontalFlow() const { @@ -479,22 +479,23 @@ bool LayoutFlexibleBox::IsLeftToRightFlow() const { if (IsColumnFlow()) { - return blink::IsHorizontalWritingMode(Style()->GetWritingMode()) || - IsFlippedLinesWritingMode(Style()->GetWritingMode()); + return blink::IsHorizontalWritingMode(StyleRef().GetWritingMode()) || + IsFlippedLinesWritingMode(StyleRef().GetWritingMode()); } - return Style()->IsLeftToRightDirection() ^ - (Style()->FlexDirection() == EFlexDirection::kRowReverse); + return StyleRef().IsLeftToRightDirection() ^ + (StyleRef().FlexDirection() == EFlexDirection::kRowReverse); } bool LayoutFlexibleBox::IsMultiline() const { - return Style()->FlexWrap() != EFlexWrap::kNowrap; + return StyleRef().FlexWrap() != EFlexWrap::kNowrap; } Length LayoutFlexibleBox::FlexBasisForChild(const LayoutBox& child) const { - Length flex_length = child.Style()->FlexBasis(); - if (flex_length.IsAuto()) - flex_length = - IsHorizontalFlow() ? child.Style()->Width() : child.Style()->Height(); + Length flex_length = child.StyleRef().FlexBasis(); + if (flex_length.IsAuto()) { + flex_length = IsHorizontalFlow() ? child.StyleRef().Width() + : child.StyleRef().Height(); + } return flex_length; } @@ -942,7 +943,7 @@ LayoutUnit main_axis_offset = FlowAwareBorderStart() + FlowAwarePaddingStart(); - if (Style()->FlexDirection() == EFlexDirection::kRowReverse && + if (StyleRef().FlexDirection() == EFlexDirection::kRowReverse && ShouldPlaceBlockDirectionScrollbarOnLogicalLeft()) { main_axis_offset += IsHorizontalFlow() ? VerticalScrollbarWidth() : HorizontalScrollbarHeight(); @@ -971,11 +972,12 @@ bool LayoutFlexibleBox::HasAutoMarginsInCrossAxis( const LayoutBox& child) const { - if (IsHorizontalFlow()) - return child.Style()->MarginTop().IsAuto() || - child.Style()->MarginBottom().IsAuto(); - return child.Style()->MarginLeft().IsAuto() || - child.Style()->MarginRight().IsAuto(); + if (IsHorizontalFlow()) { + return child.StyleRef().MarginTop().IsAuto() || + child.StyleRef().MarginBottom().IsAuto(); + } + return child.StyleRef().MarginLeft().IsAuto() || + child.StyleRef().MarginRight().IsAuto(); } bool LayoutFlexibleBox::UpdateAutoMarginsInCrossAxis( @@ -985,10 +987,10 @@ DCHECK_GE(available_alignment_space, LayoutUnit()); bool is_horizontal = IsHorizontalFlow(); - Length top_or_left = - is_horizontal ? child.Style()->MarginTop() : child.Style()->MarginLeft(); - Length bottom_or_right = is_horizontal ? child.Style()->MarginBottom() - : child.Style()->MarginRight(); + Length top_or_left = is_horizontal ? child.StyleRef().MarginTop() + : child.StyleRef().MarginLeft(); + Length bottom_or_right = is_horizontal ? child.StyleRef().MarginBottom() + : child.StyleRef().MarginRight(); if (top_or_left.IsAuto() && bottom_or_right.IsAuto()) { AdjustAlignmentForChild(child, available_alignment_space / 2); if (is_horizontal) { @@ -1001,13 +1003,13 @@ return true; } bool should_adjust_top_or_left = true; - if (IsColumnFlow() && !child.Style()->IsLeftToRightDirection()) { + if (IsColumnFlow() && !child.StyleRef().IsLeftToRightDirection()) { // For column flows, only make this adjustment if topOrLeft corresponds to // the "before" margin, so that flipForRightToLeftColumn will do the right // thing. should_adjust_top_or_left = false; } - if (!IsColumnFlow() && child.Style()->IsFlippedBlocksWritingMode()) { + if (!IsColumnFlow() && child.StyleRef().IsFlippedBlocksWritingMode()) { // If we are a flipped writing mode, we need to adjust the opposite side. // This is only needed for row flows because this only affects the // block-direction axis. @@ -1061,13 +1063,14 @@ // start/end margins. if (IsHorizontalFlow()) { child->SetMarginLeft( - ComputeChildMarginValue(child->Style()->MarginLeft())); + ComputeChildMarginValue(child->StyleRef().MarginLeft())); child->SetMarginRight( - ComputeChildMarginValue(child->Style()->MarginRight())); + ComputeChildMarginValue(child->StyleRef().MarginRight())); } else { - child->SetMarginTop(ComputeChildMarginValue(child->Style()->MarginTop())); + child->SetMarginTop( + ComputeChildMarginValue(child->StyleRef().MarginTop())); child->SetMarginBottom( - ComputeChildMarginValue(child->Style()->MarginBottom())); + ComputeChildMarginValue(child->StyleRef().MarginBottom())); } } } @@ -1077,8 +1080,8 @@ const LayoutBox& child) const { MinMaxSize sizes{LayoutUnit(), LayoutUnit::Max()}; - Length max = IsHorizontalFlow() ? child.Style()->MaxWidth() - : child.Style()->MaxHeight(); + Length max = IsHorizontalFlow() ? child.StyleRef().MaxWidth() + : child.StyleRef().MaxHeight(); if (max.IsSpecifiedOrIntrinsic()) { sizes.max_size = ComputeMainAxisExtentForChild(child, kMaxSize, max); if (sizes.max_size == -1) @@ -1086,8 +1089,8 @@ DCHECK_GE(sizes.max_size, LayoutUnit()); } - Length min = IsHorizontalFlow() ? child.Style()->MinWidth() - : child.Style()->MinHeight(); + Length min = IsHorizontalFlow() ? child.StyleRef().MinWidth() + : child.StyleRef().MinHeight(); if (min.IsSpecifiedOrIntrinsic()) { sizes.min_size = ComputeMainAxisExtentForChild(child, kMinSize, min); // computeMainAxisExtentForChild can return -1 when the child has a @@ -1197,10 +1200,10 @@ LayoutUnit LayoutFlexibleBox::AdjustChildSizeForAspectRatioCrossAxisMinAndMax( const LayoutBox& child, LayoutUnit child_size) const { - Length cross_min = IsHorizontalFlow() ? child.Style()->MinHeight() - : child.Style()->MinWidth(); - Length cross_max = IsHorizontalFlow() ? child.Style()->MaxHeight() - : child.Style()->MaxWidth(); + Length cross_min = IsHorizontalFlow() ? child.StyleRef().MinHeight() + : child.StyleRef().MinWidth(); + Length cross_max = IsHorizontalFlow() ? child.StyleRef().MaxHeight() + : child.StyleRef().MaxWidth(); if (CrossAxisLengthIsDefinite(child, cross_max)) { LayoutUnit max_value = @@ -1380,8 +1383,8 @@ FlowAwareBorderStart() + FlowAwarePaddingStart(); if (child_layer->StaticInlinePosition() != static_inline_position) { child_layer->SetStaticInlinePosition(static_inline_position); - if (child.Style()->HasStaticInlinePosition( - Style()->IsHorizontalWritingMode())) + if (child.StyleRef().HasStaticInlinePosition( + StyleRef().IsHorizontalWritingMode())) child.SetChildNeedsLayout(kMarkOnlyThis); } @@ -1389,8 +1392,8 @@ FlowAwareBorderBefore() + FlowAwarePaddingBefore(); if (child_layer->StaticBlockPosition() != static_block_position) { child_layer->SetStaticBlockPosition(static_block_position); - if (child.Style()->HasStaticBlockPosition( - Style()->IsHorizontalWritingMode())) + if (child.StyleRef().HasStaticBlockPosition( + StyleRef().IsHorizontalWritingMode())) child.SetChildNeedsLayout(kMarkOnlyThis); } } @@ -1400,14 +1403,14 @@ if (HasAutoMarginsInCrossAxis(child)) { child.UpdateLogicalHeight(); if (IsHorizontalFlow()) { - if (child.Style()->MarginTop().IsAuto()) + if (child.StyleRef().MarginTop().IsAuto()) child.SetMarginTop(LayoutUnit()); - if (child.Style()->MarginBottom().IsAuto()) + if (child.StyleRef().MarginBottom().IsAuto()) child.SetMarginBottom(LayoutUnit()); } else { - if (child.Style()->MarginLeft().IsAuto()) + if (child.StyleRef().MarginLeft().IsAuto()) child.SetMarginLeft(LayoutUnit()); - if (child.Style()->MarginRight().IsAuto()) + if (child.StyleRef().MarginRight().IsAuto()) child.SetMarginRight(LayoutUnit()); } } @@ -1437,10 +1440,10 @@ bool result = false; if (IsHorizontalFlow() != child.StyleRef().IsHorizontalWritingMode()) { Length child_flex_basis = FlexBasisForChild(child); - Length child_min_size = IsHorizontalFlow() ? child.Style()->MinWidth() - : child.Style()->MinHeight(); - Length child_max_size = IsHorizontalFlow() ? child.Style()->MaxWidth() - : child.Style()->MaxHeight(); + Length child_min_size = IsHorizontalFlow() ? child.StyleRef().MinWidth() + : child.StyleRef().MinHeight(); + Length child_max_size = IsHorizontalFlow() ? child.StyleRef().MaxWidth() + : child.StyleRef().MaxHeight(); if (child_flex_basis.IsIntrinsic() || child_min_size.IsIntrinsicOrAuto() || child_max_size.IsIntrinsic()) result = true; @@ -1544,7 +1547,7 @@ CrossAxisScrollbarExtent())); } - if (Style()->FlexDirection() == EFlexDirection::kColumnReverse) { + if (StyleRef().FlexDirection() == EFlexDirection::kColumnReverse) { // We have to do an extra pass for column-reverse to reposition the flex // items since the start depends on the height of the flexbox, which we // only know after we've positioned all the flex items. @@ -1690,7 +1693,7 @@ min_margin_after_baselines.push_back(min_margin_after_baseline); } - if (Style()->FlexWrap() != EFlexWrap::kWrapReverse) + if (StyleRef().FlexWrap() != EFlexWrap::kWrapReverse) return; // wrap-reverse flips the cross axis start and end. For baseline alignment, @@ -1716,7 +1719,7 @@ LayoutUnit line_cross_axis_extent) { LayoutBox& child = *flex_item.box; if (!flex_item.HasOrthogonalFlow() && - child.Style()->LogicalHeight().IsAuto()) { + child.StyleRef().LogicalHeight().IsAuto()) { LayoutUnit stretched_logical_height = std::max(child.BorderAndPaddingLogicalHeight(), line_cross_axis_extent - flex_item.CrossAxisMarginExtent()); @@ -1754,7 +1757,7 @@ child_intrinsic_content_logical_height); } } else if (flex_item.HasOrthogonalFlow() && - child.Style()->LogicalWidth().IsAuto()) { + child.StyleRef().LogicalWidth().IsAuto()) { LayoutUnit child_width = (line_cross_axis_extent - flex_item.CrossAxisMarginExtent()) .ClampNegativeToZero(); @@ -1771,7 +1774,7 @@ void LayoutFlexibleBox::FlipForRightToLeftColumn( const Vector<FlexLine>& line_contexts) { - if (Style()->IsLeftToRightDirection() || !IsColumnFlow()) + if (StyleRef().IsLeftToRightDirection() || !IsColumnFlow()) return; LayoutUnit cross_extent = CrossAxisExtent();
diff --git a/third_party/blink/renderer/core/layout/layout_frame.cc b/third_party/blink/renderer/core/layout/layout_frame.cc index 73500ad..5f31c15 100644 --- a/third_party/blink/renderer/core/layout/layout_frame.cc +++ b/third_party/blink/renderer/core/layout/layout_frame.cc
@@ -44,7 +44,7 @@ void LayoutFrame::ImageChanged(WrappedImagePtr image, CanDeferInvalidation, const IntRect*) { - if (const CursorList* cursors = Style()->Cursors()) { + if (const CursorList* cursors = StyleRef().Cursors()) { for (const CursorData& cursor : *cursors) { if (cursor.GetImage() && cursor.GetImage()->CachedImage() == image) { if (LocalFrame* frame = GetFrame()) {
diff --git a/third_party/blink/renderer/core/layout/layout_frame_set.cc b/third_party/blink/renderer/core/layout/layout_frame_set.cc index 9e31845..0faa36f5 100644 --- a/third_party/blink/renderer/core/layout/layout_frame_set.cc +++ b/third_party/blink/renderer/core/layout/layout_frame_set.cc
@@ -96,7 +96,7 @@ int count_fixed = 0; int count_percent = 0; - float effective_zoom = Style()->EffectiveZoom(); + float effective_zoom = StyleRef().EffectiveZoom(); // First we need to investigate how many columns of each type we have and // how much space these columns are going to require. @@ -588,4 +588,22 @@ return LayoutBox::GetCursor(point, cursor); } +void LayoutFrameSet::InsertedIntoTree() { + LayoutBox::InsertedIntoTree(); + // User scrollability on the scroll paint property depends on framesets (see: + // LayoutView::CalculateScrollbarModes) so we need to ensure the property gets + // updated. + if (Parent() && Parent() == View()) + Parent()->SetNeedsPaintPropertyUpdate(); +} + +void LayoutFrameSet::WillBeRemovedFromTree() { + LayoutBox::WillBeRemovedFromTree(); + // User scrollability on the scroll paint property depends on framesets (see: + // LayoutView::CalculateScrollbarModes) so we need to ensure the property gets + // updated. + if (Parent() && Parent() == View()) + Parent()->SetNeedsPaintPropertyUpdate(); +} + } // namespace blink
diff --git a/third_party/blink/renderer/core/layout/layout_frame_set.h b/third_party/blink/renderer/core/layout/layout_frame_set.h index 6e4df71..843744e1 100644 --- a/third_party/blink/renderer/core/layout/layout_frame_set.h +++ b/third_party/blink/renderer/core/layout/layout_frame_set.h
@@ -153,6 +153,9 @@ return false; } + void InsertedIntoTree() override; + void WillBeRemovedFromTree() override; + LayoutObjectChildList children_; GridAxis rows_;
diff --git a/third_party/blink/renderer/core/layout/layout_geometry_map.cc b/third_party/blink/renderer/core/layout/layout_geometry_map.cc index c9948bf..73c4c9b 100644 --- a/third_party/blink/renderer/core/layout/layout_geometry_map.cc +++ b/third_party/blink/renderer/core/layout/layout_geometry_map.cc
@@ -269,8 +269,8 @@ base::AutoReset<size_t> position_change(&insertion_position_, mapping_.size()); bool accumulating_transform = - layout_object.Style()->Preserves3D() || - ancestor_layer->GetLayoutObject().Style()->Preserves3D(); + layout_object.StyleRef().Preserves3D() || + ancestor_layer->GetLayoutObject().StyleRef().Preserves3D(); Push(&layout_object, ToLayoutSize(layer_offset), accumulating_transform ? kAccumulatingTransform : 0); return;
diff --git a/third_party/blink/renderer/core/layout/layout_grid.cc b/third_party/blink/renderer/core/layout/layout_grid.cc index 66e5e93..351edfd 100644 --- a/third_party/blink/renderer/core/layout/layout_grid.cc +++ b/third_party/blink/renderer/core/layout/layout_grid.cc
@@ -960,7 +960,7 @@ Grid& grid, const Vector<LayoutBox*>& auto_grid_items) const { bool is_for_columns = AutoPlacementMajorAxisDirection() == kForColumns; - bool is_grid_auto_flow_dense = Style()->IsGridAutoFlowAlgorithmDense(); + bool is_grid_auto_flow_dense = StyleRef().IsGridAutoFlowAlgorithmDense(); // Mapping between the major axis tracks (rows or columns) and the last // auto-placed item's position inserted on that track. This is needed to @@ -1009,7 +1009,7 @@ Grid& grid, const Vector<LayoutBox*>& auto_grid_items) const { std::pair<size_t, size_t> auto_placement_cursor = std::make_pair(0, 0); - bool is_grid_auto_flow_dense = Style()->IsGridAutoFlowAlgorithmDense(); + bool is_grid_auto_flow_dense = StyleRef().IsGridAutoFlowAlgorithmDense(); for (auto* const auto_grid_item : auto_grid_items) { PlaceAutoMajorAxisItemOnGrid(grid, *auto_grid_item, auto_placement_cursor); @@ -1115,11 +1115,11 @@ } GridTrackSizingDirection LayoutGrid::AutoPlacementMajorAxisDirection() const { - return Style()->IsGridAutoFlowDirectionColumn() ? kForColumns : kForRows; + return StyleRef().IsGridAutoFlowDirectionColumn() ? kForColumns : kForRows; } GridTrackSizingDirection LayoutGrid::AutoPlacementMinorAxisDirection() const { - return Style()->IsGridAutoFlowDirectionColumn() ? kForRows : kForColumns; + return StyleRef().IsGridAutoFlowDirectionColumn() ? kForRows : kForColumns; } void LayoutGrid::DirtyGrid() { @@ -1975,11 +1975,11 @@ int end_line = span.UntranslatedEndLine() + smallest_start; int last_line = NumTracks(direction, *grid_); GridPosition start_position = direction == kForColumns - ? child.Style()->GridColumnStart() - : child.Style()->GridRowStart(); + ? child.StyleRef().GridColumnStart() + : child.StyleRef().GridRowStart(); GridPosition end_position = direction == kForColumns - ? child.Style()->GridColumnEnd() - : child.Style()->GridRowEnd(); + ? child.StyleRef().GridColumnEnd() + : child.StyleRef().GridRowEnd(); bool start_is_auto = GridPositionIsAutoForOutOfFlow(start_position, direction) || @@ -2040,7 +2040,7 @@ LayoutUnit child_margin = is_flowaware_row_axis ? child.MarginLineLeft() : child.MarginBefore(); LayoutUnit offset = child_position - grid_border - child_margin; - if (!is_row_axis || Style()->IsLeftToRightDirection()) + if (!is_row_axis || StyleRef().IsLeftToRightDirection()) return offset; LayoutUnit child_breadth = @@ -2297,7 +2297,7 @@ // We stored column_position_'s data ignoring the direction, hence we might // need now to translate positions from RTL to LTR, as it's more convenient // for painting. - if (!Style()->IsLeftToRightDirection()) { + if (!StyleRef().IsLeftToRightDirection()) { row_axis_offset = (child.IsOutOfFlowPositioned() ? TranslateOutOfFlowRTLCoordinate(child, row_axis_offset) @@ -2321,7 +2321,7 @@ // See comment in findChildLogicalPosition() about why we need sometimes to // translate from RTL to LTR the rowAxisOffset coordinate. - return LayoutPoint(Style()->IsLeftToRightDirection() + return LayoutPoint(StyleRef().IsLeftToRightDirection() ? row_axis_offset : TranslateRTLCoordinate(row_axis_offset), column_axis_offset);
diff --git a/third_party/blink/renderer/core/layout/layout_html_canvas.cc b/third_party/blink/renderer/core/layout/layout_html_canvas.cc index ad04b69..c3276c2 100644 --- a/third_party/blink/renderer/core/layout/layout_html_canvas.cc +++ b/third_party/blink/renderer/core/layout/layout_html_canvas.cc
@@ -52,8 +52,8 @@ void LayoutHTMLCanvas::CanvasSizeChanged() { IntSize canvas_size = ToHTMLCanvasElement(GetNode())->Size(); - LayoutSize zoomed_size(canvas_size.Width() * Style()->EffectiveZoom(), - canvas_size.Height() * Style()->EffectiveZoom()); + LayoutSize zoomed_size(canvas_size.Width() * StyleRef().EffectiveZoom(), + canvas_size.Height() * StyleRef().EffectiveZoom()); if (zoomed_size == IntrinsicSize()) return;
diff --git a/third_party/blink/renderer/core/layout/layout_iframe.cc b/third_party/blink/renderer/core/layout/layout_iframe.cc index b0c1de4..b13a56e 100644 --- a/third_party/blink/renderer/core/layout/layout_iframe.cc +++ b/third_party/blink/renderer/core/layout/layout_iframe.cc
@@ -41,7 +41,7 @@ } PaintLayerType LayoutIFrame::LayerTypeRequired() const { - if (Style()->Resize() != EResize::kNone) + if (StyleRef().Resize() != EResize::kNone) return kNormalPaintLayer; return LayoutEmbeddedContent::LayerTypeRequired(); }
diff --git a/third_party/blink/renderer/core/layout/layout_image.cc b/third_party/blink/renderer/core/layout/layout_image.cc index 1c907c9..27b17a7 100644 --- a/third_party/blink/renderer/core/layout/layout_image.cc +++ b/third_party/blink/renderer/core/layout/layout_image.cc
@@ -129,7 +129,7 @@ bool old_orientation = old_style ? old_style->RespectImageOrientation() : ComputedStyleInitialValues::InitialRespectImageOrientation(); - if (Style() && Style()->RespectImageOrientation() != old_orientation) + if (Style() && StyleRef().RespectImageOrientation() != old_orientation) IntrinsicSizeChanged(); } @@ -202,7 +202,7 @@ CanDeferInvalidation defer) { LayoutSize old_intrinsic_size = IntrinsicSize(); LayoutSize new_intrinsic_size = - RoundedLayoutSize(image_resource_->ImageSize(Style()->EffectiveZoom())); + RoundedLayoutSize(image_resource_->ImageSize(StyleRef().EffectiveZoom())); UpdateIntrinsicSizeIfNeeded(new_intrinsic_size); // In the case of generated image content using :before/:after/content, we @@ -218,17 +218,17 @@ // If the actual area occupied by the image has changed and it is not // constrained by style then a layout is required. - bool image_size_is_constrained = Style()->LogicalWidth().IsSpecified() && - Style()->LogicalHeight().IsSpecified(); + bool image_size_is_constrained = StyleRef().LogicalWidth().IsSpecified() && + StyleRef().LogicalHeight().IsSpecified(); // FIXME: We only need to recompute the containing block's preferred size if // the containing block's size depends on the image's size (i.e., the // container uses shrink-to-fit sizing). There's no easy way to detect that // shrink-to-fit is needed, always force a layout. bool containing_block_needs_to_recompute_preferred_size = - Style()->LogicalWidth().IsPercentOrCalc() || - Style()->LogicalMaxWidth().IsPercentOrCalc() || - Style()->LogicalMinWidth().IsPercentOrCalc(); + StyleRef().LogicalWidth().IsPercentOrCalc() || + StyleRef().LogicalMaxWidth().IsPercentOrCalc() || + StyleRef().LogicalMinWidth().IsPercentOrCalc(); if (image_source_has_changed_size && (!image_size_is_constrained || @@ -307,23 +307,23 @@ return false; if (!ContentBoxRect().Contains(local_rect)) return false; - EFillBox background_clip = Style()->BackgroundClip(); + EFillBox background_clip = StyleRef().BackgroundClip(); // Background paints under borders. - if (background_clip == EFillBox::kBorder && Style()->HasBorder() && - !Style()->BorderObscuresBackground()) + if (background_clip == EFillBox::kBorder && StyleRef().HasBorder() && + !StyleRef().BorderObscuresBackground()) return false; // Background shows in padding area. if ((background_clip == EFillBox::kBorder || background_clip == EFillBox::kPadding) && - Style()->HasPadding()) + StyleRef().HasPadding()) return false; // Object-position may leave parts of the content box empty, regardless of the // value of object-fit. - if (Style()->ObjectPosition() != + if (StyleRef().ObjectPosition() != ComputedStyleInitialValues::InitialObjectPosition()) return false; // Object-fit may leave parts of the content box empty. - EObjectFit object_fit = Style()->GetObjectFit(); + EObjectFit object_fit = StyleRef().GetObjectFit(); if (object_fit != EObjectFit::kFill && object_fit != EObjectFit::kCover) return false; // Check for image with alpha. @@ -375,8 +375,8 @@ // Handle zoom & vertical writing modes here, as the embedded SVG document // doesn't know about them. - intrinsic_sizing_info.size.Scale(Style()->EffectiveZoom()); - if (Style()->GetObjectFit() != EObjectFit::kScaleDown) + intrinsic_sizing_info.size.Scale(StyleRef().EffectiveZoom()); + if (StyleRef().GetObjectFit() != EObjectFit::kScaleDown) intrinsic_sizing_info.size.Scale(ImageDevicePixelRatio()); if (!IsHorizontalWritingMode())
diff --git a/third_party/blink/renderer/core/layout/layout_inline.cc b/third_party/blink/renderer/core/layout/layout_inline.cc index 44bc054..9e367c81 100644 --- a/third_party/blink/renderer/core/layout/layout_inline.cc +++ b/third_party/blink/renderer/core/layout/layout_inline.cc
@@ -290,8 +290,8 @@ (parent_layout_inline && parent_layout_inline->AlwaysCreateLineBoxes()) || (parent_layout_inline && parent_style.VerticalAlign() != EVerticalAlign::kBaseline) || - Style()->VerticalAlign() != EVerticalAlign::kBaseline || - Style()->GetTextEmphasisMark() != TextEmphasisMark::kNone || + StyleRef().VerticalAlign() != EVerticalAlign::kBaseline || + StyleRef().GetTextEmphasisMark() != TextEmphasisMark::kNone || (check_fonts && (!StyleRef().HasIdenticalAscentDescentAndLineGap(parent_style) || parent_style.LineHeight() != StyleRef().LineHeight())); @@ -421,7 +421,7 @@ // collect the x/y offsets from inline parents later. if (LayoutObject* positioned_ancestor = InFlowPositionedInlineAncestor(this)) - new_style->SetPosition(positioned_ancestor->Style()->GetPosition()); + new_style->SetPosition(positioned_ancestor->StyleRef().GetPosition()); LayoutBlockFlow* new_box = LayoutBlockFlow::CreateAnonymous(&GetDocument(), std::move(new_style)); @@ -710,7 +710,7 @@ if (!CulledInlineFirstLineBox()) return; - bool is_horizontal = Style()->IsHorizontalWritingMode(); + bool is_horizontal = StyleRef().IsHorizontalWritingMode(); LayoutUnit logical_top, logical_height; for (LayoutObject* curr = FirstChild(); curr; curr = curr->NextSibling()) { @@ -890,19 +890,19 @@ } LayoutUnit LayoutInline::MarginLeft() const { - return ComputeMargin(this, Style()->MarginLeft()); + return ComputeMargin(this, StyleRef().MarginLeft()); } LayoutUnit LayoutInline::MarginRight() const { - return ComputeMargin(this, Style()->MarginRight()); + return ComputeMargin(this, StyleRef().MarginRight()); } LayoutUnit LayoutInline::MarginTop() const { - return ComputeMargin(this, Style()->MarginTop()); + return ComputeMargin(this, StyleRef().MarginTop()); } LayoutUnit LayoutInline::MarginBottom() const { - return ComputeMargin(this, Style()->MarginBottom()); + return ComputeMargin(this, StyleRef().MarginBottom()); } bool LayoutInline::NodeAtPoint(HitTestResult& result, @@ -1092,7 +1092,7 @@ logical_right_side = curr->LogicalRight(); } - bool is_horizontal = Style()->IsHorizontalWritingMode(); + bool is_horizontal = StyleRef().IsHorizontalWritingMode(); LayoutUnit x = is_horizontal ? logical_left_side : FirstLineBox()->X(); LayoutUnit y = is_horizontal ? FirstLineBox()->Y() : logical_left_side; @@ -1159,7 +1159,7 @@ LinesBoundingBoxGeneratorContext context(float_result); GenerateCulledLineBoxRects(context, this); LayoutRect result(EnclosingLayoutRect(float_result)); - bool is_horizontal = Style()->IsHorizontalWritingMode(); + bool is_horizontal = StyleRef().IsHorizontalWritingMode(); for (LayoutObject* curr = FirstChild(); curr; curr = curr->NextSibling()) { if (curr->IsFloatingOrOutOfFlowPositioned()) continue; @@ -1239,7 +1239,7 @@ LayoutRect rect(logical_left_side, logical_top, logical_width, logical_height); - if (!Style()->IsHorizontalWritingMode()) + if (!StyleRef().IsHorizontalWritingMode()) rect = rect.TransposedRect(); return rect; } @@ -1298,7 +1298,7 @@ LayoutRect LayoutInline::VisualOverflowRect() const { LayoutRect overflow_rect = LinesVisualOverflowBoundingBox(); - LayoutUnit outline_outset(Style()->OutlineOutsetExtent()); + LayoutUnit outline_outset(StyleRef().OutlineOutsetExtent()); if (outline_outset) { Vector<LayoutRect> rects; if (GetDocument().InNoQuirksMode()) { @@ -1336,13 +1336,13 @@ if (!container) return true; - bool preserve3d = container->Style()->Preserves3D(); + bool preserve3d = container->StyleRef().Preserves3D(); TransformState::TransformAccumulation accumulation = preserve3d ? TransformState::kAccumulateTransform : TransformState::kFlattenTransform; - if (Style()->HasInFlowPosition() && Layer()) { + if (StyleRef().HasInFlowPosition() && Layer()) { // Apply the in-flow position offset when invalidating a rectangle. The // layer is translated, but the layout box isn't, so we need to do this to // get the right dirty rect. Since this is called from LayoutObject:: @@ -1386,7 +1386,7 @@ PaintLayerType LayoutInline::LayerTypeRequired() const { return IsInFlowPositioned() || CreatesGroup() || - Style()->ShouldCompositeForCurrentAnimations() || + StyleRef().ShouldCompositeForCurrentAnimations() || ShouldApplyPaintContainment() ? kNormalPaintLayer : kNoPaintLayer; @@ -1492,7 +1492,7 @@ return LayoutUnit(s->ComputedLineHeight()); } - return LayoutUnit(Style()->ComputedLineHeight()); + return LayoutUnit(StyleRef().ComputedLineHeight()); } LayoutUnit LayoutInline::BaselinePosition( @@ -1542,19 +1542,19 @@ // relative-positioned inline has a negative offset we need to compensate for // it so that we align the positioned object with the edge of its containing // block. - if (child.Style()->HasStaticInlinePosition( - Style()->IsHorizontalWritingMode())) + if (child.StyleRef().HasStaticInlinePosition( + StyleRef().IsHorizontalWritingMode())) logical_offset.SetWidth( std::max(LayoutUnit(), -OffsetForInFlowPosition().Width())); else logical_offset.SetWidth(inline_position); - if (!child.Style()->HasStaticBlockPosition( - Style()->IsHorizontalWritingMode())) + if (!child.StyleRef().HasStaticBlockPosition( + StyleRef().IsHorizontalWritingMode())) logical_offset.SetHeight(block_position); - return Style()->IsHorizontalWritingMode() ? logical_offset - : logical_offset.TransposedSize(); + return StyleRef().IsHorizontalWritingMode() ? logical_offset + : logical_offset.TransposedSize(); } void LayoutInline::ImageChanged(WrappedImagePtr, @@ -1650,15 +1650,15 @@ void LayoutInline::AddAnnotatedRegions(Vector<AnnotatedRegionValue>& regions) { // Convert the style regions to absolute coordinates. - if (Style()->Visibility() != EVisibility::kVisible) + if (StyleRef().Visibility() != EVisibility::kVisible) return; - if (Style()->DraggableRegionMode() == EDraggableRegionMode::kNone) + if (StyleRef().DraggableRegionMode() == EDraggableRegionMode::kNone) return; AnnotatedRegionValue region; region.draggable = - Style()->DraggableRegionMode() == EDraggableRegionMode::kDrag; + StyleRef().DraggableRegionMode() == EDraggableRegionMode::kDrag; region.bounds = LayoutRect(LinesBoundingBox()); LayoutObject* container = ContainingBlock();
diff --git a/third_party/blink/renderer/core/layout/layout_list_box.cc b/third_party/blink/renderer/core/layout/layout_list_box.cc index 2e51a69f..7e9a28f3 100644 --- a/third_party/blink/renderer/core/layout/layout_list_box.cc +++ b/third_party/blink/renderer/core/layout/layout_list_box.cc
@@ -70,7 +70,7 @@ } LayoutUnit LayoutListBox::DefaultItemHeight() const { - const SimpleFontData* font_data = Style()->GetFont().PrimaryFont(); + const SimpleFontData* font_data = StyleRef().GetFont().PrimaryFont(); if (!font_data) return LayoutUnit(); return LayoutUnit(font_data->GetFontMetrics().Height() + @@ -127,7 +127,7 @@ LayoutUnit& max_logical_width) const { LayoutBlockFlow::ComputeIntrinsicLogicalWidths(min_logical_width, max_logical_width); - if (Style()->Width().IsPercentOrCalc()) + if (StyleRef().Width().IsPercentOrCalc()) min_logical_width = LayoutUnit(); }
diff --git a/third_party/blink/renderer/core/layout/layout_list_item.cc b/third_party/blink/renderer/core/layout/layout_list_item.cc index 4c9de99..1a1b193 100644 --- a/third_party/blink/renderer/core/layout/layout_list_item.cc +++ b/third_party/blink/renderer/core/layout/layout_list_item.cc
@@ -51,8 +51,8 @@ const ComputedStyle* old_style) { LayoutBlockFlow::StyleDidChange(diff, old_style); - StyleImage* current_image = Style()->ListStyleImage(); - if (Style()->ListStyleType() != EListStyleType::kNone || + StyleImage* current_image = StyleRef().ListStyleImage(); + if (StyleRef().ListStyleType() != EListStyleType::kNone || (current_image && !current_image->ErrorOccurred())) { if (!marker_) marker_ = LayoutListMarker::CreateAnonymous(this); @@ -80,8 +80,8 @@ LayoutBlockFlow::WillBeDestroyed(); - if (Style() && Style()->ListStyleImage()) - Style()->ListStyleImage()->RemoveClient(this); + if (Style() && StyleRef().ListStyleImage()) + StyleRef().ListStyleImage()->RemoveClient(this); } void LayoutListItem::InsertedIntoTree() { @@ -397,7 +397,7 @@ // TODO(jchaffraix): Propagating the overflow to the line boxes seems // pretty wrong (https://crbug.com/554160). // FIXME: Need to account for relative positioning in the layout overflow. - if (Style()->IsLeftToRightDirection()) { + if (StyleRef().IsLeftToRightDirection()) { LayoutUnit marker_line_offset = std::min(marker_->LineOffset(), LogicalLeftOffsetForLine(marker_->LogicalTop(), @@ -482,7 +482,7 @@ LayoutPoint(marker_logical_left + line_offset, block_offset + marker_inline_box->LogicalTop()), marker_->Size()); - if (!Style()->IsHorizontalWritingMode()) + if (!StyleRef().IsHorizontalWritingMode()) marker_rect = marker_rect.TransposedRect(); LayoutBox* o = marker_; bool propagate_visual_overflow = true;
diff --git a/third_party/blink/renderer/core/layout/layout_list_marker.cc b/third_party/blink/renderer/core/layout/layout_list_marker.cc index 4e86707..e52e558 100644 --- a/third_party/blink/renderer/core/layout/layout_list_marker.cc +++ b/third_party/blink/renderer/core/layout/layout_list_marker.cc
@@ -64,7 +64,7 @@ LayoutSize LayoutListMarker::ImageBulletSize() const { DCHECK(IsImage()); - const SimpleFontData* font_data = Style()->GetFont().PrimaryFont(); + const SimpleFontData* font_data = StyleRef().GetFont().PrimaryFont(); DCHECK(font_data); if (!font_data) return LayoutSize(); @@ -76,15 +76,15 @@ LayoutUnit bullet_width = font_data->GetFontMetrics().Ascent() / LayoutUnit(2); return RoundedLayoutSize( - image_->ImageSize(GetDocument(), Style()->EffectiveZoom(), + image_->ImageSize(GetDocument(), StyleRef().EffectiveZoom(), LayoutSize(bullet_width, bullet_width))); } void LayoutListMarker::StyleWillChange(StyleDifference diff, const ComputedStyle& new_style) { if (Style() && - (new_style.ListStylePosition() != Style()->ListStylePosition() || - new_style.ListStyleType() != Style()->ListStyleType())) + (new_style.ListStylePosition() != StyleRef().ListStylePosition() || + new_style.ListStyleType() != StyleRef().ListStyleType())) SetNeedsLayoutAndPrefWidthsRecalcAndFullPaintInvalidation( LayoutInvalidationReason::kStyleChange); @@ -95,10 +95,10 @@ const ComputedStyle* old_style) { LayoutBox::StyleDidChange(diff, old_style); - if (image_ != Style()->ListStyleImage()) { + if (image_ != StyleRef().ListStyleImage()) { if (image_) image_->RemoveClient(this); - image_ = Style()->ListStyleImage(); + image_ = StyleRef().ListStyleImage(); if (image_) image_->AddClient(this); } @@ -126,7 +126,7 @@ for (LayoutBox* o = ParentBox(); o && o != ListItem(); o = o->ParentBox()) { block_offset += o->LogicalTop(); } - if (ListItem()->Style()->IsLeftToRightDirection()) { + if (ListItem()->StyleRef().IsLeftToRightDirection()) { line_offset_ = ListItem()->LogicalLeftOffsetForLine( block_offset, kDoNotIndentText, LayoutUnit()); } else { @@ -139,7 +139,7 @@ SetWidth(image_size.Width()); SetHeight(image_size.Height()); } else { - const SimpleFontData* font_data = Style()->GetFont().PrimaryFont(); + const SimpleFontData* font_data = StyleRef().GetFont().PrimaryFont(); DCHECK(font_data); SetLogicalWidth(MinPreferredLogicalWidth()); SetLogicalHeight( @@ -149,8 +149,8 @@ SetMarginStart(LayoutUnit()); SetMarginEnd(LayoutUnit()); - Length start_margin = Style()->MarginStart(); - Length end_margin = Style()->MarginEnd(); + Length start_margin = StyleRef().MarginStart(); + Length end_margin = StyleRef().MarginEnd(); if (start_margin.IsFixed()) SetMarginStart(LayoutUnit(start_margin.Value())); if (end_margin.IsFixed()) @@ -194,11 +194,11 @@ case ListStyleCategory::kNone: break; case ListStyleCategory::kSymbol: - text_ = ListMarkerText::GetText(Style()->ListStyleType(), + text_ = ListMarkerText::GetText(StyleRef().ListStyleType(), 0); // value is ignored for these types break; case ListStyleCategory::kLanguage: - text_ = ListMarkerText::GetText(Style()->ListStyleType(), + text_ = ListMarkerText::GetText(StyleRef().ListStyleType(), list_item_->Value()); break; } @@ -206,7 +206,7 @@ String LayoutListMarker::TextAlternative() const { UChar suffix = - ListMarkerText::Suffix(Style()->ListStyleType(), list_item_->Value()); + ListMarkerText::Suffix(StyleRef().ListStyleType(), list_item_->Value()); // Return suffix after the marker text, even in RTL, reflecting speech order. return text_ + suffix + ' '; } @@ -214,15 +214,15 @@ LayoutUnit LayoutListMarker::GetWidthOfTextWithSuffix() const { if (text_.IsEmpty()) return LayoutUnit(); - const Font& font = Style()->GetFont(); + const Font& font = StyleRef().GetFont(); LayoutUnit item_width = LayoutUnit(font.Width(TextRun(text_))); // TODO(wkorman): Look into constructing a text run for both text and suffix // and painting them together. UChar suffix[2] = { - ListMarkerText::Suffix(Style()->ListStyleType(), list_item_->Value()), + ListMarkerText::Suffix(StyleRef().ListStyleType(), list_item_->Value()), ' '}; TextRun run = - ConstructTextRun(font, suffix, 2, StyleRef(), Style()->Direction()); + ConstructTextRun(font, suffix, 2, StyleRef(), StyleRef().Direction()); LayoutUnit suffix_space_width = LayoutUnit(font.Width(run)); return item_width + suffix_space_width; } @@ -234,8 +234,8 @@ if (IsImage()) { LayoutSize image_size(ImageBulletSize()); min_preferred_logical_width_ = max_preferred_logical_width_ = - Style()->IsHorizontalWritingMode() ? image_size.Width() - : image_size.Height(); + StyleRef().IsHorizontalWritingMode() ? image_size.Width() + : image_size.Height(); ClearPreferredLogicalWidthsDirty(); UpdateMargins(); return; @@ -460,7 +460,7 @@ bool LayoutListMarker::IsInside() const { return list_item_->Ordinal().NotInList() || - Style()->ListStylePosition() == EListStylePosition::kInside; + StyleRef().ListStylePosition() == EListStylePosition::kInside; } LayoutRect LayoutListMarker::GetRelativeMarkerRect() const { @@ -474,7 +474,7 @@ case ListStyleCategory::kSymbol: return RelativeSymbolMarkerRect(StyleRef(), Size().Width()); case ListStyleCategory::kLanguage: { - const SimpleFontData* font_data = Style()->GetFont().PrimaryFont(); + const SimpleFontData* font_data = StyleRef().GetFont().PrimaryFont(); DCHECK(font_data); if (!font_data) return relative_rect; @@ -485,7 +485,7 @@ } } - if (!Style()->IsHorizontalWritingMode()) { + if (!StyleRef().IsHorizontalWritingMode()) { relative_rect = relative_rect.TransposedRect(); relative_rect.SetX(Size().Width() - relative_rect.X() - relative_rect.Width()); @@ -524,8 +524,8 @@ if (Style()) { // Reuse the current margins. Otherwise resetting the margins to initial // values would trigger unnecessary layout. - new_style->SetMarginStart(Style()->MarginStart()); - new_style->SetMarginEnd(Style()->MarginRight()); + new_style->SetMarginStart(StyleRef().MarginStart()); + new_style->SetMarginEnd(StyleRef().MarginRight()); } SetStyle(std::move(new_style)); }
diff --git a/third_party/blink/renderer/core/layout/layout_menu_list.cc b/third_party/blink/renderer/core/layout/layout_menu_list.cc index 7d60efb..f9d218a 100644 --- a/third_party/blink/renderer/core/layout/layout_menu_list.cc +++ b/third_party/blink/renderer/core/layout/layout_menu_list.cc
@@ -125,7 +125,7 @@ // when the content overflows, treat it the same as align-items: flex-start. // But we only do that for the cases where html.css would otherwise use // center. - if (Style()->AlignItemsPosition() == ItemPosition::kCenter) { + if (StyleRef().AlignItemsPosition() == ItemPosition::kCenter) { inner_style.SetMarginTop(Length()); inner_style.SetMarginBottom(Length()); inner_style.SetAlignSelfPosition(ItemPosition::kFlexStart); @@ -199,7 +199,7 @@ } void LayoutMenuList::UpdateInnerBlockHeight() { - const SimpleFontData* font_data = Style()->GetFont().PrimaryFont(); + const SimpleFontData* font_data = StyleRef().GetFont().PrimaryFont(); DCHECK(font_data); inner_block_height_ = (font_data ? font_data->GetFontMetrics().Height() : 0) + inner_block_->BorderAndPaddingHeight(); @@ -215,9 +215,9 @@ item_style->ApplyTextTransform(&text); // We apply SELECT's style, not OPTION's style because m_optionsWidth is // used to determine intrinsic width of the menulist box. - TextRun text_run = ConstructTextRun(Style()->GetFont(), text, *Style()); + TextRun text_run = ConstructTextRun(StyleRef().GetFont(), text, *Style()); max_option_width = - std::max(max_option_width, Style()->GetFont().Width(text_run)); + std::max(max_option_width, StyleRef().GetFont().Width(text_run)); } options_width_ = static_cast<int>(ceilf(max_option_width)); } @@ -316,7 +316,7 @@ std::max(options_width_, LayoutTheme::GetTheme().MinimumMenuListSize(StyleRef())) + inner_block_->PaddingLeft() + inner_block_->PaddingRight(); - if (!Style()->Width().IsPercentOrCalc()) + if (!StyleRef().Width().IsPercentOrCalc()) min_logical_width = max_logical_width; else min_logical_width = LayoutUnit(); @@ -326,7 +326,7 @@ LayoutUnit logical_height, LayoutUnit logical_top, LogicalExtentComputedValues& computed_values) const { - if (Style()->HasAppearance()) + if (StyleRef().HasAppearance()) logical_height = inner_block_height_ + BorderAndPaddingHeight(); LayoutBox::ComputeLogicalHeight(logical_height, logical_top, computed_values); }
diff --git a/third_party/blink/renderer/core/layout/layout_multi_column_flow_thread.cc b/third_party/blink/renderer/core/layout/layout_multi_column_flow_thread.cc index 4f96b5b..5fc48cc 100644 --- a/third_party/blink/renderer/core/layout/layout_multi_column_flow_thread.cc +++ b/third_party/blink/renderer/core/layout/layout_multi_column_flow_thread.cc
@@ -330,7 +330,7 @@ return column_height_available_; } const LayoutBlockFlow* multicol_block = MultiColumnBlockFlow(); - Length logical_max_height = multicol_block->Style()->LogicalMaxHeight(); + Length logical_max_height = multicol_block->StyleRef().LogicalMaxHeight(); if (!logical_max_height.IsMaxSizeNone()) { LayoutUnit resolved_logical_max_height = multicol_block->ComputeContentLogicalHeight( @@ -889,7 +889,7 @@ // The spec says that column-span only applies to in-flow block-level // elements. - if (descendant->Style()->GetColumnSpan() != EColumnSpan::kAll || + if (descendant->StyleRef().GetColumnSpan() != EColumnSpan::kAll || !descendant->IsBox() || descendant->IsInline() || descendant->IsFloatingOrOutOfFlowPositioned()) return false;
diff --git a/third_party/blink/renderer/core/layout/layout_multi_column_set.cc b/third_party/blink/renderer/core/layout/layout_multi_column_set.cc index 66b6ce78..5d3fcefb 100644 --- a/third_party/blink/renderer/core/layout/layout_multi_column_set.cc +++ b/third_party/blink/renderer/core/layout/layout_multi_column_set.cc
@@ -346,7 +346,7 @@ // 'balance' - in accordance with the spec). // Pretending that column-fill is auto also matches the old multicol // implementation, which has no support for this property. - if (MultiColumnBlockFlow()->Style()->GetColumnFill() == + if (MultiColumnBlockFlow()->StyleRef().GetColumnFill() == EColumnFill::kBalance) return true; if (LayoutBox* next = NextSiblingBox()) { @@ -492,12 +492,12 @@ LayoutUnit LayoutMultiColumnSet::ColumnGap() const { LayoutBlockFlow* parent_block = MultiColumnBlockFlow(); - if (parent_block->Style()->ColumnGap().IsNormal()) { + if (parent_block->StyleRef().ColumnGap().IsNormal()) { // "1em" is recommended as the normal gap setting. Matches <p> margins. return LayoutUnit( - parent_block->Style()->GetFontDescription().ComputedPixelSize()); + parent_block->StyleRef().GetFontDescription().ComputedPixelSize()); } - return ValueForLength(parent_block->Style()->ColumnGap().GetLength(), + return ValueForLength(parent_block->StyleRef().ColumnGap().GetLength(), AvailableLogicalWidth()); } @@ -591,7 +591,7 @@ if (col_count <= 1) return false; - bool left_to_right = Style()->IsLeftToRightDirection(); + bool left_to_right = StyleRef().IsLeftToRightDirection(); LayoutUnit curr_logical_left_offset = left_to_right ? LayoutUnit() : ContentLogicalWidth(); LayoutUnit rule_add = BorderAndPaddingLogicalLeft();
diff --git a/third_party/blink/renderer/core/layout/layout_multi_column_spanner_placeholder.cc b/third_party/blink/renderer/core/layout/layout_multi_column_spanner_placeholder.cc index 087c84f..97f9fff 100644 --- a/third_party/blink/renderer/core/layout/layout_multi_column_spanner_placeholder.cc +++ b/third_party/blink/renderer/core/layout/layout_multi_column_spanner_placeholder.cc
@@ -46,7 +46,7 @@ if (FlowThread()->RemoveSpannerPlaceholderIfNoLongerValid( object_in_flow_thread)) { // No longer a valid spanner, due to style changes. |this| is now dead. - if (object_in_flow_thread->Style()->HasOutOfFlowPosition() && + if (object_in_flow_thread->StyleRef().HasOutOfFlowPosition() && !old_style->HasOutOfFlowPosition()) { // We went from being a spanner to being out-of-flow positioned. When an // object becomes out-of-flow positioned, we need to lay out its parent,
diff --git a/third_party/blink/renderer/core/layout/layout_object.cc b/third_party/blink/renderer/core/layout/layout_object.cc index 040739d..4f03d57 100644 --- a/third_party/blink/renderer/core/layout/layout_object.cc +++ b/third_party/blink/renderer/core/layout/layout_object.cc
@@ -136,8 +136,8 @@ // LayoutObject::Container() method can actually be used to obtain the inline // directly. if (container && container->IsInline() && !container->IsAtomicInlineLevel()) { - DCHECK(container->Style()->HasInFlowPosition() || - container->Style()->HasFilter()); + DCHECK(container->StyleRef().HasInFlowPosition() || + container->StyleRef().HasFilter()); container = container->ContainingBlock(skip_info); } @@ -381,7 +381,7 @@ } if (new_child->IsText() && - new_child->Style()->TextTransform() == ETextTransform::kCapitalize) + new_child->StyleRef().TextTransform() == ETextTransform::kCapitalize) ToLayoutText(new_child)->TransformText(); } @@ -890,7 +890,7 @@ LayoutObject* container = object->Container(); if (!container && !object->IsLayoutView()) return; - if (!last->IsTextOrSVGChild() && last->Style()->HasOutOfFlowPosition()) { + if (!last->IsTextOrSVGChild() && last->StyleRef().HasOutOfFlowPosition()) { object = last->ContainingBlock(); if (object->PosChildNeedsLayout()) return; @@ -942,7 +942,7 @@ MarkingBehavior mark_parents) { bitfields_.SetPreferredLogicalWidthsDirty(true); if (mark_parents == kMarkContainerChain && - (IsText() || !Style()->HasOutOfFlowPosition())) + (IsText() || !StyleRef().HasOutOfFlowPosition())) InvalidateContainerPreferredLogicalWidths(); } @@ -981,7 +981,7 @@ o->bitfields_.SetPreferredLogicalWidthsDirty(true); // A positioned object has no effect on the min/max width of its containing // block ever. We can optimize this case and not go up any further. - if (o->Style()->HasOutOfFlowPosition()) + if (o->StyleRef().HasOutOfFlowPosition()) break; o = container; } @@ -1682,7 +1682,7 @@ transform_state.SetQuad(FloatQuad(FloatRect(rect))); } - bool preserve3d = parent->Style()->Preserves3D() && !parent->IsText(); + bool preserve3d = parent->StyleRef().Preserves3D() && !parent->IsText(); TransformState::TransformAccumulation accumulation = preserve3d ? TransformState::kAccumulateTransform @@ -1807,8 +1807,8 @@ #endif // NDEBUG bool LayoutObject::IsSelectable() const { - return !IsInert() && !(Style()->UserSelect() == EUserSelect::kNone && - Style()->UserModify() == EUserModify::kReadOnly); + return !IsInert() && !(StyleRef().UserSelect() == EUserSelect::kNone && + StyleRef().UserModify() == EUserModify::kReadOnly); } // Called when an object that was floating or positioned becomes a normal flow @@ -1818,7 +1818,7 @@ // We have gone from not affecting the inline status of the parent flow to // suddenly having an impact. See if there is a mismatch between the parent // flow's childrenInline() state and our state. - object->SetInline(object->Style()->IsDisplayInlineType()); + object->SetInline(object->StyleRef().IsDisplayInlineType()); if (object->IsInline() != object->Parent()->ChildrenInline()) { if (!object->IsInline()) { ToLayoutBoxModelObject(object->Parent())->ChildBecameNonInline(object); @@ -1852,15 +1852,15 @@ // needed if we have style or text affected by these properties. if (diff.TextDecorationOrColorChanged() && !diff.NeedsFullPaintInvalidation()) { - if (Style()->HasBorderColorReferencingCurrentColor() || - Style()->HasOutlineWithCurrentColor() || - Style()->HasBackgroundRelatedColorReferencingCurrentColor() || + if (StyleRef().HasBorderColorReferencingCurrentColor() || + StyleRef().HasOutlineWithCurrentColor() || + StyleRef().HasBackgroundRelatedColorReferencingCurrentColor() || // Skip any text nodes that do not contain text boxes. Whitespace cannot // be skipped or we will miss invalidating decorations (e.g., // underlines). (IsText() && !IsBR() && ToLayoutText(this)->HasTextBoxes()) || - (IsSVG() && Style()->SvgStyle().IsFillColorCurrentColor()) || - (IsSVG() && Style()->SvgStyle().IsStrokeColorCurrentColor()) || + (IsSVG() && StyleRef().SvgStyle().IsFillColorCurrentColor()) || + (IsSVG() && StyleRef().SvgStyle().IsStrokeColorCurrentColor()) || IsListMarker()) diff.SetNeedsPaintInvalidationObject(); } @@ -2320,7 +2320,7 @@ // properties. for (LayoutObject* child = SlowFirstChild(); child; child = child->NextSibling()) { - if (!child->IsAnonymous() || child->Style()->StyleType() != kPseudoIdNone) + if (!child->IsAnonymous() || child->StyleRef().StyleType() != kPseudoIdNone) continue; if (child->AnonymousHasStylePropagationOverride()) @@ -2328,17 +2328,17 @@ scoped_refptr<ComputedStyle> new_style = ComputedStyle::CreateAnonymousStyleWithDisplay( - StyleRef(), child->Style()->Display()); + StyleRef(), child->StyleRef().Display()); // Preserve the position style of anonymous block continuations as they can // have relative position when they contain block descendants of relative // positioned inlines. if (child->IsInFlowPositioned() && child->IsLayoutBlockFlow() && ToLayoutBlockFlow(child)->IsAnonymousBlockContinuation()) - new_style->SetPosition(child->Style()->GetPosition()); + new_style->SetPosition(child->StyleRef().GetPosition()); if (child->IsLayoutNGListMarker()) - new_style->SetWhiteSpace(child->Style()->WhiteSpace()); + new_style->SetWhiteSpace(child->StyleRef().WhiteSpace()); UpdateAnonymousChildStyle(child, *new_style); @@ -2475,7 +2475,7 @@ if (IsBox()) { mode &= ~kApplyContainerFlip; } else if (container->IsBox()) { - if (container->Style()->IsFlippedBlocksWritingMode()) { + if (container->StyleRef().IsFlippedBlocksWritingMode()) { IntPoint center_point = RoundedIntPoint(transform_state.MappedPoint()); transform_state.Move(ToLayoutBox(container)->FlipForWritingMode( LayoutPoint(center_point)) - @@ -2506,8 +2506,8 @@ // them. bool preserve3d = mode & kUseTransforms && - ((container->Style()->Preserves3D() && !container->IsText()) || - (Style()->Preserves3D() && !IsText())); + ((container->StyleRef().Preserves3D() && !container->IsText()) || + (StyleRef().Preserves3D() && !IsText())); if (mode & kUseTransforms && ShouldUseTransformFromContainer(container)) { TransformationMatrix t; GetTransformFromContainer(container, container_offset, t); @@ -2531,7 +2531,7 @@ : TransformState::kFlattenTransform); // If the ancestor is fixed, then the rect is already in its coordinates so // doesn't need viewport-adjusting. - if (ancestor->Style()->GetPosition() != EPosition::kFixed && + if (ancestor->StyleRef().GetPosition() != EPosition::kFixed && container->IsLayoutView() && StyleRef().GetPosition() == EPosition::kFixed) { LayoutSize adjustment = ToLayoutView(container)->OffsetForFixedPosition(); @@ -2566,7 +2566,7 @@ if (IsBox()) { mode &= ~kApplyContainerFlip; } else if (container->IsBox()) { - apply_container_flip = container->Style()->IsFlippedBlocksWritingMode(); + apply_container_flip = container->StyleRef().IsFlippedBlocksWritingMode(); mode &= ~kApplyContainerFlip; } } @@ -2577,7 +2577,7 @@ LayoutSize container_offset = OffsetFromContainer(container); bool preserve3d = mode & kUseTransforms && - (container->Style()->Preserves3D() || Style()->Preserves3D()); + (container->StyleRef().Preserves3D() || StyleRef().Preserves3D()); if (mode & kUseTransforms && ShouldUseTransformFromContainer(container)) { TransformationMatrix t; GetTransformFromContainer(container, container_offset, t); @@ -2611,7 +2611,7 @@ transform_state.Move(-container_offset.Width(), -container_offset.Height()); // If the ancestor is fixed, then the rect is already in its coordinates so // doesn't need viewport-adjusting. - if (ancestor->Style()->GetPosition() != EPosition::kFixed && + if (ancestor->StyleRef().GetPosition() != EPosition::kFixed && container->IsLayoutView() && StyleRef().GetPosition() == EPosition::kFixed) { LayoutSize adjustment = ToLayoutView(container)->OffsetForFixedPosition(); @@ -2626,7 +2626,7 @@ // or perspective. We just care about transform, so check the layer's // transform directly. return (HasLayer() && ToLayoutBoxModelObject(this)->Layer()->Transform()) || - (container_object && container_object->Style()->HasPerspective()); + (container_object && container_object->StyleRef().HasPerspective()); } void LayoutObject::GetTransformFromContainer( @@ -2643,7 +2643,7 @@ offset_in_container.Height().ToFloat()); if (container_object && container_object->HasLayer() && - container_object->Style()->HasPerspective()) { + container_object->StyleRef().HasPerspective()) { // Perspective on the container affects us, so we have to factor it in here. DCHECK(container_object->HasLayer()); FloatPoint perspective_origin = @@ -2651,7 +2651,7 @@ TransformationMatrix perspective_matrix; perspective_matrix.ApplyPerspective( - container_object->Style()->Perspective()); + container_object->StyleRef().Perspective()); perspective_matrix.ApplyTransformOrigin(perspective_origin.X(), perspective_origin.Y(), 0); @@ -2871,7 +2871,7 @@ iter_value = &iter->value; } TouchAction whitelisted_touch_action = - Style()->GetEffectiveTouchAction() & supported_fast_actions; + StyleRef().GetEffectiveTouchAction() & supported_fast_actions; for (size_t i = 0; i < own_rects.size(); i++) { // If we have a different touch action than the container the rect needs to // be reported even if it is contained. @@ -2946,7 +2946,7 @@ return kRespectImageOrientation; if (layout_object->Style() && - layout_object->Style()->RespectImageOrientation() == + layout_object->StyleRef().RespectImageOrientation() == kRespectImageOrientation) return kRespectImageOrientation; @@ -3105,8 +3105,8 @@ // If |this| is visible but this object was not, tell the layer it has some // visible content that needs to be drawn and layer visibility optimization // can't be used - if (Parent()->Style()->Visibility() != EVisibility::kVisible && - Style()->Visibility() == EVisibility::kVisible && !HasLayer()) { + if (Parent()->StyleRef().Visibility() != EVisibility::kVisible && + StyleRef().Visibility() == EVisibility::kVisible && !HasLayer()) { if (!layer) layer = Parent()->EnclosingLayer(); if (layer) @@ -3156,8 +3156,8 @@ // If we remove a visible child from an invisible parent, we don't know the // layer visibility any more. PaintLayer* layer = nullptr; - if (Parent()->Style()->Visibility() != EVisibility::kVisible && - Style()->Visibility() == EVisibility::kVisible && !HasLayer()) { + if (Parent()->StyleRef().Visibility() != EVisibility::kVisible && + StyleRef().Visibility() == EVisibility::kVisible && !HasLayer()) { layer = Parent()->EnclosingLayer(); if (layer) layer->DirtyVisibleContentStatus(); @@ -3526,10 +3526,10 @@ void LayoutObject::AddAnnotatedRegions(Vector<AnnotatedRegionValue>& regions) { // Convert the style regions to absolute coordinates. - if (Style()->Visibility() != EVisibility::kVisible || !IsBox()) + if (StyleRef().Visibility() != EVisibility::kVisible || !IsBox()) return; - if (Style()->DraggableRegionMode() == EDraggableRegionMode::kNone) + if (StyleRef().DraggableRegionMode() == EDraggableRegionMode::kNone) return; LayoutBox* box = ToLayoutBox(this); @@ -3538,7 +3538,7 @@ AnnotatedRegionValue region; region.draggable = - Style()->DraggableRegionMode() == EDraggableRegionMode::kDrag; + StyleRef().DraggableRegionMode() == EDraggableRegionMode::kDrag; region.bounds = LayoutRect(abs_bounds); regions.push_back(region); } @@ -3546,7 +3546,7 @@ bool LayoutObject::WillRenderImage() { // Without visibility we won't render (and therefore don't care about // animation). - if (Style()->Visibility() != EVisibility::kVisible) + if (StyleRef().Visibility() != EVisibility::kVisible) return false; // We will not render a new image when PausableObjects is paused @@ -3609,7 +3609,7 @@ if (IsFixedPositioned()) return nullptr; - float effective_zoom = Style()->EffectiveZoom(); + float effective_zoom = StyleRef().EffectiveZoom(); Node* node = nullptr; for (LayoutObject* ancestor = Parent(); ancestor; ancestor = ancestor->Parent()) { @@ -3644,7 +3644,7 @@ break; // Webkit specific extension where offsetParent stops at zoom level changes. - if (effective_zoom != ancestor->Style()->EffectiveZoom()) + if (effective_zoom != ancestor->StyleRef().EffectiveZoom()) break; } @@ -4057,7 +4057,7 @@ } bool LayoutObject::CanBeSelectionLeaf() const { - if (SlowFirstChild() || Style()->Visibility() != EVisibility::kVisible) + if (SlowFirstChild() || StyleRef().Visibility() != EVisibility::kVisible) return false; return CanBeSelectionLeafInternal(); }
diff --git a/third_party/blink/renderer/core/layout/layout_object.h b/third_party/blink/renderer/core/layout/layout_object.h index 17e9e4d7..8383b47b 100644 --- a/third_party/blink/renderer/core/layout/layout_object.h +++ b/third_party/blink/renderer/core/layout/layout_object.h
@@ -904,7 +904,7 @@ } // CSS clip only applies when position is absolute or fixed. Prefer this check - // over !Style()->HasAutoClip(). + // over !StyleRef().HasAutoClip(). bool HasClip() const { return IsOutOfFlowPositioned() && !StyleRef().HasAutoClip(); }
diff --git a/third_party/blink/renderer/core/layout/layout_paged_flow_thread.cc b/third_party/blink/renderer/core/layout/layout_paged_flow_thread.cc index b60ba59..ab2d39d 100644 --- a/third_party/blink/renderer/core/layout/layout_paged_flow_thread.cc +++ b/third_party/blink/renderer/core/layout/layout_paged_flow_thread.cc
@@ -26,7 +26,7 @@ bool LayoutPagedFlowThread::NeedsNewWidth() const { return ProgressionIsInline() != - PagedBlockFlow()->Style()->HasInlinePaginationAxis(); + PagedBlockFlow()->StyleRef().HasInlinePaginationAxis(); } void LayoutPagedFlowThread::UpdateLogicalWidth() { @@ -39,7 +39,8 @@ void LayoutPagedFlowThread::UpdateLayout() { // There should either be zero or one of those for paged layout. DCHECK_EQ(FirstMultiColumnBox(), LastMultiColumnBox()); - SetProgressionIsInline(PagedBlockFlow()->Style()->HasInlinePaginationAxis()); + SetProgressionIsInline( + PagedBlockFlow()->StyleRef().HasInlinePaginationAxis()); LayoutMultiColumnFlowThread::UpdateLayout(); LayoutMultiColumnSet* column_set = FirstMultiColumnSet();
diff --git a/third_party/blink/renderer/core/layout/layout_progress.cc b/third_party/blink/renderer/core/layout/layout_progress.cc index 83fe6ed2..ebc3235 100644 --- a/third_party/blink/renderer/core/layout/layout_progress.cc +++ b/third_party/blink/renderer/core/layout/layout_progress.cc
@@ -91,7 +91,7 @@ animation_repeat_interval_ = LayoutTheme::GetTheme().AnimationRepeatIntervalForProgressBar(); - bool animating = !IsDeterminate() && Style()->HasAppearance() && + bool animating = !IsDeterminate() && StyleRef().HasAppearance() && animation_duration_ > TimeDelta(); if (animating == animating_) return;
diff --git a/third_party/blink/renderer/core/layout/layout_quote.cc b/third_party/blink/renderer/core/layout/layout_quote.cc index 335af89..473122e 100644 --- a/third_party/blink/renderer/core/layout/layout_quote.cc +++ b/third_party/blink/renderer/core/layout/layout_quote.cc
@@ -302,10 +302,10 @@ } const QuotesData* LayoutQuote::GetQuotesData() const { - if (const QuotesData* custom_quotes = Style()->Quotes()) + if (const QuotesData* custom_quotes = StyleRef().Quotes()) return custom_quotes; - if (const QuotesData* quotes = QuotesDataForLanguage(Style()->Locale())) + if (const QuotesData* quotes = QuotesDataForLanguage(StyleRef().Locale())) return quotes; return BasicQuotesData();
diff --git a/third_party/blink/renderer/core/layout/layout_replaced.cc b/third_party/blink/renderer/core/layout/layout_replaced.cc index c70b4316..6535b0f 100644 --- a/third_party/blink/renderer/core/layout/layout_replaced.cc +++ b/third_party/blink/renderer/core/layout/layout_replaced.cc
@@ -84,7 +84,7 @@ bool had_style = !!old_style; float old_zoom = had_style ? old_style->EffectiveZoom() : ComputedStyleInitialValues::InitialZoom(); - if (Style() && Style()->EffectiveZoom() != old_zoom) + if (Style() && StyleRef().EffectiveZoom() != old_zoom) IntrinsicSizeChanged(); } @@ -110,9 +110,10 @@ } void LayoutReplaced::IntrinsicSizeChanged() { - int scaled_width = static_cast<int>(kDefaultWidth * Style()->EffectiveZoom()); + int scaled_width = + static_cast<int>(kDefaultWidth * StyleRef().EffectiveZoom()); int scaled_height = - static_cast<int>(kDefaultHeight * Style()->EffectiveZoom()); + static_cast<int>(kDefaultHeight * StyleRef().EffectiveZoom()); intrinsic_size_ = LayoutSize(scaled_width, scaled_height); SetNeedsLayoutAndPrefWidthsRecalcAndFullPaintInvalidation( LayoutInvalidationReason::kSizeChanged); @@ -123,16 +124,16 @@ } bool LayoutReplaced::HasReplacedLogicalHeight() const { - if (Style()->LogicalHeight().IsAuto()) + if (StyleRef().LogicalHeight().IsAuto()) return false; - if (Style()->LogicalHeight().IsSpecified()) { + if (StyleRef().LogicalHeight().IsSpecified()) { if (HasAutoHeightOrContainingBlockWithAutoHeight()) return false; return true; } - if (Style()->LogicalHeight().IsIntrinsic()) + if (StyleRef().LogicalHeight().IsIntrinsic()) return true; return false; @@ -142,7 +143,7 @@ // If the height is a percentage and the width is auto, then the // containingBlocks's height changing can cause this node to change it's // preferred width because it maintains aspect ratio. - return HasRelativeLogicalHeight() && Style()->LogicalWidth().IsAuto(); + return HasRelativeLogicalHeight() && StyleRef().LogicalWidth().IsAuto(); } static inline bool LayoutObjectHasAspectRatio( @@ -180,7 +181,8 @@ FloatSize constrained_size = intrinsic_sizing_info.size; if (!intrinsic_sizing_info.aspect_ratio.IsEmpty() && !intrinsic_sizing_info.size.IsEmpty() && - Style()->LogicalWidth().IsAuto() && Style()->LogicalHeight().IsAuto()) { + StyleRef().LogicalWidth().IsAuto() && + StyleRef().LogicalHeight().IsAuto()) { // We can't multiply or divide by 'intrinsicSizingInfo.aspectRatio' here, it // breaks tests, like images/zoomed-img-size.html, which // can only be fixed once subpixel precision is available for things like @@ -215,22 +217,22 @@ // To match WinIE, in quirks mode use the parent's 'direction' property // instead of the the container block's. - TextDirection container_direction = container_block->Style()->Direction(); + TextDirection container_direction = container_block->StyleRef().Direction(); // Variables to solve. bool is_horizontal = IsHorizontalWritingMode(); - Length logical_left = Style()->LogicalLeft(); - Length logical_right = Style()->LogicalRight(); + Length logical_left = StyleRef().LogicalLeft(); + Length logical_right = StyleRef().LogicalRight(); Length margin_logical_left = - is_horizontal ? Style()->MarginLeft() : Style()->MarginTop(); + is_horizontal ? StyleRef().MarginLeft() : StyleRef().MarginTop(); Length margin_logical_right = - is_horizontal ? Style()->MarginRight() : Style()->MarginBottom(); - LayoutUnit& margin_logical_left_alias = Style()->IsLeftToRightDirection() + is_horizontal ? StyleRef().MarginRight() : StyleRef().MarginBottom(); + LayoutUnit& margin_logical_left_alias = StyleRef().IsLeftToRightDirection() ? computed_values.margins_.start_ : computed_values.margins_.end_; LayoutUnit& margin_logical_right_alias = - Style()->IsLeftToRightDirection() ? computed_values.margins_.end_ - : computed_values.margins_.start_; + StyleRef().IsLeftToRightDirection() ? computed_values.margins_.end_ + : computed_values.margins_.start_; // --------------------------------------------------------------------------- // 1. The used value of 'width' is determined as for inline replaced @@ -394,7 +396,7 @@ // should use the last line box. When this is fixed elsewhere, this block // should be removed. if (container_block->IsLayoutInline() && - !container_block->Style()->IsLeftToRightDirection()) { + !container_block->StyleRef().IsLeftToRightDirection()) { const LayoutInline* flow = ToLayoutInline(container_block); InlineFlowBox* first_line = flow->FirstLineBox(); InlineFlowBox* last_line = flow->LastLineBox(); @@ -433,13 +435,13 @@ ContainingBlockLogicalWidthForPositioned(container_block, false); // Variables to solve. - Length margin_before = Style()->MarginBefore(); - Length margin_after = Style()->MarginAfter(); + Length margin_before = StyleRef().MarginBefore(); + Length margin_after = StyleRef().MarginAfter(); LayoutUnit& margin_before_alias = computed_values.margins_.before_; LayoutUnit& margin_after_alias = computed_values.margins_.after_; - Length logical_top = Style()->LogicalTop(); - Length logical_bottom = Style()->LogicalBottom(); + Length logical_top = StyleRef().LogicalTop(); + Length logical_bottom = StyleRef().LogicalBottom(); // --------------------------------------------------------------------------- // 1. The used value of 'height' is determined as for inline replaced @@ -575,10 +577,10 @@ LayoutRect LayoutReplaced::ComputeObjectFit( const LayoutSize* overridden_intrinsic_size) const { LayoutRect content_rect = ContentBoxRect(); - EObjectFit object_fit = Style()->GetObjectFit(); + EObjectFit object_fit = StyleRef().GetObjectFit(); if (object_fit == EObjectFit::kFill && - Style()->ObjectPosition() == + StyleRef().ObjectPosition() == ComputedStyleInitialValues::InitialObjectPosition()) { return content_rect; } @@ -624,10 +626,11 @@ NOTREACHED(); } - LayoutUnit x_offset = MinimumValueForLength( - Style()->ObjectPosition().X(), content_rect.Width() - final_rect.Width()); + LayoutUnit x_offset = + MinimumValueForLength(StyleRef().ObjectPosition().X(), + content_rect.Width() - final_rect.Width()); LayoutUnit y_offset = - MinimumValueForLength(Style()->ObjectPosition().Y(), + MinimumValueForLength(StyleRef().ObjectPosition().Y(), content_rect.Height() - final_rect.Height()); final_rect.Move(x_offset, y_offset); @@ -684,9 +687,9 @@ // This solves above equation for 'width' (== logicalWidth). LayoutUnit margin_start = - MinimumValueForLength(Style()->MarginStart(), logical_width); + MinimumValueForLength(StyleRef().MarginStart(), logical_width); LayoutUnit margin_end = - MinimumValueForLength(Style()->MarginEnd(), logical_width); + MinimumValueForLength(StyleRef().MarginEnd(), logical_width); logical_width = (logical_width - (margin_start + margin_end + (Size().Width() - ClientWidth()))) .ClampNegativeToZero(); @@ -696,11 +699,11 @@ LayoutUnit LayoutReplaced::ComputeReplacedLogicalWidth( ShouldComputePreferred should_compute_preferred) const { - if (Style()->LogicalWidth().IsSpecified() || - Style()->LogicalWidth().IsIntrinsic()) + if (StyleRef().LogicalWidth().IsSpecified() || + StyleRef().LogicalWidth().IsIntrinsic()) return ComputeReplacedLogicalWidthRespectingMinMaxWidth( ComputeReplacedLogicalWidthUsing(kMainOrPreferredSize, - Style()->LogicalWidth()), + StyleRef().LogicalWidth()), should_compute_preferred); // 10.3.2 Inline, replaced elements: @@ -711,8 +714,8 @@ FloatSize constrained_size = ConstrainIntrinsicSizeToMinMax(intrinsic_sizing_info); - if (Style()->LogicalWidth().IsAuto()) { - bool computed_height_is_auto = Style()->LogicalHeight().IsAuto(); + if (StyleRef().LogicalWidth().IsAuto()) { + bool computed_height_is_auto = StyleRef().LogicalHeight().IsAuto(); // If 'height' and 'width' both have computed values of 'auto' and the // element also has an intrinsic width, then that intrinsic width is the @@ -783,10 +786,11 @@ LayoutUnit estimated_used_width) const { // 10.5 Content height: the 'height' property: // http://www.w3.org/TR/CSS21/visudet.html#propdef-height - if (HasReplacedLogicalHeight()) + if (HasReplacedLogicalHeight()) { return ComputeReplacedLogicalHeightRespectingMinMaxHeight( ComputeReplacedLogicalHeightUsing(kMainOrPreferredSize, - Style()->LogicalHeight())); + StyleRef().LogicalHeight())); + } // 10.6.2 Inline, replaced elements: // http://www.w3.org/TR/CSS21/visudet.html#inline-replaced-height @@ -796,7 +800,7 @@ FloatSize constrained_size = ConstrainIntrinsicSizeToMinMax(intrinsic_sizing_info); - bool width_is_auto = Style()->LogicalWidth().IsAuto(); + bool width_is_auto = StyleRef().LogicalWidth().IsAuto(); // If 'height' and 'width' both have computed values of 'auto' and the element // also has an intrinsic height, then that intrinsic height is the used value @@ -842,7 +846,7 @@ // We cannot resolve some logical width here (i.e. percent, fill-available or // fit-content) as the available logical width may not be set on our // containing block. - const Length& logical_width = Style()->LogicalWidth(); + const Length& logical_width = StyleRef().LogicalWidth(); if (logical_width.IsPercentOrCalc() || logical_width.IsFillAvailable() || logical_width.IsFitContent()) ComputeIntrinsicLogicalWidths(min_preferred_logical_width_, @@ -994,10 +998,10 @@ RootInlineBox& root = InlineBoxWrapper()->Root(); LayoutUnit new_logical_top = - root.Block().Style()->IsFlippedBlocksWritingMode() + root.Block().StyleRef().IsFlippedBlocksWritingMode() ? InlineBoxWrapper()->LogicalBottom() - root.SelectionBottom() : root.SelectionTop() - InlineBoxWrapper()->LogicalTop(); - if (root.Block().Style()->IsHorizontalWritingMode()) + if (root.Block().StyleRef().IsHorizontalWritingMode()) return LayoutRect(LayoutUnit(), new_logical_top, Size().Width(), root.SelectionHeight()); return LayoutRect(new_logical_top, LayoutUnit(), root.SelectionHeight(),
diff --git a/third_party/blink/renderer/core/layout/layout_replaced.h b/third_party/blink/renderer/core/layout/layout_replaced.h index 5074401..62be25f 100644 --- a/third_party/blink/renderer/core/layout/layout_replaced.h +++ b/third_party/blink/renderer/core/layout/layout_replaced.h
@@ -81,7 +81,7 @@ LayoutRect LocalSelectionRect() const final; bool HasObjectFit() const { - return Style()->GetObjectFit() != + return StyleRef().GetObjectFit() != ComputedStyleInitialValues::InitialObjectFit(); }
diff --git a/third_party/blink/renderer/core/layout/layout_ruby_run.cc b/third_party/blink/renderer/core/layout/layout_ruby_run.cc index 141eee16..699e128 100644 --- a/third_party/blink/renderer/core/layout/layout_ruby_run.cc +++ b/third_party/blink/renderer/core/layout/layout_ruby_run.cc
@@ -237,8 +237,8 @@ last_line_ruby_text_bottom = root_box->LogicalBottomLayoutOverflow(); } - if (Style()->IsFlippedLinesWritingMode() == - (Style()->GetRubyPosition() == RubyPosition::kAfter)) { + if (StyleRef().IsFlippedLinesWritingMode() == + (StyleRef().GetRubyPosition() == RubyPosition::kAfter)) { LayoutUnit first_line_top; if (LayoutRubyBase* rb = RubyBase()) { RootInlineBox* root_box = rb->FirstRootBox(); @@ -295,10 +295,10 @@ (logical_width - root_inline_box->LogicalRight()).ToInt()); } - start_overhang = Style()->IsLeftToRightDirection() ? logical_left_overhang - : logical_right_overhang; - end_overhang = Style()->IsLeftToRightDirection() ? logical_right_overhang - : logical_left_overhang; + start_overhang = StyleRef().IsLeftToRightDirection() ? logical_left_overhang + : logical_right_overhang; + end_overhang = StyleRef().IsLeftToRightDirection() ? logical_right_overhang + : logical_left_overhang; if (!start_layout_object || !start_layout_object->IsText() || start_layout_object->Style(first_line)->FontSize() >
diff --git a/third_party/blink/renderer/core/layout/layout_ruby_text.cc b/third_party/blink/renderer/core/layout/layout_ruby_text.cc index 7c63b99..5990208 100644 --- a/third_party/blink/renderer/core/layout/layout_ruby_text.cc +++ b/third_party/blink/renderer/core/layout/layout_ruby_text.cc
@@ -44,7 +44,7 @@ ETextAlign LayoutRubyText::TextAlignmentForLine( bool ends_with_soft_break) const { - ETextAlign text_align = Style()->GetTextAlign(); + ETextAlign text_align = StyleRef().GetTextAlign(); // FIXME: This check is bogus since user can set the initial value. if (text_align != ComputedStyleInitialValues::InitialTextAlign()) return LayoutBlockFlow::TextAlignmentForLine(ends_with_soft_break); @@ -58,7 +58,7 @@ unsigned expansion_opportunity_count, LayoutUnit& logical_left, LayoutUnit& logical_width) const { - ETextAlign text_align = Style()->GetTextAlign(); + ETextAlign text_align = StyleRef().GetTextAlign(); // FIXME: This check is bogus since user can set the initial value. if (text_align != ComputedStyleInitialValues::InitialTextAlign()) return LayoutBlockFlow::AdjustInlineDirectionLineBounds( @@ -73,7 +73,7 @@ LayoutUnit inset = (logical_width - max_preferred_logical_width) / (expansion_opportunity_count + 1); if (expansion_opportunity_count) - inset = std::min(LayoutUnit(2 * Style()->FontSize()), inset); + inset = std::min(LayoutUnit(2 * StyleRef().FontSize()), inset); logical_left += inset / 2; logical_width -= inset;
diff --git a/third_party/blink/renderer/core/layout/layout_scrollbar_part.cc b/third_party/blink/renderer/core/layout/layout_scrollbar_part.cc index a11e72a8..7900a41 100644 --- a/third_party/blink/renderer/core/layout/layout_scrollbar_part.cc +++ b/third_party/blink/renderer/core/layout/layout_scrollbar_part.cc
@@ -165,18 +165,18 @@ // up to date, especially since we are called at style change. // FIXME: Querying the style's border information doesn't work on table cells // with collapsing borders. - int visible_size = box->Size().Width() - box->Style()->BorderLeftWidth() - - box->Style()->BorderRightWidth(); + int visible_size = box->Size().Width() - box->StyleRef().BorderLeftWidth() - + box->StyleRef().BorderRightWidth(); SetWidth(LayoutUnit(ComputeScrollbarWidth(visible_size, Style()))); // Buttons and track pieces can all have margins along the axis of the // scrollbar. Values are rounded because scrollbar parts need to be rendered // at device pixel boundaries. SetMarginLeft(LayoutUnit( - MinimumValueForLength(Style()->MarginLeft(), LayoutUnit(visible_size)) + MinimumValueForLength(StyleRef().MarginLeft(), LayoutUnit(visible_size)) .Round())); SetMarginRight(LayoutUnit( - MinimumValueForLength(Style()->MarginRight(), LayoutUnit(visible_size)) + MinimumValueForLength(StyleRef().MarginRight(), LayoutUnit(visible_size)) .Round())); } @@ -188,18 +188,18 @@ // up to date, especially since we are called at style change. // FIXME: Querying the style's border information doesn't work on table cells // with collapsing borders. - int visible_size = box->Size().Height() - box->Style()->BorderTopWidth() - - box->Style()->BorderBottomWidth(); + int visible_size = box->Size().Height() - box->StyleRef().BorderTopWidth() - + box->StyleRef().BorderBottomWidth(); SetHeight(LayoutUnit(ComputeScrollbarHeight(visible_size, Style()))); // Buttons and track pieces can all have margins along the axis of the // scrollbar. Values are rounded because scrollbar parts need to be rendered // at device pixel boundaries. SetMarginTop(LayoutUnit( - MinimumValueForLength(Style()->MarginTop(), LayoutUnit(visible_size)) + MinimumValueForLength(StyleRef().MarginTop(), LayoutUnit(visible_size)) .Round())); SetMarginBottom(LayoutUnit( - MinimumValueForLength(Style()->MarginBottom(), LayoutUnit(visible_size)) + MinimumValueForLength(StyleRef().MarginBottom(), LayoutUnit(visible_size)) .Round())); }
diff --git a/third_party/blink/renderer/core/layout/layout_slider.cc b/third_party/blink/renderer/core/layout/layout_slider.cc index a442b80..7918e4b 100644 --- a/third_party/blink/renderer/core/layout/layout_slider.cc +++ b/third_party/blink/renderer/core/layout/layout_slider.cc
@@ -52,8 +52,8 @@ LayoutUnit& min_logical_width, LayoutUnit& max_logical_width) const { max_logical_width = - LayoutUnit(kDefaultTrackLength * Style()->EffectiveZoom()); - if (!Style()->Width().IsPercentOrCalc()) + LayoutUnit(kDefaultTrackLength * StyleRef().EffectiveZoom()); + if (!StyleRef().Width().IsPercentOrCalc()) min_logical_width = max_logical_width; }
diff --git a/third_party/blink/renderer/core/layout/layout_slider_container.cc b/third_party/blink/renderer/core/layout/layout_slider_container.cc index 111cbab..4a8785dd 100644 --- a/third_party/blink/renderer/core/layout/layout_slider_container.cc +++ b/third_party/blink/renderer/core/layout/layout_slider_container.cc
@@ -76,7 +76,7 @@ int tick_length = LayoutTheme::GetTheme().SliderTickSize().Height(); track_height = LayoutUnit(2 * (offset_from_center + tick_length)); } - float zoom_factor = Style()->EffectiveZoom(); + float zoom_factor = StyleRef().EffectiveZoom(); if (zoom_factor != 1.0) track_height *= zoom_factor; @@ -133,7 +133,7 @@ if (is_vertical) { thumb_location.SetY(thumb_location.Y() + track->ContentHeight() - thumb->Size().Height() - offset); - } else if (Style()->IsLeftToRightDirection()) { + } else if (StyleRef().IsLeftToRightDirection()) { thumb_location.SetX(thumb_location.X() + offset); } else { thumb_location.SetX(thumb_location.X() - offset);
diff --git a/third_party/blink/renderer/core/layout/layout_state.cc b/third_party/blink/renderer/core/layout/layout_state.cc index 1dc29c6d..c352cdc 100644 --- a/third_party/blink/renderer/core/layout/layout_state.cc +++ b/third_party/blink/renderer/core/layout/layout_state.cc
@@ -85,7 +85,7 @@ if (!layout_object.IsOutOfFlowPositioned()) return; if (LayoutObject* container = layout_object.Container()) { - if (container->Style()->HasInFlowPosition() && + if (container->StyleRef().HasInFlowPosition() && container->IsLayoutInline()) { pagination_offset_ += ToLayoutInline(container)->OffsetForInFlowPositionedInline(
diff --git a/third_party/blink/renderer/core/layout/layout_table.cc b/third_party/blink/renderer/core/layout/layout_table.cc index abc5986..f2497d62 100644 --- a/third_party/blink/renderer/core/layout/layout_table.cc +++ b/third_party/blink/renderer/core/layout/layout_table.cc
@@ -90,20 +90,21 @@ old_style ? old_style->IsFixedTableLayout() : false; // In the collapsed border model, there is no cell spacing. - h_spacing_ = ShouldCollapseBorders() ? 0 : Style()->HorizontalBorderSpacing(); - v_spacing_ = ShouldCollapseBorders() ? 0 : Style()->VerticalBorderSpacing(); + h_spacing_ = + ShouldCollapseBorders() ? 0 : StyleRef().HorizontalBorderSpacing(); + v_spacing_ = ShouldCollapseBorders() ? 0 : StyleRef().VerticalBorderSpacing(); DCHECK_GE(h_spacing_, 0); DCHECK_GE(v_spacing_, 0); if (!table_layout_ || - Style()->IsFixedTableLayout() != old_fixed_table_layout) { + StyleRef().IsFixedTableLayout() != old_fixed_table_layout) { if (table_layout_) table_layout_->WillChangeTableLayout(); // According to the CSS2 spec, you only use fixed table layout if an // explicit width is specified on the table. Auto width implies auto table // layout. - if (Style()->IsFixedTableLayout()) + if (StyleRef().IsFixedTableLayout()) table_layout_ = std::make_unique<TableLayoutAlgorithmFixed>(this); else table_layout_ = std::make_unique<TableLayoutAlgorithmAuto>(this); @@ -138,7 +139,7 @@ static inline bool NeedsTableSection(LayoutObject* object) { // Return true if 'object' can't exist in an anonymous table without being // wrapped in a table section box. - EDisplay display = object->Style()->Display(); + EDisplay display = object->StyleRef().Display(); return display != EDisplay::kTableCaption && display != EDisplay::kTableColumnGroup && display != EDisplay::kTableColumn; @@ -153,7 +154,7 @@ has_col_elements_ = true; wrap_in_anonymous_section = false; } else if (child->IsTableSection()) { - switch (child->Style()->Display()) { + switch (child->StyleRef().Display()) { case EDisplay::kTableHeaderGroup: ResetSectionPointerIfNotBefore(head_, before_child); if (!head_) { @@ -266,7 +267,7 @@ } bool LayoutTable::IsLogicalWidthAuto() const { - Length style_logical_width = Style()->LogicalWidth(); + Length style_logical_width = StyleRef().LogicalWidth(); return (!style_logical_width.IsSpecified() || !style_logical_width.IsPositive()) && !style_logical_width.IsIntrinsic(); @@ -302,24 +303,24 @@ LayoutUnit available_logical_width = ContainingBlockLogicalWidthForContent(); bool has_perpendicular_containing_block = - cb->Style()->IsHorizontalWritingMode() != - Style()->IsHorizontalWritingMode(); + cb->StyleRef().IsHorizontalWritingMode() != + StyleRef().IsHorizontalWritingMode(); LayoutUnit container_width_in_inline_direction = has_perpendicular_containing_block ? PerpendicularContainingBlockLogicalHeight() : available_logical_width; - Length style_logical_width = Style()->LogicalWidth(); + Length style_logical_width = StyleRef().LogicalWidth(); if (!IsLogicalWidthAuto()) { SetLogicalWidth(ConvertStyleLogicalWidthToComputedWidth( style_logical_width, container_width_in_inline_direction)); } else { // Subtract out any fixed margins from our available width for auto width // tables. - LayoutUnit margin_start = - MinimumValueForLength(Style()->MarginStart(), available_logical_width); + LayoutUnit margin_start = MinimumValueForLength(StyleRef().MarginStart(), + available_logical_width); LayoutUnit margin_end = - MinimumValueForLength(Style()->MarginEnd(), available_logical_width); + MinimumValueForLength(StyleRef().MarginEnd(), available_logical_width); LayoutUnit margin_total = margin_start + margin_end; // Subtract out our margins to get the available content width. @@ -346,7 +347,7 @@ } // Ensure we aren't bigger than our max-width style. - Length style_max_logical_width = Style()->LogicalMaxWidth(); + Length style_max_logical_width = StyleRef().LogicalMaxWidth(); if ((style_max_logical_width.IsSpecified() && !style_max_logical_width.IsNegative()) || style_max_logical_width.IsIntrinsic()) { @@ -364,7 +365,7 @@ LayoutUnit(std::max(LogicalWidth(), MinPreferredLogicalWidth()).Floor())); // Ensure we aren't smaller than our min-width style. - Length style_min_logical_width = Style()->LogicalMinWidth(); + Length style_min_logical_width = StyleRef().LogicalMinWidth(); if ((style_min_logical_width.IsSpecified() && !style_min_logical_width.IsNegative()) || style_min_logical_width.IsIntrinsic()) { @@ -379,8 +380,8 @@ ComputedMarginValues margin_values; ComputeMarginsForDirection(kInlineDirection, cb, available_logical_width, LogicalWidth(), margin_values.start_, - margin_values.end_, Style()->MarginStart(), - Style()->MarginEnd()); + margin_values.end_, StyleRef().MarginStart(), + StyleRef().MarginEnd()); SetMarginStart(margin_values.start_); SetMarginEnd(margin_values.end_); @@ -408,7 +409,7 @@ bool is_css_table = !IsHTMLTableElement(GetNode()); if (is_css_table && style_logical_width.IsSpecified() && style_logical_width.IsPositive() && - Style()->BoxSizing() == EBoxSizing::kContentBox) { + StyleRef().BoxSizing() == EBoxSizing::kContentBox) { borders = BorderStart() + BorderEnd() + (ShouldCollapseBorders() ? LayoutUnit() : PaddingStart() + PaddingEnd()); @@ -434,7 +435,7 @@ // FIXME: We cannot apply box-sizing: content-box on <table> which other // browsers allow. if (IsHTMLTableElement(GetNode()) || - Style()->BoxSizing() == EBoxSizing::kBorderBox) { + StyleRef().BoxSizing() == EBoxSizing::kBorderBox) { borders = border_and_padding; } computed_logical_height = @@ -508,7 +509,7 @@ LayoutUnit LayoutTable::LogicalHeightFromStyle() const { LayoutUnit computed_logical_height; - Length logical_height_length = Style()->LogicalHeight(); + Length logical_height_length = StyleRef().LogicalHeight(); if (logical_height_length.IsIntrinsic() || (logical_height_length.IsSpecified() && logical_height_length.IsPositive())) { @@ -516,7 +517,7 @@ ConvertStyleLogicalHeightToComputedHeight(logical_height_length); } - Length logical_max_height_length = Style()->LogicalMaxHeight(); + Length logical_max_height_length = StyleRef().LogicalMaxHeight(); if (logical_max_height_length.IsIntrinsic() || (logical_max_height_length.IsSpecified() && !logical_max_height_length.IsNegative())) { @@ -526,7 +527,7 @@ std::min(computed_logical_height, computed_max_logical_height); } - Length logical_min_height_length = Style()->LogicalMinHeight(); + Length logical_min_height_length = StyleRef().LogicalMinHeight(); if (logical_min_height_length.IsIntrinsic() || (logical_min_height_length.IsSpecified() && !logical_min_height_length.IsNegative())) { @@ -630,7 +631,7 @@ // Lay out top captions. // FIXME: Collapse caption margin. for (unsigned i = 0; i < captions_.size(); i++) { - if (captions_[i]->Style()->CaptionSide() == ECaptionSide::kBottom) + if (captions_[i]->StyleRef().CaptionSide() == ECaptionSide::kBottom) continue; LayoutCaption(*captions_[i], layouter); } @@ -652,10 +653,10 @@ SetLogicalHeight(table_box_logical_top + border_and_padding_before); LayoutUnit section_logical_left = LayoutUnit( - Style()->IsLeftToRightDirection() ? BorderStart() : BorderEnd()); + StyleRef().IsLeftToRightDirection() ? BorderStart() : BorderEnd()); if (!collapsing) { section_logical_left += - Style()->IsLeftToRightDirection() ? PaddingStart() : PaddingEnd(); + StyleRef().IsLeftToRightDirection() ? PaddingStart() : PaddingEnd(); } LayoutUnit current_available_logical_height = AvailableLogicalHeight(kIncludeMarginBorderPadding); @@ -797,7 +798,7 @@ // Lay out bottom captions. for (unsigned i = 0; i < captions_.size(); i++) { - if (captions_[i]->Style()->CaptionSide() != ECaptionSide::kBottom) + if (captions_[i]->StyleRef().CaptionSide() != ECaptionSide::kBottom) continue; LayoutCaption(*captions_[i], layouter); } @@ -869,9 +870,9 @@ ColAndColGroup colElement = ColElementAtAbsoluteColumn(absolute_column_index); LayoutTableCol* col = colElement.col; LayoutTableCol* colgroup = colElement.colgroup; - return (col && col->Style()->Visibility() == EVisibility::kCollapse) || + return (col && col->StyleRef().Visibility() == EVisibility::kCollapse) || (colgroup && - colgroup->Style()->Visibility() == EVisibility::kCollapse); + colgroup->StyleRef().Visibility() == EVisibility::kCollapse); } void LayoutTable::InvalidateCollapsedBorders() { @@ -946,9 +947,9 @@ captions_[i]->MarginBefore() + captions_[i]->MarginAfter(); bool caption_is_before = - (captions_[i]->Style()->CaptionSide() != ECaptionSide::kBottom) ^ - Style()->IsFlippedBlocksWritingMode(); - if (Style()->IsHorizontalWritingMode()) { + (captions_[i]->StyleRef().CaptionSide() != ECaptionSide::kBottom) ^ + StyleRef().IsFlippedBlocksWritingMode(); + if (StyleRef().IsHorizontalWritingMode()) { rect.SetHeight(rect.Height() - caption_logical_height); if (caption_is_before) rect.Move(LayoutUnit(), caption_logical_height); @@ -1204,7 +1205,7 @@ LayoutObject* next_sibling; for (LayoutObject* child = FirstChild(); child; child = next_sibling) { next_sibling = child->NextSibling(); - switch (child->Style()->Display()) { + switch (child->StyleRef().Display()) { case EDisplay::kTableColumn: case EDisplay::kTableColumnGroup: has_col_elements_ = true; @@ -1512,7 +1513,7 @@ // mapping them to top/bottom, we might have to hack this code first // (depending on what order we do these bug fixes in). if (!captions_.IsEmpty()) { - if (Style()->IsHorizontalWritingMode()) { + if (StyleRef().IsHorizontalWritingMode()) { rect.SetHeight(Size().Height()); rect.SetY(location.Y()); } else {
diff --git a/third_party/blink/renderer/core/layout/layout_table.h b/third_party/blink/renderer/core/layout/layout_table.h index 2c5835d..045eff0 100644 --- a/third_party/blink/renderer/core/layout/layout_table.h +++ b/third_party/blink/renderer/core/layout/layout_table.h
@@ -145,7 +145,7 @@ int VBorderSpacing() const { return v_spacing_; } bool ShouldCollapseBorders() const { - return Style()->BorderCollapse() == EBorderCollapse::kCollapse; + return StyleRef().BorderCollapse() == EBorderCollapse::kCollapse; } LayoutUnit BorderLeft() const override;
diff --git a/third_party/blink/renderer/core/layout/layout_table_box_component.cc b/third_party/blink/renderer/core/layout/layout_table_box_component.cc index 4b09846b..b080706 100644 --- a/third_party/blink/renderer/core/layout/layout_table_box_component.cc +++ b/third_party/blink/renderer/core/layout/layout_table_box_component.cc
@@ -61,7 +61,7 @@ const ComputedStyle* old_style) { LayoutBox::StyleDidChange(diff, old_style); SetCanContainFixedPositionObjects( - Style()->CanContainFixedPositionObjects(false) || + StyleRef().CanContainFixedPositionObjects(false) || ShouldApplyPaintContainment() || ShouldApplyLayoutContainment()); }
diff --git a/third_party/blink/renderer/core/layout/layout_table_cell.cc b/third_party/blink/renderer/core/layout/layout_table_cell.cc index 07472c7e..9c7f0761f 100644 --- a/third_party/blink/renderer/core/layout/layout_table_cell.cc +++ b/third_party/blink/renderer/core/layout/layout_table_cell.cc
@@ -150,7 +150,7 @@ unsigned col_span_count = ColSpan(); int col_width_sum = 0; for (unsigned i = 1; i <= col_span_count; i++) { - Length col_width = table_col->Style()->LogicalWidth(); + Length col_width = table_col->StyleRef().LogicalWidth(); // Percentage value should be returned only for colSpan == 1. // Otherwise we return original width for the cell. @@ -198,7 +198,7 @@ if (logical_height > -1) SetOverrideLogicalHeight(logical_height); - if (GetNode() && Style()->AutoWrap()) { + if (GetNode() && StyleRef().AutoWrap()) { // See if nowrap was set. Length w = StyleOrColLogicalWidth(); const AtomicString& nowrap = ToElement(GetNode())->getAttribute(nowrapAttr); @@ -316,8 +316,8 @@ ComputedCSSPaddingTop() + LogicalIntrinsicPaddingToPhysical().Top(); // TODO(crbug.com/377847): The ToInt call should be removed when Table is // sub-pixel aware. - return Style()->IsHorizontalWritingMode() ? LayoutUnit(result.ToInt()) - : result; + return StyleRef().IsHorizontalWritingMode() ? LayoutUnit(result.ToInt()) + : result; } LayoutUnit LayoutTableCell::PaddingBottom() const { @@ -325,8 +325,8 @@ ComputedCSSPaddingBottom() + LogicalIntrinsicPaddingToPhysical().Bottom(); // TODO(crbug.com/377847): The ToInt call should be removed when Table is // sub-pixel aware. - return Style()->IsHorizontalWritingMode() ? LayoutUnit(result.ToInt()) - : result; + return StyleRef().IsHorizontalWritingMode() ? LayoutUnit(result.ToInt()) + : result; } LayoutUnit LayoutTableCell::PaddingLeft() const { @@ -334,8 +334,8 @@ ComputedCSSPaddingLeft() + LogicalIntrinsicPaddingToPhysical().Left(); // TODO(crbug.com/377847): The ToInt call should be removed when Table is // sub-pixel aware. - return Style()->IsHorizontalWritingMode() ? result - : LayoutUnit(result.ToInt()); + return StyleRef().IsHorizontalWritingMode() ? result + : LayoutUnit(result.ToInt()); } LayoutUnit LayoutTableCell::PaddingRight() const { @@ -343,8 +343,8 @@ ComputedCSSPaddingRight() + LogicalIntrinsicPaddingToPhysical().Right(); // TODO(crbug.com/377847): The ToInt call should be removed when Table is // sub-pixel aware. - return Style()->IsHorizontalWritingMode() ? result - : LayoutUnit(result.ToInt()); + return StyleRef().IsHorizontalWritingMode() ? result + : LayoutUnit(result.ToInt()); } void LayoutTableCell::SetOverrideLogicalHeightFromRowHeight( @@ -452,7 +452,7 @@ void LayoutTableCell::StyleDidChange(StyleDifference diff, const ComputedStyle* old_style) { - DCHECK_EQ(Style()->Display(), EDisplay::kTableCell); + DCHECK_EQ(StyleRef().Display(), EDisplay::kTableCell); LayoutBlockFlow::StyleDidChange(diff, old_style); SetHasBoxDecorationBackground(true); @@ -460,14 +460,14 @@ if (!old_style) return; - if (Parent() && Section() && Style()->Height() != old_style->Height()) + if (Parent() && Section() && StyleRef().Height() != old_style->Height()) Section()->RowLogicalHeightChanged(Row()); // Our intrinsic padding pushes us down to align with the baseline of other // cells on the row. If our vertical-align has changed then so will the // padding needed to align with other cells - clear it so we can recalculate // it from scratch. - if (Style()->VerticalAlign() != old_style->VerticalAlign()) + if (StyleRef().VerticalAlign() != old_style->VerticalAlign()) ClearIntrinsicPadding(); if (!Parent()) @@ -797,14 +797,14 @@ const CSSProperty& after_color_property = ResolveBorderProperty(GetCSSPropertyBorderBlockEndColor()); CollapsedBorderValue result = CollapsedBorderValue( - Style()->BorderBeforeStyle(), Style()->BorderBeforeWidth(), + StyleRef().BorderBeforeStyle(), StyleRef().BorderBeforeWidth(), ResolveColor(before_color_property), kBorderPrecedenceCell); if (cell_above) { // (2) A before cell's after border. result = ChooseBorder( - CollapsedBorderValue(cell_above->Style()->BorderAfterStyle(), - cell_above->Style()->BorderAfterWidth(), + CollapsedBorderValue(cell_above->StyleRef().BorderAfterStyle(), + cell_above->StyleRef().BorderAfterWidth(), cell_above->ResolveColor(after_color_property), kBorderPrecedenceCell), result); @@ -815,8 +815,8 @@ // (3) Our row's before border. result = ChooseBorder( result, - CollapsedBorderValue(Parent()->Style()->BorderBeforeStyle(), - Parent()->Style()->BorderBeforeWidth(), + CollapsedBorderValue(Parent()->StyleRef().BorderBeforeStyle(), + Parent()->StyleRef().BorderBeforeWidth(), Parent()->ResolveColor(before_color_property), kBorderPrecedenceRow)); if (!result.Exists()) @@ -832,8 +832,8 @@ if (prev_row) { result = ChooseBorder( - CollapsedBorderValue(prev_row->Style()->BorderAfterStyle(), - prev_row->Style()->BorderAfterWidth(), + CollapsedBorderValue(prev_row->StyleRef().BorderAfterStyle(), + prev_row->StyleRef().BorderAfterWidth(), prev_row->ResolveColor(after_color_property), kBorderPrecedenceRow), result); @@ -848,8 +848,8 @@ // (5) Our row group's before border. result = ChooseBorder( result, - CollapsedBorderValue(curr_section->Style()->BorderBeforeStyle(), - curr_section->Style()->BorderBeforeWidth(), + CollapsedBorderValue(curr_section->StyleRef().BorderBeforeStyle(), + curr_section->StyleRef().BorderBeforeWidth(), curr_section->ResolveColor(before_color_property), kBorderPrecedenceRowGroup)); if (!result.Exists()) @@ -859,8 +859,8 @@ curr_section = table->SectionAbove(curr_section, kSkipEmptySections); if (curr_section) { result = ChooseBorder( - CollapsedBorderValue(curr_section->Style()->BorderAfterStyle(), - curr_section->Style()->BorderAfterWidth(), + CollapsedBorderValue(curr_section->StyleRef().BorderAfterStyle(), + curr_section->StyleRef().BorderAfterWidth(), curr_section->ResolveColor(after_color_property), kBorderPrecedenceRowGroup), result); @@ -877,8 +877,8 @@ if (col_elt) { result = ChooseBorder( result, - CollapsedBorderValue(col_elt->Style()->BorderBeforeStyle(), - col_elt->Style()->BorderBeforeWidth(), + CollapsedBorderValue(col_elt->StyleRef().BorderBeforeStyle(), + col_elt->StyleRef().BorderBeforeWidth(), col_elt->ResolveColor(before_color_property), kBorderPrecedenceColumn)); if (!result.Exists()) @@ -888,8 +888,8 @@ result = ChooseBorder( result, CollapsedBorderValue( - enclosing_column_group->Style()->BorderBeforeStyle(), - enclosing_column_group->Style()->BorderBeforeWidth(), + enclosing_column_group->StyleRef().BorderBeforeStyle(), + enclosing_column_group->StyleRef().BorderBeforeWidth(), enclosing_column_group->ResolveColor(before_color_property), kBorderPrecedenceColumnGroup)); if (!result.Exists()) @@ -899,8 +899,8 @@ // (9) The table's before border. result = ChooseBorder( - result, CollapsedBorderValue(table->Style()->BorderBeforeStyle(), - table->Style()->BorderBeforeWidth(), + result, CollapsedBorderValue(table->StyleRef().BorderBeforeStyle(), + table->StyleRef().BorderBeforeWidth(), table->ResolveColor(before_color_property), kBorderPrecedenceTable)); if (!result.Exists()) @@ -928,15 +928,15 @@ const CSSProperty& after_color_property = ResolveBorderProperty(GetCSSPropertyBorderBlockEndColor()); CollapsedBorderValue result = CollapsedBorderValue( - Style()->BorderAfterStyle(), Style()->BorderAfterWidth(), + StyleRef().BorderAfterStyle(), StyleRef().BorderAfterWidth(), ResolveColor(after_color_property), kBorderPrecedenceCell); if (cell_below) { // (2) An after cell's before border. result = ChooseBorder( result, - CollapsedBorderValue(cell_below->Style()->BorderBeforeStyle(), - cell_below->Style()->BorderBeforeWidth(), + CollapsedBorderValue(cell_below->StyleRef().BorderBeforeStyle(), + cell_below->StyleRef().BorderBeforeWidth(), cell_below->ResolveColor(before_color_property), kBorderPrecedenceCell)); if (!result.Exists()) @@ -945,8 +945,8 @@ // (3) Our row's after border. (FIXME: Deal with rowspan!) result = ChooseBorder( - result, CollapsedBorderValue(Parent()->Style()->BorderAfterStyle(), - Parent()->Style()->BorderAfterWidth(), + result, CollapsedBorderValue(Parent()->StyleRef().BorderAfterStyle(), + Parent()->StyleRef().BorderAfterWidth(), Parent()->ResolveColor(after_color_property), kBorderPrecedenceRow)); if (!result.Exists()) @@ -956,8 +956,8 @@ if (cell_below) { result = ChooseBorder( result, CollapsedBorderValue( - cell_below->Parent()->Style()->BorderBeforeStyle(), - cell_below->Parent()->Style()->BorderBeforeWidth(), + cell_below->Parent()->StyleRef().BorderBeforeStyle(), + cell_below->Parent()->StyleRef().BorderBeforeWidth(), cell_below->Parent()->ResolveColor(before_color_property), kBorderPrecedenceRow)); if (!result.Exists()) @@ -970,8 +970,8 @@ // (5) Our row group's after border. result = ChooseBorder( result, - CollapsedBorderValue(curr_section->Style()->BorderAfterStyle(), - curr_section->Style()->BorderAfterWidth(), + CollapsedBorderValue(curr_section->StyleRef().BorderAfterStyle(), + curr_section->StyleRef().BorderAfterWidth(), curr_section->ResolveColor(after_color_property), kBorderPrecedenceRowGroup)); if (!result.Exists()) @@ -982,8 +982,8 @@ if (curr_section) { result = ChooseBorder( result, CollapsedBorderValue( - curr_section->Style()->BorderBeforeStyle(), - curr_section->Style()->BorderBeforeWidth(), + curr_section->StyleRef().BorderBeforeStyle(), + curr_section->StyleRef().BorderBeforeWidth(), curr_section->ResolveColor(before_color_property), kBorderPrecedenceRowGroup)); if (!result.Exists()) @@ -999,8 +999,8 @@ if (col_elt) { result = ChooseBorder( result, - CollapsedBorderValue(col_elt->Style()->BorderAfterStyle(), - col_elt->Style()->BorderAfterWidth(), + CollapsedBorderValue(col_elt->StyleRef().BorderAfterStyle(), + col_elt->StyleRef().BorderAfterWidth(), col_elt->ResolveColor(after_color_property), kBorderPrecedenceColumn)); if (!result.Exists()) @@ -1010,8 +1010,8 @@ result = ChooseBorder( result, CollapsedBorderValue( - enclosing_column_group->Style()->BorderAfterStyle(), - enclosing_column_group->Style()->BorderAfterWidth(), + enclosing_column_group->StyleRef().BorderAfterStyle(), + enclosing_column_group->StyleRef().BorderAfterWidth(), enclosing_column_group->ResolveColor(after_color_property), kBorderPrecedenceColumnGroup)); if (!result.Exists()) @@ -1021,8 +1021,8 @@ // (9) The table's after border. result = ChooseBorder( - result, CollapsedBorderValue(table->Style()->BorderAfterStyle(), - table->Style()->BorderAfterWidth(), + result, CollapsedBorderValue(table->StyleRef().BorderAfterStyle(), + table->StyleRef().BorderAfterWidth(), table->ResolveColor(after_color_property), kBorderPrecedenceTable)); if (!result.Exists()) @@ -1142,7 +1142,7 @@ // Shrink our intrinsic padding as much as possible to accommodate the // scrollbar. - if (Style()->VerticalAlign() == EVerticalAlign::kMiddle) { + if (StyleRef().VerticalAlign() == EVerticalAlign::kMiddle) { LayoutUnit total_height = LogicalHeight(); LayoutUnit height_without_intrinsic_padding = total_height - IntrinsicPaddingBefore() - IntrinsicPaddingAfter();
diff --git a/third_party/blink/renderer/core/layout/layout_table_cell.h b/third_party/blink/renderer/core/layout/layout_table_cell.h index 2299fe6..44dedd1 100644 --- a/third_party/blink/renderer/core/layout/layout_table_cell.h +++ b/third_party/blink/renderer/core/layout/layout_table_cell.h
@@ -144,7 +144,7 @@ } Length StyleOrColLogicalWidth() const { - Length style_width = Style()->LogicalWidth(); + Length style_width = StyleRef().LogicalWidth(); if (!style_width.IsAuto()) return style_width; if (LayoutTableCol* first_column = @@ -156,7 +156,7 @@ } int LogicalHeightFromStyle() const { - Length height = Style()->LogicalHeight(); + Length height = StyleRef().LogicalHeight(); int style_logical_height = height.IsIntrinsicOrAuto() ? 0 @@ -166,7 +166,7 @@ // add in the border and padding. // Call computedCSSPadding* directly to avoid including implicitPadding. if (!GetDocument().InQuirksMode() && - Style()->BoxSizing() != EBoxSizing::kBorderBox) { + StyleRef().BoxSizing() != EBoxSizing::kBorderBox) { style_logical_height += (ComputedCSSPaddingBefore() + ComputedCSSPaddingAfter()).Floor() + (BorderBefore() + BorderAfter()).Floor(); @@ -199,7 +199,7 @@ LayoutUnit CellBaselinePosition() const; bool IsBaselineAligned() const { - EVerticalAlign va = Style()->VerticalAlign(); + EVerticalAlign va = StyleRef().VerticalAlign(); return va == EVerticalAlign::kBaseline || va == EVerticalAlign::kTextBottom || va == EVerticalAlign::kTextTop || va == EVerticalAlign::kSuper ||
diff --git a/third_party/blink/renderer/core/layout/layout_table_col.cc b/third_party/blink/renderer/core/layout/layout_table_col.cc index d24abbb..f70ca59 100644 --- a/third_party/blink/renderer/core/layout/layout_table_col.cc +++ b/third_party/blink/renderer/core/layout/layout_table_col.cc
@@ -43,8 +43,8 @@ void LayoutTableCol::StyleDidChange(StyleDifference diff, const ComputedStyle* old_style) { - DCHECK(Style()->Display() == EDisplay::kTableColumn || - Style()->Display() == EDisplay::kTableColumnGroup); + DCHECK(StyleRef().Display() == EDisplay::kTableColumn || + StyleRef().Display() == EDisplay::kTableColumnGroup); LayoutTableBoxComponent::StyleDidChange(diff, old_style); @@ -58,7 +58,7 @@ LayoutTableBoxComponent::InvalidateCollapsedBordersOnStyleChange( *this, *table, diff, *old_style); - if ((old_style->LogicalWidth() != Style()->LogicalWidth()) || + if ((old_style->LogicalWidth() != StyleRef().LogicalWidth()) || LayoutTableBoxComponent::DoCellsHaveDirtyWidth(*this, *table, diff, *old_style)) { // TODO(dgrogan): Optimization opportunities:
diff --git a/third_party/blink/renderer/core/layout/layout_table_col.h b/third_party/blink/renderer/core/layout/layout_table_col.h index 2496e1b4..56634d3d 100644 --- a/third_party/blink/renderer/core/layout/layout_table_col.h +++ b/third_party/blink/renderer/core/layout/layout_table_col.h
@@ -68,10 +68,10 @@ bool IsTableColumnGroupWithColumnChildren() { return FirstChild(); } bool IsTableColumn() const { - return Style()->Display() == EDisplay::kTableColumn; + return StyleRef().Display() == EDisplay::kTableColumn; } bool IsTableColumnGroup() const { - return Style()->Display() == EDisplay::kTableColumnGroup; + return StyleRef().Display() == EDisplay::kTableColumnGroup; } LayoutTableCol* EnclosingColumnGroup() const;
diff --git a/third_party/blink/renderer/core/layout/layout_table_row.cc b/third_party/blink/renderer/core/layout/layout_table_row.cc index a8f12d0..3d6f912 100644 --- a/third_party/blink/renderer/core/layout/layout_table_row.cc +++ b/third_party/blink/renderer/core/layout/layout_table_row.cc
@@ -53,7 +53,7 @@ void LayoutTableRow::StyleDidChange(StyleDifference diff, const ComputedStyle* old_style) { - DCHECK_EQ(Style()->Display(), EDisplay::kTableRow); + DCHECK_EQ(StyleRef().Display(), EDisplay::kTableRow); LayoutTableBoxComponent::StyleDidChange(diff, old_style); PropagateStyleToAnonymousChildren(); @@ -61,7 +61,7 @@ if (!old_style) return; - if (Section() && Style()->LogicalHeight() != old_style->LogicalHeight()) + if (Section() && StyleRef().LogicalHeight() != old_style->LogicalHeight()) Section()->RowLogicalHeightChanged(this); if (!Parent()) @@ -100,7 +100,7 @@ // When a row gets collapsed or uncollapsed, it's necessary to check all the // rows to find any cell that may span the current row. if ((old_style->Visibility() == EVisibility::kCollapse) != - (Style()->Visibility() == EVisibility::kCollapse)) { + (StyleRef().Visibility() == EVisibility::kCollapse)) { for (LayoutTableRow* row = Section()->FirstRow(); row; row = row->NextRow()) { for (LayoutTableCell* cell = row->FirstCell(); cell;
diff --git a/third_party/blink/renderer/core/layout/layout_table_row.h b/third_party/blink/renderer/core/layout/layout_table_row.h index 649d16a7..f70334f4 100644 --- a/third_party/blink/renderer/core/layout/layout_table_row.h +++ b/third_party/blink/renderer/core/layout/layout_table_row.h
@@ -138,7 +138,7 @@ PaintLayerType LayerTypeRequired() const override { if (HasTransformRelatedProperty() || HasHiddenBackface() || - CreatesGroup() || Style()->ShouldCompositeForCurrentAnimations() || + CreatesGroup() || StyleRef().ShouldCompositeForCurrentAnimations() || IsStickyPositioned()) return kNormalPaintLayer;
diff --git a/third_party/blink/renderer/core/layout/layout_table_section.cc b/third_party/blink/renderer/core/layout/layout_table_section.cc index 48c2d52..ca17a55d 100644 --- a/third_party/blink/renderer/core/layout/layout_table_section.cc +++ b/third_party/blink/renderer/core/layout/layout_table_section.cc
@@ -106,9 +106,9 @@ void LayoutTableSection::StyleDidChange(StyleDifference diff, const ComputedStyle* old_style) { - DCHECK(Style()->Display() == EDisplay::kTableFooterGroup || - Style()->Display() == EDisplay::kTableRowGroup || - Style()->Display() == EDisplay::kTableHeaderGroup); + DCHECK(StyleRef().Display() == EDisplay::kTableFooterGroup || + StyleRef().Display() == EDisplay::kTableRowGroup || + StyleRef().Display() == EDisplay::kTableHeaderGroup); LayoutTableBoxComponent::StyleDidChange(diff, old_style); PropagateStyleToAnonymousChildren(); @@ -774,8 +774,8 @@ bool LayoutTableSection::RowHasVisibilityCollapse(unsigned row) const { return ((grid_[row].row && - grid_[row].row->Style()->Visibility() == EVisibility::kCollapse) || - Style()->Visibility() == EVisibility::kCollapse); + grid_[row].row->StyleRef().Visibility() == EVisibility::kCollapse) || + StyleRef().Visibility() == EVisibility::kCollapse); } // Find out the baseline of the cell @@ -1142,7 +1142,7 @@ } bool CellHasExplicitlySpecifiedHeight(const LayoutTableCell& cell) { - if (cell.Style()->LogicalHeight().IsFixed()) + if (cell.StyleRef().LogicalHeight().IsFixed()) return true; LayoutBlock* cb = cell.ContainingBlock(); if (cb->AvailableLogicalHeightForPercentageComputation() == -1) @@ -1154,8 +1154,8 @@ LayoutObject* cell_descendant) { if (!CellHasExplicitlySpecifiedHeight(cell)) return false; - if (cell_descendant->Style()->OverflowY() == EOverflow::kVisible || - cell_descendant->Style()->OverflowY() == EOverflow::kHidden) + if (cell_descendant->StyleRef().OverflowY() == EOverflow::kVisible || + cell_descendant->StyleRef().OverflowY() == EOverflow::kHidden) return true; return cell_descendant->IsBox() && ToLayoutBox(cell_descendant)->ShouldBeConsideredAsReplaced(); @@ -1244,7 +1244,7 @@ LayoutUnit(r_height))) cell_vertical_align = EVerticalAlign::kTop; else - cell_vertical_align = cell->Style()->VerticalAlign(); + cell_vertical_align = cell->StyleRef().VerticalAlign(); // Calculate total collapsed height affecting one cell. int collapsed_height = 0; @@ -1903,12 +1903,13 @@ // as we discover new bugs. :) bool cell_children_flex = false; bool flex_all_children = CellHasExplicitlySpecifiedHeight(cell) || - (!Table()->Style()->LogicalHeight().IsAuto() && + (!Table()->StyleRef().LogicalHeight().IsAuto() && row_height != cell.LogicalHeight()); for (LayoutObject* child = cell.FirstChild(); child; child = child->NextSibling()) { - if (!child->IsText() && child->Style()->LogicalHeight().IsPercentOrCalc() && + if (!child->IsText() && + child->StyleRef().LogicalHeight().IsPercentOrCalc() && (flex_all_children || ShouldFlexCellChild(cell, child)) && (!child->IsTable() || ToLayoutTable(child)->HasSections())) { cell_children_flex = true;
diff --git a/third_party/blink/renderer/core/layout/layout_text.cc b/third_party/blink/renderer/core/layout/layout_text.cc index 61df7611..c436e1de 100644 --- a/third_party/blink/renderer/core/layout/layout_text.cc +++ b/third_party/blink/renderer/core/layout/layout_text.cc
@@ -436,7 +436,7 @@ const LayoutRect& passed_boundaries) const { FloatRect boundaries(passed_boundaries); if (!ellipsis_rect.IsEmpty()) { - if (Style()->IsHorizontalWritingMode()) + if (StyleRef().IsHorizontalWritingMode()) boundaries.SetWidth(ellipsis_rect.MaxX() - boundaries.X()); else boundaries.SetHeight(ellipsis_rect.MaxY() - boundaries.Y()); @@ -739,7 +739,7 @@ FirstTextBox()->IsHorizontal() ? point.X() : point.Y(); LayoutUnit point_block_direction = FirstTextBox()->IsHorizontal() ? point.Y() : point.X(); - bool blocks_are_flipped = Style()->IsFlippedBlocksWritingMode(); + bool blocks_are_flipped = StyleRef().IsFlippedBlocksWritingMode(); InlineTextBox* last_box = nullptr; for (InlineTextBox* box : TextBoxes()) { @@ -869,7 +869,7 @@ // for unicode-bidi: plaintext, use inlineBoxBidiLevel() to test the correct // direction for the cursor. - if (right_aligned && Style()->GetUnicodeBidi() == UnicodeBidi::kPlaintext) { + if (right_aligned && StyleRef().GetUnicodeBidi() == UnicodeBidi::kPlaintext) { if (inline_box->BidiLevel() % 2 != 1) right_aligned = false; } @@ -883,7 +883,7 @@ } return LayoutRect( - Style()->IsHorizontalWritingMode() + StyleRef().IsHorizontalWritingMode() ? IntRect(left.ToInt(), top, caret_width.ToInt(), height) : IntRect(top, left.ToInt(), height, caret_width.ToInt())); } @@ -898,7 +898,7 @@ HashSet<const SimpleFontData*>* fallback_fonts, FloatRect* glyph_bounds_accumulation, float expansion) const { - if (Style()->HasTextCombine() && IsCombineText()) { + if (StyleRef().HasTextCombine() && IsCombineText()) { const LayoutTextCombine* combine_text = ToLayoutTextCombine(this); if (combine_text->IsCombined()) return combine_text->CombinedTextWidth(f); @@ -908,7 +908,7 @@ ConstructTextRun(f, this, start, len, StyleRef(), text_direction); run.SetCharactersLength(TextLength() - start); DCHECK_GE(run.CharactersLength(), run.length()); - run.SetTabSize(!Style()->CollapseWhiteSpace(), Style()->GetTabSize()); + run.SetTabSize(!StyleRef().CollapseWhiteSpace(), StyleRef().GetTabSize()); run.SetXPos(lead_width + text_width_so_far); run.SetExpansion(expansion); @@ -942,7 +942,7 @@ // below. float lead_width = lead_width_layout_unit.ToFloat(); - bool collapse_white_space = Style()->CollapseWhiteSpace(); + bool collapse_white_space = StyleRef().CollapseWhiteSpace(); if (!collapse_white_space) strip_front_spaces = false; @@ -978,9 +978,9 @@ DCHECK(text_); StringImpl& text = *text_.Impl(); if (text[0] == kSpaceCharacter || - (text[0] == kNewlineCharacter && !Style()->PreserveNewline()) || + (text[0] == kNewlineCharacter && !StyleRef().PreserveNewline()) || text[0] == kTabulationCharacter) { - const Font& font = Style()->GetFont(); // FIXME: This ignores first-line. + const Font& font = StyleRef().GetFont(); // FIXME: This ignores first-line. if (strip_front_spaces) { const UChar kSpaceChar = kSpaceCharacter; TextRun run = @@ -994,12 +994,12 @@ strip_front_spaces = collapse_white_space && has_end_white_space_; - if (!Style()->AutoWrap() || float_min_width > float_max_width) + if (!StyleRef().AutoWrap() || float_min_width > float_max_width) float_min_width = float_max_width; // Compute our max widths by scanning the string for newlines. if (has_break) { - const Font& f = Style()->GetFont(); // FIXME: This ignores first-line. + const Font& f = StyleRef().GetFont(); // FIXME: This ignores first-line. bool first_line = true; first_line_max_width = LayoutUnit(float_max_width); last_line_max_width = LayoutUnit(float_max_width); @@ -1424,7 +1424,7 @@ } else { // Nowrap can never be broken, so don't bother setting the breakable // character boolean. Pre can only be broken if we encounter a newline. - if (Style()->AutoWrap() || is_newline) + if (StyleRef().AutoWrap() || is_newline) has_breakable_char_ = true; if (curr_min_width > min_width_) @@ -1448,7 +1448,8 @@ ConstructTextRun(f, this, i, 1, style_to_use, text_direction); run.SetCharactersLength(len - i); DCHECK_GE(run.CharactersLength(), run.length()); - run.SetTabSize(!Style()->CollapseWhiteSpace(), Style()->GetTabSize()); + run.SetTabSize(!StyleRef().CollapseWhiteSpace(), + StyleRef().GetTabSize()); run.SetXPos(lead_width + curr_max_width); curr_max_width += f.Width(run); @@ -1492,13 +1493,13 @@ unsigned length = TextLength(); if (Is8Bit()) { for (unsigned i = 0; i < length; ++i) { - if (!Style()->IsCollapsibleWhiteSpace(Characters8()[i])) + if (!StyleRef().IsCollapsibleWhiteSpace(Characters8()[i])) return false; } return true; } for (unsigned i = 0; i < length; ++i) { - if (!Style()->IsCollapsibleWhiteSpace(Characters16()[i])) + if (!StyleRef().IsCollapsibleWhiteSpace(Characters16()[i])) return false; } return true; @@ -1886,8 +1887,8 @@ return 0; float w; - if (&f == &Style()->GetFont()) { - if (!Style()->PreserveNewline() && !from && len == TextLength()) { + if (&f == &StyleRef().GetFont()) { + if (!StyleRef().PreserveNewline() && !from && len == TextLength()) { if (fallback_fonts) { DCHECK(glyph_bounds); if (PreferredLogicalWidthsDirty() || @@ -1913,7 +1914,7 @@ run.SetCharactersLength(TextLength() - from); DCHECK_GE(run.CharactersLength(), run.length()); - run.SetTabSize(!Style()->CollapseWhiteSpace(), Style()->GetTabSize()); + run.SetTabSize(!StyleRef().CollapseWhiteSpace(), StyleRef().GetTabSize()); run.SetXPos(x_pos.ToFloat()); w = f.Width(run, fallback_fonts, glyph_bounds); } @@ -1947,7 +1948,7 @@ logical_right_side = curr->LogicalRight().ToFloat(); } - bool is_horizontal = Style()->IsHorizontalWritingMode(); + bool is_horizontal = StyleRef().IsHorizontalWritingMode(); float x = is_horizontal ? logical_left_side : FirstTextBox()->X().ToFloat(); float y = is_horizontal ? FirstTextBox()->Y().ToFloat() : logical_left_side; @@ -2001,7 +2002,7 @@ LayoutRect rect(logical_left_side, logical_top, logical_width, logical_height); - if (!Style()->IsHorizontalWritingMode()) + if (!StyleRef().IsHorizontalWritingMode()) rect = rect.TransposedRect(); return rect; }
diff --git a/third_party/blink/renderer/core/layout/layout_text.h b/third_party/blink/renderer/core/layout/layout_text.h index 36a11637..e1d4868 100644 --- a/third_party/blink/renderer/core/layout/layout_text.h +++ b/third_party/blink/renderer/core/layout/layout_text.h
@@ -278,7 +278,7 @@ bool ContainsReversedText() const { return contains_reversed_text_; } bool IsSecure() const { - return Style()->TextSecurity() != ETextSecurity::kNone; + return StyleRef().TextSecurity() != ETextSecurity::kNone; } void MomentarilyRevealLastTypedCharacter( unsigned last_typed_character_offset);
diff --git a/third_party/blink/renderer/core/layout/layout_text_combine.cc b/third_party/blink/renderer/core/layout/layout_text_combine.cc index dde546f..4056a1f 100644 --- a/third_party/blink/renderer/core/layout/layout_text_combine.cc +++ b/third_party/blink/renderer/core/layout/layout_text_combine.cc
@@ -149,7 +149,7 @@ void LayoutTextCombine::UpdateIsCombined() { // CSS3 spec says text-combine works only in vertical writing mode. - is_combined_ = !Style()->IsHorizontalWritingMode() + is_combined_ = !StyleRef().IsHorizontalWritingMode() // Nothing to combine. && !HasEmptyText(); }
diff --git a/third_party/blink/renderer/core/layout/layout_text_combine.h b/third_party/blink/renderer/core/layout/layout_text_combine.h index 9ad8dc9..d356152 100644 --- a/third_party/blink/renderer/core/layout/layout_text_combine.h +++ b/third_party/blink/renderer/core/layout/layout_text_combine.h
@@ -39,7 +39,7 @@ float CombinedTextWidth(const Font& font) const { return font.GetFontDescription().ComputedSize(); } - const Font& OriginalFont() const { return Parent()->Style()->GetFont(); } + const Font& OriginalFont() const { return Parent()->StyleRef().GetFont(); } void TransformToInlineCoordinates(GraphicsContext&, const LayoutRect& box_rect, bool clip = false) const;
diff --git a/third_party/blink/renderer/core/layout/layout_text_control.cc b/third_party/blink/renderer/core/layout/layout_text_control.cc index 921bc92..42e0196 100644 --- a/third_party/blink/renderer/core/layout/layout_text_control.cc +++ b/third_party/blink/renderer/core/layout/layout_text_control.cc
@@ -108,9 +108,9 @@ // We are able to have a horizontal scrollbar if the overflow style is // scroll, or if its auto and there's no word wrap. - if (Style()->OverflowInlineDirection() == EOverflow::kScroll || - (Style()->OverflowInlineDirection() == EOverflow::kAuto && - inner_editor->GetLayoutObject()->Style()->OverflowWrap() == + if (StyleRef().OverflowInlineDirection() == EOverflow::kScroll || + (StyleRef().OverflowInlineDirection() == EOverflow::kAuto && + inner_editor->GetLayoutObject()->StyleRef().OverflowWrap() == EOverflowWrap::kNormal)) logical_height += ScrollbarThickness(); @@ -214,7 +214,7 @@ } float LayoutTextControl::GetAvgCharWidth(const AtomicString& family) const { - const Font& font = Style()->GetFont(); + const Font& font = StyleRef().GetFont(); const SimpleFontData* primary_font = font.PrimaryFont(); if (primary_font && HasValidAvgCharWidth(primary_font, family)) @@ -231,7 +231,7 @@ // This matches the unitsPerEm value for MS Shell Dlg and Courier New from the // "head" font table. float units_per_em = 2048.0f; - return roundf(Style()->GetFont().GetFontDescription().ComputedSize() * x / + return roundf(StyleRef().GetFont().GetFontDescription().ComputedSize() * x / units_per_em); } @@ -240,7 +240,7 @@ LayoutUnit& max_logical_width) const { // Use average character width. Matches IE. AtomicString family = - Style()->GetFont().GetFontDescription().Family().Family(); + StyleRef().GetFont().GetFontDescription().Family().Family(); max_logical_width = PreferredContentLogicalWidth( const_cast<LayoutTextControl*>(this)->GetAvgCharWidth(family)); if (InnerEditorElement()) { @@ -249,7 +249,7 @@ max_logical_width += inner_editor_layout_box->PaddingStart() + inner_editor_layout_box->PaddingEnd(); } - if (!Style()->LogicalWidth().IsPercentOrCalc()) + if (!StyleRef().LogicalWidth().IsPercentOrCalc()) min_logical_width = max_logical_width; }
diff --git a/third_party/blink/renderer/core/layout/layout_text_control_single_line.cc b/third_party/blink/renderer/core/layout/layout_text_control_single_line.cc index f01b6cd9..b119224d 100644 --- a/third_party/blink/renderer/core/layout/layout_text_control_single_line.cc +++ b/third_party/blink/renderer/core/layout/layout_text_control_single_line.cc
@@ -223,7 +223,7 @@ LayoutUnit result = LayoutUnit::FromFloatCeil(char_width * factor); float max_char_width = 0.f; - const Font& font = Style()->GetFont(); + const Font& font = StyleRef().GetFont(); AtomicString family = font.GetFontDescription().Family().Family(); // Match the default system font to the width of MS Shell Dlg, the default // font for textareas in Firefox, Safari Win and IE for some encodings (in
diff --git a/third_party/blink/renderer/core/layout/layout_tree_as_text.cc b/third_party/blink/renderer/core/layout/layout_tree_as_text.cc index 02b79e4..71941d1a 100644 --- a/third_party/blink/renderer/core/layout/layout_tree_as_text.cc +++ b/third_party/blink/renderer/core/layout/layout_tree_as_text.cc
@@ -156,8 +156,8 @@ if (behavior & kLayoutAsTextShowAddresses) ts << " " << static_cast<const void*>(&o); - if (o.Style() && o.Style()->ZIndex()) - ts << " zI: " << o.Style()->ZIndex(); + if (o.Style() && o.StyleRef().ZIndex()) + ts << " zI: " << o.StyleRef().ZIndex(); if (o.GetNode()) { String tag_name = GetTagName(o.GetNode()); @@ -201,10 +201,10 @@ text_stroke_color != color && text_stroke_color.Rgb()) ts << " [textStrokeColor=" << text_stroke_color << "]"; - if (o.Parent()->Style()->TextStrokeWidth() != - o.Style()->TextStrokeWidth() && - o.Style()->TextStrokeWidth() > 0) - ts << " [textStrokeWidth=" << o.Style()->TextStrokeWidth() << "]"; + if (o.Parent()->StyleRef().TextStrokeWidth() != + o.StyleRef().TextStrokeWidth() && + o.StyleRef().TextStrokeWidth() > 0) + ts << " [textStrokeWidth=" << o.StyleRef().TextStrokeWidth() << "]"; } if (!o.IsBoxModelObject()) @@ -215,44 +215,44 @@ box.BorderLeft()) { ts << " [border:"; - BorderValue prev_border = o.Style()->BorderTop(); + BorderValue prev_border = o.StyleRef().BorderTop(); if (!box.BorderTop()) { ts << " none"; } else { ts << " (" << box.BorderTop() << "px "; - PrintBorderStyle(ts, o.Style()->BorderTopStyle()); + PrintBorderStyle(ts, o.StyleRef().BorderTopStyle()); ts << o.ResolveColor(GetCSSPropertyBorderTopColor()) << ")"; } - if (!o.Style()->BorderRightEquals(prev_border)) { - prev_border = o.Style()->BorderRight(); + if (!o.StyleRef().BorderRightEquals(prev_border)) { + prev_border = o.StyleRef().BorderRight(); if (!box.BorderRight()) { ts << " none"; } else { ts << " (" << box.BorderRight() << "px "; - PrintBorderStyle(ts, o.Style()->BorderRightStyle()); + PrintBorderStyle(ts, o.StyleRef().BorderRightStyle()); ts << o.ResolveColor(GetCSSPropertyBorderRightColor()) << ")"; } } - if (!o.Style()->BorderBottomEquals(prev_border)) { - prev_border = box.Style()->BorderBottom(); + if (!o.StyleRef().BorderBottomEquals(prev_border)) { + prev_border = box.StyleRef().BorderBottom(); if (!box.BorderBottom()) { ts << " none"; } else { ts << " (" << box.BorderBottom() << "px "; - PrintBorderStyle(ts, o.Style()->BorderBottomStyle()); + PrintBorderStyle(ts, o.StyleRef().BorderBottomStyle()); ts << o.ResolveColor(GetCSSPropertyBorderBottomColor()) << ")"; } } - if (!o.Style()->BorderLeftEquals(prev_border)) { - prev_border = o.Style()->BorderLeft(); + if (!o.StyleRef().BorderLeftEquals(prev_border)) { + prev_border = o.StyleRef().BorderLeft(); if (!box.BorderLeft()) { ts << " none"; } else { ts << " (" << box.BorderLeft() << "px "; - PrintBorderStyle(ts, o.Style()->BorderLeftStyle()); + PrintBorderStyle(ts, o.StyleRef().BorderLeftStyle()); ts << o.ResolveColor(GetCSSPropertyBorderLeftColor()) << ")"; } } @@ -443,9 +443,10 @@ ts << ": " << QuoteAndEscapeNonPrintables( String(o.GetText()).Substring(run.Start(), run.Len())); - if (run.HasHyphen()) + if (run.HasHyphen()) { ts << " + hyphen string " - << QuoteAndEscapeNonPrintables(o.Style()->HyphenString()); + << QuoteAndEscapeNonPrintables(o.StyleRef().HyphenString()); + } ts << "\n"; } @@ -609,7 +610,7 @@ WriteIndent(ts, indent); - if (layer.GetLayoutObject().Style()->Visibility() == EVisibility::kHidden) + if (layer.GetLayoutObject().StyleRef().Visibility() == EVisibility::kHidden) ts << "hidden "; ts << "layer "; @@ -653,11 +654,11 @@ else if (paint_phase == kLayerPaintPhaseForeground) ts << " layerType: foreground only"; - if (layer.GetLayoutObject().Style()->HasBlendMode()) { + if (layer.GetLayoutObject().StyleRef().HasBlendMode()) { ts << " blendMode: " << CompositeOperatorName( kCompositeSourceOver, - layer.GetLayoutObject().Style()->GetBlendMode()); + layer.GetLayoutObject().StyleRef().GetBlendMode()); } if (behavior & kLayoutAsTextShowCompositedLayers) {
diff --git a/third_party/blink/renderer/core/layout/layout_video.cc b/third_party/blink/renderer/core/layout/layout_video.cc index 964735e..9b5702b 100644 --- a/third_party/blink/renderer/core/layout/layout_video.cc +++ b/third_party/blink/renderer/core/layout/layout_video.cc
@@ -52,7 +52,7 @@ void LayoutVideo::UpdateIntrinsicSize() { LayoutSize size = CalculateIntrinsicSize(); - size.Scale(Style()->EffectiveZoom()); + size.Scale(StyleRef().EffectiveZoom()); // Never set the element size to zero when in a media document. if (size.IsEmpty() && GetNode()->ownerDocument() &&
diff --git a/third_party/blink/renderer/core/layout/layout_view.cc b/third_party/blink/renderer/core/layout/layout_view.cc index 3241d32..da81439 100644 --- a/third_party/blink/renderer/core/layout/layout_view.cc +++ b/third_party/blink/renderer/core/layout/layout_view.cc
@@ -251,11 +251,11 @@ // should fully invalidate on viewport resize if the background image is not // composited and needs full paint invalidation on background positioning area // resize. - if (Style()->HasFixedBackgroundImage()) { + if (StyleRef().HasFixedBackgroundImage()) { if ((width_changed && MustInvalidateFillLayersPaintOnWidthChange( - Style()->BackgroundLayers())) || + StyleRef().BackgroundLayers())) || (height_changed && MustInvalidateFillLayersPaintOnHeightChange( - Style()->BackgroundLayers()))) + StyleRef().BackgroundLayers()))) SetShouldDoFullPaintInvalidation(PaintInvalidationReason::kBackground); } } @@ -269,8 +269,8 @@ // sufficient. if (Element* body = GetDocument().body()) { if (LayoutObject* body_layout_object = body->GetLayoutObject()) { - return body_layout_object->Style() - ->ShouldPlaceBlockDirectionScrollbarOnLogicalLeft(); + return body_layout_object->StyleRef() + .ShouldPlaceBlockDirectionScrollbarOnLogicalLeft(); } } return false; @@ -294,9 +294,9 @@ continue; if ((child->IsBox() && ToLayoutBox(child)->HasRelativeLogicalHeight()) || - child->Style()->LogicalHeight().IsPercentOrCalc() || - child->Style()->LogicalMinHeight().IsPercentOrCalc() || - child->Style()->LogicalMaxHeight().IsPercentOrCalc()) + child->StyleRef().LogicalHeight().IsPercentOrCalc() || + child->StyleRef().LogicalMinHeight().IsPercentOrCalc() || + child->StyleRef().LogicalMaxHeight().IsPercentOrCalc()) layout_scope.SetChildNeedsLayout(child); } @@ -761,14 +761,14 @@ int LayoutView::ViewLogicalWidth( IncludeScrollbarsInRect scrollbar_inclusion) const { - return Style()->IsHorizontalWritingMode() ? ViewWidth(scrollbar_inclusion) - : ViewHeight(scrollbar_inclusion); + return StyleRef().IsHorizontalWritingMode() ? ViewWidth(scrollbar_inclusion) + : ViewHeight(scrollbar_inclusion); } int LayoutView::ViewLogicalHeight( IncludeScrollbarsInRect scrollbar_inclusion) const { - return Style()->IsHorizontalWritingMode() ? ViewHeight(scrollbar_inclusion) - : ViewWidth(scrollbar_inclusion); + return StyleRef().IsHorizontalWritingMode() ? ViewHeight(scrollbar_inclusion) + : ViewWidth(scrollbar_inclusion); } LayoutUnit LayoutView::ViewLogicalHeightForPercentages() const {
diff --git a/third_party/blink/renderer/core/layout/layout_vtt_cue.cc b/third_party/blink/renderer/core/layout/layout_vtt_cue.cc index 5f78b14e..04c9b6c7 100644 --- a/third_party/blink/renderer/core/layout/layout_vtt_cue.cc +++ b/third_party/blink/renderer/core/layout/layout_vtt_cue.cc
@@ -84,7 +84,7 @@ // 7. Round line to an integer by adding 0.5 and then flooring it. LayoutUnit line_position(floorf(cue_box_.SnapToLinesPosition() + 0.5f)); - WritingMode writing_mode = cue_box_.Style()->GetWritingMode(); + WritingMode writing_mode = cue_box_.StyleRef().GetWritingMode(); // 8. Vertical Growing Left: Add one to line then negate it. if (IsFlippedBlocksWritingMode(writing_mode)) line_position = -(line_position + 1); @@ -195,7 +195,7 @@ // into which cues will not be placed. // 2. Horizontal: Let full dimension be the height of video's rendering area // Vertical: Let full dimension be the width of video's rendering area. - WritingMode writing_mode = cue_box_.Style()->GetWritingMode(); + WritingMode writing_mode = cue_box_.StyleRef().GetWritingMode(); LayoutBlock* parent_block = cue_box_.ContainingBlock(); LayoutUnit full_dimension = blink::IsHorizontalWritingMode(writing_mode) ? parent_block->Size().Height()
diff --git a/third_party/blink/renderer/core/layout/line/abstract_inline_text_box.cc b/third_party/blink/renderer/core/layout/line/abstract_inline_text_box.cc index 26865edd..2d8baac 100644 --- a/third_party/blink/renderer/core/layout/line/abstract_inline_text_box.cc +++ b/third_party/blink/renderer/core/layout/line/abstract_inline_text_box.cc
@@ -138,7 +138,7 @@ if (!inline_text_box_ || !GetLineLayoutItem()) return kLeftToRight; - if (GetLineLayoutItem().Style()->IsHorizontalWritingMode()) { + if (GetLineLayoutItem().StyleRef().IsHorizontalWritingMode()) { return (inline_text_box_->Direction() == TextDirection::kRtl ? kRightToLeft : kLeftToRight);
diff --git a/third_party/blink/renderer/core/layout/line/breaking_context_inline_headers.h b/third_party/blink/renderer/core/layout/line/breaking_context_inline_headers.h index 9a3994b..346446333 100644 --- a/third_party/blink/renderer/core/layout/line/breaking_context_inline_headers.h +++ b/third_party/blink/renderer/core/layout/line/breaking_context_inline_headers.h
@@ -254,8 +254,8 @@ if (flow.GetDocument().InNoQuirksMode() && (flow.Style(line_info.IsFirstLine())->LineHeight() != parent.Style(line_info.IsFirstLine())->LineHeight() || - flow.Style()->VerticalAlign() != parent.Style()->VerticalAlign() || - !parent.Style()->HasIdenticalAscentDescentAndLineGap(flow.StyleRef()))) + flow.StyleRef().VerticalAlign() != parent.StyleRef().VerticalAlign() || + !parent.StyleRef().HasIdenticalAscentDescentAndLineGap(flow.StyleRef()))) return true; return false; } @@ -356,12 +356,13 @@ current_.GetLineLayoutItem().Parent())) include_end_width_ = true; - curr_ws_ = current_.GetLineLayoutItem().IsLayoutInline() - ? current_style_->WhiteSpace() - : current_.GetLineLayoutItem().Parent().Style()->WhiteSpace(); + curr_ws_ = + current_.GetLineLayoutItem().IsLayoutInline() + ? current_style_->WhiteSpace() + : current_.GetLineLayoutItem().Parent().StyleRef().WhiteSpace(); last_ws_ = last_object_.IsLayoutInline() - ? last_object_.Style()->WhiteSpace() - : last_object_.Parent().Style()->WhiteSpace(); + ? last_object_.StyleRef().WhiteSpace() + : last_object_.Parent().StyleRef().WhiteSpace(); bool is_svg_text = current_.GetLineLayoutItem().IsSVGInlineText(); auto_wrap_ = !is_svg_text && ComputedStyle::AutoWrap(curr_ws_); @@ -481,7 +482,7 @@ // If our original display wasn't an inline type, then we can // go ahead and determine our static inline position now. LineLayoutBox box(current_.GetLineLayoutItem()); - bool is_inline_type = box.Style()->IsOriginalDisplayInlineType(); + bool is_inline_type = box.StyleRef().IsOriginalDisplayInlineType(); if (!is_inline_type) { block_.SetStaticInlinePositionForChild(box, block_.StartOffsetForContent()); } else { @@ -573,7 +574,7 @@ LineLayoutText(next).TextLength() > 0) { LineLayoutText next_text(next); UChar next_char = next_text.CharacterAt(0); - if (next_text.Style()->IsCollapsibleWhiteSpace(next_char)) { + if (next_text.StyleRef().IsCollapsibleWhiteSpace(next_char)) { line_midpoint_state.StartIgnoringSpaces(InlineIterator(nullptr, o, 0)); return true; } @@ -718,12 +719,14 @@ bool collapse_white_space, HashSet<const SimpleFontData*>* fallback_fonts = nullptr, FloatRect* glyph_bounds = nullptr) { - if ((!from && len == text.TextLength()) || text.Style()->HasTextCombine()) + if ((!from && len == text.TextLength()) || text.StyleRef().HasTextCombine()) { return text.Width(from, len, font, LayoutUnit(x_pos), - text.Style()->Direction(), fallback_fonts, glyph_bounds); + text.StyleRef().Direction(), fallback_fonts, + glyph_bounds); + } TextRun run = ConstructTextRun(font, text, from, len, text.StyleRef()); - run.SetTabSize(!collapse_white_space, text.Style()->GetTabSize()); + run.SetTabSize(!collapse_white_space, text.StyleRef().GetTabSize()); run.SetXPos(x_pos); return font.Width(run, fallback_fonts, glyph_bounds); } @@ -1506,7 +1509,7 @@ check_for_break = true; } else if (next_object_ && current_.GetLineLayoutItem().IsText() && next_object_.IsText() && !next_object_.IsBR() && - (auto_wrap_ || next_object_.Style()->AutoWrap())) { + (auto_wrap_ || next_object_.StyleRef().AutoWrap())) { if (auto_wrap_ && current_character_is_space_) { check_for_break = true; } else {
diff --git a/third_party/blink/renderer/core/layout/line/inline_flow_box.cc b/third_party/blink/renderer/core/layout/line/inline_flow_box.cc index 07e0c550..ddb0ad2 100644 --- a/third_party/blink/renderer/core/layout/line/inline_flow_box.cc +++ b/third_party/blink/renderer/core/layout/line/inline_flow_box.cc
@@ -355,14 +355,14 @@ // The root inline box never has borders/margins/padding. if (Parent()) { - bool ltr = GetLineLayoutItem().Style()->IsLeftToRightDirection(); + bool ltr = GetLineLayoutItem().StyleRef().IsLeftToRightDirection(); // Check to see if all initial lines are unconstructed. If so, then // we know the inline began on this line (unless we are a continuation). LineBoxList* line_box_list = LineBoxes(); if (!line_box_list->First()->IsConstructed() && !GetLineLayoutItem().IsInlineElementContinuation()) { - if (GetLineLayoutItem().Style()->BoxDecorationBreak() == + if (GetLineLayoutItem().StyleRef().BoxDecorationBreak() == EBoxDecorationBreak::kClone) include_left_edge = include_right_edge = true; else if (ltr && line_box_list->First() == this) @@ -391,7 +391,7 @@ // next line. // (4) The decoration break is set to clone therefore there will be // borders on every sides. - if (GetLineLayoutItem().Style()->BoxDecorationBreak() == + if (GetLineLayoutItem().StyleRef().BoxDecorationBreak() == EBoxDecorationBreak::kClone) { include_left_edge = include_right_edge = true; } else if (ltr) { @@ -485,8 +485,8 @@ if (curr->GetLineLayoutItem().IsOutOfFlowPositioned()) { if (curr->GetLineLayoutItem() .Parent() - .Style() - ->IsLeftToRightDirection()) { + .StyleRef() + .IsLeftToRightDirection()) { curr->SetLogicalLeft(logical_left); } else { // Our offset that we cache needs to be from the edge of the right @@ -825,8 +825,8 @@ // being part of the overall lineTop/lineBottom. // Really this is a workaround hack for the fact that ruby should have // been done as line layout and not done using inline-block. - if (GetLineLayoutItem().Style()->IsFlippedLinesWritingMode() == - (curr->GetLineLayoutItem().Style()->GetRubyPosition() == + if (GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode() == + (curr->GetLineLayoutItem().StyleRef().GetRubyPosition() == RubyPosition::kAfter)) has_annotations_before = true; else @@ -845,7 +845,7 @@ (ruby_base.FirstRootBox() ? ruby_base.FirstRootBox()->LineTop() : LayoutUnit()); new_logical_top += - !GetLineLayoutItem().Style()->IsFlippedLinesWritingMode() + !GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode() ? top_ruby_base_leading : bottom_ruby_base_leading; box_height -= (top_ruby_base_leading + bottom_ruby_base_leading); @@ -912,7 +912,7 @@ std::max(line_bottom, line_bottom_including_margins); } - if (GetLineLayoutItem().Style()->IsFlippedLinesWritingMode()) + if (GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode()) FlipLinesInBlockDirection(line_top_including_margins, line_bottom_including_margins); } @@ -1138,7 +1138,7 @@ float measured_width = layout_text.Width( text->Start(), text->Len(), LayoutUnit(), text->Direction(), false, &fallback_fonts, &glyph_bounds); - const Font& font = layout_text.Style()->GetFont(); + const Font& font = layout_text.StyleRef().GetFont(); glyph_overflow.SetFromBounds(glyph_bounds, font, measured_width); if (!fallback_fonts.IsEmpty()) { GlyphOverflowAndFallbackFontsMap::ValueType* it = @@ -1353,11 +1353,12 @@ overflow_rect.Location())) return false; - if (GetLineLayoutItem().Style()->HasBorderRadius()) { + if (GetLineLayoutItem().StyleRef().HasBorderRadius()) { LayoutRect border_rect = LogicalFrameRect(); border_rect.MoveBy(accumulated_offset); - FloatRoundedRect border = GetLineLayoutItem().Style()->GetRoundedBorderFor( - border_rect, IncludeLogicalLeftEdge(), IncludeLogicalRightEdge()); + FloatRoundedRect border = + GetLineLayoutItem().StyleRef().GetRoundedBorderFor( + border_rect, IncludeLogicalLeftEdge(), IncludeLogicalRightEdge()); if (!location_in_container.Intersects(border)) return false; } @@ -1402,7 +1403,8 @@ // would be clipped out, so it has to be drawn separately). StyleImage* image = last_background_layer.GetImage(); bool has_fill_image = image && image->CanRender(); - return (!has_fill_image && !GetLineLayoutItem().Style()->HasBorderRadius()) || + return (!has_fill_image && + !GetLineLayoutItem().StyleRef().HasBorderRadius()) || (!PrevForSameLayoutObject() && !NextForSameLayoutObject()) || !Parent(); } @@ -1503,14 +1505,14 @@ if (curr->GetLineLayoutItem().IsAtomicInlineLevel() && curr->GetLineLayoutItem().IsRubyRun() && - curr->GetLineLayoutItem().Style()->GetRubyPosition() == + curr->GetLineLayoutItem().StyleRef().GetRubyPosition() == RubyPosition::kBefore) { LineLayoutRubyRun ruby_run = LineLayoutRubyRun(curr->GetLineLayoutItem()); LineLayoutRubyText ruby_text = ruby_run.RubyText(); if (!ruby_text) continue; - if (!ruby_run.Style()->IsFlippedLinesWritingMode()) { + if (!ruby_run.StyleRef().IsFlippedLinesWritingMode()) { LayoutUnit top_of_first_ruby_text_line = ruby_text.LogicalTop() + (ruby_text.FirstRootBox() ? ruby_text.FirstRootBox()->LineTop() @@ -1574,14 +1576,14 @@ if (curr->GetLineLayoutItem().IsAtomicInlineLevel() && curr->GetLineLayoutItem().IsRubyRun() && - curr->GetLineLayoutItem().Style()->GetRubyPosition() == + curr->GetLineLayoutItem().StyleRef().GetRubyPosition() == RubyPosition::kAfter) { LineLayoutRubyRun ruby_run = LineLayoutRubyRun(curr->GetLineLayoutItem()); LineLayoutRubyText ruby_text = ruby_run.RubyText(); if (!ruby_text) continue; - if (ruby_run.Style()->IsFlippedLinesWritingMode()) { + if (ruby_run.StyleRef().IsFlippedLinesWritingMode()) { LayoutUnit top_of_first_ruby_text_line = ruby_text.LogicalTop() + (ruby_text.FirstRootBox() ? ruby_text.FirstRootBox()->LineTop() @@ -1645,7 +1647,7 @@ leaf_boxes_in_logical_order.push_back(leaf); } - if (GetLineLayoutItem().Style()->RtlOrdering() == EOrder::kVisual) + if (GetLineLayoutItem().StyleRef().RtlOrdering() == EOrder::kVisual) return; // Reverse of reordering of the line (L2 according to Bidi spec):
diff --git a/third_party/blink/renderer/core/layout/line/inline_flow_box.h b/third_party/blink/renderer/core/layout/line/inline_flow_box.h index f49c483..d04be47 100644 --- a/third_party/blink/renderer/core/layout/line/inline_flow_box.h +++ b/third_party/blink/renderer/core/layout/line/inline_flow_box.h
@@ -73,7 +73,7 @@ // bullet list items. Even when the list bullet is an image, the line is // still considered to be immune from the quirk. has_text_children_ = - line_layout_item.Style()->Display() == EDisplay::kListItem; + line_layout_item.StyleRef().Display() == EDisplay::kListItem; has_text_descendants_ = has_text_children_; }
diff --git a/third_party/blink/renderer/core/layout/line/inline_iterator.h b/third_party/blink/renderer/core/layout/line/inline_iterator.h index f475497..52ecfc00 100644 --- a/third_party/blink/renderer/core/layout/line/inline_iterator.h +++ b/third_party/blink/renderer/core/layout/line/inline_iterator.h
@@ -197,7 +197,7 @@ if (!observer || !object || !object.IsLayoutInline()) return; - UnicodeBidi unicode_bidi = object.Style()->GetUnicodeBidi(); + UnicodeBidi unicode_bidi = object.StyleRef().GetUnicodeBidi(); if (unicode_bidi == UnicodeBidi::kNormal) return; // Nothing to do for unicode-bidi: normal if (TreatAsIsolated(object.StyleRef())) { @@ -517,7 +517,7 @@ return WTF::Unicode::Direction(c); if (line_layout_item_ && line_layout_item_.IsListMarker()) - return line_layout_item_.Style()->IsLeftToRightDirection() + return line_layout_item_.StyleRef().IsLeftToRightDirection() ? WTF::Unicode::kLeftToRight : WTF::Unicode::kRightToLeft; @@ -549,7 +549,7 @@ character == kSoftHyphenCharacter) return true; if (character == '\n') - return !layout_text.Style()->PreserveNewline(); + return !layout_text.StyleRef().PreserveNewline(); return false; }
diff --git a/third_party/blink/renderer/core/layout/line/inline_text_box.cc b/third_party/blink/renderer/core/layout/line/inline_text_box.cc index 0583fae..b36e91b 100644 --- a/third_party/blink/renderer/core/layout/line/inline_text_box.cc +++ b/third_party/blink/renderer/core/layout/line/inline_text_box.cc
@@ -171,7 +171,7 @@ // FIXME: Remove -webkit-line-break: LineBreakAfterWhiteSpace. int end_of_line_adjustment_for_css_line_break = - GetLineLayoutItem().Style()->GetLineBreak() == + GetLineLayoutItem().StyleRef().GetLineBreak() == LineBreak::kAfterWhiteSpace ? -1 : 0; @@ -453,7 +453,7 @@ bool InlineTextBox::IsLineBreak() const { return GetLineLayoutItem().IsBR() || - (GetLineLayoutItem().Style()->PreserveNewline() && Len() == 1 && + (GetLineLayoutItem().StyleRef().PreserveNewline() && Len() == 1 && GetLineLayoutItem().GetText().length() > Start() && (*GetLineLayoutItem().GetText().Impl())[Start()] == '\n'); }
diff --git a/third_party/blink/renderer/core/layout/line/line_box_list.cc b/third_party/blink/renderer/core/layout/line/line_box_list.cc index 68c362d..2b943ba 100644 --- a/third_party/blink/renderer/core/layout/line/line_box_list.cc +++ b/third_party/blink/renderer/core/layout/line/line_box_list.cc
@@ -156,7 +156,7 @@ LayoutUnit physical_extent = AbsoluteValue(physical_end - physical_start); physical_start = std::min(physical_start, physical_end); - if (layout_object.Style()->IsHorizontalWritingMode()) { + if (layout_object.StyleRef().IsHorizontalWritingMode()) { physical_start += offset.Y(); return cull_rect.IntersectsVerticalRange(physical_start, physical_start + physical_extent);
diff --git a/third_party/blink/renderer/core/layout/line/line_breaker.cc b/third_party/blink/renderer/core/layout/line/line_breaker.cc index c0362d8..4d6464b 100644 --- a/third_party/blink/renderer/core/layout/line/line_breaker.cc +++ b/third_party/blink/renderer/core/layout/line/line_breaker.cc
@@ -38,7 +38,7 @@ if (line_layout_item.IsOutOfFlowPositioned()) { SetStaticPositions(block_, LineLayoutBox(line_layout_item), width.IndentText()); - if (line_layout_item.Style()->IsOriginalDisplayInlineType()) { + if (line_layout_item.StyleRef().IsOriginalDisplayInlineType()) { resolver.Runs().AddRun( CreateRun(0, 1, LineLayoutItem(line_layout_item), resolver)); line_info.IncrementRunsFromLeadingWhitespace();
diff --git a/third_party/blink/renderer/core/layout/line/line_width.cc b/third_party/blink/renderer/core/layout/line/line_width.cc index b1047e8..0be9101 100644 --- a/third_party/blink/renderer/core/layout/line/line_width.cc +++ b/third_party/blink/renderer/core/layout/line/line_width.cc
@@ -87,7 +87,8 @@ new_left = left_; } } - if (IndentText() == kIndentText && block_.Style()->IsLeftToRightDirection()) + if (IndentText() == kIndentText && + block_.StyleRef().IsLeftToRightDirection()) new_left += FloorToInt(block_.TextIndentOffset()); left_ = std::max(left_, new_left); } else { @@ -102,7 +103,7 @@ } } if (IndentText() == kIndentText && - !block_.Style()->IsLeftToRightDirection()) + !block_.StyleRef().IsLeftToRightDirection()) new_right -= FloorToInt(block_.TextIndentOffset()); right_ = std::min(right_, new_right); }
diff --git a/third_party/blink/renderer/core/layout/line/root_inline_box.cc b/third_party/blink/renderer/core/layout/line/root_inline_box.cc index 603f56b..0167a842 100644 --- a/third_party/blink/renderer/core/layout/line/root_inline_box.cc +++ b/third_party/blink/renderer/core/layout/line/root_inline_box.cc
@@ -307,7 +307,7 @@ LayoutUnit RootInlineBox::BeforeAnnotationsAdjustment() const { LayoutUnit result; - if (!GetLineLayoutItem().Style()->IsFlippedLinesWritingMode()) { + if (!GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode()) { // Annotations under the previous line may push us down. if (PrevRootBox() && PrevRootBox()->HasAnnotationsAfter()) result = PrevRootBox()->ComputeUnderAnnotationAdjustment(LineTop()); @@ -372,11 +372,11 @@ LayoutUnit RootInlineBox::SelectionTop() const { LayoutUnit selection_top = line_top_; if (has_annotations_before_) - selection_top -= !GetLineLayoutItem().Style()->IsFlippedLinesWritingMode() + selection_top -= !GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode() ? ComputeOverAnnotationAdjustment(line_top_) : ComputeUnderAnnotationAdjustment(line_top_); - if (GetLineLayoutItem().Style()->IsFlippedLinesWritingMode() || + if (GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode() || !PrevRootBox()) return selection_top; @@ -390,11 +390,11 @@ if (has_annotations_after_) selection_bottom += - !GetLineLayoutItem().Style()->IsFlippedLinesWritingMode() + !GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode() ? ComputeUnderAnnotationAdjustment(line_bottom_) : ComputeOverAnnotationAdjustment(line_bottom_); - if (!GetLineLayoutItem().Style()->IsFlippedLinesWritingMode() || + if (!GetLineLayoutItem().StyleRef().IsFlippedLinesWritingMode() || !NextRootBox()) return selection_bottom; @@ -402,7 +402,7 @@ } LayoutUnit RootInlineBox::BlockDirectionPointInLine() const { - return !Block().Style()->IsFlippedBlocksWritingMode() + return !Block().StyleRef().IsFlippedBlocksWritingMode() ? std::max(LineTop(), SelectionTop()) : std::min(LineBottom(), SelectionBottom()); } @@ -670,15 +670,15 @@ } LayoutUnit vertical_position; - EVerticalAlign vertical_align = box_model.Style()->VerticalAlign(); + EVerticalAlign vertical_align = box_model.StyleRef().VerticalAlign(); if (vertical_align == EVerticalAlign::kTop || vertical_align == EVerticalAlign::kBottom) return LayoutUnit(); LineLayoutItem parent = box_model.Parent(); if (parent.IsLayoutInline() && - parent.Style()->VerticalAlign() != EVerticalAlign::kTop && - parent.Style()->VerticalAlign() != EVerticalAlign::kBottom) + parent.StyleRef().VerticalAlign() != EVerticalAlign::kTop && + parent.StyleRef().VerticalAlign() != EVerticalAlign::kBottom) vertical_position = box->Parent()->LogicalTop(); if (vertical_align != EVerticalAlign::kBaseline) { @@ -726,12 +726,12 @@ LayoutUnit line_height; // Per http://www.w3.org/TR/CSS21/visudet.html#propdef-vertical-align: // 'Percentages: refer to the 'line-height' of the element itself'. - if (box_model.Style()->GetVerticalAlignLength().IsPercentOrCalc()) - line_height = LayoutUnit(box_model.Style()->ComputedLineHeight()); + if (box_model.StyleRef().GetVerticalAlignLength().IsPercentOrCalc()) + line_height = LayoutUnit(box_model.StyleRef().ComputedLineHeight()); else line_height = box_model.LineHeight(first_line, line_direction); vertical_position -= ValueForLength( - box_model.Style()->GetVerticalAlignLength(), line_height); + box_model.StyleRef().GetVerticalAlignLength(), line_height); } }
diff --git a/third_party/blink/renderer/core/layout/multi_column_fragmentainer_group.cc b/third_party/blink/renderer/core/layout/multi_column_fragmentainer_group.cc index 869820d..29fe8be9 100644 --- a/third_party/blink/renderer/core/layout/multi_column_fragmentainer_group.cc +++ b/third_party/blink/renderer/core/layout/multi_column_fragmentainer_group.cc
@@ -243,7 +243,7 @@ local_point.MoveBy(-column_rect.Location()); if (!column_set_.IsHorizontalWritingMode()) { if (snap == kSnapToColumn) { - LayoutUnit column_start = column_set_.Style()->IsLeftToRightDirection() + LayoutUnit column_start = column_set_.StyleRef().IsLeftToRightDirection() ? LayoutUnit() : column_rect.Height(); if (local_point.X() < 0) @@ -255,7 +255,7 @@ local_point.Y()); } if (snap == kSnapToColumn) { - LayoutUnit column_start = column_set_.Style()->IsLeftToRightDirection() + LayoutUnit column_start = column_set_.StyleRef().IsLeftToRightDirection() ? LayoutUnit() : column_rect.Width(); if (local_point.Y() < 0) @@ -425,7 +425,7 @@ LayoutUnit column_gap = column_set_.ColumnGap(); if (column_set_.MultiColumnFlowThread()->ProgressionIsInline()) { - if (column_set_.Style()->IsLeftToRightDirection()) + if (column_set_.StyleRef().IsLeftToRightDirection()) column_logical_left += column_index * (column_logical_width + column_gap); else column_logical_left += column_set_.ContentLogicalWidth() - @@ -476,7 +476,7 @@ // contents from a previous column in the overflow area of a following column. bool is_first_column_in_row = !column_index; bool is_last_column_in_row = column_index == ActualColumnCount() - 1; - bool is_ltr = column_set_.Style()->IsLeftToRightDirection(); + bool is_ltr = column_set_.StyleRef().IsLeftToRightDirection(); bool is_leftmost_column = is_ltr ? is_first_column_in_row : is_last_column_in_row; bool is_rightmost_column = @@ -572,7 +572,7 @@ is_horizontal_writing_mode == is_column_progression_inline ? visual_point.X() : visual_point.Y(); - if (!column_set_.Style()->IsLeftToRightDirection() && + if (!column_set_.StyleRef().IsLeftToRightDirection() && is_column_progression_inline) offset_in_column_progression_direction = column_set_.LogicalWidth() - offset_in_column_progression_direction; @@ -618,7 +618,7 @@ bool is_column_progression_inline = column_set_.MultiColumnFlowThread()->ProgressionIsInline(); bool is_flipped_column_progression = - !column_set_.Style()->IsLeftToRightDirection() && + !column_set_.StyleRef().IsLeftToRightDirection() && is_column_progression_inline; if (column_set_.IsHorizontalWritingMode() == is_column_progression_inline) { if (is_flipped_column_progression) {
diff --git a/third_party/blink/renderer/core/layout/order_iterator.cc b/third_party/blink/renderer/core/layout/order_iterator.cc index c9671634..f239179 100644 --- a/third_party/blink/renderer/core/layout/order_iterator.cc +++ b/third_party/blink/renderer/core/layout/order_iterator.cc
@@ -63,7 +63,7 @@ current_child_ = current_child_->NextSiblingBox(); } } while (!current_child_ || - current_child_->Style()->Order() != *order_values_iterator_); + current_child_->StyleRef().Order() != *order_values_iterator_); return current_child_; } @@ -79,7 +79,7 @@ } void OrderIteratorPopulator::CollectChild(const LayoutBox* child) { - iterator_.order_values_.insert(child->Style()->Order()); + iterator_.order_values_.insert(child->StyleRef().Order()); } } // namespace blink
diff --git a/third_party/blink/renderer/core/layout/scroll_anchor.cc b/third_party/blink/renderer/core/layout/scroll_anchor.cc index af6c5f7..2f3ab2d 100644 --- a/third_party/blink/renderer/core/layout/scroll_anchor.cc +++ b/third_party/blink/renderer/core/layout/scroll_anchor.cc
@@ -285,7 +285,7 @@ if (!CandidateMayMoveWithScroller(candidate, scroller_)) return ExamineResult(kSkip); - if (candidate->Style()->OverflowAnchor() == EOverflowAnchor::kNone) + if (candidate->StyleRef().OverflowAnchor() == EOverflowAnchor::kNone) return ExamineResult(kSkip); LayoutRect candidate_rect = RelativeBounds(candidate, scroller_);
diff --git a/third_party/blink/renderer/core/layout/shapes/shape_outside_info.cc b/third_party/blink/renderer/core/layout/shapes/shape_outside_info.cc index 7c9f0ec..f87c3ff3 100644 --- a/third_party/blink/renderer/core/layout/shapes/shape_outside_info.cc +++ b/third_party/blink/renderer/core/layout/shapes/shape_outside_info.cc
@@ -52,7 +52,7 @@ LayoutSize new_reference_box_logical_size) { const Document& document = layout_box_.GetDocument(); bool is_horizontal_writing_mode = - layout_box_.ContainingBlock()->Style()->IsHorizontalWritingMode(); + layout_box_.ContainingBlock()->StyleRef().IsHorizontalWritingMode(); LayoutSize margin_box_for_use_counter = new_reference_box_logical_size; if (is_horizontal_writing_mode) { @@ -63,7 +63,7 @@ layout_box_.MarginWidth()); } - switch (ReferenceBox(*layout_box_.Style()->ShapeOutside())) { + switch (ReferenceBox(*layout_box_.StyleRef().ShapeOutside())) { case CSSBoxType::kMargin: UseCounter::Count(document, WebFeature::kShapeOutsideMarginBox); if (is_horizontal_writing_mode) @@ -176,7 +176,7 @@ float margin) const { DCHECK(!style_image->IsPendingImage()); const LayoutSize& image_size = RoundedLayoutSize(style_image->ImageSize( - layout_box_.GetDocument(), layout_box_.Style()->EffectiveZoom(), + layout_box_.GetDocument(), layout_box_.StyleRef().EffectiveZoom(), reference_box_logical_size_)); const LayoutRect& margin_rect = @@ -216,7 +216,7 @@ : std::max(LayoutUnit(), containing_block.ContentWidth()); float margin = - FloatValueForLength(layout_box_.Style()->ShapeMargin(), + FloatValueForLength(layout_box_.StyleRef().ShapeMargin(), percentage_resolution_inline_size.ToFloat()); float shape_image_threshold = style.ShapeImageThreshold(); @@ -285,7 +285,7 @@ } LayoutUnit ShapeOutsideInfo::LogicalTopOffset() const { - switch (ReferenceBox(*layout_box_.Style()->ShapeOutside())) { + switch (ReferenceBox(*layout_box_.StyleRef().ShapeOutside())) { case CSSBoxType::kMargin: return -layout_box_.MarginBefore(layout_box_.ContainingBlock()->Style()); case CSSBoxType::kBorder: @@ -293,11 +293,11 @@ case CSSBoxType::kPadding: return BorderBeforeInWritingMode( layout_box_, - layout_box_.ContainingBlock()->Style()->GetWritingMode()); + layout_box_.ContainingBlock()->StyleRef().GetWritingMode()); case CSSBoxType::kContent: return BorderAndPaddingBeforeInWritingMode( layout_box_, - layout_box_.ContainingBlock()->Style()->GetWritingMode()); + layout_box_.ContainingBlock()->StyleRef().GetWritingMode()); case CSSBoxType::kMissing: break; } @@ -337,7 +337,7 @@ } LayoutUnit ShapeOutsideInfo::LogicalLeftOffset() const { - switch (ReferenceBox(*layout_box_.Style()->ShapeOutside())) { + switch (ReferenceBox(*layout_box_.StyleRef().ShapeOutside())) { case CSSBoxType::kMargin: return -layout_box_.MarginStart(layout_box_.ContainingBlock()->Style()); case CSSBoxType::kBorder: @@ -357,7 +357,7 @@ } bool ShapeOutsideInfo::IsEnabledFor(const LayoutBox& box) { - ShapeValue* shape_value = box.Style()->ShapeOutside(); + ShapeValue* shape_value = box.StyleRef().ShapeOutside(); if (!box.IsFloating() || !shape_value) return false; @@ -401,7 +401,7 @@ std::min(line_height, ShapeLogicalBottom() - border_box_line_top)); if (segment.is_valid) { LayoutUnit logical_left_margin = - containing_block.Style()->IsLeftToRightDirection() + containing_block.StyleRef().IsLeftToRightDirection() ? containing_block.MarginStartForChild(layout_box_) : containing_block.MarginEndForChild(layout_box_); LayoutUnit raw_left_margin_box_delta = @@ -410,7 +410,7 @@ raw_left_margin_box_delta, LayoutUnit(), float_margin_box_width); LayoutUnit logical_right_margin = - containing_block.Style()->IsLeftToRightDirection() + containing_block.StyleRef().IsLeftToRightDirection() ? containing_block.MarginEndForChild(layout_box_) : containing_block.MarginStartForChild(layout_box_); LayoutUnit raw_right_margin_box_delta = @@ -443,13 +443,13 @@ ComputedShape().ShapeMarginLogicalBoundingBox(); physical_bounding_box.SetX(physical_bounding_box.X() + LogicalLeftOffset()); - if (layout_box_.Style()->IsFlippedBlocksWritingMode()) + if (layout_box_.StyleRef().IsFlippedBlocksWritingMode()) physical_bounding_box.SetY(layout_box_.LogicalHeight() - physical_bounding_box.MaxY()); else physical_bounding_box.SetY(physical_bounding_box.Y() + LogicalTopOffset()); - if (!layout_box_.Style()->IsHorizontalWritingMode()) + if (!layout_box_.StyleRef().IsHorizontalWritingMode()) physical_bounding_box = physical_bounding_box.TransposedRect(); else physical_bounding_box.SetY(physical_bounding_box.Y() + LogicalTopOffset()); @@ -460,15 +460,15 @@ FloatPoint ShapeOutsideInfo::ShapeToLayoutObjectPoint(FloatPoint point) const { FloatPoint result = FloatPoint(point.X() + LogicalLeftOffset(), point.Y() + LogicalTopOffset()); - if (layout_box_.Style()->IsFlippedBlocksWritingMode()) + if (layout_box_.StyleRef().IsFlippedBlocksWritingMode()) result.SetY(layout_box_.LogicalHeight() - result.Y()); - if (!layout_box_.Style()->IsHorizontalWritingMode()) + if (!layout_box_.StyleRef().IsHorizontalWritingMode()) result = result.TransposedPoint(); return result; } FloatSize ShapeOutsideInfo::ShapeToLayoutObjectSize(FloatSize size) const { - if (!layout_box_.Style()->IsHorizontalWritingMode()) + if (!layout_box_.StyleRef().IsHorizontalWritingMode()) return size.TransposedSize(); return size; }
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_block.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_block.cc index df0f405f..c34a72b 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_block.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_block.cc
@@ -67,11 +67,12 @@ if (IsBlendingAllowed()) { bool has_blend_mode_changed = - (old_style && old_style->HasBlendMode()) == !Style()->HasBlendMode(); - if (Parent() && has_blend_mode_changed) + (old_style && old_style->HasBlendMode()) == !StyleRef().HasBlendMode(); + if (Parent() && has_blend_mode_changed) { Parent()->DescendantIsolationRequirementsChanged( - Style()->HasBlendMode() ? kDescendantIsolationRequired - : kDescendantIsolationNeedsUpdate); + StyleRef().HasBlendMode() ? kDescendantIsolationRequired + : kDescendantIsolationNeedsUpdate); + } } LayoutBlock::StyleDidChange(diff, old_style);
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_container.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_container.cc index 3dda0b8..ee9bba3 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_container.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_container.cc
@@ -85,7 +85,7 @@ SVGResourcesCache::ClientWasAddedToTree(*child, child->StyleRef()); bool should_isolate_descendants = - (child->IsBlendingAllowed() && child->Style()->HasBlendMode()) || + (child->IsBlendingAllowed() && child->StyleRef().HasBlendMode()) || child->HasNonIsolatedBlendingDescendants(); if (should_isolate_descendants) DescendantIsolationRequirementsChanged(kDescendantIsolationRequired); @@ -96,7 +96,7 @@ LayoutSVGModelObject::RemoveChild(child); bool had_non_isolated_descendants = - (child->IsBlendingAllowed() && child->Style()->HasBlendMode()) || + (child->IsBlendingAllowed() && child->StyleRef().HasBlendMode()) || child->HasNonIsolatedBlendingDescendants(); if (had_non_isolated_descendants) DescendantIsolationRequirementsChanged(kDescendantIsolationNeedsUpdate); @@ -195,7 +195,7 @@ // pointer-events: bounding-box makes it possible for containers to be direct // targets. - if (Style()->PointerEvents() == EPointerEvents::kBoundingBox) { + if (StyleRef().PointerEvents() == EPointerEvents::kBoundingBox) { // Check for a valid bounding box because it will be invalid for empty // containers. if (IsObjectBoundingBoxValid() &&
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_ellipse.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_ellipse.cc index 10e0f346..2b0bad9 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_ellipse.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_ellipse.cc
@@ -75,7 +75,7 @@ fill_bounding_box_ = FloatRect(center_ - radii_, radii_.ScaledBy(2)); stroke_bounding_box_ = fill_bounding_box_; - if (Style()->SvgStyle().HasStroke()) + if (StyleRef().SvgStyle().HasStroke()) stroke_bounding_box_.Inflate(StrokeWidth() / 2); } @@ -131,7 +131,7 @@ } bool LayoutSVGEllipse::HasContinuousStroke() const { - const SVGComputedStyle& svg_style = Style()->SvgStyle(); + const SVGComputedStyle& svg_style = StyleRef().SvgStyle(); return svg_style.StrokeDashArray()->IsEmpty(); }
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_inline_text.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_inline_text.cc index 6af5862..d037cfa 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_inline_text.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_inline_text.cc
@@ -69,7 +69,7 @@ UpdateScaledFont(); bool new_preserves = - Style() ? Style()->WhiteSpace() == EWhiteSpace::kPre : false; + Style() ? StyleRef().WhiteSpace() == EWhiteSpace::kPre : false; bool old_preserves = old_style ? old_style->WhiteSpace() == EWhiteSpace::kPre : false; if (old_preserves != new_preserves) {
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_model_object.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_model_object.cc index 4704f6d..8ba3124 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_model_object.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_model_object.cc
@@ -134,11 +134,12 @@ if (IsBlendingAllowed()) { bool has_blend_mode_changed = - (old_style && old_style->HasBlendMode()) == !Style()->HasBlendMode(); - if (Parent() && has_blend_mode_changed) + (old_style && old_style->HasBlendMode()) == !StyleRef().HasBlendMode(); + if (Parent() && has_blend_mode_changed) { Parent()->DescendantIsolationRequirementsChanged( - Style()->HasBlendMode() ? kDescendantIsolationRequired - : kDescendantIsolationNeedsUpdate); + StyleRef().HasBlendMode() ? kDescendantIsolationRequired + : kDescendantIsolationNeedsUpdate); + } if (has_blend_mode_changed) SetNeedsPaintPropertyUpdate();
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_rect.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_rect.cc index 81ab1129..aa88e85 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_rect.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_rect.cc
@@ -117,7 +117,7 @@ // Returns true if the stroke is continuous and definitely uses miter joins. bool LayoutSVGRect::DefinitelyHasSimpleStroke() const { - const SVGComputedStyle& svg_style = Style()->SvgStyle(); + const SVGComputedStyle& svg_style = StyleRef().SvgStyle(); // The four angles of a rect are 90 degrees. Using the formula at: // http://www.w3.org/TR/SVG/painting.html#StrokeMiterlimitProperty
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_resource_masker.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_resource_masker.cc index 3aa0518c..bb916b86 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_resource_masker.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_resource_masker.cc
@@ -66,7 +66,7 @@ PaintRecordBuilder builder(nullptr, &context); ColorFilter mask_content_filter = - Style()->SvgStyle().ColorInterpolation() == CI_LINEARRGB + StyleRef().SvgStyle().ColorInterpolation() == CI_LINEARRGB ? kColorFilterSRGBToLinearRGB : kColorFilterNone; builder.Context().SetColorFilter(mask_content_filter);
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_root.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_root.cc index 6de0dd4..29f9a4d 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_root.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_root.cc
@@ -147,7 +147,7 @@ return ContainingBlock()->AvailableLogicalHeight( kIncludeMarginBorderPadding); - const Length& logical_height = Style()->LogicalHeight(); + const Length& logical_height = StyleRef().LogicalHeight(); if (IsDocumentElement() && logical_height.IsPercentOrCalc()) { return ValueForLength( logical_height, @@ -242,9 +242,9 @@ // clipped. When the svg is stand-alone (isDocumentElement() == true) the // viewport clipping should always be applied, noting that the window // scrollbars should be hidden if overflow=hidden. - return Style()->OverflowX() == EOverflow::kHidden || - Style()->OverflowX() == EOverflow::kAuto || - Style()->OverflowX() == EOverflow::kScroll || IsDocumentElement(); + return StyleRef().OverflowX() == EOverflow::kHidden || + StyleRef().OverflowX() == EOverflow::kAuto || + StyleRef().OverflowX() == EOverflow::kScroll || IsDocumentElement(); } LayoutRect LayoutSVGRoot::VisualOverflowRect() const { @@ -326,7 +326,7 @@ SVGResourcesCache::ClientWasAddedToTree(*child, child->StyleRef()); bool should_isolate_descendants = - (child->IsBlendingAllowed() && child->Style()->HasBlendMode()) || + (child->IsBlendingAllowed() && child->StyleRef().HasBlendMode()) || child->HasNonIsolatedBlendingDescendants(); if (should_isolate_descendants) DescendantIsolationRequirementsChanged(kDescendantIsolationRequired); @@ -337,7 +337,7 @@ LayoutReplaced::RemoveChild(child); bool had_non_isolated_descendants = - (child->IsBlendingAllowed() && child->Style()->HasBlendMode()) || + (child->IsBlendingAllowed() && child->StyleRef().HasBlendMode()) || child->HasNonIsolatedBlendingDescendants(); if (had_non_isolated_descendants) DescendantIsolationRequirementsChanged(kDescendantIsolationNeedsUpdate); @@ -411,7 +411,7 @@ SVGTransformChangeDetector change_detector(local_to_border_box_transform_); SVGSVGElement* svg = ToSVGSVGElement(GetNode()); DCHECK(svg); - float scale = Style()->EffectiveZoom(); + float scale = StyleRef().EffectiveZoom(); local_to_border_box_transform_ = svg->ViewBoxToViewTransform( ContentWidth() / scale, ContentHeight() / scale);
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_shape.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_shape.cc index 452e6ad..69fd4258 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_shape.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_shape.cc
@@ -139,7 +139,7 @@ } FloatRect LayoutSVGShape::HitTestStrokeBoundingBox() const { - if (Style()->SvgStyle().HasStroke()) + if (StyleRef().SvgStyle().HasStroke()) return stroke_bounding_box_; // Implementation of @@ -360,7 +360,7 @@ PointerEventsHitRules hit_rules( PointerEventsHitRules::SVG_GEOMETRY_HITTESTING, - result.GetHitTestRequest(), Style()->PointerEvents()); + result.GetHitTestRequest(), StyleRef().PointerEvents()); if (NodeAtFloatPointInternal(result.GetHitTestRequest(), local_point, hit_rules)) { const LayoutPoint& local_layout_point = LayoutPoint(local_point); @@ -406,7 +406,7 @@ DCHECK(path_); FloatRect stroke_bounding_box = fill_bounding_box_; - if (Style()->SvgStyle().HasStroke()) { + if (StyleRef().SvgStyle().HasStroke()) { StrokeData stroke_data; SVGLayoutSupport::ApplyStrokeStyleToStrokeData(stroke_data, StyleRef(), *this, DashScaleFactor()); @@ -430,7 +430,7 @@ float LayoutSVGShape::StrokeWidth() const { SVGLengthContext length_context(GetElement()); - return length_context.ValueForLength(Style()->SvgStyle().StrokeWidth()); + return length_context.ValueForLength(StyleRef().SvgStyle().StrokeWidth()); } LayoutSVGShapeRareData& LayoutSVGShape::EnsureRareData() const {
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_shape.h b/third_party/blink/renderer/core/layout/svg/layout_svg_shape.h index 0daeb6b..c291ae4 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_shape.h +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_shape.h
@@ -86,7 +86,7 @@ } bool HasNonScalingStroke() const { - return Style()->SvgStyle().VectorEffect() == VE_NON_SCALING_STROKE; + return StyleRef().SvgStyle().VectorEffect() == VE_NON_SCALING_STROKE; } const Path& NonScalingStrokePath() const { DCHECK(HasNonScalingStroke());
diff --git a/third_party/blink/renderer/core/layout/svg/layout_svg_text.cc b/third_party/blink/renderer/core/layout/svg/layout_svg_text.cc index a27aece..0d720fe 100644 --- a/third_party/blink/renderer/core/layout/svg/layout_svg_text.cc +++ b/third_party/blink/renderer/core/layout/svg/layout_svg_text.cc
@@ -378,7 +378,7 @@ FloatRect LayoutSVGText::StrokeBoundingBox() const { FloatRect stroke_boundaries = ObjectBoundingBox(); - const SVGComputedStyle& svg_style = Style()->SvgStyle(); + const SVGComputedStyle& svg_style = StyleRef().SvgStyle(); if (!svg_style.HasStroke()) return stroke_boundaries; @@ -393,7 +393,7 @@ FloatRect visual_rect = StrokeBoundingBox(); SVGLayoutSupport::AdjustVisualRectWithResources(*this, visual_rect); - if (const ShadowList* text_shadow = Style()->TextShadow()) + if (const ShadowList* text_shadow = StyleRef().TextShadow()) text_shadow->AdjustRectForShadow(visual_rect); return visual_rect;
diff --git a/third_party/blink/renderer/core/layout/svg/svg_layout_support.h b/third_party/blink/renderer/core/layout/svg/svg_layout_support.h index dbc43c7..8737a84c 100644 --- a/third_party/blink/renderer/core/layout/svg/svg_layout_support.h +++ b/third_party/blink/renderer/core/layout/svg/svg_layout_support.h
@@ -216,7 +216,7 @@ const LayoutObjectType* object) { for (LayoutObject* child = object->FirstChild(); child; child = child->NextSibling()) { - if (child->IsBlendingAllowed() && child->Style()->HasBlendMode()) + if (child->IsBlendingAllowed() && child->StyleRef().HasBlendMode()) return true; if (child->HasNonIsolatedBlendingDescendants() && !WillIsolateBlendingDescendantsForObject(child))
diff --git a/third_party/blink/renderer/core/layout/svg/svg_layout_tree_as_text.cc b/third_party/blink/renderer/core/layout/svg/svg_layout_tree_as_text.cc index 3510f53ef..2cd2bea2 100644 --- a/third_party/blink/renderer/core/layout/svg/svg_layout_tree_as_text.cc +++ b/third_party/blink/renderer/core/layout/svg/svg_layout_tree_as_text.cc
@@ -455,7 +455,7 @@ LineLayoutSVGInlineText text_line_layout = LineLayoutSVGInlineText(text_box->GetLineLayoutItem()); - const SVGComputedStyle& svg_style = text_line_layout.Style()->SvgStyle(); + const SVGComputedStyle& svg_style = text_line_layout.StyleRef().SvgStyle(); String text = text_box->GetLineLayoutItem().GetText(); unsigned fragments_size = fragments.size(); @@ -471,7 +471,7 @@ ts << "chunk 1 "; ETextAnchor anchor = svg_style.TextAnchor(); bool is_vertical_text = - !text_line_layout.Style()->IsHorizontalWritingMode(); + !text_line_layout.StyleRef().IsHorizontalWritingMode(); if (anchor == TA_MIDDLE) { ts << "(middle anchor"; if (is_vertical_text)
diff --git a/third_party/blink/renderer/core/layout/svg/svg_text_layout_engine_baseline.cc b/third_party/blink/renderer/core/layout/svg/svg_text_layout_engine_baseline.cc index bbf32ba..c7824b10 100644 --- a/third_party/blink/renderer/core/layout/svg/svg_text_layout_engine_baseline.cc +++ b/third_party/blink/renderer/core/layout/svg/svg_text_layout_engine_baseline.cc
@@ -62,7 +62,7 @@ DCHECK(text_line_layout); DCHECK(text_line_layout.Style()); - const SVGComputedStyle& style = text_line_layout.Style()->SvgStyle(); + const SVGComputedStyle& style = text_line_layout.StyleRef().SvgStyle(); EDominantBaseline baseline = style.DominantBaseline(); if (baseline == DB_AUTO) { @@ -119,7 +119,7 @@ DCHECK(text_line_layout_parent); EAlignmentBaseline baseline = - text_line_layout.Style()->SvgStyle().AlignmentBaseline(); + text_line_layout.StyleRef().SvgStyle().AlignmentBaseline(); if (baseline == AB_AUTO || baseline == AB_BASELINE) { baseline = DominantBaselineToAlignmentBaseline(is_vertical_text, text_line_layout_parent);
diff --git a/third_party/blink/renderer/core/layout/svg/svg_text_query.cc b/third_party/blink/renderer/core/layout/svg/svg_text_query.cc index b062998..236be0f 100644 --- a/third_party/blink/renderer/core/layout/svg/svg_text_query.cc +++ b/third_party/blink/renderer/core/layout/svg/svg_text_query.cc
@@ -108,7 +108,7 @@ LineLayoutSVGInlineText(text_box->GetLineLayoutItem()); query_data->is_vertical_text = - !query_data->text_line_layout.Style()->IsHorizontalWritingMode(); + !query_data->text_line_layout.StyleRef().IsHorizontalWritingMode(); // Loop over all text fragments in this text box, firing a callback for each. for (const SVGTextFragment& fragment : text_box->TextFragments()) {
diff --git a/third_party/blink/renderer/core/layout/table_layout_algorithm_auto.cc b/third_party/blink/renderer/core/layout/table_layout_algorithm_auto.cc index 1a8efd8..7110087 100644 --- a/third_party/blink/renderer/core/layout/table_layout_algorithm_auto.cc +++ b/third_party/blink/renderer/core/layout/table_layout_algorithm_auto.cc
@@ -170,9 +170,9 @@ for (LayoutTableCol* column = table_->FirstColumn(); column; column = column->NextColumn()) { if (column->IsTableColumnGroupWithColumnChildren()) { - group_logical_width = column->Style()->LogicalWidth(); + group_logical_width = column->StyleRef().LogicalWidth(); } else { - Length col_logical_width = column->Style()->LogicalWidth(); + Length col_logical_width = column->StyleRef().LogicalWidth(); // FIXME: calc() on tables should be handled consistently with other // lengths. See bug: https://crbug.com/382725 if (col_logical_width.IsCalculated() || col_logical_width.IsAuto()) @@ -242,19 +242,19 @@ // A special case. If this table is not fixed width and contained inside // a cell, then don't bloat the maxwidth by examining percentage growth. while (true) { - Length tw = table->Style()->Width(); + Length tw = table->StyleRef().Width(); if ((!tw.IsAuto() && !tw.IsPercentOrCalc()) || table->IsOutOfFlowPositioned()) return true; LayoutBlock* cb = table->ContainingBlock(); while (!cb->IsLayoutView() && !cb->IsTableCell() && - cb->Style()->Width().IsAuto() && !cb->IsOutOfFlowPositioned()) + cb->StyleRef().Width().IsAuto() && !cb->IsOutOfFlowPositioned()) cb = cb->ContainingBlock(); // TODO(dgrogan): Should the second clause check for isFixed() instead? - if (!cb->IsTableCell() || (!cb->Style()->Width().IsAuto() && - !cb->Style()->Width().IsPercentOrCalc())) + if (!cb->IsTableCell() || (!cb->StyleRef().Width().IsAuto() && + !cb->StyleRef().Width().IsPercentOrCalc())) return true; LayoutTableCell* cell = ToLayoutTableCell(cb); @@ -328,7 +328,7 @@ void TableLayoutAlgorithmAuto::ApplyPreferredLogicalWidthQuirks( LayoutUnit& min_width, LayoutUnit& max_width) const { - Length table_logical_width = table_->Style()->LogicalWidth(); + Length table_logical_width = table_->StyleRef().LogicalWidth(); if (table_logical_width.IsFixed() && table_logical_width.IsPositive()) { // |minWidth| is the result of measuring the intrinsic content's size. Keep // it to make sure we are *never* smaller than the actual content. @@ -339,7 +339,8 @@ min_width = max_width = LayoutUnit( std::max<int>(min_width.Floor(), table_logical_width.Value())); - const Length& style_max_logical_width = table_->Style()->LogicalMaxWidth(); + const Length& style_max_logical_width = + table_->StyleRef().LogicalMaxWidth(); if (style_max_logical_width.IsFixed() && !style_max_logical_width.IsNegative()) { min_width = LayoutUnit(
diff --git a/third_party/blink/renderer/core/layout/table_layout_algorithm_fixed.cc b/third_party/blink/renderer/core/layout/table_layout_algorithm_fixed.cc index 7057cd8..66cba73d 100644 --- a/third_party/blink/renderer/core/layout/table_layout_algorithm_fixed.cc +++ b/third_party/blink/renderer/core/layout/table_layout_algorithm_fixed.cc
@@ -98,7 +98,7 @@ if (col->IsTableColumnGroupWithColumnChildren()) continue; - Length col_style_logical_width = col->Style()->LogicalWidth(); + Length col_style_logical_width = col->StyleRef().LogicalWidth(); int effective_col_width = 0; if (col_style_logical_width.IsFixed() && col_style_logical_width.Value() > 0) @@ -196,7 +196,7 @@ void TableLayoutAlgorithmFixed::ApplyPreferredLogicalWidthQuirks( LayoutUnit& min_width, LayoutUnit& max_width) const { - Length table_logical_width = table_->Style()->LogicalWidth(); + Length table_logical_width = table_->StyleRef().LogicalWidth(); if (table_logical_width.IsFixed() && table_logical_width.IsPositive()) { min_width = max_width = LayoutUnit( max(min_width, @@ -218,7 +218,7 @@ // In this example, the two inner tables should be as large as the outer // table. We can achieve this effect by making the maxwidth of fixed tables // with percentage widths be infinite. - if (table_->Style()->LogicalWidth().IsPercentOrCalc() && + if (table_->StyleRef().LogicalWidth().IsPercentOrCalc() && max_width < kTableMaxWidth) max_width = LayoutUnit(kTableMaxWidth); }
diff --git a/third_party/blink/renderer/core/layout/text_autosizer.cc b/third_party/blink/renderer/core/layout/text_autosizer.cc index 520cfbf..5e8973d8 100644 --- a/third_party/blink/renderer/core/layout/text_autosizer.cc +++ b/third_party/blink/renderer/core/layout/text_autosizer.cc
@@ -101,7 +101,7 @@ if (!layout_object->IsLayoutBlock()) return false; if (layout_object->IsInline() && - !layout_object->Style()->IsDisplayReplacedType()) + !layout_object->StyleRef().IsDisplayReplacedType()) return false; if (layout_object->IsListItemIncludingNG()) return (layout_object->IsFloating() || @@ -120,9 +120,9 @@ layout_object->IsFlexibleBoxIncludingDeprecated() || (containing_block && containing_block->IsHorizontalWritingMode() != layout_object->IsHorizontalWritingMode()) || - layout_object->Style()->IsDisplayReplacedType() || + layout_object->StyleRef().IsDisplayReplacedType() || layout_object->IsTextArea() || - layout_object->Style()->UserModify() != EUserModify::kReadOnly; + layout_object->StyleRef().UserModify() != EUserModify::kReadOnly; } static bool BlockIsRowOfLinks(const LayoutBlock* block) { @@ -145,12 +145,12 @@ if (!layout_object->IsInline() || layout_object->IsBR()) return false; } - if (layout_object->Style()->IsLink()) { + if (layout_object->StyleRef().IsLink()) { link_count++; if (matching_font_size < 0) - matching_font_size = layout_object->Style()->SpecifiedFontSize(); + matching_font_size = layout_object->StyleRef().SpecifiedFontSize(); else if (matching_font_size != - layout_object->Style()->SpecifiedFontSize()) + layout_object->StyleRef().SpecifiedFontSize()) return false; // Skip traversing descendants of the link. @@ -211,7 +211,7 @@ // Don't autosize block-level text that can't wrap (as it's likely to // expand sideways and break the page's layout). - if (!block->Style()->AutoWrap()) + if (!block->StyleRef().AutoWrap()) return true; if (BlockHeightConstrained(block)) @@ -223,7 +223,7 @@ static bool HasExplicitWidth(const LayoutBlock* block) { // FIXME: This heuristic may need to be expanded to other ways a block can be // wider or narrower than its parent containing block. - return block->Style() && block->Style()->Width().IsSpecified(); + return block->Style() && block->StyleRef().Width().IsSpecified(); } static LayoutObject* GetParent(const LayoutObject* object) { @@ -354,14 +354,14 @@ // Cells in auto-layout tables are handled separately by inflateAutoTable. bool is_auto_table_cell = block->IsTableCell() && - !ToLayoutTableCell(block)->Table()->Style()->IsFixedTableLayout(); + !ToLayoutTableCell(block)->Table()->StyleRef().IsFixedTableLayout(); if (!is_auto_table_cell && !cluster_stack_.IsEmpty()) Inflate(block, layouter); } void TextAutosizer::InflateAutoTable(LayoutTable* table) { DCHECK(table); - DCHECK(!table->Style()->IsFixedTableLayout()); + DCHECK(!table->StyleRef().IsFixedTableLayout()); DCHECK(table->ContainingBlock()); Cluster* cluster = CurrentCluster(); @@ -727,7 +727,7 @@ // TextAreas and user-modifiable areas get a free pass to autosize regardless // of text content. - if (root->IsTextArea() || (root->Style() && root->Style()->UserModify() != + if (root->IsTextArea() || (root->Style() && root->StyleRef().UserModify() != EUserModify::kReadOnly)) { cluster->has_enough_text_to_autosize_ = kHasEnoughText; return true; @@ -763,7 +763,7 @@ // layout. These values can be different. // Note: This is an approximation assuming each character is 1em wide. length += ToLayoutText(descendant)->GetText().StripWhiteSpace().length() * - descendant->Style()->SpecifiedFontSize(); + descendant->StyleRef().SpecifiedFontSize(); if (length >= minimum_text_length_to_autosize) { cluster->has_enough_text_to_autosize_ = kHasEnoughText; @@ -988,7 +988,7 @@ Length specified_width = block->IsTableCell() ? ToLayoutTableCell(block)->StyleOrColLogicalWidth() - : block->Style()->LogicalWidth(); + : block->StyleRef().LogicalWidth(); if (specified_width.IsFixed()) { if ((width = specified_width.Value()) > 0) return width;
diff --git a/third_party/blink/renderer/core/layout/text_autosizer_test.cc b/third_party/blink/renderer/core/layout/text_autosizer_test.cc index 6bf81b4f..fde0c2e 100644 --- a/third_party/blink/renderer/core/layout/text_autosizer_test.cc +++ b/third_party/blink/renderer/core/layout/text_autosizer_test.cc
@@ -78,11 +78,11 @@ )HTML"); Element* autosized = GetDocument().getElementById("autosized"); EXPECT_FLOAT_EQ(16.f, - autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 40px. EXPECT_FLOAT_EQ(40.f, - autosized->GetLayoutObject()->Style()->ComputedFontSize()); + autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, TextSizeAdjustDisablesAutosizing) { @@ -121,16 +121,16 @@ )HTML"); LayoutObject* text_size_adjust_auto = GetDocument().getElementById("textSizeAdjustAuto")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust_auto->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(40.f, text_size_adjust_auto->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_auto->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(40.f, text_size_adjust_auto->StyleRef().ComputedFontSize()); LayoutObject* text_size_adjust_none = GetDocument().getElementById("textSizeAdjustNone")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust_none->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(16.f, text_size_adjust_none->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_none->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_none->StyleRef().ComputedFontSize()); LayoutObject* text_size_adjust100 = GetDocument().getElementById("textSizeAdjust100")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust100->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(16.f, text_size_adjust100->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust100->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust100->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ParagraphWithChangingTextSizeAdjustment) { @@ -154,37 +154,37 @@ )HTML"); Element* autosized_div = GetDocument().getElementById("autosized"); EXPECT_FLOAT_EQ( - 16.f, autosized_div->GetLayoutObject()->Style()->SpecifiedFontSize()); + 16.f, autosized_div->GetLayoutObject()->StyleRef().SpecifiedFontSize()); EXPECT_FLOAT_EQ( - 40.f, autosized_div->GetLayoutObject()->Style()->ComputedFontSize()); + 40.f, autosized_div->GetLayoutObject()->StyleRef().ComputedFontSize()); autosized_div->setAttribute(HTMLNames::classAttr, "none"); GetDocument().View()->UpdateAllLifecyclePhases(); EXPECT_FLOAT_EQ( - 16.f, autosized_div->GetLayoutObject()->Style()->SpecifiedFontSize()); + 16.f, autosized_div->GetLayoutObject()->StyleRef().SpecifiedFontSize()); EXPECT_FLOAT_EQ( - 16.f, autosized_div->GetLayoutObject()->Style()->ComputedFontSize()); + 16.f, autosized_div->GetLayoutObject()->StyleRef().ComputedFontSize()); autosized_div->setAttribute(HTMLNames::classAttr, "small"); GetDocument().View()->UpdateAllLifecyclePhases(); EXPECT_FLOAT_EQ( - 16.f, autosized_div->GetLayoutObject()->Style()->SpecifiedFontSize()); + 16.f, autosized_div->GetLayoutObject()->StyleRef().SpecifiedFontSize()); EXPECT_FLOAT_EQ( - 8.f, autosized_div->GetLayoutObject()->Style()->ComputedFontSize()); + 8.f, autosized_div->GetLayoutObject()->StyleRef().ComputedFontSize()); autosized_div->setAttribute(HTMLNames::classAttr, "large"); GetDocument().View()->UpdateAllLifecyclePhases(); EXPECT_FLOAT_EQ( - 16.f, autosized_div->GetLayoutObject()->Style()->SpecifiedFontSize()); + 16.f, autosized_div->GetLayoutObject()->StyleRef().SpecifiedFontSize()); EXPECT_FLOAT_EQ( - 24.f, autosized_div->GetLayoutObject()->Style()->ComputedFontSize()); + 24.f, autosized_div->GetLayoutObject()->StyleRef().ComputedFontSize()); autosized_div->removeAttribute(HTMLNames::classAttr); GetDocument().View()->UpdateAllLifecyclePhases(); EXPECT_FLOAT_EQ( - 16.f, autosized_div->GetLayoutObject()->Style()->SpecifiedFontSize()); + 16.f, autosized_div->GetLayoutObject()->StyleRef().SpecifiedFontSize()); EXPECT_FLOAT_EQ( - 40.f, autosized_div->GetLayoutObject()->Style()->ComputedFontSize()); + 40.f, autosized_div->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ZeroTextSizeAdjustment) { @@ -205,8 +205,8 @@ )HTML"); LayoutObject* text_size_adjust_zero = GetDocument().getElementById("textSizeAdjustZero")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust_zero->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(0.f, text_size_adjust_zero->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_zero->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(0.f, text_size_adjust_zero->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, NegativeTextSizeAdjustment) { @@ -228,8 +228,9 @@ LayoutObject* text_size_adjust_negative = GetDocument().getElementById("textSizeAdjustNegative")->GetLayoutObject(); EXPECT_FLOAT_EQ(16.f, - text_size_adjust_negative->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(40.f, text_size_adjust_negative->Style()->ComputedFontSize()); + text_size_adjust_negative->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(40.f, + text_size_adjust_negative->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, TextSizeAdjustmentPixelUnits) { @@ -250,8 +251,9 @@ "</div>"); LayoutObject* text_size_adjust_pixels = GetDocument().getElementById("textSizeAdjustPixels")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust_pixels->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(40.f, text_size_adjust_pixels->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, + text_size_adjust_pixels->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(40.f, text_size_adjust_pixels->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, NestedTextSizeAdjust) { @@ -281,14 +283,14 @@ )HTML"); LayoutObject* text_size_adjust_a = GetDocument().getElementById("textSizeAdjustA")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust_a->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_a->StyleRef().SpecifiedFontSize()); // 16px * 47% = 7.52 - EXPECT_FLOAT_EQ(7.52f, text_size_adjust_a->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(7.52f, text_size_adjust_a->StyleRef().ComputedFontSize()); LayoutObject* text_size_adjust_b = GetDocument().getElementById("textSizeAdjustB")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust_b->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_b->StyleRef().SpecifiedFontSize()); // 16px * 53% = 8.48 - EXPECT_FLOAT_EQ(8.48f, text_size_adjust_b->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(8.48f, text_size_adjust_b->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, PrefixedTextSizeAdjustIsAlias) { @@ -309,10 +311,10 @@ )HTML"); LayoutObject* text_size_adjust = GetDocument().getElementById("textSizeAdjust")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(8.f, text_size_adjust->Style()->ComputedFontSize()); - EXPECT_FLOAT_EQ(.5f, - text_size_adjust->Style()->GetTextSizeAdjust().Multiplier()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(8.f, text_size_adjust->StyleRef().ComputedFontSize()); + EXPECT_FLOAT_EQ( + .5f, text_size_adjust->StyleRef().GetTextSizeAdjust().Multiplier()); } TEST_F(TextAutosizerTest, AccessibilityFontScaleFactor) { @@ -334,11 +336,11 @@ )HTML"); Element* autosized = GetDocument().getElementById("autosized"); EXPECT_FLOAT_EQ(16.f, - autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // 1.5 * (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 60px. EXPECT_FLOAT_EQ(60.f, - autosized->GetLayoutObject()->Style()->ComputedFontSize()); + autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, AccessibilityFontScaleFactorWithTextSizeAdjustNone) { @@ -371,19 +373,19 @@ )HTML"); Element* autosized = GetDocument().getElementById("autosized"); EXPECT_FLOAT_EQ(16.f, - autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // 1.5 * (specified font-size = 16px) = 24px. EXPECT_FLOAT_EQ(24.f, - autosized->GetLayoutObject()->Style()->ComputedFontSize()); + autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); // Because this does not autosize (due to the width), no accessibility font // scale factor should be applied. Element* not_autosized = GetDocument().getElementById("notAutosized"); EXPECT_FLOAT_EQ( - 16.f, not_autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + 16.f, not_autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // specified font-size = 16px. EXPECT_FLOAT_EQ( - 16.f, not_autosized->GetLayoutObject()->Style()->ComputedFontSize()); + 16.f, not_autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ChangingAccessibilityFontScaleFactor) { @@ -405,21 +407,21 @@ )HTML"); Element* autosized = GetDocument().getElementById("autosized"); EXPECT_FLOAT_EQ(16.f, - autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // 1.0 * (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 40px. EXPECT_FLOAT_EQ(40.f, - autosized->GetLayoutObject()->Style()->ComputedFontSize()); + autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); GetDocument().GetSettings()->SetAccessibilityFontScaleFactor(2); GetDocument().View()->UpdateAllLifecyclePhases(); EXPECT_FLOAT_EQ(16.f, - autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // 2.0 * (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 80px. EXPECT_FLOAT_EQ(80.f, - autosized->GetLayoutObject()->Style()->ComputedFontSize()); + autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, TextSizeAdjustDoesNotDisableAccessibility) { @@ -452,21 +454,21 @@ GetDocument().getElementById("textSizeAdjustNone"); EXPECT_FLOAT_EQ( 16.f, - text_size_adjust_none->GetLayoutObject()->Style()->SpecifiedFontSize()); + text_size_adjust_none->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // 1.5 * (specified font-size = 16px) = 24px. EXPECT_FLOAT_EQ( 24.f, - text_size_adjust_none->GetLayoutObject()->Style()->ComputedFontSize()); + text_size_adjust_none->GetLayoutObject()->StyleRef().ComputedFontSize()); Element* text_size_adjust_double = GetDocument().getElementById("textSizeAdjustDouble"); - EXPECT_FLOAT_EQ( - 16.f, - text_size_adjust_double->GetLayoutObject()->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_double->GetLayoutObject() + ->StyleRef() + .SpecifiedFontSize()); // 1.5 * (specified font-size = 16px) * (text size adjustment = 2) = 48px. - EXPECT_FLOAT_EQ( - 48.f, - text_size_adjust_double->GetLayoutObject()->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(48.f, text_size_adjust_double->GetLayoutObject() + ->StyleRef() + .ComputedFontSize()); // Changing the accessibility font scale factor should change the adjusted // size. @@ -475,19 +477,19 @@ EXPECT_FLOAT_EQ( 16.f, - text_size_adjust_none->GetLayoutObject()->Style()->SpecifiedFontSize()); + text_size_adjust_none->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // 2.0 * (specified font-size = 16px) = 32px. EXPECT_FLOAT_EQ( 32.f, - text_size_adjust_none->GetLayoutObject()->Style()->ComputedFontSize()); + text_size_adjust_none->GetLayoutObject()->StyleRef().ComputedFontSize()); - EXPECT_FLOAT_EQ( - 16.f, - text_size_adjust_double->GetLayoutObject()->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust_double->GetLayoutObject() + ->StyleRef() + .SpecifiedFontSize()); // 2.0 * (specified font-size = 16px) * (text size adjustment = 2) = 64px. - EXPECT_FLOAT_EQ( - 64.f, - text_size_adjust_double->GetLayoutObject()->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(64.f, text_size_adjust_double->GetLayoutObject() + ->StyleRef() + .ComputedFontSize()); } // https://crbug.com/646237 @@ -506,10 +508,10 @@ LayoutObject* text_size_adjust = GetDocument().getElementById("textSizeAdjust")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, text_size_adjust->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(24.f, text_size_adjust->Style()->ComputedFontSize()); - EXPECT_FLOAT_EQ(1.5f, - text_size_adjust->Style()->GetTextSizeAdjust().Multiplier()); + EXPECT_FLOAT_EQ(16.f, text_size_adjust->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(24.f, text_size_adjust->StyleRef().ComputedFontSize()); + EXPECT_FLOAT_EQ( + 1.5f, text_size_adjust->StyleRef().GetTextSizeAdjust().Multiplier()); } TEST_F(TextAutosizerTest, DeviceScaleAdjustmentWithViewport) { @@ -536,23 +538,23 @@ Element* autosized = GetDocument().getElementById("autosized"); EXPECT_FLOAT_EQ(16.f, - autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 40px. // The device scale adjustment of 1.5 is ignored. EXPECT_FLOAT_EQ(40.f, - autosized->GetLayoutObject()->Style()->ComputedFontSize()); + autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); GetDocument().GetSettings()->SetViewportMetaEnabled(false); GetDocument().View()->UpdateAllLifecyclePhases(); autosized = GetDocument().getElementById("autosized"); EXPECT_FLOAT_EQ(16.f, - autosized->GetLayoutObject()->Style()->SpecifiedFontSize()); + autosized->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // (device scale adjustment = 1.5) * (specified font-size = 16px) * // (viewport width = 800px) / (window width = 320px) = 60px. EXPECT_FLOAT_EQ(60.f, - autosized->GetLayoutObject()->Style()->ComputedFontSize()); + autosized->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ChangingSuperClusterFirstText) { @@ -590,14 +592,14 @@ LayoutObject* long_text = GetDocument().getElementById("longText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, long_text->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, long_text->StyleRef().SpecifiedFontSize()); //(specified font-size = 16px) * (block width = 560px) / // (window width = 320px) = 28px. - EXPECT_FLOAT_EQ(28.f, long_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(28.f, long_text->StyleRef().ComputedFontSize()); LayoutObject* short_text = GetDocument().getElementById("shortText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, short_text->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(28.f, short_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, short_text->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(28.f, short_text->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ChangingSuperClusterSecondText) { @@ -635,14 +637,14 @@ LayoutObject* long_text = GetDocument().getElementById("longText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, long_text->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, long_text->StyleRef().SpecifiedFontSize()); //(specified font-size = 16px) * (block width = 560px) / // (window width = 320px) = 28px. - EXPECT_FLOAT_EQ(28.f, long_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(28.f, long_text->StyleRef().ComputedFontSize()); LayoutObject* short_text = GetDocument().getElementById("shortText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, short_text->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(28.f, short_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, short_text->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(28.f, short_text->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, AddingSuperCluster) { @@ -682,14 +684,14 @@ LayoutObject* long_text = GetDocument().getElementById("longText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, long_text->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, long_text->StyleRef().SpecifiedFontSize()); //(specified font-size = 16px) * (block width = 560px) / // (window width = 320px) = 28px. - EXPECT_FLOAT_EQ(28.f, long_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(28.f, long_text->StyleRef().ComputedFontSize()); LayoutObject* short_text = GetDocument().getElementById("shortText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, short_text->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(28.f, short_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, short_text->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(28.f, short_text->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ChangingInheritedClusterTextInsideSuperCluster) { @@ -728,14 +730,14 @@ LayoutObject* long_text = GetDocument().getElementById("longText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, long_text->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ(16.f, long_text->StyleRef().SpecifiedFontSize()); //(specified font-size = 16px) * (block width = 560px) / // (window width = 320px) = 28px. - EXPECT_FLOAT_EQ(28.f, long_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(28.f, long_text->StyleRef().ComputedFontSize()); LayoutObject* short_text = GetDocument().getElementById("shortText")->GetLayoutObject(); - EXPECT_FLOAT_EQ(16.f, short_text->Style()->SpecifiedFontSize()); - EXPECT_FLOAT_EQ(28.f, short_text->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, short_text->StyleRef().SpecifiedFontSize()); + EXPECT_FLOAT_EQ(28.f, short_text->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, AutosizeInnerContentOfRuby) { @@ -777,20 +779,20 @@ GetDocument().View()->UpdateAllLifecyclePhases(); Element* ruby_inline = GetDocument().getElementById("rubyInline"); - EXPECT_FLOAT_EQ(16.f, - ruby_inline->GetLayoutObject()->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ( + 16.f, ruby_inline->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 40px. - EXPECT_FLOAT_EQ(40.f, - ruby_inline->GetLayoutObject()->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ( + 40.f, ruby_inline->GetLayoutObject()->StyleRef().ComputedFontSize()); Element* ruby_block = GetDocument().getElementById("rubyBlock"); - EXPECT_FLOAT_EQ(16.f, - ruby_block->GetLayoutObject()->Style()->SpecifiedFontSize()); + EXPECT_FLOAT_EQ( + 16.f, ruby_block->GetLayoutObject()->StyleRef().SpecifiedFontSize()); // (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 40px. EXPECT_FLOAT_EQ(40.f, - ruby_block->GetLayoutObject()->Style()->ComputedFontSize()); + ruby_block->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ResizeAndGlyphOverflowChanged) { @@ -868,7 +870,7 @@ //(content width = 200px) / (window width = 320px) < 1.0f, multiplier = 1.0, // font-size = 16px; EXPECT_FLOAT_EQ(16.f, - content->GetLayoutObject()->Style()->ComputedFontSize()); + content->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, LayoutViewWidthProvider) { @@ -900,7 +902,7 @@ // (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 40px. EXPECT_FLOAT_EQ(40.f, - content->GetLayoutObject()->Style()->ComputedFontSize()); + content->GetLayoutObject()->StyleRef().ComputedFontSize()); GetDocument().getElementById("panel")->SetInnerHTMLFromString("insert text"); content->SetInnerHTMLFromString(content->InnerHTMLAsString()); @@ -909,7 +911,7 @@ // (specified font-size = 16px) * (viewport width = 800px) / // (window width = 320px) = 40px. EXPECT_FLOAT_EQ(40.f, - content->GetLayoutObject()->Style()->ComputedFontSize()); + content->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, MultiColumns) { @@ -942,7 +944,8 @@ Element* target = GetDocument().getElementById("target"); // (specified font-size = 16px) * ( thread flow layout width = 800px / 3) / // (window width = 320px) < 16px. - EXPECT_FLOAT_EQ(16.f, target->GetLayoutObject()->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(16.f, + target->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ScaledbyDSF) { @@ -970,7 +973,7 @@ // (specified font-size = 16px) * (thread flow layout width = 800px) / // (window width = 320px) * (device scale factor) = 40px * device_scale. EXPECT_FLOAT_EQ(40.0f * device_scale, - target->GetLayoutObject()->Style()->ComputedFontSize()); + target->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, ClusterHasNotEnoughTextToAutosizeForZoomDSF) { @@ -992,7 +995,8 @@ // minimum_text_length_to_autosize < length. Thus, ClusterMultiplier() // returns 1 (not multiplied by the accessibility font scale factor). // computed font-size = specified font-size = 8px. - EXPECT_FLOAT_EQ(8.0f, target->GetLayoutObject()->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(8.0f, + target->GetLayoutObject()->StyleRef().ComputedFontSize()); } // TODO(jaebaek): Unit tests ClusterHasNotEnoughTextToAutosizeForZoomDSF and @@ -1029,7 +1033,7 @@ // ClusterHasEnoughTextToAutosize() returns true and both accessibility font // scale factor and device scale factor are multiplied. EXPECT_FLOAT_EQ(20.0f * device_scale, - target->GetLayoutObject()->Style()->ComputedFontSize()); + target->GetLayoutObject()->StyleRef().ComputedFontSize()); } TEST_F(TextAutosizerTest, AfterPrint) { @@ -1051,11 +1055,12 @@ )HTML"); Element* target = GetDocument().getElementById("target"); EXPECT_FLOAT_EQ(20.0f * device_scale, - target->GetLayoutObject()->Style()->ComputedFontSize()); + target->GetLayoutObject()->StyleRef().ComputedFontSize()); GetDocument().GetFrame()->StartPrinting(print_size, print_size, 1.0); - EXPECT_FLOAT_EQ(8.0f, target->GetLayoutObject()->Style()->ComputedFontSize()); + EXPECT_FLOAT_EQ(8.0f, + target->GetLayoutObject()->StyleRef().ComputedFontSize()); GetDocument().GetFrame()->EndPrinting(); EXPECT_FLOAT_EQ(20.0f * device_scale, - target->GetLayoutObject()->Style()->ComputedFontSize()); + target->GetLayoutObject()->StyleRef().ComputedFontSize()); } } // namespace blink
diff --git a/third_party/blink/renderer/core/loader/base_fetch_context.cc b/third_party/blink/renderer/core/loader/base_fetch_context.cc index 940d69d..d1e925ec 100644 --- a/third_party/blink/renderer/core/loader/base_fetch_context.cc +++ b/third_party/blink/renderer/core/loader/base_fetch_context.cc
@@ -155,9 +155,9 @@ } else { OriginAccessEntry access_entry( request.Url().Protocol(), request.Url().Host(), - OriginAccessEntry::kAllowRegisterableDomains); + network::cors::OriginAccessEntry::kAllowRegisterableDomains); if (access_entry.MatchesOrigin(*GetSecurityOrigin()) == - OriginAccessEntry::kMatchesOrigin) { + network::cors::OriginAccessEntry::kMatchesOrigin) { site_value = "same-site"; } }
diff --git a/third_party/blink/renderer/core/loader/link_loader.cc b/third_party/blink/renderer/core/loader/link_loader.cc index c90c90bd..c9400a6 100644 --- a/third_party/blink/renderer/core/loader/link_loader.cc +++ b/third_party/blink/renderer/core/loader/link_loader.cc
@@ -574,9 +574,13 @@ ResourceRequest resource_request(params.href); resource_request.SetReferrerPolicy(params.referrer_policy); - resource_request.SetFetchImportanceMode( GetFetchImportanceAttributeValue(params.importance)); + if (RuntimeEnabledFeatures::SignedHTTPExchangeEnabled()) { + DEFINE_STATIC_LOCAL(const AtomicString, accept_prefetch, + ("application/signed-exchange;v=b1;q=0.9,*/*;q=0.8")); + resource_request.SetHTTPAccept(accept_prefetch); + } ResourceLoaderOptions options; options.initiator_info.name = FetchInitiatorTypeNames::link;
diff --git a/third_party/blink/renderer/core/loader/resource/image_resource.cc b/third_party/blink/renderer/core/loader/resource/image_resource.cc index 86c73da..727f74f 100644 --- a/third_party/blink/renderer/core/loader/resource/image_resource.cc +++ b/third_party/blink/renderer/core/loader/resource/image_resource.cc
@@ -24,7 +24,9 @@ #include "third_party/blink/renderer/core/loader/resource/image_resource.h" #include <stdint.h> +#include <algorithm> #include <memory> +#include <utility> #include "third_party/blink/public/platform/platform.h" #include "third_party/blink/renderer/core/loader/resource/image_resource_content.h" @@ -74,7 +76,8 @@ USING_GARBAGE_COLLECTED_MIXIN(ImageResourceInfoImpl); public: - ImageResourceInfoImpl(ImageResource* resource) : resource_(resource) { + explicit ImageResourceInfoImpl(ImageResource* resource) + : resource_(resource) { DCHECK(resource_); } void Trace(blink::Visitor* visitor) override { @@ -139,7 +142,7 @@ STACK_ALLOCATED(); public: - ImageResourceFactory(const FetchParameters& fetch_params) + explicit ImageResourceFactory(const FetchParameters& fetch_params) : NonTextResourceFactory(Resource::kImage), fetch_params_(&fetch_params) {} @@ -234,9 +237,8 @@ Resource::OnMemoryDump(level_of_detail, memory_dump); const String name = GetMemoryDumpName() + "/image_content"; auto* dump = memory_dump->CreateMemoryAllocatorDump(name); - size_t encoded_size = - content_->HasImage() ? content_->GetImage()->Data()->size() : 0; - dump->AddScalar("size", "bytes", encoded_size); + if (content_->HasImage() && content_->GetImage()->Data()) + dump->AddScalar("size", "bytes", content_->GetImage()->Data()->size()); } void ImageResource::Trace(blink::Visitor* visitor) {
diff --git a/third_party/blink/renderer/core/mojo/mojo_handle.cc b/third_party/blink/renderer/core/mojo/mojo_handle.cc index 9932560..a77ab76 100644 --- a/third_party/blink/renderer/core/mojo/mojo_handle.cc +++ b/third_party/blink/renderer/core/mojo/mojo_handle.cc
@@ -221,10 +221,12 @@ result_dict.setResult(result); if (result == MOJO_RESULT_OK) { WTF::ArrayBufferContents::DataHandle data_handle( - data, num_bytes, [](void* buffer) { + data, num_bytes, + [](void* buffer, size_t length, void* alloc_data) { MojoResult result = MojoUnmapBuffer(buffer); DCHECK_EQ(result, MOJO_RESULT_OK); - }); + }, + nullptr); WTF::ArrayBufferContents contents(std::move(data_handle), WTF::ArrayBufferContents::kNotShared); result_dict.setBuffer(DOMArrayBuffer::Create(contents));
diff --git a/third_party/blink/renderer/core/paint/compositing/composited_layer_mapping.cc b/third_party/blink/renderer/core/paint/compositing/composited_layer_mapping.cc index b3351795..f346ef04 100644 --- a/third_party/blink/renderer/core/paint/compositing/composited_layer_mapping.cc +++ b/third_party/blink/renderer/core/paint/compositing/composited_layer_mapping.cc
@@ -1176,8 +1176,8 @@ UpdateFilters(); if (!GetLayoutObject() - .Style() - ->IsRunningBackdropFilterAnimationOnCompositor()) + .StyleRef() + .IsRunningBackdropFilterAnimationOnCompositor()) UpdateBackdropFilters(); IntRect local_compositing_bounds;
diff --git a/third_party/blink/renderer/core/paint/compositing/compositing_layer_assigner.cc b/third_party/blink/renderer/core/paint/compositing/compositing_layer_assigner.cc index 0f9721c..1e011f6df 100644 --- a/third_party/blink/renderer/core/paint/compositing/compositing_layer_assigner.cc +++ b/third_party/blink/renderer/core/paint/compositing/compositing_layer_assigner.cc
@@ -203,11 +203,11 @@ .StyleRef() .SubtreeWillChangeContents() && squashing_layer.GetLayoutObject() - .Style() - ->IsRunningAnimationOnCompositor()) || + .StyleRef() + .IsRunningAnimationOnCompositor()) || squashing_layer.GetLayoutObject() - .Style() - ->ShouldCompositeForCurrentAnimations()) + .StyleRef() + .ShouldCompositeForCurrentAnimations()) return SquashingDisallowedReason::kSquashingLayerIsAnimating; if (layer->EnclosingPaginationLayer()) @@ -314,8 +314,8 @@ if (ScrollingCoordinator* scrolling_coordinator = layer->GetScrollingCoordinator()) { if (layer->GetLayoutObject() - .Style() - ->HasViewportConstrainedPosition()) { + .StyleRef() + .HasViewportConstrainedPosition()) { scrolling_coordinator->FrameViewFixedObjectsDidChange( layer->GetLayoutObject().View()->GetFrameView()); }
diff --git a/third_party/blink/renderer/core/paint/compositing/compositing_requirements_updater.cc b/third_party/blink/renderer/core/paint/compositing/compositing_requirements_updater.cc index 7918a5d..05e8195 100644 --- a/third_party/blink/renderer/core/paint/compositing/compositing_requirements_updater.cc +++ b/third_party/blink/renderer/core/paint/compositing/compositing_requirements_updater.cc
@@ -192,7 +192,7 @@ // // TODO(smcgruer): Only composite fixed if needed (http://crbug.com/742213) const bool ignore_lcd_text = true; - if (layer->GetLayoutObject().Style()->GetPosition() == EPosition::kFixed || + if (layer->GetLayoutObject().StyleRef().GetPosition() == EPosition::kFixed || compositing_reason_finder.RequiresCompositingForScrollDependentPosition( layer, ignore_lcd_text)) { subtree_reasons |=
diff --git a/third_party/blink/renderer/core/paint/inline_text_box_painter.cc b/third_party/blink/renderer/core/paint/inline_text_box_painter.cc index c174e18a..44a593b 100644 --- a/third_party/blink/renderer/core/paint/inline_text_box_painter.cc +++ b/third_party/blink/renderer/core/paint/inline_text_box_painter.cc
@@ -302,8 +302,8 @@ bool ltr = inline_text_box_.IsLeftToRightDirection(); bool flow_is_ltr = inline_text_box_.GetLineLayoutItem() .ContainingBlock() - .Style() - ->IsLeftToRightDirection(); + .StyleRef() + .IsLeftToRightDirection(); const PaintOffsets& selection_offsets = ApplyTruncationToPaintOffsets({static_cast<unsigned>(selection_start), @@ -451,8 +451,8 @@ bool ltr = inline_text_box_.IsLeftToRightDirection(); bool flow_is_ltr = inline_text_box_.GetLineLayoutItem() .ContainingBlock() - .Style() - ->IsLeftToRightDirection(); + .StyleRef() + .IsLeftToRightDirection(); // truncation is relative to the start of the InlineTextBox, not the text // node. @@ -647,8 +647,8 @@ // Calculate start & width int delta_y = (inline_text_box_.GetLineLayoutItem() - .Style() - ->IsFlippedLinesWritingMode() + .StyleRef() + .IsFlippedLinesWritingMode() ? inline_text_box_.Root().SelectionBottom() - inline_text_box_.LogicalBottom() : inline_text_box_.LogicalTop() - @@ -690,8 +690,8 @@ bool ltr = inline_text_box_.IsLeftToRightDirection(); bool flow_is_ltr = inline_text_box_.GetLineLayoutItem() .ContainingBlock() - .Style() - ->IsLeftToRightDirection(); + .StyleRef() + .IsLeftToRightDirection(); if (inline_text_box_.Truncation() != kCNoTruncation) { // In a mixed-direction flow the ellipsis is at the start of the text // so we need to start after it. Otherwise we just need to make sure
diff --git a/third_party/blink/renderer/core/paint/paint_property_tree_builder.cc b/third_party/blink/renderer/core/paint/paint_property_tree_builder.cc index 98010d2c..a7b76d96 100644 --- a/third_party/blink/renderer/core/paint/paint_property_tree_builder.cc +++ b/third_party/blink/renderer/core/paint/paint_property_tree_builder.cc
@@ -360,8 +360,8 @@ context_.current.should_flatten_inherited_transform; state.affected_by_outer_viewport_bounds_delta = - object_.Style()->GetPosition() == EPosition::kFixed && - !object_.Style()->Bottom().IsAuto(); + object_.StyleRef().GetPosition() == EPosition::kFixed && + !object_.StyleRef().Bottom().IsAuto(); if (RuntimeEnabledFeatures::SlimmingPaintV2Enabled() || RuntimeEnabledFeatures::BlinkGenPropertyTreesEnabled())
diff --git a/third_party/blink/renderer/core/paint/svg_inline_text_box_painter.cc b/third_party/blink/renderer/core/paint/svg_inline_text_box_painter.cc index 6a66bff..8fd02345 100644 --- a/third_party/blink/renderer/core/paint/svg_inline_text_box_painter.cc +++ b/third_party/blink/renderer/core/paint/svg_inline_text_box_painter.cc
@@ -302,8 +302,8 @@ TextDecoration decoration, const SVGTextFragment& fragment) { if (svg_inline_text_box_.GetLineLayoutItem() - .Style() - ->TextDecorationsInEffect() == TextDecoration::kNone) + .StyleRef() + .TextDecorationsInEffect() == TextDecoration::kNone) return; if (fragment.width <= 0)
diff --git a/third_party/blink/renderer/core/script/pending_script.cc b/third_party/blink/renderer/core/script/pending_script.cc index bd8cdfb2..2a3901e 100644 --- a/third_party/blink/renderer/core/script/pending_script.cc +++ b/third_party/blink/renderer/core/script/pending_script.cc
@@ -138,12 +138,16 @@ return; } - // Do not execute module scripts if they are moved between documents. - // TODO(hiroshige): Also do not execute classic scripts. crbug.com/721914 - if (OriginalContextDocument() != context_document && - GetScriptType() == ScriptType::kModule) { - Dispose(); - return; + if (OriginalContextDocument() != context_document) { + if (GetScriptType() == ScriptType::kModule) { + // Do not execute module scripts if they are moved between documents. + Dispose(); + return; + } + + // TODO(hiroshige): Also do not execute classic scripts. + // https://crbug.com/721914 + UseCounter::Count(frame, WebFeature::kEvaluateScriptMovedBetweenDocuments); } Script* script = GetSource(document_url);
diff --git a/third_party/blink/renderer/core/svg/graphics/svg_image.cc b/third_party/blink/renderer/core/svg/graphics/svg_image.cc index cfbb9f3..e7da7c0 100644 --- a/third_party/blink/renderer/core/svg/graphics/svg_image.cc +++ b/third_party/blink/renderer/core/svg/graphics/svg_image.cc
@@ -187,7 +187,7 @@ return container_size; // Assure that a container size is always given for a non-identity zoom level. - DCHECK_EQ(layout_object->Style()->EffectiveZoom(), 1); + DCHECK_EQ(layout_object->StyleRef().EffectiveZoom(), 1); // No set container size; use concrete object size. return intrinsic_size_;
diff --git a/third_party/blink/renderer/core/svg/svg_fe_diffuse_lighting_element.cc b/third_party/blink/renderer/core/svg/svg_fe_diffuse_lighting_element.cc index 54ece7a..53b5eae 100644 --- a/third_party/blink/renderer/core/svg/svg_fe_diffuse_lighting_element.cc +++ b/third_party/blink/renderer/core/svg/svg_fe_diffuse_lighting_element.cc
@@ -67,7 +67,7 @@ DCHECK(layout_object); DCHECK(layout_object->Style()); return diffuse_lighting->SetLightingColor( - layout_object->Style()->SvgStyle().LightingColor()); + layout_object->StyleRef().SvgStyle().LightingColor()); } if (attr_name == SVGNames::surfaceScaleAttr) return diffuse_lighting->SetSurfaceScale( @@ -151,7 +151,7 @@ return nullptr; DCHECK(layout_object->Style()); - Color color = layout_object->Style()->SvgStyle().LightingColor(); + Color color = layout_object->StyleRef().SvgStyle().LightingColor(); const SVGFELightElement* light_node = SVGFELightElement::FindLightElement(*this);
diff --git a/third_party/blink/renderer/core/svg/svg_fe_drop_shadow_element.cc b/third_party/blink/renderer/core/svg/svg_fe_drop_shadow_element.cc index 751caf8b..cc7cccdc 100644 --- a/third_party/blink/renderer/core/svg/svg_fe_drop_shadow_element.cc +++ b/third_party/blink/renderer/core/svg/svg_fe_drop_shadow_element.cc
@@ -103,7 +103,7 @@ return nullptr; DCHECK(layout_object->Style()); - const SVGComputedStyle& svg_style = layout_object->Style()->SvgStyle(); + const SVGComputedStyle& svg_style = layout_object->StyleRef().SvgStyle(); Color color = svg_style.FloodColor(); float opacity = svg_style.FloodOpacity();
diff --git a/third_party/blink/renderer/core/svg/svg_fe_flood_element.cc b/third_party/blink/renderer/core/svg/svg_fe_flood_element.cc index 5355841..0600bab19 100644 --- a/third_party/blink/renderer/core/svg/svg_fe_flood_element.cc +++ b/third_party/blink/renderer/core/svg/svg_fe_flood_element.cc
@@ -56,7 +56,7 @@ return nullptr; DCHECK(layout_object->Style()); - const SVGComputedStyle& svg_style = layout_object->Style()->SvgStyle(); + const SVGComputedStyle& svg_style = layout_object->StyleRef().SvgStyle(); Color color = svg_style.FloodColor(); float opacity = svg_style.FloodOpacity();
diff --git a/third_party/blink/renderer/core/svg/svg_fe_specular_lighting_element.cc b/third_party/blink/renderer/core/svg/svg_fe_specular_lighting_element.cc index 8b665f73..88f88f9 100644 --- a/third_party/blink/renderer/core/svg/svg_fe_specular_lighting_element.cc +++ b/third_party/blink/renderer/core/svg/svg_fe_specular_lighting_element.cc
@@ -77,7 +77,7 @@ DCHECK(layout_object); DCHECK(layout_object->Style()); return specular_lighting->SetLightingColor( - layout_object->Style()->SvgStyle().LightingColor()); + layout_object->StyleRef().SvgStyle().LightingColor()); } if (attr_name == SVGNames::surfaceScaleAttr) return specular_lighting->SetSurfaceScale( @@ -164,7 +164,7 @@ return nullptr; DCHECK(layout_object->Style()); - Color color = layout_object->Style()->SvgStyle().LightingColor(); + Color color = layout_object->StyleRef().SvgStyle().LightingColor(); const SVGFELightElement* light_node = SVGFELightElement::FindLightElement(*this);
diff --git a/third_party/blink/renderer/core/svg/svg_geometry_element.cc b/third_party/blink/renderer/core/svg/svg_geometry_element.cc index 7096142..78b2eabe 100644 --- a/third_party/blink/renderer/core/svg/svg_geometry_element.cc +++ b/third_party/blink/renderer/core/svg/svg_geometry_element.cc
@@ -95,7 +95,7 @@ HitTestRequest request(HitTestRequest::kReadOnly); PointerEventsHitRules hit_rules( PointerEventsHitRules::SVG_GEOMETRY_HITTESTING, request, - GetLayoutObject()->Style()->PointerEvents()); + GetLayoutObject()->StyleRef().PointerEvents()); hit_rules.can_hit_stroke = false; return ToLayoutSVGShape(GetLayoutObject()) ->NodeAtFloatPointInternal(request, point->Target()->Value(), hit_rules); @@ -112,7 +112,7 @@ HitTestRequest request(HitTestRequest::kReadOnly); PointerEventsHitRules hit_rules( PointerEventsHitRules::SVG_GEOMETRY_HITTESTING, request, - GetLayoutObject()->Style()->PointerEvents()); + GetLayoutObject()->StyleRef().PointerEvents()); hit_rules.can_hit_fill = false; return ToLayoutSVGShape(GetLayoutObject()) ->NodeAtFloatPointInternal(request, point->Target()->Value(), hit_rules); @@ -124,7 +124,7 @@ DCHECK(GetLayoutObject()); DCHECK(GetLayoutObject()->Style()); - path.SetWindRule(GetLayoutObject()->Style()->SvgStyle().ClipRule()); + path.SetWindRule(GetLayoutObject()->StyleRef().SvgStyle().ClipRule()); return path; }
diff --git a/third_party/blink/renderer/core/svg/svg_svg_element.cc b/third_party/blink/renderer/core/svg/svg_svg_element.cc index 7a43561..f681199 100644 --- a/third_party/blink/renderer/core/svg/svg_svg_element.cc +++ b/third_party/blink/renderer/core/svg/svg_svg_element.cc
@@ -329,7 +329,7 @@ LayoutObject* layout_object = element.GetLayoutObject(); DCHECK(!layout_object || layout_object->Style()); if (!layout_object || - layout_object->Style()->PointerEvents() == EPointerEvents::kNone) + layout_object->StyleRef().PointerEvents() == EPointerEvents::kNone) return false; if (!IsIntersectionOrEnclosureTarget(layout_object))
diff --git a/third_party/blink/renderer/core/testing/internals.cc b/third_party/blink/renderer/core/testing/internals.cc index 91b0b66a..c359a8d 100644 --- a/third_party/blink/renderer/core/testing/internals.cc +++ b/third_party/blink/renderer/core/testing/internals.cc
@@ -3054,7 +3054,7 @@ ScriptPromise Internals::promiseCheck(ScriptState* script_state, long arg1, bool arg2, - const Dictionary& arg3, + const ScriptValue& arg3, const String& arg4, const Vector<String>& arg5, ExceptionState& exception_state) { @@ -3068,7 +3068,7 @@ ScriptPromise Internals::promiseCheckWithoutExceptionState( ScriptState* script_state, - const Dictionary& arg1, + const ScriptValue& arg1, const String& arg2, const Vector<String>& arg3) { return ScriptPromise::Cast(script_state,
diff --git a/third_party/blink/renderer/core/testing/internals.h b/third_party/blink/renderer/core/testing/internals.h index 1f8fb70..804debac 100644 --- a/third_party/blink/renderer/core/testing/internals.h +++ b/third_party/blink/renderer/core/testing/internals.h
@@ -49,7 +49,6 @@ class DOMArrayBuffer; class DOMPoint; class DOMWindow; -class Dictionary; class DictionaryTest; class Document; class DocumentMarker; @@ -469,12 +468,12 @@ ScriptPromise promiseCheck(ScriptState*, long, bool, - const Dictionary&, + const ScriptValue&, const String&, const Vector<String>&, ExceptionState&); ScriptPromise promiseCheckWithoutExceptionState(ScriptState*, - const Dictionary&, + const ScriptValue&, const String&, const Vector<String>&); ScriptPromise promiseCheckRange(ScriptState*, long);
diff --git a/third_party/blink/renderer/core/testing/internals.idl b/third_party/blink/renderer/core/testing/internals.idl index b4d63f2..fc81aaaa 100644 --- a/third_party/blink/renderer/core/testing/internals.idl +++ b/third_party/blink/renderer/core/testing/internals.idl
@@ -310,8 +310,8 @@ [CallWith=ScriptState] Promise createResolvedPromise(any value); [CallWith=ScriptState] Promise createRejectedPromise(any reason); [CallWith=ScriptState] Promise addOneToPromise(Promise promise); - [CallWith=ScriptState, RaisesException] Promise promiseCheck(long arg1, boolean arg2, Dictionary arg3, DOMString arg4, sequence<DOMString> arg5); - [CallWith=ScriptState] Promise promiseCheckWithoutExceptionState(Dictionary arg1, DOMString arg2, DOMString... variadic); + [CallWith=ScriptState, RaisesException] Promise promiseCheck(long arg1, boolean arg2, object arg3, DOMString arg4, sequence<DOMString> arg5); + [CallWith=ScriptState] Promise promiseCheckWithoutExceptionState(object arg1, DOMString arg2, DOMString... variadic); [CallWith=ScriptState] Promise promiseCheckRange([EnforceRange] octet arg1); [CallWith=ScriptState] Promise promiseCheckOverload(Location arg1); [CallWith=ScriptState] Promise promiseCheckOverload(Document arg1);
diff --git a/third_party/blink/renderer/modules/background_fetch/background_fetch_bridge.cc b/third_party/blink/renderer/modules/background_fetch/background_fetch_bridge.cc index 39ed2357..e5bc036 100644 --- a/third_party/blink/renderer/modules/background_fetch/background_fetch_bridge.cc +++ b/third_party/blink/renderer/modules/background_fetch/background_fetch_bridge.cc
@@ -112,6 +112,7 @@ if (registration) { DCHECK_EQ(error, mojom::blink::BackgroundFetchError::NONE); + DCHECK_EQ(registration->state(), "pending"); registration->Initialize(GetSupplementable()); }
diff --git a/third_party/blink/renderer/modules/background_fetch/background_fetch_manager.cc b/third_party/blink/renderer/modules/background_fetch/background_fetch_manager.cc index abfb942cf..dbe549d 100644 --- a/third_party/blink/renderer/modules/background_fetch/background_fetch_manager.cc +++ b/third_party/blink/renderer/modules/background_fetch/background_fetch_manager.cc
@@ -330,6 +330,11 @@ script_state->GetIsolate(), "There already is a registration for the given id.")); return; + case mojom::blink::BackgroundFetchError::PERMISSION_DENIED: + resolver->Reject(V8ThrowException::CreateTypeError( + script_state->GetIsolate(), + "This origin does not have permission to start a fetch.")); + return; case mojom::blink::BackgroundFetchError::STORAGE_ERROR: DCHECK(!registration); resolver->Reject(V8ThrowException::CreateTypeError( @@ -468,6 +473,7 @@ return; case mojom::blink::BackgroundFetchError::DUPLICATED_DEVELOPER_ID: case mojom::blink::BackgroundFetchError::INVALID_ARGUMENT: + case mojom::blink::BackgroundFetchError::PERMISSION_DENIED: case mojom::blink::BackgroundFetchError::QUOTA_EXCEEDED: // Not applicable for this callback. break; @@ -517,6 +523,7 @@ case mojom::blink::BackgroundFetchError::DUPLICATED_DEVELOPER_ID: case mojom::blink::BackgroundFetchError::INVALID_ARGUMENT: case mojom::blink::BackgroundFetchError::INVALID_ID: + case mojom::blink::BackgroundFetchError::PERMISSION_DENIED: case mojom::blink::BackgroundFetchError::SERVICE_WORKER_UNAVAILABLE: case mojom::blink::BackgroundFetchError::QUOTA_EXCEEDED: // Not applicable for this callback.
diff --git a/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.cc b/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.cc index c639519..36200481 100644 --- a/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.cc +++ b/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.cc
@@ -5,6 +5,7 @@ #include "third_party/blink/renderer/modules/background_fetch/background_fetch_registration.h" #include "base/optional.h" +#include "third_party/blink/public/platform/modules/background_fetch/web_background_fetch_registration.h" #include "third_party/blink/public/platform/modules/fetch/fetch_api_request.mojom-blink.h" #include "third_party/blink/renderer/core/dom/dom_exception.h" #include "third_party/blink/renderer/core/dom/events/event.h" @@ -39,6 +40,21 @@ state_(state), observer_binding_(this) {} +BackgroundFetchRegistration::BackgroundFetchRegistration( + ServiceWorkerRegistration* registration, + const WebBackgroundFetchRegistration& web_registration) + : developer_id_(web_registration.developer_id), + unique_id_(web_registration.unique_id), + upload_total_(web_registration.upload_total), + uploaded_(web_registration.uploaded), + download_total_(web_registration.download_total), + downloaded_(web_registration.downloaded), + state_(web_registration.state), + observer_binding_(this) { + DCHECK(registration); + Initialize(registration); +} + BackgroundFetchRegistration::~BackgroundFetchRegistration() = default; void BackgroundFetchRegistration::Initialize( @@ -226,6 +242,7 @@ case mojom::blink::BackgroundFetchError::SERVICE_WORKER_UNAVAILABLE: case mojom::blink::BackgroundFetchError::DUPLICATED_DEVELOPER_ID: case mojom::blink::BackgroundFetchError::INVALID_ARGUMENT: + case mojom::blink::BackgroundFetchError::PERMISSION_DENIED: case mojom::blink::BackgroundFetchError::QUOTA_EXCEEDED: // Not applicable for this callback. break;
diff --git a/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.h b/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.h index 7e7efc4..8366ed6 100644 --- a/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.h +++ b/third_party/blink/renderer/modules/background_fetch/background_fetch_registration.h
@@ -21,6 +21,7 @@ class ScriptState; class ServiceWorkerRegistration; class RequestOrUSVString; +struct WebBackgroundFetchRegistration; // Represents an individual Background Fetch registration. Gives developers // access to its properties, options, and enables them to abort the fetch. @@ -38,6 +39,11 @@ unsigned long long download_total, unsigned long long downloaded, mojom::BackgroundFetchState state); + + BackgroundFetchRegistration( + ServiceWorkerRegistration* registration, + const WebBackgroundFetchRegistration& web_registration); + ~BackgroundFetchRegistration() override; // Initializes the BackgroundFetchRegistration to be associated with the given @@ -69,6 +75,9 @@ unsigned long long uploaded() const; unsigned long long downloadTotal() const; unsigned long long downloaded() const; + const String state() const; + + const String& unique_id() const { return unique_id_; } DEFINE_ATTRIBUTE_EVENT_LISTENER(progress); @@ -78,9 +87,6 @@ const AtomicString& InterfaceName() const override; ExecutionContext* GetExecutionContext() const override; - const String& unique_id() const { return unique_id_; } - const String state() const; - void Dispose(); void Trace(blink::Visitor* visitor) override;
diff --git a/third_party/blink/renderer/modules/background_fetch/background_fetch_type_converters.cc b/third_party/blink/renderer/modules/background_fetch/background_fetch_type_converters.cc index b4b7d6d..27deb460 100644 --- a/third_party/blink/renderer/modules/background_fetch/background_fetch_type_converters.cc +++ b/third_party/blink/renderer/modules/background_fetch/background_fetch_type_converters.cc
@@ -23,7 +23,7 @@ mojo_registration->developer_id, mojo_registration->unique_id, mojo_registration->upload_total, mojo_registration->uploaded, mojo_registration->download_total, mojo_registration->downloaded, - blink::mojom::BackgroundFetchState::PENDING); + mojo_registration->state); } blink::mojom::blink::BackgroundFetchOptionsPtr TypeConverter<
diff --git a/third_party/blink/renderer/modules/background_fetch/background_fetch_update_ui_event.cc b/third_party/blink/renderer/modules/background_fetch/background_fetch_update_ui_event.cc index d1b219c..6df619e 100644 --- a/third_party/blink/renderer/modules/background_fetch/background_fetch_update_ui_event.cc +++ b/third_party/blink/renderer/modules/background_fetch/background_fetch_update_ui_event.cc
@@ -113,6 +113,7 @@ case mojom::blink::BackgroundFetchError::DUPLICATED_DEVELOPER_ID: case mojom::blink::BackgroundFetchError::INVALID_ARGUMENT: case mojom::blink::BackgroundFetchError::SERVICE_WORKER_UNAVAILABLE: + case mojom::blink::BackgroundFetchError::PERMISSION_DENIED: case mojom::blink::BackgroundFetchError::QUOTA_EXCEEDED: // Not applicable for this callback. break;
diff --git a/third_party/blink/renderer/modules/credentialmanager/credentials_container.cc b/third_party/blink/renderer/modules/credentialmanager/credentials_container.cc index 9f399a23..863f1fd 100644 --- a/third_party/blink/renderer/modules/credentialmanager/credentials_container.cc +++ b/third_party/blink/renderer/modules/credentialmanager/credentials_container.cc
@@ -154,8 +154,9 @@ // TODO(crbug.com/803077): Avoid constructing an OriginAccessEntry just // for the IP address check. - OriginAccessEntry access_entry(origin->Protocol(), effective_domain, - blink::OriginAccessEntry::kAllowSubdomains); + OriginAccessEntry access_entry( + origin->Protocol(), effective_domain, + network::cors::OriginAccessEntry::MatchMode::kAllowSubdomains); if (effective_domain.IsEmpty() || access_entry.HostIsIPAddress()) { resolver->Reject( DOMException::Create(DOMExceptionCode::kSecurityError, @@ -167,11 +168,12 @@ // https://w3c.github.io/webauthn/#CreateCred-DetermineRpId and // https://w3c.github.io/webauthn/#GetAssn-DetermineRpId. if (!relying_party_id.IsNull()) { - OriginAccessEntry access_entry(origin->Protocol(), relying_party_id, - blink::OriginAccessEntry::kAllowSubdomains); + OriginAccessEntry access_entry( + origin->Protocol(), relying_party_id, + network::cors::OriginAccessEntry::kAllowSubdomains); if (relying_party_id.IsEmpty() || access_entry.MatchesDomain(*origin) != - blink::OriginAccessEntry::kMatchesOrigin) { + network::cors::OriginAccessEntry::kMatchesOrigin) { resolver->Reject(DOMException::Create( DOMExceptionCode::kSecurityError, "The relying party ID '" + relying_party_id +
diff --git a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.cc b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.cc index e6a4a40..464688b6 100644 --- a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.cc +++ b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.cc
@@ -117,9 +117,7 @@ void ServiceWorkerGlobalScopeProxy::DispatchBackgroundFetchAbortEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state) { + const WebBackgroundFetchRegistration& registration) { DCHECK(WorkerGlobalScope()->IsContextThread()); WaitUntilObserver* observer = WaitUntilObserver::Create( WorkerGlobalScope(), WaitUntilObserver::kBackgroundFetchAbort, event_id); @@ -131,13 +129,10 @@ // BackgroundFetchSettledFetches::Create which eventually calls ToV8. ScriptState::Scope scope(script_state); - // TODO(crbug.com/869918): Update to take a BackgroundFetchRegistration - // object, or all information required to build one. - BackgroundFetchRegistration* registration = new BackgroundFetchRegistration( - developer_id, unique_id, 0 /* upload_total */, 0 /* uploaded */, - 0 /* download_total */, 0 /* downloaded */, state); BackgroundFetchEventInit init; - init.setRegistration(registration); + init.setRegistration(new BackgroundFetchRegistration( + WorkerGlobalScope()->registration() /* service_worker_registration */, + registration)); BackgroundFetchEvent* event = BackgroundFetchEvent::Create( EventTypeNames::backgroundfetchabort, init, observer); @@ -147,20 +142,15 @@ void ServiceWorkerGlobalScopeProxy::DispatchBackgroundFetchClickEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state) { + const WebBackgroundFetchRegistration& registration) { DCHECK(WorkerGlobalScope()->IsContextThread()); WaitUntilObserver* observer = WaitUntilObserver::Create( WorkerGlobalScope(), WaitUntilObserver::kBackgroundFetchClick, event_id); - // TODO(crbug.com/869918): Update to take a BackgroundFetchRegistration - // object, or all information required to build one. - BackgroundFetchRegistration* registration = new BackgroundFetchRegistration( - developer_id, unique_id, 0 /* upload_total */, 0 /* uploaded */, - 0 /* download_total */, 0 /* downloaded */, state); BackgroundFetchEventInit init; - init.setRegistration(registration); + init.setRegistration(new BackgroundFetchRegistration( + WorkerGlobalScope()->registration() /* service_worker_registration */, + registration)); BackgroundFetchEvent* event = BackgroundFetchEvent::Create( EventTypeNames::backgroundfetchclick, init, observer); @@ -170,9 +160,7 @@ void ServiceWorkerGlobalScopeProxy::DispatchBackgroundFetchFailEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const WebBackgroundFetchRegistration& registration, const WebVector<WebBackgroundFetchSettledFetch>& fetches) { DCHECK(WorkerGlobalScope()->IsContextThread()); WaitUntilObserver* observer = WaitUntilObserver::Create( @@ -185,13 +173,10 @@ // BackgroundFetchSettledFetches::Create which eventually calls ToV8. ScriptState::Scope scope(script_state); - // TODO(crbug.com/869918): Update to take a BackgroundFetchRegistration - // object, or all information required to build one. - BackgroundFetchRegistration* registration = new BackgroundFetchRegistration( - developer_id, unique_id, 0 /* upload_total */, 0 /* uploaded */, - 0 /* download_total */, 0 /* downloaded */, state); BackgroundFetchEventInit init; - init.setRegistration(registration); + init.setRegistration(new BackgroundFetchRegistration( + WorkerGlobalScope()->registration() /* service_worker_registration */, + registration)); BackgroundFetchUpdateUIEvent* event = BackgroundFetchUpdateUIEvent::Create( EventTypeNames::backgroundfetchfail, init, observer, @@ -204,9 +189,7 @@ void ServiceWorkerGlobalScopeProxy::DispatchBackgroundFetchSuccessEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const WebBackgroundFetchRegistration& registration, const WebVector<WebBackgroundFetchSettledFetch>& fetches) { DCHECK(WorkerGlobalScope()->IsContextThread()); WaitUntilObserver* observer = WaitUntilObserver::Create( @@ -220,13 +203,10 @@ // BackgroundFetchSettledFetches::Create which eventually calls ToV8. ScriptState::Scope scope(script_state); - // TODO(crbug.com/869918): Update to take a BackgroundFetchRegistration - // object, or all information required to build one. - BackgroundFetchRegistration* registration = new BackgroundFetchRegistration( - developer_id, unique_id, 0 /* upload_total */, 0 /* uploaded */, - 0 /* download_total */, 0 /* downloaded */, state); BackgroundFetchEventInit init; - init.setRegistration(registration); + init.setRegistration(new BackgroundFetchRegistration( + WorkerGlobalScope()->registration() /* service_worker_registration */, + registration)); BackgroundFetchUpdateUIEvent* event = BackgroundFetchUpdateUIEvent::Create( EventTypeNames::backgroundfetchsuccess, init, observer,
diff --git a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.h b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.h index 22509a6d..7ca4e2a 100644 --- a/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.h +++ b/third_party/blink/renderer/modules/service_worker/service_worker_global_scope_proxy.h
@@ -83,25 +83,17 @@ void DispatchActivateEvent(int) override; void DispatchBackgroundFetchAbortEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state) override; + const WebBackgroundFetchRegistration& registration) override; void DispatchBackgroundFetchClickEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state) override; + const WebBackgroundFetchRegistration& registration) override; void DispatchBackgroundFetchFailEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const WebBackgroundFetchRegistration& registration, const WebVector<WebBackgroundFetchSettledFetch>& fetches) override; void DispatchBackgroundFetchSuccessEvent( int event_id, - const WebString& developer_id, - const WebString& unique_id, - blink::mojom::BackgroundFetchState state, + const WebBackgroundFetchRegistration& registration, const WebVector<WebBackgroundFetchSettledFetch>& fetches) override; void DispatchCookieChangeEvent( int event_id,
diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn index 7a7e127..ef168b8b 100644 --- a/third_party/blink/renderer/platform/BUILD.gn +++ b/third_party/blink/renderer/platform/BUILD.gn
@@ -1829,7 +1829,6 @@ "web_vector_test.cc", "weborigin/known_ports_test.cc", "weborigin/kurl_test.cc", - "weborigin/origin_access_entry_test.cc", "weborigin/scheme_registry_test.cc", "weborigin/security_origin_test.cc", "weborigin/security_policy_test.cc",
diff --git a/third_party/blink/renderer/platform/bindings/v8_per_isolate_data.cc b/third_party/blink/renderer/platform/bindings/v8_per_isolate_data.cc index 11e20df..c98c6ec 100644 --- a/third_party/blink/renderer/platform/bindings/v8_per_isolate_data.cc +++ b/third_party/blink/renderer/platform/bindings/v8_per_isolate_data.cc
@@ -66,10 +66,13 @@ scoped_refptr<base::SingleThreadTaskRunner> task_runner, V8ContextSnapshotMode v8_context_snapshot_mode) : v8_context_snapshot_mode_(v8_context_snapshot_mode), - isolate_holder_(task_runner, - gin::IsolateHolder::kSingleThread, - IsMainThread() ? gin::IsolateHolder::kDisallowAtomicsWait - : gin::IsolateHolder::kAllowAtomicsWait), + isolate_holder_( + task_runner, + gin::IsolateHolder::kSingleThread, + IsMainThread() ? gin::IsolateHolder::kDisallowAtomicsWait + : gin::IsolateHolder::kAllowAtomicsWait, + IsMainThread() ? gin::IsolateHolder::IsolateType::kBlinkMainThread + : gin::IsolateHolder::IsolateType::kBlinkWorkerThread), interface_template_map_for_v8_context_snapshot_(GetIsolate()), string_cache_(std::make_unique<StringCache>(GetIsolate())), private_property_(V8PrivateProperty::Create()), @@ -94,6 +97,7 @@ isolate_holder_(Platform::Current()->MainThread()->GetTaskRunner(), gin::IsolateHolder::kSingleThread, gin::IsolateHolder::kAllowAtomicsWait, + gin::IsolateHolder::IsolateType::kBlinkMainThread, gin::IsolateHolder::IsolateCreationMode::kCreateSnapshot), interface_template_map_for_v8_context_snapshot_(GetIsolate()), string_cache_(std::make_unique<StringCache>(GetIsolate())),
diff --git a/third_party/blink/renderer/platform/exported/web_runtime_features.cc b/third_party/blink/renderer/platform/exported/web_runtime_features.cc index c4b40a8..38a936d2 100644 --- a/third_party/blink/renderer/platform/exported/web_runtime_features.cc +++ b/third_party/blink/renderer/platform/exported/web_runtime_features.cc
@@ -380,6 +380,10 @@ RuntimeEnabledFeatures::SetSharedWorkerEnabled(enable); } +void WebRuntimeFeatures::EnableSignedHTTPExchange(bool enable) { + RuntimeEnabledFeatures::SetSignedHTTPExchangeEnabled(enable); +} + void WebRuntimeFeatures::EnablePreciseMemoryInfo(bool enable) { RuntimeEnabledFeatures::SetPreciseMemoryInfoEnabled(enable); }
diff --git a/third_party/blink/renderer/platform/runtime_enabled_features.json5 b/third_party/blink/renderer/platform/runtime_enabled_features.json5 index c5bf2ad..5e61a7fb 100644 --- a/third_party/blink/renderer/platform/runtime_enabled_features.json5 +++ b/third_party/blink/renderer/platform/runtime_enabled_features.json5
@@ -1123,6 +1123,9 @@ status: "experimental", }, { + name: "SignedHTTPExchange", + }, + { name: "SlimmingPaintV2", }, {
diff --git a/third_party/blink/renderer/platform/weborigin/DEPS b/third_party/blink/renderer/platform/weborigin/DEPS index b33b9de..8dd4818 100644 --- a/third_party/blink/renderer/platform/weborigin/DEPS +++ b/third_party/blink/renderer/platform/weborigin/DEPS
@@ -9,6 +9,7 @@ # net/ includes should be allowed only in a limited set of directories, # so we have separate DEPS from platform's one. "+net/base", + "+services/network/public/cpp/cors/origin_access_entry.h", "+third_party/blink/renderer/platform/blob/blob_url.h", "+third_party/blink/renderer/platform/platform_export.h", "+third_party/blink/renderer/platform/runtime_enabled_features.h",
diff --git a/third_party/blink/renderer/platform/weborigin/origin_access_entry.cc b/third_party/blink/renderer/platform/weborigin/origin_access_entry.cc index 37220fd5..9e729629 100644 --- a/third_party/blink/renderer/platform/weborigin/origin_access_entry.cc +++ b/third_party/blink/renderer/platform/weborigin/origin_access_entry.cc
@@ -30,143 +30,32 @@ #include "third_party/blink/renderer/platform/weborigin/origin_access_entry.h" -#include "net/base/registry_controlled_domains/registry_controlled_domain.h" -#include "third_party/blink/public/platform/platform.h" -#include "third_party/blink/renderer/platform/weborigin/kurl.h" #include "third_party/blink/renderer/platform/weborigin/security_origin.h" -#include "third_party/blink/renderer/platform/wtf/text/string_utf8_adaptor.h" -#include "url/third_party/mozilla/url_parse.h" -#include "url/url_canon.h" namespace blink { -namespace { +OriginAccessEntry::OriginAccessEntry( + const String& protocol, + const String& host, + network::cors::OriginAccessEntry::MatchMode match_mode) + : private_(std::string(protocol.Utf8().data()), + std::string(host.Utf8().data()), + match_mode) {} -// TODO(mkwst): This basically replicates GURL::HostIsIPAddress. If/when -// we re-evaluate everything after merging the Blink and Chromium -// repositories, perhaps we can just use that directly. -bool HostIsIPAddress(const String& host) { - if (host.IsEmpty()) - return false; +OriginAccessEntry::OriginAccessEntry(OriginAccessEntry&& from) = default; - String protocol("https://"); - KURL url(NullURL(), protocol + host + "/"); - if (!url.IsValid()) - return false; - - url::RawCanonOutputT<char, 128> ignored_output; - url::CanonHostInfo host_info; - url::Component host_component(0, - static_cast<int>(url.Host().Utf8().length())); - url::CanonicalizeIPAddress(url.Host().Utf8().data(), host_component, - &ignored_output, &host_info); - return host_info.IsIPAddress(); -} - -bool IsSubdomainOfHost(const String& subdomain, const String& host) { - if (subdomain.length() <= host.length()) - return false; - - if (subdomain[subdomain.length() - host.length() - 1] != '.') - return false; - - if (!subdomain.EndsWith(host)) - return false; - - return true; -} -} // namespace - -OriginAccessEntry::OriginAccessEntry(const String& protocol, - const String& host, - SubdomainSetting subdomain_setting) - : protocol_(protocol), - host_(host), - subdomain_settings_(subdomain_setting), - host_is_public_suffix_(false) { - DCHECK(subdomain_setting >= kAllowSubdomains || - subdomain_setting <= kDisallowSubdomains); - - host_is_ip_address_ = blink::HostIsIPAddress(host); - - // Look for top-level domains, either with or without an additional dot. - if (!host_is_ip_address_) { - // Blink passes some things that aren't technically hosts like "*.foo", so - // use the permissive variant. - size_t public_suffix_length = - net::registry_controlled_domains::PermissiveGetHostRegistryLength( - StringUTF8Adaptor(host_).AsStringPiece(), - net::registry_controlled_domains::INCLUDE_UNKNOWN_REGISTRIES, - net::registry_controlled_domains::INCLUDE_PRIVATE_REGISTRIES); - if (public_suffix_length == 0) - public_suffix_length = host_.length(); - - if (host_.length() <= public_suffix_length + 1) { - host_is_public_suffix_ = true; - } else if (subdomain_setting == kAllowRegisterableDomains && - public_suffix_length) { - // The "2" in the next line is 1 for the '.', plus a 1-char minimum label - // length. - const size_t dot = - host_.ReverseFind('.', host_.length() - public_suffix_length - 2); - if (dot == kNotFound) - registerable_domain_ = host; - else - registerable_domain_ = host.Substring(dot + 1); - } - } -} - -OriginAccessEntry::MatchResult OriginAccessEntry::MatchesOrigin( +network::cors::OriginAccessEntry::MatchResult OriginAccessEntry::MatchesOrigin( const SecurityOrigin& origin) const { - if (protocol_ != origin.Protocol()) - return kDoesNotMatchOrigin; - - return MatchesDomain(origin); + return private_.MatchesOrigin(origin.ToUrlOrigin()); } -OriginAccessEntry::MatchResult OriginAccessEntry::MatchesDomain( +network::cors::OriginAccessEntry::MatchResult OriginAccessEntry::MatchesDomain( const SecurityOrigin& origin) const { - // Special case: Include subdomains and empty host means "all hosts, including - // ip addresses". - if (subdomain_settings_ != kDisallowSubdomains && host_.IsEmpty()) - return kMatchesOrigin; + return private_.MatchesDomain(origin.ToUrlOrigin()); +} - // Exact match. - if (host_ == origin.Host()) - return kMatchesOrigin; - - // Don't try to do subdomain matching on IP addresses. - if (host_is_ip_address_) - return kDoesNotMatchOrigin; - - // Match subdomains. - switch (subdomain_settings_) { - case kDisallowSubdomains: - return kDoesNotMatchOrigin; - - case kAllowSubdomains: - if (!IsSubdomainOfHost(origin.Host(), host_)) - return kDoesNotMatchOrigin; - break; - - case kAllowRegisterableDomains: - // Fall back to a simple subdomain check if no registerable domain could - // be found: - if (registerable_domain_.IsEmpty()) { - if (!IsSubdomainOfHost(origin.Host(), host_)) - return kDoesNotMatchOrigin; - } else if (registerable_domain_ != origin.Host() && - !IsSubdomainOfHost(origin.Host(), registerable_domain_)) { - return kDoesNotMatchOrigin; - } - break; - }; - - if (host_is_public_suffix_) - return kMatchesOriginButIsPublicSuffix; - - return kMatchesOrigin; +bool OriginAccessEntry::HostIsIPAddress() const { + return private_.host_is_ip_address(); } } // namespace blink
diff --git a/third_party/blink/renderer/platform/weborigin/origin_access_entry.h b/third_party/blink/renderer/platform/weborigin/origin_access_entry.h index 73212c78..037cae5 100644 --- a/third_party/blink/renderer/platform/weborigin/origin_access_entry.h +++ b/third_party/blink/renderer/platform/weborigin/origin_access_entry.h
@@ -31,6 +31,7 @@ #ifndef THIRD_PARTY_BLINK_RENDERER_PLATFORM_WEBORIGIN_ORIGIN_ACCESS_ENTRY_H_ #define THIRD_PARTY_BLINK_RENDERER_PLATFORM_WEBORIGIN_ORIGIN_ACCESS_ENTRY_H_ +#include "services/network/public/cpp/cors/origin_access_entry.h" #include "third_party/blink/renderer/platform/platform_export.h" #include "third_party/blink/renderer/platform/wtf/allocator.h" #include "third_party/blink/renderer/platform/wtf/text/wtf_string.h" @@ -39,67 +40,35 @@ class SecurityOrigin; +// A class to wrap network::cors::OriginAccessEntry to use with Blink types. class PLATFORM_EXPORT OriginAccessEntry { USING_FAST_MALLOC(OriginAccessEntry); public: - enum SubdomainSetting { - // 'www.example.com' matches an OriginAccessEntry for 'example.com' - kAllowSubdomains, - - // 'www.example.com' matches an OriginAccessEntry for 'not-www.example.com' - kAllowRegisterableDomains, - - // 'www.example.com' does not match an OriginAccessEntry for 'example.com' - kDisallowSubdomains - }; - - enum MatchResult { - kMatchesOrigin, - kMatchesOriginButIsPublicSuffix, - kDoesNotMatchOrigin - }; - - // If host is empty string and SubdomainSetting is not DisallowSubdomains, the - // entry will match all domains in the specified protocol. + // If host is empty string and MatchMode is not DisallowSubdomains, the entry + // will match all domains in the specified protocol. // IPv6 addresses must include brackets (e.g. // '[2001:db8:85a3::8a2e:370:7334]', not '2001:db8:85a3::8a2e:370:7334'). OriginAccessEntry(const String& protocol, const String& host, - SubdomainSetting); + network::cors::OriginAccessEntry::MatchMode); + OriginAccessEntry(OriginAccessEntry&& from); // 'matchesOrigin' requires a protocol match (e.g. 'http' != 'https'). // 'matchesDomain' relaxes this constraint. - MatchResult MatchesOrigin(const SecurityOrigin&) const; - MatchResult MatchesDomain(const SecurityOrigin&) const; + network::cors::OriginAccessEntry::MatchResult MatchesOrigin( + const SecurityOrigin&) const; + network::cors::OriginAccessEntry::MatchResult MatchesDomain( + const SecurityOrigin&) const; - const String& Protocol() const { return protocol_; } - const String& Host() const { return host_; } - SubdomainSetting SubdomainSettings() const { return subdomain_settings_; } - bool HostIsIPAddress() const { return host_is_ip_address_; } - const String& Registerable() const { return registerable_domain_; } + bool HostIsIPAddress() const; private: - String protocol_; - String host_; - String registerable_domain_; - SubdomainSetting subdomain_settings_; - bool host_is_ip_address_; - bool host_is_public_suffix_; + network::cors::OriginAccessEntry private_; + + DISALLOW_COPY_AND_ASSIGN(OriginAccessEntry); }; -PLATFORM_EXPORT inline bool operator==(const OriginAccessEntry& a, - const OriginAccessEntry& b) { - return EqualIgnoringASCIICase(a.Protocol(), b.Protocol()) && - EqualIgnoringASCIICase(a.Host(), b.Host()) && - a.SubdomainSettings() == b.SubdomainSettings(); -} - -PLATFORM_EXPORT inline bool operator!=(const OriginAccessEntry& a, - const OriginAccessEntry& b) { - return !(a == b); -} - } // namespace blink #endif // THIRD_PARTY_BLINK_RENDERER_PLATFORM_WEBORIGIN_ORIGIN_ACCESS_ENTRY_H_
diff --git a/third_party/blink/renderer/platform/weborigin/security_policy.cc b/third_party/blink/renderer/platform/weborigin/security_policy.cc index a61a1f9..fa157fa 100644 --- a/third_party/blink/renderer/platform/weborigin/security_policy.cc +++ b/third_party/blink/renderer/platform/weborigin/security_policy.cc
@@ -85,8 +85,9 @@ OriginAccessList* list = result.stored_value->value.get(); list->push_back(OriginAccessEntry( destination_protocol, destination_domain, - allow_destination_subdomains ? OriginAccessEntry::kAllowSubdomains - : OriginAccessEntry::kDisallowSubdomains)); + allow_destination_subdomains + ? network::cors::OriginAccessEntry::kAllowSubdomains + : network::cors::OriginAccessEntry::kDisallowSubdomains)); } static void RemoveAllOriginAccessEntriesForOrigin( @@ -106,7 +107,7 @@ if (OriginAccessList* list = access_map.at(active_origin->ToString())) { for (size_t i = 0; i < list->size(); ++i) { if (list->at(i).MatchesOrigin(*target_origin) != - OriginAccessEntry::kDoesNotMatchOrigin) + network::cors::OriginAccessEntry::kDoesNotMatchOrigin) return true; } }
diff --git a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc index 053babc..0640d2c6 100644 --- a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc +++ b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.cc
@@ -128,12 +128,13 @@ ArrayBufferContents::DataHandle ArrayBufferContents::CreateDataHandle( size_t size, InitializationPolicy policy) { - return DataHandle(ArrayBufferContents::AllocateMemoryOrNull(size, policy), - size, FreeMemory); + return DataHandle( + ArrayBufferContents::AllocateMemoryOrNull(size, policy), size, + [](void* buffer, size_t, void*) { FreeMemory(buffer); }, nullptr); } ArrayBufferContents::DataHolder::DataHolder() - : data_(nullptr, 0, FreeMemory), + : data_(nullptr, 0, [](void*, size_t, void*) {}, nullptr), is_shared_(kNotShared), has_registered_external_allocation_(false) {}
diff --git a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h index 809229c..759a8df4 100644 --- a/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h +++ b/third_party/blink/renderer/platform/wtf/typed_arrays/array_buffer_contents.h
@@ -50,7 +50,7 @@ // ArrayBufferContents::FreeMemory as the DataDeleter. Most clients would want // to use ArrayBufferContents::CreateDataHandle, which allocates memory and // specifies the correct deleter. - using DataDeleter = void (*)(void* data); + using DataDeleter = void (*)(void* data, size_t length, void* info); enum class AllocationKind { kNormal, kReservation }; @@ -58,25 +58,31 @@ DISALLOW_COPY_AND_ASSIGN(DataHandle); public: - DataHandle(void* data, size_t length, DataDeleter deleter) + DataHandle(void* data, + size_t length, + DataDeleter deleter, + void* deleter_info) : allocation_base_(data), allocation_length_(length), data_(data), data_length_(length), kind_(AllocationKind::kNormal), - deleter_(deleter) {} + deleter_(deleter), + deleter_info_(deleter_info) {} DataHandle(void* allocation_base, size_t allocation_length, void* data, size_t data_length, AllocationKind kind, - DataDeleter deleter) + DataDeleter deleter, + void* deleter_info) : allocation_base_(allocation_base), allocation_length_(allocation_length), data_(data), data_length_(data_length), kind_(kind), - deleter_(deleter) { + deleter_(deleter), + deleter_info_(deleter_info) { DCHECK(reinterpret_cast<uintptr_t>(allocation_base_) <= reinterpret_cast<uintptr_t>(data_)); DCHECK(reinterpret_cast<uintptr_t>(data_) + data_length_ <= @@ -96,7 +102,7 @@ switch (kind_) { case AllocationKind::kNormal: DCHECK(deleter_); - deleter_(data_); + deleter_(data_, data_length_, deleter_info_); return; case AllocationKind::kReservation: base::FreePages(allocation_base_, allocation_length_); @@ -112,6 +118,7 @@ data_length_ = other.data_length_; kind_ = other.kind_; deleter_ = other.deleter_; + deleter_info_ = other.deleter_info_; other.allocation_base_ = nullptr; return *this; } @@ -137,6 +144,7 @@ ArrayBufferContents::AllocationKind kind_; DataDeleter deleter_; + void* deleter_info_; }; enum InitializationPolicy { kZeroInitialize, kDontInitialize };
diff --git a/third_party/blink/tools/audit_non_blink_usage.py b/third_party/blink/tools/audit_non_blink_usage.py index 7b7df05..1c6f3ff3 100755 --- a/third_party/blink/tools/audit_non_blink_usage.py +++ b/third_party/blink/tools/audit_non_blink_usage.py
@@ -286,6 +286,13 @@ ], }, { + 'paths': ['third_party/blink/renderer/core/fetch/data_consumer_handle_test_util.cc'], + 'allowed': [ + # The existing code already contains gin::IsolateHolder. + 'gin::IsolateHolder', + ], + }, + { 'paths': ['third_party/blink/renderer/core/paint'], 'allowed': [ # cc painting types.
diff --git a/third_party/feed/README.chromium b/third_party/feed/README.chromium index 434cdf7..d6140ef 100644 --- a/third_party/feed/README.chromium +++ b/third_party/feed/README.chromium
@@ -2,7 +2,7 @@ Short name: feed URL: https://chromium.googlesource.com/feed Version: 0 -Revision: a4e91c7238e329ad11e48b068fe3b1e935c0de9b +Revision: 831b51c0ac199fea3278ceb9de361c22486da935 License: Apache 2.0 License File: LICENSE Security Critical: yes
diff --git a/third_party/feed/java_sources.gni b/third_party/feed/java_sources.gni index bb0fdf11..9fd7083 100644 --- a/third_party/feed/java_sources.gni +++ b/third_party/feed/java_sources.gni
@@ -8,6 +8,7 @@ "src/src/main/java/com/google/android/libraries/feed/api/actionmanager/ActionManager.java", "src/src/main/java/com/google/android/libraries/feed/api/actionmanager/ActionReader.java", "src/src/main/java/com/google/android/libraries/feed/api/actionparser/ActionParser.java", + "src/src/main/java/com/google/android/libraries/feed/api/actionparser/ActionParserFactory.java", "src/src/main/java/com/google/android/libraries/feed/api/common/DismissActionWithSemanticProperties.java", "src/src/main/java/com/google/android/libraries/feed/api/common/MutationContext.java", "src/src/main/java/com/google/android/libraries/feed/api/common/PayloadWithId.java", @@ -75,6 +76,7 @@ "src/src/main/java/com/google/android/libraries/feed/basicstream/internal/viewholders/HeaderViewHolder.java", "src/src/main/java/com/google/android/libraries/feed/basicstream/internal/viewholders/NoContentViewHolder.java", "src/src/main/java/com/google/android/libraries/feed/basicstream/internal/viewholders/PietViewHolder.java", + "src/src/main/java/com/google/android/libraries/feed/basicstream/internal/viewholders/SwipeNotifier.java", "src/src/main/java/com/google/android/libraries/feed/basicstream/internal/viewholders/SwipeableViewHolder.java", "src/src/main/java/com/google/android/libraries/feed/basicstream/internal/viewholders/ViewHolderType.java", "src/src/main/java/com/google/android/libraries/feed/basicstream/internal/viewholders/ZeroStateViewHolder.java", @@ -88,6 +90,7 @@ "src/src/main/java/com/google/android/libraries/feed/common/concurrent/TaskQueue.java", "src/src/main/java/com/google/android/libraries/feed/common/functional/Committer.java", "src/src/main/java/com/google/android/libraries/feed/common/functional/Consumer.java", + "src/src/main/java/com/google/android/libraries/feed/common/functional/Function.java", "src/src/main/java/com/google/android/libraries/feed/common/functional/Predicate.java", "src/src/main/java/com/google/android/libraries/feed/common/functional/SettableSupplier.java", "src/src/main/java/com/google/android/libraries/feed/common/functional/Supplier.java", @@ -102,7 +105,8 @@ "src/src/main/java/com/google/android/libraries/feed/common/ui/LayoutUtils.java", "src/src/main/java/com/google/android/libraries/feed/feedactionmanager/FeedActionManagerImpl.java", "src/src/main/java/com/google/android/libraries/feed/feedactionparser/FeedActionParser.java", - "src/src/main/java/com/google/android/libraries/feed/feedactionparser/internal/PietFeedActionPaylaodRetriever.java", + "src/src/main/java/com/google/android/libraries/feed/feedactionparser/FeedActionParserFactory.java", + "src/src/main/java/com/google/android/libraries/feed/feedactionparser/internal/PietFeedActionPayloadRetriever.java", "src/src/main/java/com/google/android/libraries/feed/feedactionreader/FeedActionReader.java", "src/src/main/java/com/google/android/libraries/feed/feedapplifecyclelistener/FeedAppLifecycleListener.java", "src/src/main/java/com/google/android/libraries/feed/feedapplifecyclelistener/FeedLifecycleListener.java", @@ -117,6 +121,9 @@ "src/src/main/java/com/google/android/libraries/feed/feedmodelprovider/internal/UpdatableModelFeature.java", "src/src/main/java/com/google/android/libraries/feed/feedmodelprovider/internal/UpdatableModelToken.java", "src/src/main/java/com/google/android/libraries/feed/feedprotocoladapter/FeedProtocolAdapter.java", + "src/src/main/java/com/google/android/libraries/feed/feedprotocoladapter/internal/transformers/ContentDataOperationTransformer.java", + "src/src/main/java/com/google/android/libraries/feed/feedprotocoladapter/internal/transformers/DataOperationTransformer.java", + "src/src/main/java/com/google/android/libraries/feed/feedprotocoladapter/internal/transformers/FeatureDataOperationTransformer.java", "src/src/main/java/com/google/android/libraries/feed/feedrequestmanager/FeedRequestManager.java", "src/src/main/java/com/google/android/libraries/feed/feedsessionmanager/FeedSessionManager.java", "src/src/main/java/com/google/android/libraries/feed/feedsessionmanager/FeedSessionManagerFactory.java",
diff --git a/third_party/feed/proto_sources.gni b/third_party/feed/proto_sources.gni index b5c4743..afbe8fc 100644 --- a/third_party/feed/proto_sources.gni +++ b/third_party/feed/proto_sources.gni
@@ -22,6 +22,7 @@ "src/src/main/proto/search/now/ui/piet/shadows.proto", "src/src/main/proto/search/now/ui/piet/styles.proto", "src/src/main/proto/search/now/ui/piet/text.proto", + "src/src/main/proto/search/now/ui/stream/stream_offline_extension.proto", "src/src/main/proto/search/now/ui/stream/stream_structure.proto", "src/src/main/proto/search/now/ui/stream/stream_swipe_extension.proto", "src/src/main/proto/search/now/wire/feed/action_type.proto",
diff --git a/third_party/gvr-android-keyboard/OWNERS b/third_party/gvr-android-keyboard/OWNERS index 60abf2a..de83b91 100644 --- a/third_party/gvr-android-keyboard/OWNERS +++ b/third_party/gvr-android-keyboard/OWNERS
@@ -1,5 +1,4 @@ acondor@chromium.org -asimjour@chromium.org vollick@chromium.org # TEAM: xr-dev@chromium.org
diff --git a/third_party/robolectric/custom_asynctask/java/src/org/chromium/base/test/asynctask/ShadowAsyncTask.java b/third_party/robolectric/custom_asynctask/java/src/org/chromium/base/test/asynctask/ShadowAsyncTask.java index d440264d..e4443e7 100644 --- a/third_party/robolectric/custom_asynctask/java/src/org/chromium/base/test/asynctask/ShadowAsyncTask.java +++ b/third_party/robolectric/custom_asynctask/java/src/org/chromium/base/test/asynctask/ShadowAsyncTask.java
@@ -88,9 +88,7 @@ return future.get(timeout, unit); } - @SuppressWarnings("unchecked") - @Implementation - public AsyncTask<Result> execute() { + public AsyncTask<Result> executeInRobolectric() { status = AsyncTask.Status.RUNNING; getBridge().onPreExecute();
diff --git a/third_party/tlslite/patches/tls13_intolerance.patch b/third_party/tlslite/patches/tls13_intolerance.patch index 6f19571..ef50fed 100644 --- a/third_party/tlslite/patches/tls13_intolerance.patch +++ b/third_party/tlslite/patches/tls13_intolerance.patch
@@ -6,7 +6,7 @@ signed_cert_timestamps = 18 # RFC 6962 extended_master_secret = 23 # RFC 7627 token_binding = 24 # draft-ietf-tokbind-negotiation -+ supported_versions = 43 # draft-ietf-tls-tls13-18 ++ supported_versions = 43 # RFC 8446 tack = 0xF300 supports_npn = 13172 channel_id = 30032
diff --git a/third_party/tlslite/tlslite/constants.py b/third_party/tlslite/tlslite/constants.py index 8fb75d0..bac05c2f 100644 --- a/third_party/tlslite/tlslite/constants.py +++ b/third_party/tlslite/tlslite/constants.py
@@ -58,7 +58,7 @@ signed_cert_timestamps = 18 # RFC 6962 extended_master_secret = 23 # RFC 7627 token_binding = 24 # draft-ietf-tokbind-negotiation - supported_versions = 43 # draft-ietf-tls-tls13-18 + supported_versions = 43 # RFC 8446 tack = 0xF300 supports_npn = 13172 channel_id = 30032
diff --git a/tools/code_coverage/coverage_utils.py b/tools/code_coverage/coverage_utils.py index db06248e..09b1e226 100644 --- a/tools/code_coverage/coverage_utils.py +++ b/tools/code_coverage/coverage_utils.py
@@ -242,7 +242,9 @@ """Initializes CoverageReportPostProcessor object.""" # Caller provided parameters. self.output_dir = output_dir - self.src_root_dir = src_root_dir.rstrip(os.sep) + self.src_root_dir = os.path.normpath(GetFullPath(src_root_dir)) + if not self.src_root_dir.endswith(os.sep): + self.src_root_dir += os.sep self.summary_data = json.loads(summary_data) assert len(self.summary_data['data']) == 1 self.no_component_view = no_component_view @@ -318,7 +320,7 @@ while True: per_directory_coverage_summary[parent_dir].AddSummary(summary) - if parent_dir == self.src_root_dir: + if os.path.normpath(parent_dir) == os.path.normpath(self.src_root_dir): break parent_dir = os.path.dirname(parent_dir) @@ -457,7 +459,7 @@ per_file_coverage_summary = {} for file_coverage_data in files_coverage_data: file_path = file_coverage_data['filename'] - assert file_path.startswith(self.src_root_dir + os.sep), ( + assert file_path.startswith(self.src_root_dir), ( 'File path "%s" in coverage summary is outside source checkout.' % file_path)
diff --git a/tools/metrics/histograms/enums.xml b/tools/metrics/histograms/enums.xml index dcc5612..361284c 100644 --- a/tools/metrics/histograms/enums.xml +++ b/tools/metrics/histograms/enums.xml
@@ -3096,6 +3096,9 @@ <int value="2" label="Invalid argument"/> <int value="3" label="Invalid ID"/> <int value="4" label="Storage error"/> + <int value="5" label="Service Worker unavailable"/> + <int value="6" label="Quota exceeded"/> + <int value="7" label="Permission denied"/> </enum> <enum name="BackgroundFetchEventDispatchResult"> @@ -14242,6 +14245,7 @@ <int value="465" label="PowerSmartDimEnabled"/> <int value="466" label="CoalesceH2ConnectionsWithClientCertificatesForHosts"/> <int value="467" label="NetBiosDiscoveryEnabled"/> + <int value="468" label="WebAppInstallForceList"/> </enum> <enum name="EnterprisePolicyInvalidations"> @@ -19820,6 +19824,10 @@ <int value="2525" label="V8MediaStreamTrack_ContentHint_AttributeGetter"/> <int value="2526" label="V8MediaStreamTrack_ContentHint_AttributeSetter"/> <int value="2527" label="V8IDBFactory_Open_Method"/> + <int value="2528" label="EvaluateScriptMovedBetweenDocuments"/> + <int value="2529" label="ReportingObserver"/> + <int value="2530" label="DeprecationReport"/> + <int value="2531" label="InterventionReport"/> </enum> <enum name="FeedbackSource"> @@ -27706,6 +27714,7 @@ <int value="1" label="Load failed - Invalid path"/> <int value="2" label="Load failed - File read error"/> <int value="3" label="Load failed - Ruleset verification error"/> + <int value="4" label="Load failed - Version mismatch"/> </enum> <enum name="LoadType">
diff --git a/tools/perf/benchmarks/loading.py b/tools/perf/benchmarks/loading.py index 9de446e..61caa2c 100644 --- a/tools/perf/benchmarks/loading.py +++ b/tools/perf/benchmarks/loading.py
@@ -18,6 +18,11 @@ options = {'pageset_repeat': 2} + def SetExtraBrowserOptions(self, options): + options.AppendExtraBrowserArgs([ + '--enable-features=TracingPerfettoBackend', + ]) + def CreateCoreTimelineBasedMeasurementOptions(self): tbm_options = timeline_based_measurement.Options() loading_metrics_category.AugmentOptionsForLoadingMetrics(tbm_options)
diff --git a/tools/perf/contrib/blink_layoutng_perf/OWNERS b/tools/perf/contrib/blink_layoutng_perf/OWNERS new file mode 100644 index 0000000..d80a064 --- /dev/null +++ b/tools/perf/contrib/blink_layoutng_perf/OWNERS
@@ -0,0 +1,2 @@ +eae@chromium.org +cbiesinger@chromium.org
diff --git a/tools/perf/contrib/blink_layoutng_perf/__init__.py b/tools/perf/contrib/blink_layoutng_perf/__init__.py new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/tools/perf/contrib/blink_layoutng_perf/__init__.py
diff --git a/tools/perf/contrib/blink_layoutng_perf/blink_layoutng_perf.py b/tools/perf/contrib/blink_layoutng_perf/blink_layoutng_perf.py new file mode 100644 index 0000000..9c799cd49b --- /dev/null +++ b/tools/perf/contrib/blink_layoutng_perf/blink_layoutng_perf.py
@@ -0,0 +1,19 @@ +# Copyright 2018 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. +from benchmarks import blink_perf +from telemetry import benchmark + +# pylint: disable=protected-access +@benchmark.Info(emails=['cbiesinger@chromium.org'], + documentation_url='https://bit.ly/blink-perf-benchmarks') +class BlinkPerfLayoutNg(blink_perf._BlinkPerfBenchmark): + subdir = 'layout' + + def SetExtraBrowserOptions(self, options): + super(BlinkPerfLayoutNg, self).SetExtraBrowserOptions(options) + options.AppendExtraBrowserArgs('--enable-blink-features=LayoutNG') + + @classmethod + def Name(cls): + return 'blink_perf.layout_ng'
diff --git a/tools/perf/core/perf_benchmark.py b/tools/perf/core/perf_benchmark.py index 7a8ba55..77722d2 100644 --- a/tools/perf/core/perf_benchmark.py +++ b/tools/perf/core/perf_benchmark.py
@@ -104,12 +104,6 @@ # with the test results. options.AppendExtraBrowserArgs( '--disable-gpu-process-for-dx12-vulkan-info-collection') - - # Switch Chrome to use Perfetto instead of TraceLog as the tracing backend, - # needed until the feature gets turned on by default everywhere. - if options.browser_type != 'reference': - options.AppendExtraBrowserArgs( - '--enable-features=TracingPerfettoBackend') self.SetExtraBrowserOptions(options) @staticmethod
diff --git a/tools/perf/expectations.config b/tools/perf/expectations.config index 2dc99c86..924c340 100644 --- a/tools/perf/expectations.config +++ b/tools/perf/expectations.config
@@ -181,14 +181,6 @@ crbug.com/873011 [ Android_Webview ] rasterize_and_record_micro.top_25/file://static_top_25/yahoonews.html [ Skip ] crbug.com/865400 [ Pixel_2 ] rasterize_and_record_micro.top_25/file://static_top_25/yahoonews.html [ Skip ] -# Benchmark: smoothness.tough_pinch_zoom_cases -crbug.com/875859 [ Nexus_5X ] smoothness.tough_pinch_zoom_cases/youtube_pinch_2018 [ Skip ] -crbug.com/875859 [ Pixel_2 ] smoothness.tough_pinch_zoom_cases/youtube_pinch_2018 [ Skip ] - -# Benchmark: smoothness.gpu_rasterization.tough_pinch_zoom_cases -crbug.com/875859 [ Nexus_5X ] smoothness.gpu_rasterization.tough_pinch_zoom_cases/youtube_pinch_2018 [ Skip ] -crbug.com/875859 [ Pixel_2 ] smoothness.gpu_rasterization.tough_pinch_zoom_cases/youtube_pinch_2018 [ Skip ] - # Benchmark: system_health.common_desktop crbug.com/828917 [ Mac ] system_health.common_desktop/multitab:misc:typical24 [ Skip ] crbug.com/874803 [ Win_10 ] system_health.common_desktop/multitab:misc:typical24 [ Skip ] @@ -271,7 +263,6 @@ crbug.com/805934 [ Mac_10.12 ] v8.browsing_desktop/browse:tech:discourse_infinite_scroll [ Skip ] crbug.com/839470 [ Win ] v8.browsing_desktop/browse:social:twitter_infinite_scroll [ Skip ] crbug.com/854239 [ Linux ] v8.browsing_desktop/browse:social:twitter_infinite_scroll [ Skip ] -crbug.com/864718 [ Linux ] v8.browsing_desktop/browse:news:flipboard [ Skip ] crbug.com/875159 [ Win_10 ] v8.browsing_desktop/browse:social:facebook_infinite_scroll [ Skip ] crbug.com/875159 [ Win_10 ] v8.browsing_desktop/browse:media:imgur [ Skip ] crbug.com/875159 [ Win_10 ] v8.browsing_desktop/browse:media:tumblr [ Skip ]
diff --git a/ui/accessibility/platform/ax_platform_node_auralinux.cc b/ui/accessibility/platform/ax_platform_node_auralinux.cc index 8218efe..08941cb0 100644 --- a/ui/accessibility/platform/ax_platform_node_auralinux.cc +++ b/ui/accessibility/platform/ax_platform_node_auralinux.cc
@@ -754,6 +754,67 @@ nullptr, nullptr}; // +// AtkText interface. +// + +static gchar* ax_platform_node_auralinux_get_text(AtkText* atk_text, + gint start_offset, + gint end_offset) { + AtkObject* atk_object = ATK_OBJECT(atk_text); + ui::AXPlatformNodeAuraLinux* obj = + AtkObjectToAXPlatformNodeAuraLinux(atk_object); + if (!obj) + return nullptr; + + std::string text = obj->GetTextForATK(); + if (end_offset < 0) + end_offset = g_utf8_strlen(text.c_str(), -1); + + return g_utf8_substring(text.c_str(), start_offset, end_offset); +} + +static gint ax_platform_node_auralinux_get_character_count(AtkText* atk_text) { + AtkObject* atk_object = ATK_OBJECT(atk_text); + ui::AXPlatformNodeAuraLinux* obj = + AtkObjectToAXPlatformNodeAuraLinux(atk_object); + if (!obj) + return 0; + + std::string text = obj->GetTextForATK(); + return g_utf8_strlen(text.c_str(), -1); +} + +static AtkAttributeSet* ax_platform_node_auralinux_get_run_attributes( + AtkText* atk_text, + gint offset, + gint* start_offset, + gint* end_offset) { + *start_offset = -1; + *end_offset = -1; + + AtkObject* atk_object = ATK_OBJECT(atk_text); + ui::AXPlatformNodeAuraLinux* obj = + AtkObjectToAXPlatformNodeAuraLinux(atk_object); + if (!obj) + return nullptr; + + *start_offset = 0; + *end_offset = ax_platform_node_auralinux_get_character_count(atk_text); + + return nullptr; +} + +static void ax_text_interface_base_init(AtkTextIface* iface) { + iface->get_text = ax_platform_node_auralinux_get_text; + iface->get_run_attributes = ax_platform_node_auralinux_get_run_attributes; + iface->get_character_count = ax_platform_node_auralinux_get_character_count; +} + +static const GInterfaceInfo TextInfo = { + reinterpret_cast<GInterfaceInitFunc>(ax_text_interface_base_init), nullptr, + nullptr}; + +// // The rest of the AXPlatformNodeAtk code, not specific to one // of the Atk* interfaces. // @@ -879,6 +940,10 @@ if (role == ATK_ROLE_LINK) interface_mask |= 1 << ATK_HYPERLINK_INTERFACE; + // Text interface + if (role == ATK_ROLE_TEXT) + interface_mask |= 1 << ATK_TEXT_INTERFACE; + return interface_mask; } @@ -916,6 +981,8 @@ if (interface_mask_ & (1 << ATK_HYPERLINK_INTERFACE)) g_type_add_interface_static(type, ATK_TYPE_HYPERLINK_IMPL, &HyperlinkImplInfo); + if (interface_mask_ & (1 << ATK_TEXT_INTERFACE)) + g_type_add_interface_static(type, ATK_TYPE_TEXT, &TextInfo); return type; } @@ -1732,4 +1799,12 @@ *attributes = PrependAtkAttributeToAtkAttributeSet(name, value, *attributes); } +std::string AXPlatformNodeAuraLinux::GetTextForATK() { + // Special case allows us to get text even in non-HTML case, e.g. browser UI. + if (IsPlainTextField()) + return GetStringAttribute(ax::mojom::StringAttribute::kValue); + + return AXPlatformNodeBase::GetText(); +} + } // namespace ui
diff --git a/ui/accessibility/platform/ax_platform_node_auralinux.h b/ui/accessibility/platform/ax_platform_node_auralinux.h index f7be935..9159e2a3 100644 --- a/ui/accessibility/platform/ax_platform_node_auralinux.h +++ b/ui/accessibility/platform/ax_platform_node_auralinux.h
@@ -86,6 +86,8 @@ void Init(AXPlatformNodeDelegate* delegate) override; int GetIndexInParent() override; + std::string GetTextForATK(); + protected: void AddAttributeToList(const char* name, const char* value,
diff --git a/ui/accessibility/platform/ax_platform_node_auralinux_unittest.cc b/ui/accessibility/platform/ax_platform_node_auralinux_unittest.cc index 7dde4be7..c4dd25b 100644 --- a/ui/accessibility/platform/ax_platform_node_auralinux_unittest.cc +++ b/ui/accessibility/platform/ax_platform_node_auralinux_unittest.cc
@@ -74,6 +74,18 @@ atk_attribute_set_free(attributes); } +static void SetStringAttributeOnNode( + AXNode* ax_node, + ax::mojom::StringAttribute attribute, + const char* attribute_value, + base::Optional<ax::mojom::Role> role = base::nullopt) { + AXNodeData new_data = AXNodeData(); + new_data.role = role.value_or(ax::mojom::Role::kApplication); + new_data.id = ax_node->data().id; + new_data.AddStringAttribute(attribute, attribute_value); + ax_node->SetData(new_data); +} + static void TestAtkObjectIntAttribute( AXNode* ax_node, AtkObject* atk_object, @@ -121,11 +133,7 @@ }; for (unsigned i = 0; i < G_N_ELEMENTS(tests); i++) { - AXNodeData new_data = AXNodeData(); - new_data.role = role.value_or(ax::mojom::Role::kApplication); - new_data.id = ax_node->data().id; - new_data.AddStringAttribute(mojom_attribute, tests[i]); - ax_node->SetData(new_data); + SetStringAttributeOnNode(ax_node, mojom_attribute, tests[i], role); EnsureAtkObjectHasAttributeWithValue(atk_object, attribute_name, tests[i]); } } @@ -849,4 +857,52 @@ g_object_unref(root_obj); } +// +// AtkText interface +// + +TEST_F(AXPlatformNodeAuraLinuxTest, TestAtkText) { + AXNodeData root_data; + root_data.id = 1; + root_data.role = ax::mojom::Role::kStaticText; + Init(root_data); + + AtkObject* root_atk_object(GetRootAtkObject()); + ASSERT_TRUE(ATK_IS_OBJECT(root_atk_object)); + ASSERT_TRUE(ATK_IS_TEXT(root_atk_object)); + g_object_ref(root_atk_object); + + AtkText* atk_text = ATK_TEXT(root_atk_object); + + auto verify_atk_text_contents = [&](const char* expected_text, + int start_offset, int end_offset) { + gchar* text = atk_text_get_text(atk_text, start_offset, end_offset); + EXPECT_STREQ(expected_text, text); + g_free(text); + }; + + AXNode* root = GetRootNode(); + SetStringAttributeOnNode(root, ax::mojom::StringAttribute::kName, "Text", + ax::mojom::Role::kStaticText); + verify_atk_text_contents("Text", 0, -1); + + EXPECT_EQ(4, atk_text_get_character_count(atk_text)); + + SetStringAttributeOnNode(root, ax::mojom::StringAttribute::kName, + "Longer String", ax::mojom::Role::kStaticText); + verify_atk_text_contents("Longer String", 0, -1); + verify_atk_text_contents("Longer ", 0, 7); + verify_atk_text_contents("String", 7, -1); + EXPECT_EQ(13, atk_text_get_character_count(atk_text)); + + SetStringAttributeOnNode(root, ax::mojom::StringAttribute::kName, + "\xE2\x98\xBA", ax::mojom::Role::kStaticText); + verify_atk_text_contents("\xE2\x98\xBA", 0, -1); + verify_atk_text_contents("\xE2\x98\xBA", 0, 1); + + EXPECT_EQ(1, atk_text_get_character_count(atk_text)); + + g_object_unref(root_atk_object); +} + } // namespace ui
diff --git a/ui/accessibility/platform/ax_platform_node_base.cc b/ui/accessibility/platform/ax_platform_node_base.cc index 7b13246..cae47b1 100644 --- a/ui/accessibility/platform/ax_platform_node_base.cc +++ b/ui/accessibility/platform/ax_platform_node_base.cc
@@ -294,11 +294,11 @@ GetData().HasState(ax::mojom::State::kRichlyEditable); } -base::string16 AXPlatformNodeBase::GetInnerText() { +std::string AXPlatformNodeBase::GetInnerText() { if (IsTextOnlyObject()) - return GetString16Attribute(ax::mojom::StringAttribute::kName); + return GetStringAttribute(ax::mojom::StringAttribute::kName); - base::string16 text; + std::string text; for (int i = 0; i < GetChildCount(); ++i) { gfx::NativeViewAccessible child_accessible = ChildAtIndex(i); AXPlatformNodeBase* child = FromNativeViewAccessible(child_accessible); @@ -556,7 +556,7 @@ GetIntAttribute(ax::mojom::IntAttribute::kScrollYMax); } -base::string16 AXPlatformNodeBase::GetText() { +std::string AXPlatformNodeBase::GetText() { return GetInnerText(); } @@ -575,7 +575,7 @@ // value to be set in text fields with rich content, even though the same // information is available on the children. if (value.empty() && IsRichTextField()) - return GetInnerText(); + return base::UTF8ToUTF16(GetInnerText()); return value; }
diff --git a/ui/accessibility/platform/ax_platform_node_base.h b/ui/accessibility/platform/ax_platform_node_base.h index 10d6b1c..447d329 100644 --- a/ui/accessibility/platform/ax_platform_node_base.h +++ b/ui/accessibility/platform/ax_platform_node_base.h
@@ -176,7 +176,7 @@ bool HasFocus(); - virtual base::string16 GetText(); + virtual std::string GetText(); virtual base::string16 GetValue(); @@ -212,7 +212,7 @@ // |GetInnerText| recursively includes all the text from descendants such as // text found in any embedded object. - base::string16 GetInnerText(); + std::string GetInnerText(); // Cast a gfx::NativeViewAccessible to an AXPlatformNodeBase if it is one, // or return NULL if it's not an instance of this class.
diff --git a/ui/accessibility/platform/ax_platform_node_mac.mm b/ui/accessibility/platform/ax_platform_node_mac.mm index 5e28513..7885fba 100644 --- a/ui/accessibility/platform/ax_platform_node_mac.mm +++ b/ui/accessibility/platform/ax_platform_node_mac.mm
@@ -389,13 +389,12 @@ // the inner text. NSString* name = [self getStringAttribute:ax::mojom::StringAttribute::kName]; - return [name length] > 0 ? name - : base::SysUTF16ToNSString(node_->GetText()); + return [name length] > 0 ? name : base::SysUTF8ToNSString(node_->GetText()); } else if (eventType == ax::mojom::Event::kLiveRegionChanged && node_->GetData().HasStringAttribute( ax::mojom::StringAttribute::kContainerLiveStatus)) { // Live regions announce their inner text. - return base::SysUTF16ToNSString(node_->GetText()); + return base::SysUTF8ToNSString(node_->GetText()); } // Only alerts and live regions have something to announce. return nil;
diff --git a/ui/accessibility/platform/ax_platform_node_win.cc b/ui/accessibility/platform/ax_platform_node_win.cc index acbea7d3..eff7262 100644 --- a/ui/accessibility/platform/ax_platform_node_win.cc +++ b/ui/accessibility/platform/ax_platform_node_win.cc
@@ -536,9 +536,9 @@ return -1; } -base::string16 AXPlatformNodeWin::GetText() { +base::string16 AXPlatformNodeWin::GetTextAsString16() { if (IsChildOfLeaf()) - return AXPlatformNodeBase::GetText(); + return base::UTF8ToUTF16(AXPlatformNodeBase::GetText()); return hypertext_.hypertext; } @@ -975,7 +975,7 @@ } if (result.empty() && target->IsRichTextField()) - result = target->GetInnerText(); + result = base::UTF8ToUTF16(target->GetInnerText()); *value = SysAllocString(result.c_str()); DCHECK(*value); @@ -5653,12 +5653,12 @@ // Special case allows us to get text even in non-HTML case, e.g. browser UI. if (IsPlainTextField()) return GetString16Attribute(ax::mojom::StringAttribute::kValue); - return GetText(); + return GetTextAsString16(); } void AXPlatformNodeWin::HandleSpecialTextOffset(LONG* offset) { if (*offset == IA2_TEXT_OFFSET_LENGTH) { - *offset = static_cast<LONG>(GetText().length()); + *offset = static_cast<LONG>(GetTextAsString16().length()); } else if (*offset == IA2_TEXT_OFFSET_CARET) { int selection_start, selection_end; GetSelectionOffsets(&selection_start, &selection_end); @@ -5851,7 +5851,7 @@ FromNativeViewAccessible(delegate_->ChildAtIndex(i))); DCHECK(sibling); if (sibling->IsTextOnlyObject()) - hypertext_offset += (int32_t)sibling->GetText().size(); + hypertext_offset += (int32_t)sibling->GetTextAsString16().size(); else ++hypertext_offset; } @@ -5948,7 +5948,7 @@ if (endpoint_index_in_common_parent < index_in_common_parent) return 0; if (endpoint_index_in_common_parent > index_in_common_parent) - return (int32_t)GetText().size(); + return (int32_t)GetTextAsString16().size(); NOTREACHED(); return -1;
diff --git a/ui/accessibility/platform/ax_platform_node_win.h b/ui/accessibility/platform/ax_platform_node_win.h index 451b4c4..e88db88 100644 --- a/ui/accessibility/platform/ax_platform_node_win.h +++ b/ui/accessibility/platform/ax_platform_node_win.h
@@ -285,9 +285,13 @@ // AXPlatformNodeBase overrides. void Destroy() override; int GetIndexInParent() override; - base::string16 GetText() override; base::string16 GetValue() override; + // For the moment, we add a special version of this method which returns a + // base::string16, but once the hypertext generation code is shared between + // platforms we can just override AXPlatformNodeBase::GetText(). + base::string16 GetTextAsString16(); + // // IAccessible methods. //
diff --git a/ui/aura/mus/input_method_mus.cc b/ui/aura/mus/input_method_mus.cc index 7d1f500..030a132d 100644 --- a/ui/aura/mus/input_method_mus.cc +++ b/ui/aura/mus/input_method_mus.cc
@@ -114,14 +114,21 @@ void InputMethodMus::OnInputLocaleChanged() { // TODO(moshayedi): crbug.com/637418. Not supported in ChromeOS. Investigate // whether we want to support this or not. + NOTIMPLEMENTED_LOG_ONCE(); } bool InputMethodMus::IsCandidatePopupOpen() const { // TODO(moshayedi): crbug.com/637416. Implement this properly when we have a // mean for displaying candidate list popup. + NOTIMPLEMENTED_LOG_ONCE(); return false; } +void InputMethodMus::ShowVirtualKeyboardIfEnabled() { + if (input_method_) + input_method_->ShowVirtualKeyboardIfEnabled(); +} + ui::EventDispatchDetails InputMethodMus::SendKeyEventToInputMethod( const ui::KeyEvent& event, EventResultCallback ack_callback) {
diff --git a/ui/aura/mus/input_method_mus.h b/ui/aura/mus/input_method_mus.h index f47be86..207aa202 100644 --- a/ui/aura/mus/input_method_mus.h +++ b/ui/aura/mus/input_method_mus.h
@@ -47,6 +47,7 @@ void CancelComposition(const ui::TextInputClient* client) override; void OnInputLocaleChanged() override; bool IsCandidatePopupOpen() const override; + void ShowVirtualKeyboardIfEnabled() override; private: friend class InputMethodMusTestApi;
diff --git a/ui/aura/mus/input_method_mus_unittest.cc b/ui/aura/mus/input_method_mus_unittest.cc index c3c1bd6..c448bff6a 100644 --- a/ui/aura/mus/input_method_mus_unittest.cc +++ b/ui/aura/mus/input_method_mus_unittest.cc
@@ -57,6 +57,9 @@ process_key_event_callbacks_.push_back(std::move(callback)); } void CancelComposition() override { was_cancel_composition_called_ = true; } + void ShowVirtualKeyboardIfEnabled() override { + was_show_virtual_keyboard_if_enabled_called_ = true; + } bool was_on_text_input_type_changed_called() { return was_on_text_input_type_changed_called_; @@ -70,10 +73,15 @@ return was_cancel_composition_called_; } + bool was_show_virtual_keyboard_if_enabled_called() { + return was_show_virtual_keyboard_if_enabled_called_; + } + private: bool was_on_text_input_type_changed_called_ = false; bool was_on_caret_bounds_changed_called_ = false; bool was_cancel_composition_called_ = false; + bool was_show_virtual_keyboard_if_enabled_called_ = false; ProcessKeyEventCallbacks process_key_event_callbacks_; DISALLOW_COPY_AND_ASSIGN(TestInputMethod); @@ -298,4 +306,15 @@ EXPECT_FALSE(test_input_method.was_cancel_composition_called()); } +// Calling ShowVirtualKeyboardIfEnabled should notify the mus side. +TEST_F(InputMethodMusTest, ShowVirtualKeyboardIfEnabled) { + TestInputMethodDelegate input_method_delegate; + InputMethodMus input_method_mus(&input_method_delegate, nullptr); + TestInputMethod test_input_method; + InputMethodMusTestApi::SetInputMethod(&input_method_mus, &test_input_method); + EXPECT_FALSE(test_input_method.was_show_virtual_keyboard_if_enabled_called()); + input_method_mus.ShowVirtualKeyboardIfEnabled(); + EXPECT_TRUE(test_input_method.was_show_virtual_keyboard_if_enabled_called()); +} + } // namespace aura
diff --git a/ui/base/ime/input_method_base.cc b/ui/base/ime/input_method_base.cc index cf50411..df1e94c 100644 --- a/ui/base/ime/input_method_base.cc +++ b/ui/base/ime/input_method_base.cc
@@ -142,9 +142,11 @@ InputMethodKeyboardController* InputMethodBase::GetInputMethodKeyboardController() { - if (!keyboard_controller_) + if (!keyboard_controller_) { + NOTIMPLEMENTED() << "Using InputMethodKeyboardControllerStub"; keyboard_controller_ = std::make_unique<InputMethodKeyboardControllerStub>(); + } return keyboard_controller_.get(); }
diff --git a/ui/file_manager/file_manager/common/images/icon128.png b/ui/file_manager/file_manager/common/images/icon128.png index c5ed558..9e1f9a35 100644 --- a/ui/file_manager/file_manager/common/images/icon128.png +++ b/ui/file_manager/file_manager/common/images/icon128.png Binary files differ
diff --git a/ui/file_manager/file_manager/common/images/icon16.png b/ui/file_manager/file_manager/common/images/icon16.png index 3884666..58d18283 100644 --- a/ui/file_manager/file_manager/common/images/icon16.png +++ b/ui/file_manager/file_manager/common/images/icon16.png Binary files differ
diff --git a/ui/file_manager/file_manager/common/images/icon192.png b/ui/file_manager/file_manager/common/images/icon192.png new file mode 100644 index 0000000..111ec9f --- /dev/null +++ b/ui/file_manager/file_manager/common/images/icon192.png Binary files differ
diff --git a/ui/file_manager/file_manager/common/images/icon256.png b/ui/file_manager/file_manager/common/images/icon256.png deleted file mode 100644 index 631c951..0000000 --- a/ui/file_manager/file_manager/common/images/icon256.png +++ /dev/null Binary files differ
diff --git a/ui/file_manager/file_manager/common/images/icon32.png b/ui/file_manager/file_manager/common/images/icon32.png deleted file mode 100644 index 082d689..0000000 --- a/ui/file_manager/file_manager/common/images/icon32.png +++ /dev/null Binary files differ
diff --git a/ui/file_manager/file_manager/common/images/icon48.png b/ui/file_manager/file_manager/common/images/icon48.png index ec9ad58c..2bb8555 100644 --- a/ui/file_manager/file_manager/common/images/icon48.png +++ b/ui/file_manager/file_manager/common/images/icon48.png Binary files differ
diff --git a/ui/file_manager/file_manager/common/images/icon64.png b/ui/file_manager/file_manager/common/images/icon64.png deleted file mode 100644 index bed4978..0000000 --- a/ui/file_manager/file_manager/common/images/icon64.png +++ /dev/null Binary files differ
diff --git a/ui/file_manager/file_manager/common/images/icon96.png b/ui/file_manager/file_manager/common/images/icon96.png index 24ed0bfb..070057de 100644 --- a/ui/file_manager/file_manager/common/images/icon96.png +++ b/ui/file_manager/file_manager/common/images/icon96.png Binary files differ
diff --git a/ui/file_manager/file_manager/foreground/js/dialog_action_controller.js b/ui/file_manager/file_manager/foreground/js/dialog_action_controller.js index 74beb84b..ddaef5dc 100644 --- a/ui/file_manager/file_manager/foreground/js/dialog_action_controller.js +++ b/ui/file_manager/file_manager/foreground/js/dialog_action_controller.js
@@ -120,13 +120,15 @@ fileSelectionHandler.addEventListener( FileSelectionHandler.EventType.CHANGE_THROTTLED, this.onFileSelectionChanged_.bind(this)); + volumeManager.addEventListener( + 'drive-connection-changed', this.updateOkButton_.bind(this)); dialogFooter.initFileTypeFilter( this.fileTypes_, launchParam.includeAllFiles); this.onFileTypeFilterChanged_(); this.newFolderCommand_ = - /** @type {cr.ui.Command} */ (document.getElementById('new-folder')); + /** @type {cr.ui.Command} */ ($('new-folder')); this.newFolderCommand_.addEventListener( 'disabledChange', this.updateNewFolderButton_.bind(this)); }
diff --git a/ui/file_manager/file_manager/foreground/js/file_selection.js b/ui/file_manager/file_manager/foreground/js/file_selection.js index cbbb5d3..7003c59 100644 --- a/ui/file_manager/file_manager/foreground/js/file_selection.js +++ b/ui/file_manager/file_manager/foreground/js/file_selection.js
@@ -252,9 +252,13 @@ return; // Calculate all additional and heavy properties. - selection.computeAdditional(this.metadataModel_); + selection.computeAdditional(this.metadataModel_).then(() => { + if (this.selection !== selection) + return; - cr.dispatchSimpleEvent(this, FileSelectionHandler.EventType.CHANGE_THROTTLED); + cr.dispatchSimpleEvent( + this, FileSelectionHandler.EventType.CHANGE_THROTTLED); + }); }; /**
diff --git a/ui/file_manager/file_manager/manifest.json b/ui/file_manager/file_manager/manifest.json index 68bd831..2de08b7 100644 --- a/ui/file_manager/file_manager/manifest.json +++ b/ui/file_manager/file_manager/manifest.json
@@ -8,12 +8,10 @@ "incognito" : "split", "icons": { "16": "common/images/icon16.png", - "32": "common/images/icon32.png", "48": "common/images/icon48.png", - "64": "common/images/icon64.png", "96": "common/images/icon96.png", "128": "common/images/icon128.png", - "256": "common/images/icon256.png" + "192": "common/images/icon192.png" }, "permissions": [ "chrome://extension-icon/",
diff --git a/ui/file_manager/file_manager_resources.grd b/ui/file_manager/file_manager_resources.grd index 4d64bd53..1e37bbc 100644 --- a/ui/file_manager/file_manager_resources.grd +++ b/ui/file_manager/file_manager_resources.grd
@@ -70,12 +70,10 @@ <!-- Images referenced from the manifest or the code --> <include name="IDR_FILE_MANAGER_ICON_16" file="file_manager/common/images/icon16.png" type="BINDATA" /> - <include name="IDR_FILE_MANAGER_ICON_32" file="file_manager/common/images/icon32.png" type="BINDATA" /> <include name="IDR_FILE_MANAGER_ICON_48" file="file_manager/common/images/icon48.png" type="BINDATA" /> - <include name="IDR_FILE_MANAGER_ICON_64" file="file_manager/common/images/icon64.png" type="BINDATA" /> <include name="IDR_FILE_MANAGER_ICON_96" file="file_manager/common/images/icon96.png" type="BINDATA" /> <include name="IDR_FILE_MANAGER_ICON_128" file="file_manager/common/images/icon128.png" type="BINDATA" /> - <include name="IDR_FILE_MANAGER_ICON_256" file="file_manager/common/images/icon256.png" type="BINDATA" /> + <include name="IDR_FILE_MANAGER_ICON_192" file="file_manager/common/images/icon192.png" type="BINDATA" /> <include name="IDR_FILE_MANAGER_GALLERY_ICON_16" file="gallery/images/icon16.png" type="BINDATA" /> <include name="IDR_FILE_MANAGER_GALLERY_ICON_32" file="gallery/images/icon32.png" type="BINDATA" /> <include name="IDR_FILE_MANAGER_GALLERY_ICON_48" file="gallery/images/icon48.png" type="BINDATA" />
diff --git a/ui/file_manager/integration_tests/file_manager/create_new_folder.js b/ui/file_manager/integration_tests/file_manager/create_new_folder.js index 3a1a545..ff7263fc 100644 --- a/ui/file_manager/integration_tests/file_manager/create_new_folder.js +++ b/ui/file_manager/integration_tests/file_manager/create_new_folder.js
@@ -15,25 +15,25 @@ /** * Selects the first item in the file list. * - * @param {string} windowId The Files app windowId. + * @param {string} appId The Files app appId. * @return {Promise} Promise to be fulfilled on success. */ -function selectFirstFileListItem(windowId) { +function selectFirstFileListItem(appId) { return Promise.resolve().then(function() { // Ensure no file list items are selected. - return remoteCall.waitForElementLost(windowId, ['#file-list [selected]']); + return remoteCall.waitForElementLost(appId, ['#file-list [selected]']); }).then(function() { // Press DownArrow key to select an item. const key = ['#file-list', 'ArrowDown', 'Down', false, false, false]; - return remoteCall.callRemoteTestUtil('fakeKeyDown', windowId, key); + return remoteCall.callRemoteTestUtil('fakeKeyDown', appId, key); }).then(function(result) { chrome.test.assertTrue(result); // Await file list item selection. - return remoteCall.waitForElement(windowId, ['.table-row[selected]']); + return remoteCall.waitForElement(appId, ['.table-row[selected]']); }).then(function() { // Retrieve all selected items in the file list. return remoteCall.callRemoteTestUtil( - 'queryAllElements', windowId, ['#file-list [selected]']); + 'queryAllElements', appId, ['#file-list [selected]']); }).then(function(elements) { // Check: the first list item only should be selected. chrome.test.assertEq(1, elements.length); @@ -44,42 +44,42 @@ /** * Creates a new folder in the file list. * - * @param {string} windowId The Files app windowId. + * @param {string} appId The Files app appId. * @param {Array<TestEntryInfo>} initialEntrySet Initial set of entries. * @param {string} selector Downloads or Drive directory tree item selector. * @return {Promise} Promise to be fulfilled on success. */ -function createNewFolder(windowId, initialEntrySet, selector) { +function createNewFolder(appId, initialEntrySet, selector) { const textInput = '#file-list .table-row[renaming] input.rename'; return new Promise(function(resolve) { // Focus the file-list. - remoteCall.callRemoteTestUtil('focus', windowId, ['#file-list'], resolve); + remoteCall.callRemoteTestUtil('focus', appId, ['#file-list'], resolve); }).then(function(result) { chrome.test.assertTrue(result); // Press Ctrl+E to create a new folder. const key = ['#file-list', 'e', 'U+0045', true, false, false]; - return remoteCall.callRemoteTestUtil('fakeKeyDown', windowId, key); + return remoteCall.callRemoteTestUtil('fakeKeyDown', appId, key); }).then(function(result) { chrome.test.assertTrue(result); // Check: a new folder should be shown in the file list. const files = [['New Folder', '--', 'Folder', '']].concat( TestEntryInfo.getExpectedRows(initialEntrySet)); return remoteCall.waitForFiles( - windowId, files, {ignoreLastModifiedTime: true}); + appId, files, {ignoreLastModifiedTime: true}); }).then(function() { // Check: a new folder should be present in the directory tree. const newSubtreeChildItem = selector + ' .tree-children .tree-item[entry-label="New Folder"]'; - return remoteCall.waitForElement(windowId, newSubtreeChildItem); + return remoteCall.waitForElement(appId, newSubtreeChildItem); }).then(function() { // Check: the text input should be shown in the file list. - return remoteCall.waitForElement(windowId, textInput); + return remoteCall.waitForElement(appId, textInput); }).then(function() { // Get all file list rows that have attribute 'renaming'. const renamingFileListRows = ['#file-list .table-row[renaming]']; return remoteCall.callRemoteTestUtil( - 'queryAllElements', windowId, renamingFileListRows); + 'queryAllElements', appId, renamingFileListRows); }).then(function(elements) { // Check: the new folder only should be 'renaming'. chrome.test.assertEq(1, elements.length); @@ -89,7 +89,7 @@ // Get all file list rows that have attribute 'selected'. const selectedFileListRows = ['#file-list .table-row[selected]']; return remoteCall.callRemoteTestUtil( - 'queryAllElements', windowId, selectedFileListRows); + 'queryAllElements', appId, selectedFileListRows); }).then(function(elements) { // Check: the new folder only should be 'selected'. chrome.test.assertEq(1, elements.length); @@ -98,32 +98,32 @@ }).then(function() { // Type the test folder name. return remoteCall.callRemoteTestUtil( - 'inputText', windowId, [textInput, 'Test Folder Name']); + 'inputText', appId, [textInput, 'Test Folder Name']); }).then(function() { // Press the Enter key. const key = [textInput, 'Enter', 'Enter', false, false, false]; - return remoteCall.callRemoteTestUtil('fakeKeyDown', windowId, key); + return remoteCall.callRemoteTestUtil('fakeKeyDown', appId, key); }).then(function(result) { chrome.test.assertTrue(result); // Wait until renaming is complete. const renamingItem = ['#file-list .table-row[renaming]']; - return remoteCall.waitForElementLost(windowId, renamingItem); + return remoteCall.waitForElementLost(appId, renamingItem); }).then(function() { // Check: the test folder should be shown in the file list. const files = [['Test Folder Name', '--', 'Folder', '']].concat( TestEntryInfo.getExpectedRows(initialEntrySet)); return remoteCall.waitForFiles( - windowId, files, {ignoreLastModifiedTime: true}); + appId, files, {ignoreLastModifiedTime: true}); }).then(function(elements) { // Check: the test folder should be present in the directory tree. const testSubtreeChildItem = selector + ' .tree-children .tree-item[entry-label="Test Folder Name"]'; - return remoteCall.waitForElement(windowId, testSubtreeChildItem); + return remoteCall.waitForElement(appId, testSubtreeChildItem); }).then(function() { // Get all file list rows that have attribute 'selected'. const selectedFileListRows = ['#file-list .table-row[selected]']; return remoteCall.callRemoteTestUtil( - 'queryAllElements', windowId, selectedFileListRows); + 'queryAllElements', appId, selectedFileListRows); }).then(function(elements) { // Check: the test folder only should be 'selected'. chrome.test.assertEq(1, elements.length); @@ -135,7 +135,7 @@ * Expands the directory tree item given by |selector| (Downloads or Drive) * to reveal its subtree child items. * - * @param {string} appId The Files app windowId. + * @param {string} appId The Files app appId. * @param {string} selector Downloads or Drive directory tree item selector. * @return {Promise} Promise fulfilled on success. */ @@ -161,71 +161,71 @@ } testcase.selectCreateFolderDownloads = function() { - let windowId; + let appId; const promise = new Promise(function(resolve) { setupAndWaitUntilReady( null, RootPath.DOWNLOADS, resolve, BASIC_LOCAL_ENTRY_SET, []); }).then(function(results) { - windowId = results.windowId; - return expandRoot(windowId, TREEITEM_DOWNLOADS); + appId = results.windowId; + return expandRoot(appId, TREEITEM_DOWNLOADS); }).then(function() { - return selectFirstFileListItem(windowId); + return selectFirstFileListItem(appId); }).then(function() { - return createNewFolder(windowId, BASIC_LOCAL_ENTRY_SET, TREEITEM_DOWNLOADS); + return createNewFolder(appId, BASIC_LOCAL_ENTRY_SET, TREEITEM_DOWNLOADS); }); testPromise(promise); }; testcase.createFolderDownloads = function() { - let windowId; + let appId; const promise = new Promise(function(resolve) { setupAndWaitUntilReady( null, RootPath.DOWNLOADS, resolve, BASIC_LOCAL_ENTRY_SET, []); }).then(function(results) { - windowId = results.windowId; - return expandRoot(windowId, TREEITEM_DOWNLOADS); + appId = results.windowId; + return expandRoot(appId, TREEITEM_DOWNLOADS); }).then(function() { - return createNewFolder(windowId, BASIC_LOCAL_ENTRY_SET, TREEITEM_DOWNLOADS); + return createNewFolder(appId, BASIC_LOCAL_ENTRY_SET, TREEITEM_DOWNLOADS); }); testPromise(promise); }; testcase.createFolderNestedDownloads = function() { - let windowId; + let appId; const promise = new Promise(function(resolve) { setupAndWaitUntilReady( null, RootPath.DOWNLOADS, resolve, BASIC_LOCAL_ENTRY_SET, []); }).then(function(results) { - windowId = results.windowId; - return expandRoot(windowId, TREEITEM_DOWNLOADS); + appId = results.windowId; + return expandRoot(appId, TREEITEM_DOWNLOADS); }).then(function() { - return navigateWithDirectoryTree(windowId, '/photos', 'Downloads'); + return navigateWithDirectoryTree(appId, '/photos', 'Downloads'); }).then(function() { return remoteCall.waitForFiles( - windowId, [], {ignoreLastModifiedTime: true}); + appId, [], {ignoreLastModifiedTime: true}); }).then(function() { - return createNewFolder(windowId, [], TREEITEM_DOWNLOADS); + return createNewFolder(appId, [], TREEITEM_DOWNLOADS); }); testPromise(promise); }; testcase.createFolderDrive = function() { - let windowId; + let appId; const promise = new Promise(function(resolve) { setupAndWaitUntilReady( null, RootPath.DRIVE, resolve, [], BASIC_DRIVE_ENTRY_SET); }).then(function(results) { - windowId = results.windowId; - return expandRoot(windowId, TREEITEM_DRIVE); + appId = results.windowId; + return expandRoot(appId, TREEITEM_DRIVE); }).then(function() { - return createNewFolder(windowId, BASIC_DRIVE_ENTRY_SET, TREEITEM_DRIVE); + return createNewFolder(appId, BASIC_DRIVE_ENTRY_SET, TREEITEM_DRIVE); }); testPromise(promise);
diff --git a/ui/webui/resources/cr_components/certificate_manager/BUILD.gn b/ui/webui/resources/cr_components/certificate_manager/BUILD.gn index 2c8a161a..59a88d5 100644 --- a/ui/webui/resources/cr_components/certificate_manager/BUILD.gn +++ b/ui/webui/resources/cr_components/certificate_manager/BUILD.gn
@@ -46,6 +46,7 @@ deps = [ ":certificate_manager_types", ":certificates_browser_proxy", + "//ui/webui/resources/cr_elements/policy:cr_policy_indicator", "//ui/webui/resources/js:cr", "//ui/webui/resources/js:i18n_behavior", ] @@ -105,6 +106,7 @@ ":certificates_browser_proxy", "//ui/webui/resources/cr_elements/cr_action_menu:cr_action_menu", "//ui/webui/resources/cr_elements/cr_lazy_render:cr_lazy_render", + "//ui/webui/resources/cr_elements/policy:cr_policy_indicator", "//ui/webui/resources/js:cr", "//ui/webui/resources/js:i18n_behavior", ]
diff --git a/ui/webui/resources/cr_components/certificate_manager/certificate_entry.html b/ui/webui/resources/cr_components/certificate_manager/certificate_entry.html index 8dcb4409..aa89d1e 100644 --- a/ui/webui/resources/cr_components/certificate_manager/certificate_entry.html +++ b/ui/webui/resources/cr_components/certificate_manager/certificate_entry.html
@@ -1,6 +1,7 @@ <link rel="import" href="chrome://resources/html/polymer.html"> <link rel="import" href="chrome://resources/cr_elements/cr_expand_button/cr_expand_button.html"> +<link rel="import" href="chrome://resources/cr_elements/policy/cr_policy_indicator.html"> <link rel="import" href="chrome://resources/html/i18n_behavior.html"> <link rel="import" href="chrome://resources/polymer/v1_0/iron-flex-layout/iron-flex-layout-classes.html"> <link rel="import" href="certificate_shared_css.html"> @@ -20,6 +21,8 @@ </style> <div class="expand-box"> <div class="flex">[[model.id]]</div> + <cr-policy-indicator indicator-type="[[getPolicyIndicatorType_(model)]]"> + </cr-policy-indicator> <cr-expand-button expanded="{{expanded_}}" alt="[[i18n('certificateManagerExpandA11yLabel')]]"> </cr-expand-button>
diff --git a/ui/webui/resources/cr_components/certificate_manager/certificate_entry.js b/ui/webui/resources/cr_components/certificate_manager/certificate_entry.js index bcd900e..f0124eb 100644 --- a/ui/webui/resources/cr_components/certificate_manager/certificate_entry.js +++ b/ui/webui/resources/cr_components/certificate_manager/certificate_entry.js
@@ -11,7 +11,7 @@ behaviors: [I18nBehavior], properties: { - /** @type {!Certificate} */ + /** @type {!CertificatesOrgGroup} */ model: Object, /** @type {!CertificateType} */ @@ -26,4 +26,9 @@ isLast_: function(index) { return index == this.model.subnodes.length - 1; }, + + getPolicyIndicatorType_() { + return this.model.containsPolicyCerts ? CrPolicyIndicatorType.USER_POLICY : + CrPolicyIndicatorType.NONE; + }, });
diff --git a/ui/webui/resources/cr_components/certificate_manager/certificate_list.js b/ui/webui/resources/cr_components/certificate_manager/certificate_list.js index b2a1fe5..8bd3109 100644 --- a/ui/webui/resources/cr_components/certificate_manager/certificate_list.js +++ b/ui/webui/resources/cr_components/certificate_manager/certificate_list.js
@@ -10,7 +10,7 @@ is: 'certificate-list', properties: { - /** @type {!Array<!Certificate>} */ + /** @type {!Array<!CertificatesOrgGroup>} */ certificates: { type: Array, value: function() {
diff --git a/ui/webui/resources/cr_components/certificate_manager/certificate_manager.js b/ui/webui/resources/cr_components/certificate_manager/certificate_manager.js index cb8da3e..9ef17af 100644 --- a/ui/webui/resources/cr_components/certificate_manager/certificate_manager.js +++ b/ui/webui/resources/cr_components/certificate_manager/certificate_manager.js
@@ -17,7 +17,7 @@ value: 0, }, - /** @type {!Array<!Certificate>} */ + /** @type {!Array<!CertificatesOrgGroup>} */ personalCerts: { type: Array, value: function() { @@ -25,7 +25,7 @@ }, }, - /** @type {!Array<!Certificate>} */ + /** @type {!Array<!CertificatesOrgGroup>} */ serverCerts: { type: Array, value: function() { @@ -33,7 +33,7 @@ }, }, - /** @type {!Array<!Certificate>} */ + /** @type {!Array<!CertificatesOrgGroup>} */ caCerts: { type: Array, value: function() { @@ -41,7 +41,7 @@ }, }, - /** @type {!Array<!Certificate>} */ + /** @type {!Array<!CertificatesOrgGroup>} */ otherCerts: { type: Array, value: function() {
diff --git a/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.html b/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.html index 409975b..2407809 100644 --- a/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.html +++ b/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.html
@@ -2,6 +2,7 @@ <link rel="import" href="chrome://resources/cr_elements/cr_action_menu/cr_action_menu.html"> <link rel="import" href="chrome://resources/cr_elements/cr_lazy_render/cr_lazy_render.html"> +<link rel="import" href="chrome://resources/cr_elements/policy/cr_policy_indicator.html"> <link rel="import" href="chrome://resources/cr_elements/icons.html"> <link rel="import" href="chrome://resources/html/i18n_behavior.html"> <link rel="import" href="chrome://resources/polymer/v1_0/paper-icon-button/paper-icon-button-light.html"> @@ -32,6 +33,8 @@ [[i18n('certificateManagerUntrusted')]] </div> <div class="name">[[model.name]]</div> + <cr-policy-indicator indicator-type="[[getPolicyIndicatorType_(model)]]"> + </cr-policy-indicator> <paper-icon-button-light class="icon-more-vert"> <button id="dots" title="[[i18n('moreActions')]]" on-tap="onDotsTap_"> </button>
diff --git a/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.js b/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.js index 8467bd7..3f2c5423f 100644 --- a/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.js +++ b/ui/webui/resources/cr_components/certificate_manager/certificate_subentry.js
@@ -147,4 +147,10 @@ var actionMenu = /** @type {!CrActionMenuElement} */ (this.$.menu.get()); actionMenu.showAt(this.$.dots); }, + + /** @private */ + getPolicyIndicatorType_: function(model) { + return model.policy ? CrPolicyIndicatorType.USER_POLICY : + CrPolicyIndicatorType.NONE; + }, });
diff --git a/ui/webui/resources/cr_components/certificate_manager/certificates_browser_proxy.js b/ui/webui/resources/cr_components/certificate_manager/certificates_browser_proxy.js index bbf1d73f..826b4bb7 100644 --- a/ui/webui/resources/cr_components/certificate_manager/certificates_browser_proxy.js +++ b/ui/webui/resources/cr_components/certificate_manager/certificates_browser_proxy.js
@@ -13,6 +13,7 @@ * id: string, * name: string, * policy: boolean, + * webTrustAnchor: boolean, * readonly: boolean, * untrusted: boolean, * }} @@ -30,14 +31,19 @@ var NewCertificateSubNode; /** + * Top-level grouping node in a certificate list, representing an organization + * and containing certs that belong to the organization in |subnodes|. If a + * certificate does not have an organization name, it will be grouped under its + * own CertificatesOrgGroup with |name| set to its display name. * @typedef {{ * id: string, * name: string, + * containsPolicyCerts: boolean, * subnodes: !Array<!CertificateSubnode> * }} * @see chrome/browser/ui/webui/settings/certificates_handler.cc */ -var Certificate; +var CertificatesOrgGroup; /** * @typedef {{