diff --git a/BUILD.gn b/BUILD.gn index 5b0fa041..5f6c39f 100644 --- a/BUILD.gn +++ b/BUILD.gn
@@ -623,6 +623,7 @@ "//third_party/breakpad:dump_syms", # The following are accessibility API tools. + "//tools/accessibility/inspect:ax_dump_events", "//tools/accessibility/inspect:ax_dump_tree", ] deps -= [
diff --git a/DEPS b/DEPS index 8cd5417..be82838f 100644 --- a/DEPS +++ b/DEPS
@@ -207,11 +207,11 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling ANGLE # and whatever else without interference from each other. - 'angle_revision': 'be75fbcca886a8c821ce6543df38e3e2f5e9fbf1', + 'angle_revision': '68a5baeb5ba08575c2a3a6e31a0bd8eb4b39d4de', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling SwiftShader # and whatever else without interference from each other. - 'swiftshader_revision': 'a09406249fa35754129856e6eba2ab9a8dae88d5', + 'swiftshader_revision': 'b94db86cf9b3369ebd3c99ffe0d4072bac0a7b75', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling PDFium # and whatever else without interference from each other. @@ -258,7 +258,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': '85d92d37c4c268323dbaeded5dd1de8e2a1abbc7', + 'catapult_revision': '3cd3b4e18cd1d23b2d514f149aecd16f0efc0ef8', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling libFuzzer # and whatever else without interference from each other. @@ -1254,7 +1254,7 @@ }, 'src/third_party/perfetto': - Var('android_git') + '/platform/external/perfetto.git' + '@' + '3d8fd27d9a8ae4431ebae8f9d163489d89cd9b9a', + Var('android_git') + '/platform/external/perfetto.git' + '@' + 'df53732e1b695553e7ac2fc23cc874961034e637', 'src/third_party/perl': { 'url': Var('chromium_git') + '/chromium/deps/perl.git' + '@' + '6f3e5028eb65d0b4c5fdd792106ac4c84eee1eb3', @@ -1332,7 +1332,7 @@ 'packages': [ { 'package': 'fuchsia/third_party/aemu/linux-amd64', - 'version': 'kVxPs86vReFhkroiE9m-5oTHDydp7wn3ehJbz9Pf40UC' + 'version': 'E-5mQKtC1iTlxrYCskskqJebP37mgKGmQhNKk_fPQ3UC' }, ], 'condition': 'host_os == "linux" and checkout_fuchsia', @@ -1486,7 +1486,7 @@ }, 'src/third_party/webrtc': - Var('webrtc_git') + '/src.git' + '@' + 'afef7a74a7964fbd488f5e3956c3f07b2b084f25', + Var('webrtc_git') + '/src.git' + '@' + '9e81182f8ea5f17339aa10b307f8f875422b667f', 'src/third_party/libgifcodec': Var('skia_git') + '/libgifcodec' + '@'+ Var('libgifcodec_revision'), @@ -1566,7 +1566,7 @@ 'packages': [ { 'package': 'chromeos_internal/apps/help_app/app', - 'version': 'uJOBjWHF-V8jOwZMkbWeP1rWi_kNv9l_Fsc2gObjg3wC', + 'version': 'pmx13oYqsBxVgUj6p9fCwrTtgN1M6INq4nvwNMlYmL4C', }, ], 'condition': 'checkout_chromeos and checkout_src_internal', @@ -1577,7 +1577,7 @@ 'packages': [ { 'package': 'chromeos_internal/apps/media_app/app', - 'version': '2a08myhDLFnYjNwtbn3d4RoitoxiNvUZkfWohkxJIP8C', + 'version': 'jVnFFKK_QUsuM6vpE9PGM0P46Dc1MxtkuRNyoYqmMlEC', }, ], 'condition': 'checkout_chromeos and checkout_src_internal',
diff --git a/android_webview/nonembedded/java/src/org/chromium/android_webview/devui/CrashesListFragment.java b/android_webview/nonembedded/java/src/org/chromium/android_webview/devui/CrashesListFragment.java index a2dd0241e..de8d693 100644 --- a/android_webview/nonembedded/java/src/org/chromium/android_webview/devui/CrashesListFragment.java +++ b/android_webview/nonembedded/java/src/org/chromium/android_webview/devui/CrashesListFragment.java
@@ -503,7 +503,8 @@ // Show a button to open GMS settings activity only if it exists. if (intentResolveInfo.size() > 0) { logCrashCollectionState(CollectionState.DISABLED_BY_USER_CONSENT); - errorView.setActionButton("Open Settings", v -> startActivity(settingsIntent)); + errorView.setActionButton( + "Open Settings", v -> mContext.startActivity(settingsIntent)); } else { logCrashCollectionState( CollectionState.DISABLED_BY_USER_CONSENT_CANNOT_FIND_SETTINGS); @@ -520,7 +521,7 @@ dialogBuilder.setMessage(CRASH_BUG_DIALOG_MESSAGE); dialogBuilder.setPositiveButton("Provide more info", (dialog, id) -> { logCrashInteraction(CrashInteraction.FILE_BUG_REPORT_DIALOG_PROCEED); - startActivity(new CrashBugUrlFactory(crashInfo).getReportIntent()); + mContext.startActivity(new CrashBugUrlFactory(crashInfo).getReportIntent()); }); dialogBuilder.setNegativeButton("Dismiss", (dialog, id) -> { logCrashInteraction(CrashInteraction.FILE_BUG_REPORT_DIALOG_DISMISS);
diff --git a/ash/app_list/BUILD.gn b/ash/app_list/BUILD.gn index a2787445..612b782 100644 --- a/ash/app_list/BUILD.gn +++ b/ash/app_list/BUILD.gn
@@ -116,6 +116,7 @@ "//ash/keyboard/ui", "//ash/public/cpp/app_list/vector_icons", "//ash/resources/vector_icons", + "//ash/search_box", "//ash/strings", "//base", "//base:i18n", @@ -135,7 +136,6 @@ "//ui/base", "//ui/base/ime", "//ui/base/ime/chromeos", - "//ui/chromeos/search_box", "//ui/compositor", "//ui/compositor_extra", "//ui/display", @@ -246,6 +246,7 @@ "//ash/keyboard/ui", "//ash/public/cpp", "//ash/public/cpp/app_list/vector_icons", + "//ash/search_box", "//base", "//base/test:test_support", "//chromeos/constants", @@ -259,7 +260,6 @@ "//testing/gtest", "//ui/accessibility", "//ui/base", - "//ui/chromeos/search_box", "//ui/compositor", "//ui/events:test_support", "//ui/gfx:test_support",
diff --git a/ash/app_list/DEPS b/ash/app_list/DEPS index 83ae3fe..204af9f 100644 --- a/ash/app_list/DEPS +++ b/ash/app_list/DEPS
@@ -15,7 +15,6 @@ "+ui/aura", "+ui/base", "+ui/display", - "+ui/chromeos/search_box", "+ui/compositor", "+ui/events", "+ui/gfx",
diff --git a/ash/app_list/views/app_list_main_view.cc b/ash/app_list/views/app_list_main_view.cc index a715359..e476732 100644 --- a/ash/app_list/views/app_list_main_view.cc +++ b/ash/app_list/views/app_list_main_view.cc
@@ -22,6 +22,7 @@ #include "ash/app_list/views/search_result_page_view.h" #include "ash/public/cpp/app_list/app_list_features.h" #include "ash/public/cpp/pagination/pagination_model.h" +#include "ash/search_box/search_box_view_base.h" #include "base/bind.h" #include "base/callback.h" #include "base/files/file_path.h" @@ -31,7 +32,6 @@ #include "base/strings/string_util.h" #include "chromeos/constants/chromeos_features.h" #include "ui/aura/window.h" -#include "ui/chromeos/search_box/search_box_view_base.h" #include "ui/gfx/geometry/insets.h" #include "ui/views/border.h" #include "ui/views/controls/button/button.h"
diff --git a/ash/app_list/views/app_list_main_view.h b/ash/app_list/views/app_list_main_view.h index 489497e..7d377792 100644 --- a/ash/app_list/views/app_list_main_view.h +++ b/ash/app_list/views/app_list_main_view.h
@@ -10,10 +10,10 @@ #include "ash/app_list/app_list_export.h" #include "ash/app_list/model/app_list_model_observer.h" #include "ash/app_list/model/search/search_model.h" +#include "ash/search_box/search_box_view_delegate.h" #include "base/macros.h" #include "base/memory/weak_ptr.h" #include "base/timer/timer.h" -#include "ui/chromeos/search_box/search_box_view_delegate.h" #include "ui/views/view.h" namespace search_box {
diff --git a/ash/app_list/views/app_list_view_unittest.cc b/ash/app_list/views/app_list_view_unittest.cc index 0a8a0f4..97c9ead 100644 --- a/ash/app_list/views/app_list_view_unittest.cc +++ b/ash/app_list/views/app_list_view_unittest.cc
@@ -44,6 +44,7 @@ #include "ash/public/cpp/ash_features.h" #include "ash/public/cpp/pagination/pagination_model.h" #include "ash/public/cpp/presentation_time_recorder.h" +#include "ash/search_box/search_box_constants.h" #include "base/macros.h" #include "base/run_loop.h" #include "base/strings/string_number_conversions.h" @@ -56,7 +57,6 @@ #include "services/content/public/cpp/test/fake_navigable_contents.h" #include "testing/gtest/include/gtest/gtest.h" #include "ui/base/models/simple_menu_model.h" -#include "ui/chromeos/search_box/search_box_constants.h" #include "ui/compositor/layer_animator.h" #include "ui/display/display.h" #include "ui/display/screen.h"
diff --git a/ash/app_list/views/apps_container_view.cc b/ash/app_list/views/apps_container_view.cc index 99c2436..8ed5a0d 100644 --- a/ash/app_list/views/apps_container_view.cc +++ b/ash/app_list/views/apps_container_view.cc
@@ -22,9 +22,9 @@ #include "ash/keyboard/ui/keyboard_ui_controller.h" #include "ash/public/cpp/app_list/app_list_config.h" #include "ash/public/cpp/app_list/app_list_switches.h" +#include "ash/search_box/search_box_constants.h" #include "base/command_line.h" #include "ui/base/l10n/l10n_util.h" -#include "ui/chromeos/search_box/search_box_constants.h" #include "ui/compositor/layer.h" #include "ui/compositor/layer_animation_element.h" #include "ui/compositor/layer_animator.h"
diff --git a/ash/app_list/views/assistant/assistant_main_view.cc b/ash/app_list/views/assistant/assistant_main_view.cc index 9556dfcb..e009900 100644 --- a/ash/app_list/views/assistant/assistant_main_view.cc +++ b/ash/app_list/views/assistant/assistant_main_view.cc
@@ -17,7 +17,7 @@ #include "ash/assistant/util/assistant_util.h" #include "ash/public/cpp/app_list/app_list_features.h" #include "ash/public/cpp/assistant/controller/assistant_ui_controller.h" -#include "ui/chromeos/search_box/search_box_constants.h" +#include "ash/search_box/search_box_constants.h" #include "ui/views/layout/box_layout.h" namespace ash {
diff --git a/ash/app_list/views/assistant/assistant_page_view.cc b/ash/app_list/views/assistant/assistant_page_view.cc index fe3a302..75e53a5 100644 --- a/ash/app_list/views/assistant/assistant_page_view.cc +++ b/ash/app_list/views/assistant/assistant_page_view.cc
@@ -21,11 +21,11 @@ #include "ash/public/cpp/assistant/assistant_state.h" #include "ash/public/cpp/assistant/controller/assistant_ui_controller.h" #include "ash/public/cpp/view_shadow.h" +#include "ash/search_box/search_box_constants.h" #include "ash/strings/grit/ash_strings.h" #include "base/metrics/histogram_functions.h" #include "base/strings/utf_string_conversions.h" #include "ui/base/l10n/l10n_util.h" -#include "ui/chromeos/search_box/search_box_constants.h" #include "ui/compositor/animation_throughput_reporter.h" #include "ui/compositor/scoped_layer_animation_settings.h" #include "ui/compositor_extra/shadow.h"
diff --git a/ash/app_list/views/search_box_view.cc b/ash/app_list/views/search_box_view.cc index c569410..d5f4a055 100644 --- a/ash/app_list/views/search_box_view.cc +++ b/ash/app_list/views/search_box_view.cc
@@ -27,6 +27,8 @@ #include "ash/public/cpp/app_list/vector_icons/vector_icons.h" #include "ash/public/cpp/wallpaper_types.h" #include "ash/resources/vector_icons/vector_icons.h" +#include "ash/search_box/search_box_constants.h" +#include "ash/search_box/search_box_view_delegate.h" #include "base/bind.h" #include "base/macros.h" #include "base/metrics/histogram_macros.h" @@ -37,8 +39,6 @@ #include "ui/base/ime/composition_text.h" #include "ui/base/l10n/l10n_util.h" #include "ui/base/resource/resource_bundle.h" -#include "ui/chromeos/search_box/search_box_constants.h" -#include "ui/chromeos/search_box/search_box_view_delegate.h" #include "ui/events/event.h" #include "ui/gfx/canvas.h" #include "ui/gfx/color_palette.h"
diff --git a/ash/app_list/views/search_box_view.h b/ash/app_list/views/search_box_view.h index 7feec4b..4ed22e8 100644 --- a/ash/app_list/views/search_box_view.h +++ b/ash/app_list/views/search_box_view.h
@@ -11,7 +11,7 @@ #include "ash/app_list/app_list_view_delegate.h" #include "ash/app_list/model/search/search_box_model_observer.h" #include "ash/public/cpp/app_list/app_list_types.h" -#include "ui/chromeos/search_box/search_box_view_base.h" +#include "ash/search_box/search_box_view_base.h" namespace views { class Textfield;
diff --git a/ash/app_list/views/search_box_view_unittest.cc b/ash/app_list/views/search_box_view_unittest.cc index 33c75c41..2f14ff6 100644 --- a/ash/app_list/views/search_box_view_unittest.cc +++ b/ash/app_list/views/search_box_view_unittest.cc
@@ -19,13 +19,13 @@ #include "ash/app_list/views/search_result_page_view.h" #include "ash/public/cpp/app_list/app_list_features.h" #include "ash/public/cpp/app_list/vector_icons/vector_icons.h" +#include "ash/search_box/search_box_constants.h" +#include "ash/search_box/search_box_view_delegate.h" #include "base/macros.h" #include "base/strings/utf_string_conversions.h" #include "base/test/metrics/user_action_tester.h" #include "base/test/scoped_feature_list.h" #include "ui/base/ime/composition_text.h" -#include "ui/chromeos/search_box/search_box_constants.h" -#include "ui/chromeos/search_box/search_box_view_delegate.h" #include "ui/events/base_event_utils.h" #include "ui/gfx/image/image_skia.h" #include "ui/gfx/image/image_unittest_util.h"
diff --git a/ash/app_list/views/search_result_page_view.cc b/ash/app_list/views/search_result_page_view.cc index 0c6a918a..53e53f7 100644 --- a/ash/app_list/views/search_result_page_view.cc +++ b/ash/app_list/views/search_result_page_view.cc
@@ -21,12 +21,12 @@ #include "ash/public/cpp/app_list/app_list_config.h" #include "ash/public/cpp/app_list/app_list_features.h" #include "ash/public/cpp/view_shadow.h" +#include "ash/search_box/search_box_constants.h" #include "base/bind.h" #include "base/memory/ptr_util.h" #include "base/optional.h" #include "base/strings/string_number_conversions.h" #include "ui/base/l10n/l10n_util.h" -#include "ui/chromeos/search_box/search_box_constants.h" #include "ui/compositor/layer.h" #include "ui/compositor/scoped_layer_animation_settings.h" #include "ui/compositor_extra/shadow.h"
diff --git a/ash/ash_prefs.cc b/ash/ash_prefs.cc index 6d86821..f4c1241d 100644 --- a/ash/ash_prefs.cc +++ b/ash/ash_prefs.cc
@@ -24,6 +24,7 @@ #include "ash/system/bluetooth/bluetooth_power_controller.h" #include "ash/system/caps_lock_notification_controller.h" #include "ash/system/gesture_education/gesture_education_notification_controller.h" +#include "ash/system/media/media_tray.h" #include "ash/system/message_center/message_center_controller.h" #include "ash/system/network/vpn_list_view.h" #include "ash/system/night_light/night_light_controller_impl.h" @@ -72,6 +73,7 @@ TouchDevicesController::RegisterProfilePrefs(registry, for_test); tray::VPNListView::RegisterProfilePrefs(registry); WmGestureHandler::RegisterProfilePrefs(registry); + MediaTray::RegisterProfilePrefs(registry); // Provide prefs registered in the browser for ash_unittests. if (for_test) {
diff --git a/ash/ash_strings.grd b/ash/ash_strings.grd index 95cfa30..e266c239 100644 --- a/ash/ash_strings.grd +++ b/ash/ash_strings.grd
@@ -2534,6 +2534,14 @@ Media Controls </message> + <message name="IDS_ASH_GLOBAL_MEDIA_CONTROLS_PINNED_BUTTON_TOOLTIP_TEXT" desc="Tooltip for pinned button showing in global media controls' title."> + Unpin global media controls from shelf + </message> + + <message name="IDS_ASH_GLOBAL_MEDIA_CONTROLS_UNPINNED_BUTTON_TOOLTIP_TEXT" desc="Tooltip for unpinned button showing in global media controls' title."> + Pin global media controls to shelf + </message> + <!-- Power off menu --> <message name="IDS_ASH_POWER_BUTTON_MENU_POWER_OFF_BUTTON" desc="Text shown on power off button in power button menu."> Power off
diff --git a/ash/ash_strings_grd/IDS_ASH_GLOBAL_MEDIA_CONTROLS_PINNED_BUTTON_TOOLTIP_TEXT.png.sha1 b/ash/ash_strings_grd/IDS_ASH_GLOBAL_MEDIA_CONTROLS_PINNED_BUTTON_TOOLTIP_TEXT.png.sha1 new file mode 100644 index 0000000..231d84ac --- /dev/null +++ b/ash/ash_strings_grd/IDS_ASH_GLOBAL_MEDIA_CONTROLS_PINNED_BUTTON_TOOLTIP_TEXT.png.sha1
@@ -0,0 +1 @@ +8c9e0930ef90d9cc07121d233d359101728f0cd7 \ No newline at end of file
diff --git a/ash/ash_strings_grd/IDS_ASH_GLOBAL_MEDIA_CONTROLS_UNPINNED_BUTTON_TOOLTIP_TEXT.png.sha1 b/ash/ash_strings_grd/IDS_ASH_GLOBAL_MEDIA_CONTROLS_UNPINNED_BUTTON_TOOLTIP_TEXT.png.sha1 new file mode 100644 index 0000000..55574a96 --- /dev/null +++ b/ash/ash_strings_grd/IDS_ASH_GLOBAL_MEDIA_CONTROLS_UNPINNED_BUTTON_TOOLTIP_TEXT.png.sha1
@@ -0,0 +1 @@ +15ecf6fae90556515bc942b81da7b7351f057a27 \ No newline at end of file
diff --git a/ash/capture_mode/capture_mode_session.cc b/ash/capture_mode/capture_mode_session.cc index a6795928..263ede22 100644 --- a/ash/capture_mode/capture_mode_session.cc +++ b/ash/capture_mode/capture_mode_session.cc
@@ -26,6 +26,8 @@ #include "ui/gfx/geometry/rect.h" #include "ui/gfx/paint_vector_icon.h" #include "ui/gfx/scoped_canvas.h" +#include "ui/gfx/shadow_value.h" +#include "ui/gfx/skia_paint_util.h" #include "ui/views/controls/button/label_button.h" #include "ui/views/controls/label.h" @@ -33,7 +35,7 @@ namespace { -constexpr int kBorderStrokePx = 2; +constexpr int kBorderStrokePx = 1; // The visual radius of the drag affordance circles which are shown while // resizing a drag region. @@ -49,6 +51,19 @@ // Blue300 at 30%. constexpr SkColor kCaptureRegionColor = SkColorSetA(gfx::kGoogleBlue300, 77); +// Values for the shadows of the capture region components. +constexpr gfx::ShadowValue kRegionOutlineShadow(gfx::Vector2d(0, 0), + 2, + SkColorSetARGB(41, 0, 0, 0)); +constexpr gfx::ShadowValue kRegionAffordanceCircleShadow1( + gfx::Vector2d(0, 1), + 2, + SkColorSetARGB(76, 0, 0, 0)); +constexpr gfx::ShadowValue kRegionAffordanceCircleShadow2( + gfx::Vector2d(0, 2), + 6, + SkColorSetARGB(38, 0, 0, 0)); + // Mouse cursor warping is disabled when the capture source is a custom region. // Sets the mouse warp status to |enable| and return the original value. bool SetMouseWarpEnabled(bool enable) { @@ -273,7 +288,14 @@ region.Inset(-kBorderStrokePx, -kBorderStrokePx); canvas->FillRect(region, SK_ColorTRANSPARENT, SkBlendMode::kClear); - canvas->DrawRect(gfx::RectF(region), kRegionBorderColor); + + // Draw the region border. + cc::PaintFlags border_flags; + border_flags.setColor(kRegionBorderColor); + border_flags.setStyle(cc::PaintFlags::kStroke_Style); + border_flags.setStrokeWidth(kBorderStrokePx); + border_flags.setLooper(gfx::CreateShadowDrawLooper({kRegionOutlineShadow})); + canvas->DrawRect(gfx::RectF(region), border_flags); if (is_select_phase_) return; @@ -283,19 +305,24 @@ return; // Draw the drag affordance circles. - // TODO(sammiequon): Draw a drop shadow for the affordance circles and the - // border. - cc::PaintFlags flags; - flags.setColor(kRegionBorderColor); - flags.setStyle(cc::PaintFlags::kFill_Style); - canvas->DrawCircle(region.origin(), kAffordanceCircleRadiusDp, flags); - canvas->DrawCircle(region.top_center(), kAffordanceCircleRadiusDp, flags); - canvas->DrawCircle(region.top_right(), kAffordanceCircleRadiusDp, flags); - canvas->DrawCircle(region.left_center(), kAffordanceCircleRadiusDp, flags); - canvas->DrawCircle(region.right_center(), kAffordanceCircleRadiusDp, flags); - canvas->DrawCircle(region.bottom_left(), kAffordanceCircleRadiusDp, flags); - canvas->DrawCircle(region.bottom_center(), kAffordanceCircleRadiusDp, flags); - canvas->DrawCircle(region.bottom_right(), kAffordanceCircleRadiusDp, flags); + cc::PaintFlags circle_flags; + circle_flags.setColor(kRegionBorderColor); + circle_flags.setStyle(cc::PaintFlags::kFill_Style); + circle_flags.setLooper(gfx::CreateShadowDrawLooper( + {kRegionAffordanceCircleShadow1, kRegionAffordanceCircleShadow2})); + + auto draw_circle = [&canvas, &circle_flags](const gfx::Point& location) { + canvas->DrawCircle(location, kAffordanceCircleRadiusDp, circle_flags); + }; + + draw_circle(region.origin()); + draw_circle(region.top_center()); + draw_circle(region.top_right()); + draw_circle(region.right_center()); + draw_circle(region.bottom_right()); + draw_circle(region.bottom_center()); + draw_circle(region.bottom_left()); + draw_circle(region.left_center()); } void CaptureModeSession::OnLocatedEvent(ui::LocatedEvent* event,
diff --git a/ash/frame_throttler/frame_throttling_controller.cc b/ash/frame_throttler/frame_throttling_controller.cc index 1954073..979b91d 100644 --- a/ash/frame_throttler/frame_throttling_controller.cc +++ b/ash/frame_throttler/frame_throttling_controller.cc
@@ -61,11 +61,15 @@ void FrameThrottlingController::StartThrottling( const std::vector<aura::Window*>& windows) { + if (windows_throttled_) + EndThrottling(); + + windows_throttled_ = true; std::vector<viz::FrameSinkId> frame_sink_ids; frame_sink_ids.reserve(windows.size()); - CollectBrowserFrameSinkIds(windows, &frame_sink_ids); - StartThrottling(frame_sink_ids, fps_); + if (!frame_sink_ids.empty()) + StartThrottling(frame_sink_ids, fps_); for (auto& observer : observers_) { observer.OnThrottlingStarted(windows); @@ -76,7 +80,8 @@ const std::vector<viz::FrameSinkId>& frame_sink_ids, uint8_t fps) { DCHECK_GT(fps, 0); - if (context_factory_ && !frame_sink_ids.empty()) { + DCHECK(!frame_sink_ids.empty()); + if (context_factory_) { context_factory_->GetHostFrameSinkManager()->StartThrottling( frame_sink_ids, base::TimeDelta::FromSeconds(1) / fps); } @@ -89,6 +94,7 @@ for (auto& observer : observers_) { observer.OnThrottlingEnded(); } + windows_throttled_ = false; } void FrameThrottlingController::AddObserver(Observer* observer) {
diff --git a/ash/frame_throttler/frame_throttling_controller.h b/ash/frame_throttler/frame_throttling_controller.h index 1e9ef8c9..904c3aa 100644 --- a/ash/frame_throttler/frame_throttling_controller.h +++ b/ash/frame_throttler/frame_throttling_controller.h
@@ -57,6 +57,7 @@ base::ObserverList<Observer> observers_; // The fps used for throttling. uint8_t fps_ = kDefaultThrottleFps; + bool windows_throttled_ = false; }; } // namespace ash
diff --git a/ash/public/cpp/ash_pref_names.cc b/ash/public/cpp/ash_pref_names.cc index 97b99050..dae82a1 100644 --- a/ash/public/cpp/ash_pref_names.cc +++ b/ash/public/cpp/ash_pref_names.cc
@@ -593,6 +593,11 @@ const char kReverseGestureNotificationCount[] = "ash.wm.reverse_gesture_notification_count"; +// An integer pref that indicates whether global media controls is pinned to +// shelf or it's unset and need to be determined by screen size during runtime. +const char kGlobalMediaControlsPinned[] = + "ash.system.global_media_controls_pinned"; + // NOTE: New prefs should start with the "ash." prefix. Existing prefs moved // into this file should not be renamed, since they may be synced.
diff --git a/ash/public/cpp/ash_pref_names.h b/ash/public/cpp/ash_pref_names.h index 760f2c5..381b647a 100644 --- a/ash/public/cpp/ash_pref_names.h +++ b/ash/public/cpp/ash_pref_names.h
@@ -214,6 +214,8 @@ ASH_PUBLIC_EXPORT extern const char kReverseGestureNotificationCount[]; +ASH_PUBLIC_EXPORT extern const char kGlobalMediaControlsPinned[]; + } // namespace prefs } // namespace ash
diff --git a/ash/public/cpp/resources/unscaled_resources/settings_logo_192.png b/ash/public/cpp/resources/unscaled_resources/settings_logo_192.png index 0966334..749c310 100644 --- a/ash/public/cpp/resources/unscaled_resources/settings_logo_192.png +++ b/ash/public/cpp/resources/unscaled_resources/settings_logo_192.png Binary files differ
diff --git a/ash/public/cpp/resources/unscaled_resources/shortcut_viewer_logo_192.png b/ash/public/cpp/resources/unscaled_resources/shortcut_viewer_logo_192.png index eb154ba6c40..2d38595 100644 --- a/ash/public/cpp/resources/unscaled_resources/shortcut_viewer_logo_192.png +++ b/ash/public/cpp/resources/unscaled_resources/shortcut_viewer_logo_192.png Binary files differ
diff --git a/ash/resources/vector_icons/BUILD.gn b/ash/resources/vector_icons/BUILD.gn index bc2ad71..f0d17d9 100644 --- a/ash/resources/vector_icons/BUILD.gn +++ b/ash/resources/vector_icons/BUILD.gn
@@ -138,6 +138,7 @@ "palette_tray_icon_magnify.icon", "palette_tray_icon_metalayer.icon", "pin_request_lock.icon", + "pinned.icon", "phone_hub_mobile_no_connection.icon", "phone_hub_mobile_no_sim.icon", "privacy_screen.icon", @@ -309,6 +310,7 @@ "unified_network_badge_captive_portal.icon", "unified_network_badge_secure.icon", "unified_network_badge_vpn.icon", + "unpinned.icon", "unrendered_html_placeholder.icon", "wallpaper.icon", ]
diff --git a/ash/resources/vector_icons/pinned.icon b/ash/resources/vector_icons/pinned.icon new file mode 100644 index 0000000..ee44cffc --- /dev/null +++ b/ash/resources/vector_icons/pinned.icon
@@ -0,0 +1,24 @@ +// Copyright 2020 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. + +CANVAS_DIMENSIONS, 24, +MOVE_TO, 16, 5, +R_H_LINE_TO, 0.99f, +LINE_TO, 17, 3, +H_LINE_TO, 7, +R_V_LINE_TO, 2, +R_H_LINE_TO, 1, +R_V_LINE_TO, 7, +R_LINE_TO, -2, 2, +R_V_LINE_TO, 2, +R_H_LINE_TO, 5, +R_V_LINE_TO, 6, +R_LINE_TO, 1, 1, +R_LINE_TO, 1, -1, +R_V_LINE_TO, -6, +R_H_LINE_TO, 5, +R_V_LINE_TO, -2, +R_LINE_TO, -2, -2, +V_LINE_TO, 5, +CLOSE
diff --git a/ash/resources/vector_icons/unpinned.icon b/ash/resources/vector_icons/unpinned.icon new file mode 100644 index 0000000..e074b5df --- /dev/null +++ b/ash/resources/vector_icons/unpinned.icon
@@ -0,0 +1,31 @@ +// Copyright 2020 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. + +CANVAS_DIMENSIONS, 24, +MOVE_TO, 14, 5, +R_V_LINE_TO, 7.83f, +LINE_TO, 15.17f, 14, +H_LINE_TO, 8.83f, +LINE_TO, 10, 12.83f, +V_LINE_TO, 5, +R_H_LINE_TO, 4, +R_MOVE_TO, 3, -2, +H_LINE_TO, 7, +R_V_LINE_TO, 2, +R_H_LINE_TO, 1, +R_V_LINE_TO, 7, +R_LINE_TO, -2, 2, +R_V_LINE_TO, 2, +R_H_LINE_TO, 5, +R_V_LINE_TO, 6, +R_LINE_TO, 1, 1, +R_LINE_TO, 1, -1, +R_V_LINE_TO, -6, +R_H_LINE_TO, 5, +R_V_LINE_TO, -2, +R_LINE_TO, -2, -2, +V_LINE_TO, 5, +R_H_LINE_TO, 1, +V_LINE_TO, 3, +CLOSE
diff --git a/ash/root_window_controller.cc b/ash/root_window_controller.cc index e5e0c1c8..ca0e0a7b 100644 --- a/ash/root_window_controller.cc +++ b/ash/root_window_controller.cc
@@ -880,11 +880,8 @@ base::BindOnce(&RootWindowController::OnFirstWallpaperWidgetSet, base::Unretained(this))); - int container = Shell::Get()->session_controller()->IsUserSessionBlocked() - ? kShellWindowId_LockScreenWallpaperContainer - : kShellWindowId_WallpaperContainer; - wallpaper_widget_controller_->Init(container); - + wallpaper_widget_controller_->Init( + Shell::Get()->session_controller()->IsUserSessionBlocked()); root_window_layout_manager_->OnWindowResized(); // Explicitly update the desks controller before notifying the ShellObservers.
diff --git a/ui/chromeos/search_box/BUILD.gn b/ash/search_box/BUILD.gn similarity index 94% rename from ui/chromeos/search_box/BUILD.gn rename to ash/search_box/BUILD.gn index 826cad9..b2b497c 100644 --- a/ui/chromeos/search_box/BUILD.gn +++ b/ash/search_box/BUILD.gn
@@ -5,6 +5,7 @@ source_set("search_box") { sources = [ "search_box_constants.h", + "search_box_export.h", "search_box_view_base.cc", "search_box_view_base.h", "search_box_view_delegate.h",
diff --git a/ui/chromeos/search_box/OWNERS b/ash/search_box/OWNERS similarity index 100% rename from ui/chromeos/search_box/OWNERS rename to ash/search_box/OWNERS
diff --git a/ui/chromeos/search_box/search_box_constants.h b/ash/search_box/search_box_constants.h similarity index 85% rename from ui/chromeos/search_box/search_box_constants.h rename to ash/search_box/search_box_constants.h index 9460354..2a32e7c2 100644 --- a/ui/chromeos/search_box/search_box_constants.h +++ b/ash/search_box/search_box_constants.h
@@ -2,11 +2,11 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_CONSTANTS_H_ -#define UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_CONSTANTS_H_ +#ifndef ASH_SEARCH_BOX_SEARCH_BOX_CONSTANTS_H_ +#define ASH_SEARCH_BOX_SEARCH_BOX_CONSTANTS_H_ +#include "ash/search_box/search_box_export.h" #include "third_party/skia/include/core/SkColor.h" -#include "ui/chromeos/search_box/search_box_export.h" #include "ui/gfx/color_palette.h" namespace search_box { @@ -39,4 +39,4 @@ } // namespace search_box -#endif // UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_CONSTANTS_H_ +#endif // ASH_SEARCH_BOX_SEARCH_BOX_CONSTANTS_H_
diff --git a/ui/chromeos/search_box/search_box_export.h b/ash/search_box/search_box_export.h similarity index 82% rename from ui/chromeos/search_box/search_box_export.h rename to ash/search_box/search_box_export.h index c70a482..f98e631 100644 --- a/ui/chromeos/search_box/search_box_export.h +++ b/ash/search_box/search_box_export.h
@@ -2,8 +2,8 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_EXPORT_H_ -#define UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_EXPORT_H_ +#ifndef ASH_SEARCH_BOX_SEARCH_BOX_EXPORT_H_ +#define ASH_SEARCH_BOX_SEARCH_BOX_EXPORT_H_ // Defines SEARCH_BOX_EXPORT so that functionality implemented by the search_box // module can be exported to consumers. @@ -29,4 +29,4 @@ #define SEARCH_BOX_EXPORT #endif -#endif // UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_EXPORT_H_ +#endif // ASH_SEARCH_BOX_SEARCH_BOX_EXPORT_H_
diff --git a/ui/chromeos/search_box/search_box_view_base.cc b/ash/search_box/search_box_view_base.cc similarity index 98% rename from ui/chromeos/search_box/search_box_view_base.cc rename to ash/search_box/search_box_view_base.cc index 1abc20c..7cb40d36 100644 --- a/ui/chromeos/search_box/search_box_view_base.cc +++ b/ash/search_box/search_box_view_base.cc
@@ -2,16 +2,16 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#include "ui/chromeos/search_box/search_box_view_base.h" +#include "ash/search_box/search_box_view_base.h" #include <algorithm> #include <memory> #include <vector> +#include "ash/search_box/search_box_view_delegate.h" #include "base/macros.h" #include "third_party/skia/include/core/SkPath.h" #include "ui/base/ime/text_input_flags.h" -#include "ui/chromeos/search_box/search_box_view_delegate.h" #include "ui/events/event.h" #include "ui/gfx/canvas.h" #include "ui/gfx/color_palette.h"
diff --git a/ui/chromeos/search_box/search_box_view_base.h b/ash/search_box/search_box_view_base.h similarity index 96% rename from ui/chromeos/search_box/search_box_view_base.h rename to ash/search_box/search_box_view_base.h index 401fe48..1af6212 100644 --- a/ui/chromeos/search_box/search_box_view_base.h +++ b/ash/search_box/search_box_view_base.h
@@ -2,16 +2,16 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_VIEW_BASE_H_ -#define UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_VIEW_BASE_H_ +#ifndef ASH_SEARCH_BOX_SEARCH_BOX_VIEW_BASE_H_ +#define ASH_SEARCH_BOX_SEARCH_BOX_VIEW_BASE_H_ #include <vector> +#include "ash/search_box/search_box_constants.h" +#include "ash/search_box/search_box_export.h" #include "base/bind.h" #include "base/macros.h" #include "base/strings/string16.h" -#include "ui/chromeos/search_box/search_box_constants.h" -#include "ui/chromeos/search_box/search_box_export.h" #include "ui/events/types/event_type.h" #include "ui/views/background.h" #include "ui/views/controls/button/image_button.h" @@ -220,4 +220,4 @@ } // namespace search_box -#endif // UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_VIEW_BASE_H_ +#endif // ASH_SEARCH_BOX_SEARCH_BOX_VIEW_BASE_H_
diff --git a/ui/chromeos/search_box/search_box_view_delegate.h b/ash/search_box/search_box_view_delegate.h similarity index 79% rename from ui/chromeos/search_box/search_box_view_delegate.h rename to ash/search_box/search_box_view_delegate.h index 6db6daa9..fec0cc1 100644 --- a/ui/chromeos/search_box/search_box_view_delegate.h +++ b/ash/search_box/search_box_view_delegate.h
@@ -2,10 +2,10 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#ifndef UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_VIEW_DELEGATE_H_ -#define UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_VIEW_DELEGATE_H_ +#ifndef ASH_SEARCH_BOX_SEARCH_BOX_VIEW_DELEGATE_H_ +#define ASH_SEARCH_BOX_SEARCH_BOX_VIEW_DELEGATE_H_ -#include "ui/chromeos/search_box/search_box_export.h" +#include "ash/search_box/search_box_export.h" namespace search_box { @@ -34,4 +34,4 @@ } // namespace search_box -#endif // UI_CHROMEOS_SEARCH_BOX_SEARCH_BOX_VIEW_DELEGATE_H_ +#endif // ASH_SEARCH_BOX_SEARCH_BOX_VIEW_DELEGATE_H_
diff --git a/ash/shortcut_viewer/BUILD.gn b/ash/shortcut_viewer/BUILD.gn index 83ff5e94..d9b54855 100644 --- a/ash/shortcut_viewer/BUILD.gn +++ b/ash/shortcut_viewer/BUILD.gn
@@ -28,13 +28,13 @@ "//ash", "//ash/public/cpp", "//ash/public/cpp/resources:ash_public_unscaled_resources", + "//ash/search_box", "//ash/shortcut_viewer/strings", "//ash/shortcut_viewer/vector_icons", "//cc/paint", "//ui/accessibility", "//ui/aura", "//ui/chromeos/events", - "//ui/chromeos/search_box", "//ui/events:events_base", "//ui/events/devices", "//ui/events/ozone/layout",
diff --git a/ash/shortcut_viewer/views/keyboard_shortcut_view.cc b/ash/shortcut_viewer/views/keyboard_shortcut_view.cc index 0444413a..450b5a91 100644 --- a/ash/shortcut_viewer/views/keyboard_shortcut_view.cc +++ b/ash/shortcut_viewer/views/keyboard_shortcut_view.cc
@@ -16,6 +16,7 @@ #include "ash/public/cpp/resources/grit/ash_public_unscaled_resources.h" #include "ash/public/cpp/shelf_item.h" #include "ash/public/cpp/window_properties.h" +#include "ash/search_box/search_box_view_base.h" #include "ash/shell.h" #include "ash/shortcut_viewer/keyboard_shortcut_viewer_metadata.h" #include "ash/shortcut_viewer/strings/grit/shortcut_viewer_strings.h" @@ -38,7 +39,6 @@ #include "ui/base/l10n/l10n_util.h" #include "ui/base/resource/resource_bundle.h" #include "ui/chromeos/events/keyboard_layout_util.h" -#include "ui/chromeos/search_box/search_box_view_base.h" #include "ui/events/event_constants.h" #include "ui/events/types/event_type.h" #include "ui/gfx/paint_vector_icon.h"
diff --git a/ash/shortcut_viewer/views/keyboard_shortcut_view.h b/ash/shortcut_viewer/views/keyboard_shortcut_view.h index 0494c574..a0323a15 100644 --- a/ash/shortcut_viewer/views/keyboard_shortcut_view.h +++ b/ash/shortcut_viewer/views/keyboard_shortcut_view.h
@@ -9,10 +9,10 @@ #include <memory> #include <vector> +#include "ash/search_box/search_box_view_delegate.h" #include "base/macros.h" #include "base/optional.h" #include "base/timer/timer.h" -#include "ui/chromeos/search_box/search_box_view_delegate.h" #include "ui/views/widget/widget_delegate.h" namespace aura {
diff --git a/ash/shortcut_viewer/views/ksv_search_box_view.cc b/ash/shortcut_viewer/views/ksv_search_box_view.cc index 8402bbc1..af7a554 100644 --- a/ash/shortcut_viewer/views/ksv_search_box_view.cc +++ b/ash/shortcut_viewer/views/ksv_search_box_view.cc
@@ -4,12 +4,12 @@ #include "ash/shortcut_viewer/views/ksv_search_box_view.h" +#include "ash/search_box/search_box_view_delegate.h" #include "ash/shortcut_viewer/strings/grit/shortcut_viewer_strings.h" #include "ash/shortcut_viewer/vector_icons/vector_icons.h" #include "ui/accessibility/ax_enums.mojom.h" #include "ui/accessibility/ax_node_data.h" #include "ui/base/l10n/l10n_util.h" -#include "ui/chromeos/search_box/search_box_view_delegate.h" #include "ui/gfx/canvas.h" #include "ui/gfx/color_palette.h" #include "ui/gfx/paint_vector_icon.h"
diff --git a/ash/shortcut_viewer/views/ksv_search_box_view.h b/ash/shortcut_viewer/views/ksv_search_box_view.h index a7c6c69..2efbaef0 100644 --- a/ash/shortcut_viewer/views/ksv_search_box_view.h +++ b/ash/shortcut_viewer/views/ksv_search_box_view.h
@@ -5,9 +5,9 @@ #ifndef ASH_SHORTCUT_VIEWER_VIEWS_KSV_SEARCH_BOX_VIEW_H_ #define ASH_SHORTCUT_VIEWER_VIEWS_KSV_SEARCH_BOX_VIEW_H_ +#include "ash/search_box/search_box_view_base.h" #include "base/macros.h" #include "base/strings/string16.h" -#include "ui/chromeos/search_box/search_box_view_base.h" namespace search_box { class SearchBoxViewDelegate;
diff --git a/ash/system/media/media_tray.cc b/ash/system/media/media_tray.cc index 157e0c2..1b49c5c 100644 --- a/ash/system/media/media_tray.cc +++ b/ash/system/media/media_tray.cc
@@ -4,8 +4,10 @@ #include "ash/system/media/media_tray.h" +#include "ash/public/cpp/ash_pref_names.h" #include "ash/public/cpp/media_notification_provider.h" #include "ash/resources/vector_icons/vector_icons.h" +#include "ash/root_window_controller.h" #include "ash/session/session_controller_impl.h" #include "ash/shelf/shelf.h" #include "ash/shell.h" @@ -18,18 +20,54 @@ #include "ash/system/tray/tray_popup_item_style.h" #include "ash/system/tray/tray_utils.h" #include "base/strings/string_util.h" +#include "components/prefs/pref_change_registrar.h" +#include "components/prefs/pref_registry_simple.h" +#include "components/prefs/pref_service.h" #include "ui/base/l10n/l10n_util.h" +#include "ui/display/manager/display_manager.h" +#include "ui/display/manager/managed_display_info.h" #include "ui/gfx/geometry/insets.h" #include "ui/gfx/paint_vector_icon.h" +#include "ui/views/controls/button/image_button.h" #include "ui/views/controls/image_view.h" #include "ui/views/controls/label.h" -#include "ui/views/controls/separator.h" #include "ui/views/layout/box_layout.h" namespace ash { namespace { +constexpr gfx::Insets kTitleViewInsets = gfx::Insets(0, 16, 0, 16); + +// Minimum screen diagonal (in inches) for pinning global media controls +// on shelf by default. +constexpr float kMinimumScreenSizeDiagonal = 10.0f; + +// Calculate screen size and returns true if screen size is larger than +// kMinimumScreenSizeDiagonal. +bool GetIsPinnedToShelfByDefault() { + // Happens in test. + if (!Shell::HasInstance()) + return false; + + display::ManagedDisplayInfo info = + Shell::Get()->display_manager()->GetDisplayInfo( + display::Screen::GetScreen()->GetPrimaryDisplay().id()); + DCHECK(info.device_dpi()); + float screen_width = info.size_in_pixel().width() / info.device_dpi(); + float screen_height = info.size_in_pixel().height() / info.device_dpi(); + + float diagonal_len = sqrt(pow(screen_width, 2) + pow(screen_height, 2)); + return diagonal_len > kMinimumScreenSizeDiagonal; +} + +// Enum that specifies the pin state of global media controls. +enum PinState { + kDefault = 0, + kUnpinned, + kPinned, +}; + // View that contains global media controls' title. class GlobalMediaControlsTitleView : public views::View { public: @@ -43,24 +81,91 @@ kMenuSeparatorVerticalPadding - kMenuSeparatorWidth, 0))); auto* box_layout = SetLayoutManager(std::make_unique<views::BoxLayout>( - views::BoxLayout::Orientation::kHorizontal, gfx::Insets(0, 0, 0, 0))); + views::BoxLayout::Orientation::kHorizontal, kTitleViewInsets)); box_layout->set_minimum_cross_axis_size(kTrayPopupItemMinHeight); + box_layout->set_cross_axis_alignment( + views::BoxLayout::CrossAxisAlignment::kCenter); auto* title_label = AddChildView(std::make_unique<views::Label>()); title_label->SetText( l10n_util::GetStringUTF16(IDS_ASH_GLOBAL_MEDIA_CONTROLS_TITLE)); title_label->SetHorizontalAlignment(gfx::ALIGN_LEFT); - title_label->SetBorder(views::CreateEmptyBorder(0, 16, 0, 0)); TrayPopupItemStyle style(TrayPopupItemStyle::FontStyle::SMALL_TITLE, true /* use_unified_theme */); style.SetupLabel(title_label); + // Media tray should always be pinned to shelf when we are opening the + // dialog. + DCHECK(MediaTray::IsPinnedToShelf()); + pin_button_ = AddChildView(std::make_unique<MediaTray::PinButton>()); + box_layout->SetFlexForView(title_label, 1); } + + views::Button* pin_button() { return pin_button_; } + + private: + MediaTray::PinButton* pin_button_ = nullptr; }; } // namespace +// static +void MediaTray::RegisterProfilePrefs(PrefRegistrySimple* registry) { + registry->RegisterIntegerPref(prefs::kGlobalMediaControlsPinned, + PinState::kDefault); +} + +// static +bool MediaTray::IsPinnedToShelf() { + PrefService* pref_service = + Shell::Get()->session_controller()->GetActivePrefService(); + DCHECK(pref_service); + switch (pref_service->GetInteger(prefs::kGlobalMediaControlsPinned)) { + case PinState::kPinned: + return true; + case PinState::kUnpinned: + return false; + case PinState::kDefault: + return GetIsPinnedToShelfByDefault(); + } + + NOTREACHED(); + return false; +} + +// static +void MediaTray::SetPinnedToShelf(bool pinned) { + PrefService* pref_service = + Shell::Get()->session_controller()->GetActivePrefService(); + DCHECK(pref_service); + pref_service->SetInteger(prefs::kGlobalMediaControlsPinned, + pinned ? PinState::kPinned : PinState::kUnpinned); +} + +MediaTray::PinButton::PinButton() + : TopShortcutButton( + this, + MediaTray::IsPinnedToShelf() ? kPinnedIcon : kUnpinnedIcon, + MediaTray::IsPinnedToShelf() + ? IDS_ASH_GLOBAL_MEDIA_CONTROLS_PINNED_BUTTON_TOOLTIP_TEXT + : IDS_ASH_GLOBAL_MEDIA_CONTROLS_UNPINNED_BUTTON_TOOLTIP_TEXT) {} + +void MediaTray::PinButton::ButtonPressed(views::Button* sender, + const ui::Event& event) { + MediaTray::SetPinnedToShelf(!MediaTray::IsPinnedToShelf()); + SetImage(views::Button::STATE_NORMAL, + CreateVectorIcon( + MediaTray::IsPinnedToShelf() ? kPinnedIcon : kUnpinnedIcon, + kTrayTopShortcutButtonIconSize, + AshColorProvider::Get()->GetContentLayerColor( + AshColorProvider::ContentLayerType::kIconColorPrimary))); + SetTooltipText(l10n_util::GetStringUTF16( + MediaTray::IsPinnedToShelf() + ? IDS_ASH_GLOBAL_MEDIA_CONTROLS_PINNED_BUTTON_TOOLTIP_TEXT + : IDS_ASH_GLOBAL_MEDIA_CONTROLS_UNPINNED_BUTTON_TOOLTIP_TEXT)); +} + MediaTray::MediaTray(Shelf* shelf) : TrayBackgroundView(shelf) { if (MediaNotificationProvider::Get()) MediaNotificationProvider::Get()->AddObserver(this); @@ -142,10 +247,11 @@ TrayBubbleView* bubble_view = new TrayBubbleView(init_params); - auto* title_view_ptr = bubble_view->AddChildView( + auto* title_view = bubble_view->AddChildView( std::make_unique<GlobalMediaControlsTitleView>()); - title_view_ptr->SetPaintToLayer(); - title_view_ptr->layer()->SetFillsBoundsOpaquely(false); + title_view->SetPaintToLayer(); + title_view->layer()->SetFillsBoundsOpaquely(false); + pin_button_ = title_view->pin_button(); bubble_view->AddChildView( MediaNotificationProvider::Get()->GetMediaNotificationListView( @@ -179,6 +285,16 @@ UpdateDisplayState(); } +void MediaTray::OnActiveUserPrefServiceChanged(PrefService* pref_service) { + pref_change_registrar_ = std::make_unique<PrefChangeRegistrar>(); + pref_change_registrar_->Init(pref_service); + pref_change_registrar_->Add( + prefs::kGlobalMediaControlsPinned, + base::BindRepeating(&MediaTray::OnGlobalMediaControlsPinPrefChanged, + base::Unretained(this))); + OnGlobalMediaControlsPinPrefChanged(); +} + void MediaTray::UpdateDisplayState() { if (!MediaNotificationProvider::Get()) return; @@ -186,11 +302,16 @@ bool should_show = (MediaNotificationProvider::Get()->HasActiveNotifications() || MediaNotificationProvider::Get()->HasFrozenNotifications()) && - !Shell::Get()->session_controller()->IsScreenLocked(); + !Shell::Get()->session_controller()->IsScreenLocked() && + IsPinnedToShelf(); if (!should_show && bubble_) CloseBubble(); SetVisiblePreferred(should_show); } +void MediaTray::OnGlobalMediaControlsPinPrefChanged() { + UpdateDisplayState(); +} + } // namespace ash
diff --git a/ash/system/media/media_tray.h b/ash/system/media/media_tray.h index dac2a05f..4a0595d 100644 --- a/ash/system/media/media_tray.h +++ b/ash/system/media/media_tray.h
@@ -5,9 +5,15 @@ #ifndef ASH_SYSTEM_MEDIA_MEDIA_TRAY_H_ #define ASH_SYSTEM_MEDIA_MEDIA_TRAY_H_ +#include "ash/ash_export.h" #include "ash/public/cpp/media_notification_provider_observer.h" #include "ash/public/cpp/session/session_observer.h" #include "ash/system/tray/tray_background_view.h" +#include "ash/system/unified/top_shortcut_button.h" + +class PrefChangeRegistrar; +class PrefRegistrySimple; +class PrefService; namespace views { class ImageView; @@ -18,10 +24,30 @@ class Shelf; class TrayBubbleWrapper; -class MediaTray : public MediaNotificationProviderObserver, - public TrayBackgroundView, - public SessionObserver { +class ASH_EXPORT MediaTray : public MediaNotificationProviderObserver, + public TrayBackgroundView, + public SessionObserver { public: + // Register prefs::kGlobalMediaControlsPinned. + static void RegisterProfilePrefs(PrefRegistrySimple* registry); + + // Returns if global media controls is pinned to shelf. + static bool IsPinnedToShelf(); + + // Set kGlobalMediaControlsPinned. + static void SetPinnedToShelf(bool pinned); + + // Pin button showed in media tray bubble's title view and media controls + // detailed view's title view. + class PinButton : public TopShortcutButton, public ButtonListener { + public: + PinButton(); + ~PinButton() override = default; + + // views::ButtonListener implementation. + void ButtonPressed(views::Button* sender, const ui::Event& event) override; + }; + explicit MediaTray(Shelf* shelf); ~MediaTray() override; @@ -41,16 +67,26 @@ // SessionObserver implementation. void OnLockStateChanged(bool locked) override; - - TrayBubbleWrapper* tray_bubble_wrapper_for_testing() { return bubble_.get(); } - - private: - friend class MediaTrayTest; + void OnActiveUserPrefServiceChanged(PrefService* pref_service) override; // Show/hide media tray. void UpdateDisplayState(); + TrayBubbleWrapper* tray_bubble_wrapper_for_testing() { return bubble_.get(); } + + views::View* pin_button_for_testing() { return pin_button_; } + + private: + friend class MediaTrayTest; + + // Called when global media controls pin pref is changed. + void OnGlobalMediaControlsPinPrefChanged(); + + // Ptr to pin button in the dialog, owned by the view hierarchy. + views::Button* pin_button_ = nullptr; + std::unique_ptr<TrayBubbleWrapper> bubble_; + std::unique_ptr<PrefChangeRegistrar> pref_change_registrar_; // Weak pointer, will be parented by TrayContainer for its lifetime. views::ImageView* icon_;
diff --git a/ash/system/media/media_tray_unittest.cc b/ash/system/media/media_tray_unittest.cc index eef1c9d..08d1e58 100644 --- a/ash/system/media/media_tray_unittest.cc +++ b/ash/system/media/media_tray_unittest.cc
@@ -69,6 +69,7 @@ media_tray_ = StatusAreaWidgetTestHelper::GetStatusAreaWidget()->media_tray(); + ASSERT_TRUE(MediaTray::IsPinnedToShelf()); } void SimulateNotificationListChanged() { @@ -81,6 +82,15 @@ media_tray_->PerformAction(tap); } + void SimulateTapOnPinButton() { + ASSERT_TRUE(media_tray_->pin_button_for_testing()); + ui::test::EventGenerator* generator = GetEventGenerator(); + generator->MoveMouseTo(media_tray_->pin_button_for_testing() + ->GetBoundsInScreen() + .CenterPoint()); + generator->ClickLeftButton(); + } + TrayBubbleWrapper* GetBubbleWrapper() { return media_tray_->tray_bubble_wrapper_for_testing(); } @@ -124,6 +134,11 @@ // Media tray should be visible again when we unlock the screen. GetSessionControllerClient()->UnlockScreen(); EXPECT_TRUE(media_tray()->GetVisible()); + + // Media tray should not be visible if global media controls is + // not pinned to shelf. + MediaTray::SetPinnedToShelf(false); + EXPECT_FALSE(media_tray()->GetVisible()); } TEST_F(MediaTrayTest, ShowAndHideBubbleTest) { @@ -177,4 +192,36 @@ EXPECT_FALSE(media_tray()->GetVisible()); } +TEST_F(MediaTrayTest, PinButtonTest) { + // Media tray should be invisible initially. + ASSERT_TRUE(media_tray()); + EXPECT_FALSE(media_tray()->GetVisible()); + + // Open global media controls dialog. + provider()->SetHasActiveNotifications(true); + SimulateNotificationListChanged(); + EXPECT_TRUE(media_tray()->GetVisible()); + SimulateTapOnMediaTray(); + EXPECT_NE(GetBubbleWrapper(), nullptr); + + // Tapping the pin button while the media controls dialog is opened + // should have the dialog closed and the media tray hidden. + SimulateTapOnPinButton(); + EXPECT_EQ(GetBubbleWrapper(), nullptr); + EXPECT_FALSE(media_tray()->GetVisible()); + EXPECT_FALSE(MediaTray::IsPinnedToShelf()); +} + +TEST_F(MediaTrayTest, PinToShelfDefaultBehavior) { + // Media controls should be pinned on shelf by default on a + // 10 inch display. + UpdateDisplay("800x530"); + EXPECT_FALSE(MediaTray::IsPinnedToShelf()); + + // Media controls should be pinned on shelf by default on a + // display larger than 10 inches. + UpdateDisplay("800x600"); + EXPECT_TRUE(MediaTray::IsPinnedToShelf()); +} + } // namespace ash
diff --git a/ash/system/media/unified_media_controls_detailed_view.cc b/ash/system/media/unified_media_controls_detailed_view.cc index 5ba4d86..7bb16cce 100644 --- a/ash/system/media/unified_media_controls_detailed_view.cc +++ b/ash/system/media/unified_media_controls_detailed_view.cc
@@ -6,6 +6,8 @@ #include "ash/strings/grit/ash_strings.h" #include "ash/style/ash_color_provider.h" +#include "ash/system/media/media_tray.h" +#include "ash/system/tray/tri_view.h" namespace ash { @@ -22,4 +24,13 @@ AddChildView(std::move(notification_list_view)); } +void UnifiedMediaControlsDetailedView::CreateExtraTitleRowButtons() { + // DetailedView should only be visible when global media controls + // is NOT pinned to shelf. + DCHECK(!MediaTray::IsPinnedToShelf()); + + tri_view()->SetContainerVisible(TriView::Container::END, true); + tri_view()->AddView(TriView::Container::END, new MediaTray::PinButton()); +} + } // namespace ash
diff --git a/ash/system/media/unified_media_controls_detailed_view.h b/ash/system/media/unified_media_controls_detailed_view.h index e223138..2b070e7 100644 --- a/ash/system/media/unified_media_controls_detailed_view.h +++ b/ash/system/media/unified_media_controls_detailed_view.h
@@ -16,6 +16,10 @@ DetailedViewDelegate* delegate, std::unique_ptr<views::View> notification_list_view); ~UnifiedMediaControlsDetailedView() override = default; + + private: + // TrayDetailedView implementation. + void CreateExtraTitleRowButtons() override; }; } // namespace ash
diff --git a/ash/system/media/unified_media_controls_detailed_view_controller_unittest.cc b/ash/system/media/unified_media_controls_detailed_view_controller_unittest.cc index f84af72c..36063bd 100644 --- a/ash/system/media/unified_media_controls_detailed_view_controller_unittest.cc +++ b/ash/system/media/unified_media_controls_detailed_view_controller_unittest.cc
@@ -5,6 +5,7 @@ #include "ash/system/media/unified_media_controls_detailed_view_controller.h" #include "ash/public/cpp/media_notification_provider.h" +#include "ash/system/media/media_tray.h" #include "ash/system/status_area_widget.h" #include "ash/system/status_area_widget_test_helper.h" #include "ash/system/unified/unified_system_tray.h" @@ -69,6 +70,10 @@ provider_ = std::make_unique<MockMediaNotificationProvider>(); AshTestBase::SetUp(); + // Ensure media tray is not pinned to shelf so that media controls + // show up in quick settings. + MediaTray::SetPinnedToShelf(false); + StatusAreaWidgetTestHelper::GetStatusAreaWidget() ->unified_system_tray() ->ShowBubble(false /* show_by_click */);
diff --git a/ash/system/network/vpn_list_view.cc b/ash/system/network/vpn_list_view.cc index 604b93d..569640a4 100644 --- a/ash/system/network/vpn_list_view.cc +++ b/ash/system/network/vpn_list_view.cc
@@ -145,8 +145,6 @@ SystemMenuButton* add_vpn_button = new SystemMenuButton( this, enabled_icon, disabled_icon, button_accessible_name_id); - add_vpn_button->SetInkDropColor( - UnifiedSystemTrayView::GetBackgroundColor()); // 'Add VPN' is disabled in the login screen since user configured // device-wide VPNs are unsupported.
diff --git a/ash/system/tray/actionable_view.cc b/ash/system/tray/actionable_view.cc index 9bee5a6a..0d5497b9 100644 --- a/ash/system/tray/actionable_view.cc +++ b/ash/system/tray/actionable_view.cc
@@ -5,6 +5,7 @@ #include "ash/system/tray/actionable_view.h" #include "ash/system/tray/tray_popup_utils.h" +#include "ash/system/unified/unified_system_tray_view.h" #include "ui/accessibility/ax_enums.mojom.h" #include "ui/accessibility/ax_node_data.h" #include "ui/events/keycodes/keyboard_codes.h" @@ -70,18 +71,15 @@ std::unique_ptr<views::InkDropRipple> ActionableView::CreateInkDropRipple() const { - // TODO(minch): Do not hard code the background color. Add it as a constructor - // argument to ActionableView. return TrayPopupUtils::CreateInkDropRipple( - ink_drop_style_, this, GetInkDropCenterBasedOnLastEvent(), SK_ColorWHITE); + ink_drop_style_, this, GetInkDropCenterBasedOnLastEvent(), + UnifiedSystemTrayView::GetBackgroundColor()); } std::unique_ptr<views::InkDropHighlight> ActionableView::CreateInkDropHighlight() const { - // TODO(minch): Do not hard code the background color. Add it as a constructor - // argument to ActionableView. - return TrayPopupUtils::CreateInkDropHighlight(ink_drop_style_, this, - SK_ColorWHITE); + return TrayPopupUtils::CreateInkDropHighlight( + ink_drop_style_, this, UnifiedSystemTrayView::GetBackgroundColor()); } void ActionableView::ButtonPressed(Button* sender, const ui::Event& event) {
diff --git a/ash/system/tray/system_menu_button.cc b/ash/system/tray/system_menu_button.cc index 4f546385..cb0ddb4 100644 --- a/ash/system/tray/system_menu_button.cc +++ b/ash/system/tray/system_menu_button.cc
@@ -9,6 +9,7 @@ #include "ash/system/tray/tray_constants.h" #include "ash/system/tray/tray_popup_ink_drop_style.h" #include "ash/system/tray/tray_popup_utils.h" +#include "ash/system/unified/unified_system_tray_view.h" #include "ui/base/l10n/l10n_util.h" #include "ui/gfx/paint_vector_icon.h" #include "ui/views/animation/flood_fill_ink_drop_ripple.h" @@ -62,30 +63,23 @@ SystemMenuButton::~SystemMenuButton() = default; -void SystemMenuButton::SetInkDropColor(SkColor color) { - ink_drop_color_ = color; -} - std::unique_ptr<views::InkDrop> SystemMenuButton::CreateInkDrop() { return TrayPopupUtils::CreateInkDrop(this); } -// TODO(minch): Do not hard code the background color for InkDropRipple and -// InkDropHighlight. Add it as a constructor argument to SystemMenuButton. -// Then, |ink_drop_color_| related logic can be removed. std::unique_ptr<views::InkDropRipple> SystemMenuButton::CreateInkDropRipple() const { return TrayPopupUtils::CreateInkDropRipple( TrayPopupInkDropStyle::HOST_CENTERED, this, GetInkDropCenterBasedOnLastEvent(), - ink_drop_color_.value_or(SK_ColorWHITE)); + UnifiedSystemTrayView::GetBackgroundColor()); } std::unique_ptr<views::InkDropHighlight> SystemMenuButton::CreateInkDropHighlight() const { return TrayPopupUtils::CreateInkDropHighlight( TrayPopupInkDropStyle::HOST_CENTERED, this, - ink_drop_color_.value_or(SK_ColorWHITE)); + UnifiedSystemTrayView::GetBackgroundColor()); } const char* SystemMenuButton::GetClassName() const {
diff --git a/ash/system/tray/system_menu_button.h b/ash/system/tray/system_menu_button.h index 9d5cc18..7ca4d86a 100644 --- a/ash/system/tray/system_menu_button.h +++ b/ash/system/tray/system_menu_button.h
@@ -39,11 +39,6 @@ // colors. void SetVectorIcon(const gfx::VectorIcon& icon); - // Explicity sets the ink drop color. Otherwise the default value will be used - // by TrayPopupUtils::CreateInkDropRipple() and - // TrayPopupUtils::CreateInkDropHighlight(). - void SetInkDropColor(SkColor color); - // views::ImageButton: std::unique_ptr<views::InkDrop> CreateInkDrop() override; std::unique_ptr<views::InkDropRipple> CreateInkDropRipple() const override; @@ -55,11 +50,6 @@ // Returns the size that the ink drop should be constructed with. gfx::Size GetInkDropSize() const; - // The color to use when creating the ink drop. If null the default color is - // used as defined by TrayPopupUtils::CreateInkDropRipple() and - // TrayPopupUtils::CreateInkDropHighlight(). - base::Optional<SkColor> ink_drop_color_; - DISALLOW_COPY_AND_ASSIGN(SystemMenuButton); };
diff --git a/ash/system/unified/unified_system_tray_controller.cc b/ash/system/unified/unified_system_tray_controller.cc index 3f0f01b..b5dbfbd 100644 --- a/ash/system/unified/unified_system_tray_controller.cc +++ b/ash/system/unified/unified_system_tray_controller.cc
@@ -27,6 +27,7 @@ #include "ash/system/ime/unified_ime_detailed_view_controller.h" #include "ash/system/locale/locale_feature_pod_controller.h" #include "ash/system/locale/unified_locale_detailed_view_controller.h" +#include "ash/system/media/media_tray.h" #include "ash/system/media/unified_media_controls_controller.h" #include "ash/system/media/unified_media_controls_detailed_view_controller.h" #include "ash/system/model/clock_model.h" @@ -134,7 +135,8 @@ InitFeaturePods(); if (base::FeatureList::IsEnabled(media::kGlobalMediaControlsForChromeOS) && - !Shell::Get()->session_controller()->IsScreenLocked()) { + !Shell::Get()->session_controller()->IsScreenLocked() && + !MediaTray::IsPinnedToShelf()) { media_controls_controller_ = std::make_unique<UnifiedMediaControlsController>(this); unified_view_->AddMediaControlsView(
diff --git a/ash/wallpaper/wallpaper_controller_impl.cc b/ash/wallpaper/wallpaper_controller_impl.cc index 4589109f..70c9f69 100644 --- a/ash/wallpaper/wallpaper_controller_impl.cc +++ b/ash/wallpaper/wallpaper_controller_impl.cc
@@ -1379,7 +1379,8 @@ ReloadWallpaper(/*clear_cache=*/true); } - UpdateWallpaperForRootWindow(root_window, /*lock_state_changed=*/false); + UpdateWallpaperForRootWindow(root_window, /*lock_state_changed=*/false, + /*new_root=*/true); } void WallpaperControllerImpl::OnShellInitialized() { @@ -1471,7 +1472,8 @@ void WallpaperControllerImpl::UpdateWallpaperForRootWindow( aura::Window* root_window, - bool lock_state_changed) { + bool lock_state_changed, + bool new_root) { DCHECK_EQ(WALLPAPER_IMAGE, wallpaper_mode_); auto* wallpaper_widget_controller = @@ -1480,7 +1482,7 @@ WallpaperProperty property = wallpaper_widget_controller->GetWallpaperProperty(); - if (lock_state_changed) { + if (lock_state_changed || new_root) { const bool is_wallpaper_blurred_for_lock_state = Shell::Get()->session_controller()->IsUserSessionBlocked() && IsBlurAllowedForLockState(); @@ -1501,13 +1503,13 @@ wallpaper_widget_controller->wallpaper_view()->ClearCachedImage(); wallpaper_widget_controller->SetWallpaperProperty( - property, kWallpaperLoadAnimationDuration); + property, new_root ? base::TimeDelta() : kWallpaperLoadAnimationDuration); } void WallpaperControllerImpl::UpdateWallpaperForAllRootWindows( bool lock_state_changed) { for (aura::Window* root : Shell::GetAllRootWindows()) - UpdateWallpaperForRootWindow(root, lock_state_changed); + UpdateWallpaperForRootWindow(root, lock_state_changed, /*new_root=*/false); current_max_display_size_ = GetMaxDisplaySizeInNative(); }
diff --git a/ash/wallpaper/wallpaper_controller_impl.h b/ash/wallpaper/wallpaper_controller_impl.h index f15b2107..66a968c 100644 --- a/ash/wallpaper/wallpaper_controller_impl.h +++ b/ash/wallpaper/wallpaper_controller_impl.h
@@ -347,7 +347,8 @@ // Update a Wallpaper for |root_window|. void UpdateWallpaperForRootWindow(aura::Window* root_window, - bool lock_state_changed); + bool lock_state_changed, + bool new_root); // Update a Wallpaper for all root windows. void UpdateWallpaperForAllRootWindows(bool lock_state_changed);
diff --git a/ash/wallpaper/wallpaper_controller_unittest.cc b/ash/wallpaper/wallpaper_controller_unittest.cc index c1f9fde..4f37bf5df 100644 --- a/ash/wallpaper/wallpaper_controller_unittest.cc +++ b/ash/wallpaper/wallpaper_controller_unittest.cc
@@ -2785,4 +2785,20 @@ EXPECT_EQ(root_window->bounds().size(), wallpaper_view->bounds().size()); } +TEST_F(WallpaperControllerTest, NoAnimationForNewRootWindowWhenLocked) { + ui::ScopedAnimationDurationScaleMode test_duration_mode( + ui::ScopedAnimationDurationScaleMode::NON_ZERO_DURATION); + SetSessionState(SessionState::LOCKED); + UpdateDisplay("800x600, 800x600"); + auto* secondary_root_window_controller = + Shell::Get()->GetAllRootWindowControllers()[1]; + EXPECT_FALSE(secondary_root_window_controller->wallpaper_widget_controller() + ->IsAnimating()); + EXPECT_FALSE(secondary_root_window_controller->wallpaper_widget_controller() + ->GetWidget() + ->GetLayer() + ->GetAnimator() + ->is_animating()); +} + } // namespace ash
diff --git a/ash/wallpaper/wallpaper_view.cc b/ash/wallpaper/wallpaper_view.cc index 6ead2320..f2a514e 100644 --- a/ash/wallpaper/wallpaper_view.cc +++ b/ash/wallpaper/wallpaper_view.cc
@@ -4,6 +4,7 @@ #include "ash/wallpaper/wallpaper_view.h" +#include "ash/public/cpp/shell_window_ids.h" #include "ash/public/cpp/window_animation_types.h" #include "ash/root_window_controller.h" #include "ash/session/session_controller_impl.h" @@ -208,9 +209,11 @@ std::unique_ptr<views::Widget> CreateWallpaperWidget( aura::Window* root_window, - int container_id, const WallpaperProperty& property, + bool locked, WallpaperView** out_wallpaper_view) { + int container_id = locked ? kShellWindowId_LockScreenWallpaperContainer + : kShellWindowId_WallpaperContainer; auto* controller = Shell::Get()->wallpaper_controller(); auto wallpaper_widget = std::make_unique<views::Widget>(); @@ -238,11 +241,13 @@ // 2. Wallpaper fades in from a non empty background. // 3. From an empty background, chrome transit to a logged in user session. // 4. From an empty background, guest user logged in. - if (controller->ShouldShowInitialAnimation() || - RootWindowController::ForWindow(root_window) - ->wallpaper_widget_controller() - ->IsAnimating() || - Shell::Get()->session_controller()->NumberOfLoggedInUsers()) { + // except for the lock state. + if (!locked && + (controller->ShouldShowInitialAnimation() || + RootWindowController::ForWindow(root_window) + ->wallpaper_widget_controller() + ->IsAnimating() || + Shell::Get()->session_controller()->NumberOfLoggedInUsers())) { ::wm::SetWindowVisibilityAnimationTransition(wallpaper_window, ::wm::ANIMATE_SHOW); base::TimeDelta animation_duration = controller->animation_duration();
diff --git a/ash/wallpaper/wallpaper_view.h b/ash/wallpaper/wallpaper_view.h index 560d587..5cfd174 100644 --- a/ash/wallpaper/wallpaper_view.h +++ b/ash/wallpaper/wallpaper_view.h
@@ -68,8 +68,8 @@ std::unique_ptr<views::Widget> CreateWallpaperWidget( aura::Window* root_window, - int container_id, const WallpaperProperty& property, + bool locked, WallpaperView** out_wallpaper_view); } // namespace ash
diff --git a/ash/wallpaper/wallpaper_widget_controller.cc b/ash/wallpaper/wallpaper_widget_controller.cc index 17a465cb..90f16719 100644 --- a/ash/wallpaper/wallpaper_widget_controller.cc +++ b/ash/wallpaper/wallpaper_widget_controller.cc
@@ -34,9 +34,9 @@ widget_->CloseNow(); } -void WallpaperWidgetController::Init(int container) { - widget_ = CreateWallpaperWidget( - root_window_, container, wallpaper_constants::kClear, &wallpaper_view_); +void WallpaperWidgetController::Init(bool locked) { + widget_ = CreateWallpaperWidget(root_window_, wallpaper_constants::kClear, + locked, &wallpaper_view_); } views::Widget* WallpaperWidgetController::GetWidget() {
diff --git a/ash/wallpaper/wallpaper_widget_controller.h b/ash/wallpaper/wallpaper_widget_controller.h index c57e9b64..75dcb6aa 100644 --- a/ash/wallpaper/wallpaper_widget_controller.h +++ b/ash/wallpaper/wallpaper_widget_controller.h
@@ -39,9 +39,9 @@ base::OnceClosure wallpaper_set_callback); ~WallpaperWidgetController() override; - // Initialize the widget. |container| specifies the id of the parent container - // the window will be added to. - void Init(int container); + // Initialize the widget. |lock| specifies if the wallpaper should be created + // for the locked state. + void Init(bool locked); views::Widget* GetWidget();
diff --git a/ash/wm/drag_window_resizer.cc b/ash/wm/drag_window_resizer.cc index 098f66a4..99e6572 100644 --- a/ash/wm/drag_window_resizer.cc +++ b/ash/wm/drag_window_resizer.cc
@@ -143,6 +143,11 @@ // Adjust the size and position so that it doesn't exceed the size of work // area. display::Display dst_display; + // TODO(crbug.com/1131071): It's possible that |dst_display_id| returned from + // CursorManager::GetDisplay().id() is an invalid display id thus + // |dst_display| may be invalid as well. This may cause crash later. To avoid + // crash, we early return here. However, |dst_display_id| should never be + // invalid. if (!screen->GetDisplayWithDisplayId(dst_display_id, &dst_display)) return; const gfx::Size& size = dst_display.work_area().size();
diff --git a/ash/wm/overview/overview_grid_unittest.cc b/ash/wm/overview/overview_grid_unittest.cc index ee2b883e..43c43d9 100644 --- a/ash/wm/overview/overview_grid_unittest.cc +++ b/ash/wm/overview/overview_grid_unittest.cc
@@ -4,6 +4,7 @@ #include "ash/wm/overview/overview_grid.h" +#include "ash/frame_throttler/mock_frame_throttling_observer.h" #include "ash/screen_util.h" #include "ash/shell.h" #include "ash/test/ash_test_base.h" @@ -84,6 +85,8 @@ return SplitViewController::Get(Shell::GetPrimaryRootWindow()); } + OverviewGrid* grid() { return grid_.get(); } + private: std::unique_ptr<OverviewGrid> grid_; @@ -288,4 +291,40 @@ EXPECT_FALSE(item3->should_animate_when_entering()); } +TEST_F(OverviewGridTest, FrameThrottling) { + testing::NiceMock<MockFrameThrottlingObserver> observer; + FrameThrottlingController* frame_throttling_controller = + Shell::Get()->frame_throttling_controller(); + frame_throttling_controller->AddObserver(&observer); + const int window_count = 5; + std::unique_ptr<aura::Window> created_windows[window_count]; + std::vector<aura::Window*> windows(window_count, nullptr); + for (int i = 0; i < window_count; ++i) { + created_windows[i] = CreateTestWindow(); + windows[i] = created_windows[i].get(); + } + InitializeGrid(windows); + frame_throttling_controller->StartThrottling(windows); + + // Add a new window to overview. + std::unique_ptr<aura::Window> new_window(CreateTestWindow()); + windows.push_back(new_window.get()); + EXPECT_CALL(observer, OnThrottlingEnded()); + EXPECT_CALL(observer, + OnThrottlingStarted(testing::UnorderedElementsAreArray(windows))); + grid()->AppendItem(new_window.get(), /*reposition=*/false, /*animate=*/false, + /*use_spawn_animation=*/false); + + // Remove windows one by one. + for (int i = 0; i < window_count + 1; ++i) { + aura::Window* window = windows[0]; + windows.erase(windows.begin()); + EXPECT_CALL(observer, OnThrottlingEnded()); + EXPECT_CALL(observer, OnThrottlingStarted( + testing::UnorderedElementsAreArray(windows))); + OverviewItem* item = grid()->GetOverviewItemContaining(window); + grid()->RemoveItem(item, /*item_destroying=*/false, /*reposition=*/false); + } + frame_throttling_controller->RemoveObserver(&observer); +} } // namespace ash
diff --git a/base/BUILD.gn b/base/BUILD.gn index 67b97dab..2d02460 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn
@@ -1342,7 +1342,6 @@ if (is_apple) { sources += [ "allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.cc", - "allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.h", ] } if (is_chromeos || is_linux) {
diff --git a/base/allocator/BUILD.gn b/base/allocator/BUILD.gn index 95579b4..fbf0e7a 100644 --- a/base/allocator/BUILD.gn +++ b/base/allocator/BUILD.gn
@@ -6,6 +6,13 @@ import("//build/buildflag_header.gni") import("//build/config/compiler/compiler.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + declare_args() { # Provide a way to force disable debugallocation in Debug builds, # e.g. for profiling (it's more rare to profile Debug builds,
diff --git a/base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.cc b/base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.cc index 151783e7..35b9e094 100644 --- a/base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.cc +++ b/base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.cc
@@ -2,8 +2,6 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -#include "base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.h" - #include <utility> #include "base/allocator/allocator_interception_mac.h"
diff --git a/base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.h b/base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.h deleted file mode 100644 index c248203..0000000 --- a/base/allocator/allocator_shim_default_dispatch_to_mac_zoned_malloc.h +++ /dev/null
@@ -1,14 +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 BASE_ALLOCATOR_ALLOCATOR_SHIM_DEFAULT_DISPATCH_TO_ZONED_MALLOC_H_ -#define BASE_ALLOCATOR_ALLOCATOR_SHIM_DEFAULT_DISPATCH_TO_ZONED_MALLOC_H_ - -namespace base { -namespace allocator { - -} // namespace allocator -} // namespace base - -#endif // BASE_ALLOCATOR_ALLOCATOR_SHIM_DEFAULT_DISPATCH_TO_ZONED_MALLOC_H_
diff --git a/base/allocator/allocator_shim_default_dispatch_to_partition_alloc.cc b/base/allocator/allocator_shim_default_dispatch_to_partition_alloc.cc index 3b5f52c..8d29426 100644 --- a/base/allocator/allocator_shim_default_dispatch_to_partition_alloc.cc +++ b/base/allocator/allocator_shim_default_dispatch_to_partition_alloc.cc
@@ -76,7 +76,8 @@ } auto* new_root = new (g_allocator_buffer) base::ThreadSafePartitionRoot( - false /* enforce_alignment */, true /* enable_thread_cache */); + {base::PartitionOptions::Alignment::kRegular, + base::PartitionOptions::ThreadCache::kEnabled}); g_root_.store(new_root, std::memory_order_release); // Semantically equivalent to base::Lock::Release(). @@ -105,8 +106,9 @@ base::ThreadSafePartitionRoot* AlignedAllocator() { // Since the general-purpose allocator uses the thread cache, this one cannot. - static base::NoDestructor<base::ThreadSafePartitionRoot> aligned_allocator{ - true /* enforce_alignment */, false /* enable_thread_cache */}; + static base::NoDestructor<base::ThreadSafePartitionRoot> aligned_allocator( + base::PartitionOptions{base::PartitionOptions::Alignment::kAlignedAlloc, + base::PartitionOptions::ThreadCache::kDisabled}); return aligned_allocator.get(); }
diff --git a/base/allocator/partition_allocator/partition_alloc.cc b/base/allocator/partition_allocator/partition_alloc.cc index d658be6..e58f0b69 100644 --- a/base/allocator/partition_allocator/partition_alloc.cc +++ b/base/allocator/partition_allocator/partition_alloc.cc
@@ -258,8 +258,7 @@ } template <bool thread_safe> -void PartitionRoot<thread_safe>::Init(bool enforce_alignment, - bool enable_thread_cache) { +void PartitionRoot<thread_safe>::Init(PartitionOptions opts) { ScopedGuard guard{lock_}; if (initialized) return; @@ -272,12 +271,13 @@ // If alignment needs to be enforced, disallow adding cookies and/or tags at // the beginning of the slot. - allow_extras = !enforce_alignment; + allow_extras = (opts.alignment != PartitionOptions::Alignment::kAlignedAlloc); #if !defined(OS_POSIX) // TLS in ThreadCache not supported on other OSes. with_thread_cache = false; #else - with_thread_cache = enable_thread_cache; + with_thread_cache = + (opts.thread_cache == PartitionOptions::ThreadCache::kEnabled); if (with_thread_cache) internal::ThreadCache::Init(this); @@ -874,29 +874,21 @@ } template <bool thread_safe> -void PartitionAllocator<thread_safe>::init( - PartitionAllocatorAlignment alignment, - bool with_thread_cache) { +void PartitionAllocator<thread_safe>::init(PartitionOptions opts) { #if BUILDFLAG(USE_PARTITION_ALLOC_AS_MALLOC) - PA_CHECK(!with_thread_cache) + PA_CHECK(opts.thread_cache == PartitionOptions::ThreadCache::kDisabled) << "Cannot use a thread cache when PartitionAlloc is malloc()."; #endif - partition_root_.Init( - alignment == - PartitionAllocatorAlignment::kAlignedAlloc /* enforce_alignment */, - with_thread_cache); + partition_root_.Init(opts); PartitionAllocMemoryReclaimer::Instance()->RegisterPartition( &partition_root_); } template PartitionAllocator<internal::ThreadSafe>::~PartitionAllocator(); -template void PartitionAllocator<internal::ThreadSafe>::init( - PartitionAllocatorAlignment alignment, - bool with_thread_cache); +template void PartitionAllocator<internal::ThreadSafe>::init(PartitionOptions); template PartitionAllocator<internal::NotThreadSafe>::~PartitionAllocator(); template void PartitionAllocator<internal::NotThreadSafe>::init( - PartitionAllocatorAlignment alignment, - bool with_thread_cache); + PartitionOptions); #if DCHECK_IS_ON() void DCheckIfManagedByPartitionAllocNormalBuckets(const void* ptr) {
diff --git a/base/allocator/partition_allocator/partition_alloc.h b/base/allocator/partition_allocator/partition_alloc.h index bdfe6c3..1b599d1 100644 --- a/base/allocator/partition_allocator/partition_alloc.h +++ b/base/allocator/partition_allocator/partition_alloc.h
@@ -367,6 +367,31 @@ } // namespace +// Options struct used to configure PartitionRoot and PartitionAllocator. +struct PartitionOptions { + enum class Alignment { + // By default all allocations will be aligned to 8B (16B if + // BUILDFLAG_INTERNAL_USE_PARTITION_ALLOC_AS_MALLOC is true). + kRegular, + + // In addition to the above alignment enforcement, this option allows using + // AlignedAlloc() which can align at a larger boundary. This option comes + // at a cost of disallowing cookies on Debug builds and tags/ref-counts for + // CheckedPtr. It also causes all allocations to go outside of GigaCage, so + // that CheckedPtr can easily tell if a pointer comes with a tag/ref-count + // or not. + kAlignedAlloc, + }; + + enum class ThreadCache { + kDisabled, + kEnabled, + }; + + Alignment alignment = Alignment::kRegular; + ThreadCache thread_cache = ThreadCache::kDisabled; +}; + // Never instantiate a PartitionRoot directly, instead use // PartitionAllocator. template <bool thread_safe> @@ -429,9 +454,7 @@ Bucket sentinel_bucket; PartitionRoot() = default; - PartitionRoot(bool enable_tag_pointers, bool enable_thread_cache) { - Init(enable_tag_pointers, enable_thread_cache); - } + explicit PartitionRoot(PartitionOptions opts) { Init(opts); } ~PartitionRoot(); // Public API @@ -444,7 +467,7 @@ // // Moving it a layer lower couples PartitionRoot and PartitionBucket, but // preserves the layering of the includes. - void Init(bool enforce_alignment, bool enable_thread_cache); + void Init(PartitionOptions); ALWAYS_INLINE static bool IsValidPage(Page* page); ALWAYS_INLINE static PartitionRoot* FromPage(Page* page); @@ -1144,28 +1167,13 @@ #endif } -enum class PartitionAllocatorAlignment { - // By default all allocations will be aligned to 8B (16B if - // BUILDFLAG_INTERNAL_USE_PARTITION_ALLOC_AS_MALLOC is true). - kRegular, - - // In addition to the above alignment enforcement, this option allows using - // AlignedAlloc() which can align at a larger boundary. - // This option comes at a cost of disallowing cookies on Debug builds and tags - // for CheckedPtr. It also causes all allocations to go outside of GigaCage, - // so that CheckedPtr can easily tell if a pointer comes with a tag or not. - kAlignedAlloc, -}; - namespace internal { template <bool thread_safe> struct BASE_EXPORT PartitionAllocator { PartitionAllocator() = default; ~PartitionAllocator(); - void init(PartitionAllocatorAlignment alignment = - PartitionAllocatorAlignment::kRegular, - bool with_thread_cache = false); + void init(PartitionOptions = {}); ALWAYS_INLINE PartitionRoot<thread_safe>* root() { return &partition_root_; } private:
diff --git a/base/allocator/partition_allocator/partition_alloc_perftest.cc b/base/allocator/partition_allocator/partition_alloc_perftest.cc index 9f73792b..3e9e51bd 100644 --- a/base/allocator/partition_allocator/partition_alloc_perftest.cc +++ b/base/allocator/partition_allocator/partition_alloc_perftest.cc
@@ -84,7 +84,8 @@ void Free(void* data) override { ThreadSafePartitionRoot::FreeNoHooks(data); } private: - ThreadSafePartitionRoot alloc_{false, false}; + ThreadSafePartitionRoot alloc_{{PartitionOptions::Alignment::kRegular, + PartitionOptions::ThreadCache::kDisabled}}; }; class TestLoopThread : public PlatformThread::Delegate {
diff --git a/base/allocator/partition_allocator/partition_alloc_unittest.cc b/base/allocator/partition_allocator/partition_alloc_unittest.cc index 8ed03f5..e3207fcd 100644 --- a/base/allocator/partition_allocator/partition_alloc_unittest.cc +++ b/base/allocator/partition_allocator/partition_alloc_unittest.cc
@@ -156,8 +156,8 @@ void SetUp() override { scoped_feature_list.InitWithFeatures({kPartitionAllocGigaCage}, {}); PartitionAllocGlobalInit(HandleOOM); - allocator.init(PartitionAllocatorAlignment::kRegular); - aligned_allocator.init(PartitionAllocatorAlignment::kAlignedAlloc); + allocator.init({PartitionOptions::Alignment::kRegular}); + aligned_allocator.init({PartitionOptions::Alignment::kAlignedAlloc}); test_bucket_index_ = SizeToIndex(kRealAllocSize); }
diff --git a/base/allocator/partition_allocator/thread_cache_unittest.cc b/base/allocator/partition_allocator/thread_cache_unittest.cc index 1b5cdba..9c6ae7d 100644 --- a/base/allocator/partition_allocator/thread_cache_unittest.cc +++ b/base/allocator/partition_allocator/thread_cache_unittest.cc
@@ -59,7 +59,9 @@ // PartitionRoot has to outlive it. // // Forbid extras, since they make finding out which bucket is used harder. -NoDestructor<ThreadSafePartitionRoot> g_root{true, true}; +NoDestructor<ThreadSafePartitionRoot> g_root{ + PartitionOptions{PartitionOptions::Alignment::kAlignedAlloc, + PartitionOptions::ThreadCache::kEnabled}}; size_t FillThreadCacheAndReturnIndex(size_t size, size_t count = 1) { uint16_t bucket_index = PartitionRoot<ThreadSafe>::SizeToBucketIndex(size); @@ -157,7 +159,8 @@ TEST_F(ThreadCacheTest, NoCrossPartitionCache) { const size_t kTestSize = 12; - ThreadSafePartitionRoot root{true, false}; + ThreadSafePartitionRoot root{{PartitionOptions::Alignment::kAlignedAlloc, + PartitionOptions::ThreadCache::kDisabled}}; size_t bucket_index = FillThreadCacheAndReturnIndex(kTestSize); void* ptr = root.Alloc(kTestSize, "");
diff --git a/base/ios/scoped_critical_action.mm b/base/ios/scoped_critical_action.mm index a799ca4..51f9639c 100644 --- a/base/ios/scoped_critical_action.mm +++ b/base/ios/scoped_critical_action.mm
@@ -14,53 +14,6 @@ #include "base/metrics/user_metrics.h" #include "base/strings/sys_string_conversions.h" #include "base/synchronization/lock.h" -#import "build/branding_buildflags.h" - -#if BUILDFLAG(CHROMIUM_BRANDING) -#include <dlfcn.h> -#endif // BUILDFLAG(CHROMIUM_BRANDING) - -namespace { - -// |backgroundTimeRemaining| is thread-safe, but as of Xcode 11.4 this method -// is still incorrectly marked as not thread-safe, so checking the value of -// |backgroundTimeRemaining| will trigger libMainThreadChecker (if enabled). -// Instead, for Chromium builds only, disable libMainThreadChecker for just -// this call. This logic is only useful for developer builds, and should not -// be included in official builds. These blocks should be removed if future -// versions of the library whitelists |backgroundTimeRemaining|. -NSTimeInterval GetBackgroundTimeRemaining(UIApplication* application) { -#if BUILDFLAG(CHROMIUM_BRANDING) - if (!base::ios::IsRunningOnIOS13OrLater()) { - // On developer iOS12 builds there's no way to suppress the main thread - // checker assert. Since it's a developer build, simply return 0. - return 0; - } - static char const* const lib_main_thread_checker_bundle_path = -#if TARGET_IPHONE_SIMULATOR - "/usr/lib/libMainThreadChecker.dylib"; -#else - "/Developer/usr/lib/libMainThreadChecker.dylib"; -#endif - static void* handle = - dlopen(lib_main_thread_checker_bundle_path, RTLD_NOLOAD | RTLD_LAZY); - static void (*main_thread_checker_suppression_begin)() = - (void (*)())dlsym(handle, "__main_thread_checker_suppression_begin"); - if (main_thread_checker_suppression_begin) - main_thread_checker_suppression_begin(); -#endif // BUILDFLAG(CHROMIUM_BRANDING) - NSTimeInterval time = application.backgroundTimeRemaining; -#if BUILDFLAG(CHROMIUM_BRANDING) - static void (*main_thread_checker_suppression_end)() = - (void (*)())dlsym(handle, "__main_thread_checker_suppression_end"); - if (main_thread_checker_suppression_end) - main_thread_checker_suppression_end(); - dlclose(handle); -#endif // BUILDFLAG(CHROMIUM_BRANDING) - return time; -} - -} // namespace namespace base { namespace ios { @@ -93,7 +46,7 @@ return; } - NSTimeInterval time = GetBackgroundTimeRemaining(application); + NSTimeInterval time = application.backgroundTimeRemaining; if (time != DBL_MAX && time > 0) { UMA_HISTOGRAM_MEDIUM_TIMES("IOS.CriticalActionBackgroundTimeRemaining", base::TimeDelta::FromSeconds(time));
diff --git a/base/process/process_info_win.cc b/base/process/process_info_win.cc index 594fd1d..a08835ee 100644 --- a/base/process/process_info_win.cc +++ b/base/process/process_info_win.cc
@@ -17,35 +17,34 @@ namespace { -HANDLE GetCurrentProcessToken() { - HANDLE process_token; +base::win::ScopedHandle CreateCurrentProcessToken() { + // OpenProcessToken can fail due to permission or allocation failures + // for the kernel object. Return nullptr in those cases. + HANDLE process_token = nullptr; OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &process_token); - DCHECK(process_token != NULL && process_token != INVALID_HANDLE_VALUE); - return process_token; + return base::win::ScopedHandle(process_token); } } // namespace IntegrityLevel GetCurrentProcessIntegrityLevel() { - HANDLE process_token(GetCurrentProcessToken()); + base::win::ScopedHandle scoped_process_token(CreateCurrentProcessToken()); DWORD token_info_length = 0; - if (::GetTokenInformation(process_token, TokenIntegrityLevel, nullptr, 0, - &token_info_length) || + if (::GetTokenInformation(scoped_process_token.Get(), TokenIntegrityLevel, + nullptr, 0, &token_info_length) || ::GetLastError() != ERROR_INSUFFICIENT_BUFFER) { - NOTREACHED(); return INTEGRITY_UNKNOWN; } auto token_label_bytes = std::make_unique<char[]>(token_info_length); TOKEN_MANDATORY_LABEL* token_label = reinterpret_cast<TOKEN_MANDATORY_LABEL*>(token_label_bytes.get()); - if (!::GetTokenInformation(process_token, TokenIntegrityLevel, token_label, - token_info_length, &token_info_length)) { - NOTREACHED(); + if (!::GetTokenInformation(scoped_process_token.Get(), TokenIntegrityLevel, + token_label, token_info_length, + &token_info_length)) { return INTEGRITY_UNKNOWN; } - DWORD integrity_level = *::GetSidSubAuthority( token_label->Label.Sid, static_cast<DWORD>(*::GetSidSubAuthorityCount(token_label->Label.Sid) - @@ -70,14 +69,14 @@ } bool IsCurrentProcessElevated() { - HANDLE process_token(GetCurrentProcessToken()); + base::win::ScopedHandle scoped_process_token(CreateCurrentProcessToken()); // Unlike TOKEN_ELEVATION_TYPE which returns TokenElevationTypeDefault when // UAC is turned off, TOKEN_ELEVATION returns whether the process is elevated. DWORD size; TOKEN_ELEVATION elevation; - if (!GetTokenInformation(process_token, TokenElevation, &elevation, - sizeof(elevation), &size)) { + if (!GetTokenInformation(scoped_process_token.Get(), TokenElevation, + &elevation, sizeof(elevation), &size)) { PLOG(ERROR) << "GetTokenInformation() failed"; return false; }
diff --git a/base/profiler/module_cache.cc b/base/profiler/module_cache.cc index 72fd1c5f..9c72296 100644 --- a/base/profiler/module_cache.cc +++ b/base/profiler/module_cache.cc
@@ -40,9 +40,8 @@ if (!new_module) return nullptr; const auto result = native_modules_.insert(std::move(new_module)); - // Ensure that the new module was inserted an isn't equivalent to an existing - // module. - DCHECK(result.second); + // TODO(https://crbug.com/1131769): Reintroduce DCHECK(result.second) after + // fixing the issue that is causing it to fail. return result.first->get(); }
diff --git a/build/OWNERS b/build/OWNERS index 18f9fa5..a0c1bba1 100644 --- a/build/OWNERS +++ b/build/OWNERS
@@ -6,9 +6,12 @@ thomasanderson@chromium.org tikuta@chromium.org -# Clang build config changes +# Clang build config changes: hans@chromium.org +# For java build changes: +wnwen@chromium.org + per-file .gitignore=* per-file check_gn_headers_whitelist.txt=* per-file mac_toolchain.py=erikchen@chromium.org
diff --git a/build/android/gyp/proguard.py b/build/android/gyp/proguard.py index 3ba4f819..9975ad69 100755 --- a/build/android/gyp/proguard.py +++ b/build/android/gyp/proguard.py
@@ -161,9 +161,6 @@ elif not options.output_path: parser.error('Output path required when feature splits aren\'t used') - if options.main_dex_rules_path and not options.r8_path: - parser.error('R8 must be enabled to pass main dex rules.') - options.classpath = build_utils.ParseGnList(options.classpath) options.proguard_configs = build_utils.ParseGnList(options.proguard_configs) options.input_paths = build_utils.ParseGnList(options.input_paths) @@ -376,14 +373,6 @@ def _CreateDynamicConfig(options): ret = [] - if not options.r8_path and options.min_api: - # R8 adds this option automatically, and uses -assumenosideeffects instead - # (which ProGuard doesn't support doing). - ret.append("""\ --assumevalues class android.os.Build$VERSION { - public static final int SDK_INT return %s..9999; -}""" % options.min_api) - if options.sourcefile: ret.append("-renamesourcefileattribute '%s' # OMIT FROM EXPECTATIONS" % options.sourcefile)
diff --git a/build/android/resource_sizes.py b/build/android/resource_sizes.py index 6a17cfd..efe377a0 100755 --- a/build/android/resource_sizes.py +++ b/build/android/resource_sizes.py
@@ -315,8 +315,13 @@ with zipfile.ZipFile(apk_filename, 'r') as apk: apk_contents = apk.infolist() + # Account for zipalign overhead that exists in local file header. zipalign_overhead = sum( _ReadZipInfoExtraFieldLength(apk, i) for i in apk_contents) + # Account for zipalign overhead that exists in central directory header. + # Happens when python aligns entries in apkbuilder.py, but does not + # exist when using Android's zipalign. E.g. for bundle .apks files. + zipalign_overhead += sum(len(i.extra) for i in apk_contents) sdk_version, skip_extract_lib = _ParseManifestAttributes(apk_filename)
diff --git a/build/config/compiler/BUILD.gn b/build/config/compiler/BUILD.gn index 42839cfb..1a05df7 100644 --- a/build/config/compiler/BUILD.gn +++ b/build/config/compiler/BUILD.gn
@@ -2010,7 +2010,7 @@ # Default "optimization on" config. config("optimize") { if (is_win) { - if (chrome_pgo_phase != 2) { + if (chrome_pgo_phase == 0) { # Favor size over speed, /O1 must be before the common flags. # /O1 implies /Os and /GF. cflags = [ "/O1" ] + common_optimize_on_cflags + [ "/Oi" ]
diff --git a/build/fuchsia/linux.sdk.sha1 b/build/fuchsia/linux.sdk.sha1 index ad82bb4..9a4452b 100644 --- a/build/fuchsia/linux.sdk.sha1 +++ b/build/fuchsia/linux.sdk.sha1
@@ -1 +1 @@ -0.20200924.0.1 +0.20200924.1.1
diff --git a/build/fuchsia/mac.sdk.sha1 b/build/fuchsia/mac.sdk.sha1 index ad82bb4..9a4452b 100644 --- a/build/fuchsia/mac.sdk.sha1 +++ b/build/fuchsia/mac.sdk.sha1
@@ -1 +1 @@ -0.20200924.0.1 +0.20200924.1.1
diff --git a/cc/test/pixel_test.cc b/cc/test/pixel_test.cc index 24676f9ab..55e7e11 100644 --- a/cc/test/pixel_test.cc +++ b/cc/test/pixel_test.cc
@@ -306,8 +306,7 @@ renderer_ = std::make_unique<viz::SkiaRenderer>( &renderer_settings_, &debug_settings_, output_surface_.get(), resource_provider_.get(), nullptr, - static_cast<viz::SkiaOutputSurface*>(output_surface_.get()), - viz::SkiaRenderer::DrawMode::DDL); + static_cast<viz::SkiaOutputSurface*>(output_surface_.get())); renderer_->Initialize(); renderer_->SetVisible(true);
diff --git a/chrome/android/BUILD.gn b/chrome/android/BUILD.gn index 90f7cd2..377d99c 100644 --- a/chrome/android/BUILD.gn +++ b/chrome/android/BUILD.gn
@@ -408,6 +408,7 @@ "//components/location/android:location_java", "//components/location/android:settings_java", "//components/media_router/browser/android:java", + "//components/messages/android:factory_java", "//components/messages/android:java", "//components/minidump_uploader:minidump_uploader_java", "//components/module_installer/android:module_installer_java", @@ -629,6 +630,7 @@ "//chrome/browser/ui/android/appmenu/internal:java", "//chrome/browser/video_tutorials/internal:java", "//components/browser_ui/android/bottomsheet/internal:java", + "//components/messages/android/internal:java", ] if (disable_autofill_assistant_dfm) {
diff --git a/chrome/android/features/start_surface/internal/javatests/src/org/chromium/chrome/features/start_surface/InstantStartTest.java b/chrome/android/features/start_surface/internal/javatests/src/org/chromium/chrome/features/start_surface/InstantStartTest.java index 16c918f..a1b4c1c7 100644 --- a/chrome/android/features/start_surface/internal/javatests/src/org/chromium/chrome/features/start_surface/InstantStartTest.java +++ b/chrome/android/features/start_surface/internal/javatests/src/org/chromium/chrome/features/start_surface/InstantStartTest.java
@@ -308,10 +308,13 @@ @Restriction({UiRestriction.RESTRICTION_TYPE_PHONE}) // clang-format off @EnableFeatures({ChromeFeatureList.TAB_SWITCHER_ON_RETURN + "<Study,", - ChromeFeatureList.START_SURFACE_ANDROID + "<Study"}) + ChromeFeatureList.START_SURFACE_ANDROID + "<Study", + ChromeFeatureList.TAB_GRID_LAYOUT_ANDROID + "<Study", + ChromeFeatureList.TAB_GROUPS_ANDROID, + ChromeFeatureList.TAB_GROUPS_CONTINUATION_ANDROID}) @CommandLineFlags.Add({ChromeSwitches.DISABLE_NATIVE_INITIALIZATION, "force-fieldtrials=Study/Group", - IMMEDIATE_RETURN_PARAMS + "/start_surface_variation/single"}) + IMMEDIATE_RETURN_PARAMS + "/start_surface_variation/single/enable_launch_polish/true"}) public void startSurfaceSinglePanePreNativeAndWithNativeTest() { // clang-format on startMainActivityFromLauncher();
diff --git a/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabListCoordinator.java b/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabListCoordinator.java index 496e6d5..97d7475 100644 --- a/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabListCoordinator.java +++ b/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabListCoordinator.java
@@ -274,9 +274,7 @@ private static void setThumbnailViewAspectRatio(View view) { float mExpectedThumbnailAspectRatio = - (float) ChromeFeatureList.getFieldTrialParamByFeatureAsDouble( - ChromeFeatureList.TAB_GRID_LAYOUT_ANDROID, - TabUiFeatureUtilities.THUMBNAIL_ASPECT_RATIO_PARAM, 1.0); + (float) TabUiFeatureUtilities.THUMBNAIL_ASPECT_RATIO.getValue(); mExpectedThumbnailAspectRatio = MathUtils.clamp(mExpectedThumbnailAspectRatio, 0.5f, 2.0f); TabGridThumbnailView thumbnailView = (TabGridThumbnailView) view.findViewById(R.id.tab_thumbnail);
diff --git a/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherCoordinator.java b/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherCoordinator.java index 8e8a55e..7b67500 100644 --- a/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherCoordinator.java +++ b/chrome/android/features/tab_ui/java/src/org/chromium/chrome/browser/tasks/tab_management/TabSwitcherCoordinator.java
@@ -180,6 +180,8 @@ @Override public void finishedShowing() { + if (!mTabModelSelector.isTabStateInitialized()) return; + int selectedIndex = mTabModelSelector.getTabModelFilterProvider() .getCurrentTabModelFilter() .index();
diff --git a/chrome/android/java/DEPS b/chrome/android/java/DEPS index 4045d3a..f1b1586 100644 --- a/chrome/android/java/DEPS +++ b/chrome/android/java/DEPS
@@ -37,6 +37,7 @@ "+components/gcm_driver/android/java/src/org/chromium/components/gcm_driver", "+components/language", "+components/location/android/java", + "+components/messages/android", "+components/minidump_uploader", "+components/module_installer", "+components/navigation_interception",
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/app/flags/ChromeCachedFlags.java b/chrome/android/java/src/org/chromium/chrome/browser/app/flags/ChromeCachedFlags.java index a29b84c..c1c71fe 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/app/flags/ChromeCachedFlags.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/app/flags/ChromeCachedFlags.java
@@ -60,6 +60,7 @@ ChromeFeatureList.INSTANT_START, ChromeFeatureList.INTEREST_FEED_CONTENT_SUGGESTIONS, ChromeFeatureList.INTEREST_FEED_V2, + ChromeFeatureList.MESSAGES_FOR_ANDROID_INFRASTRUCTURE, ChromeFeatureList.OMNIBOX_SUGGESTIONS_RECYCLER_VIEW, ChromeFeatureList.PAINT_PREVIEW_DEMO, ChromeFeatureList.PAINT_PREVIEW_SHOW_ON_STARTUP,
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/compositor/CompositorViewHolder.java b/chrome/android/java/src/org/chromium/chrome/browser/compositor/CompositorViewHolder.java index 11fbb94..9bebd59d 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/compositor/CompositorViewHolder.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/compositor/CompositorViewHolder.java
@@ -46,7 +46,6 @@ import org.chromium.chrome.browser.ActivityTabProvider; import org.chromium.chrome.browser.browser_controls.BrowserControlsStateProvider; import org.chromium.chrome.browser.browser_controls.BrowserControlsUtils; -import org.chromium.chrome.browser.compositor.Invalidator.Client; import org.chromium.chrome.browser.compositor.layouts.LayoutManager; import org.chromium.chrome.browser.compositor.layouts.LayoutManagerHost; import org.chromium.chrome.browser.compositor.layouts.LayoutRenderHost; @@ -137,8 +136,7 @@ private int mPendingFrameCount; - private final ArrayList<Invalidator.Client> mPendingInvalidations = - new ArrayList<>(); + private final ArrayList<Runnable> mPendingInvalidations = new ArrayList<>(); private boolean mSkipInvalidation; /** @@ -1402,11 +1400,11 @@ } @Override - public void deferInvalidate(Client client) { + public void deferInvalidate(Runnable clientInvalidator) { if (mPendingFrameCount <= 0) { - client.doInvalidate(); - } else if (!mPendingInvalidations.contains(client)) { - mPendingInvalidations.add(client); + clientInvalidator.run(); + } else if (!mPendingInvalidations.contains(clientInvalidator)) { + mPendingInvalidations.add(clientInvalidator); } } @@ -1414,7 +1412,7 @@ if (mPendingInvalidations.isEmpty()) return; TraceEvent.instant("CompositorViewHolder.flushInvalidation"); for (int i = 0; i < mPendingInvalidations.size(); i++) { - mPendingInvalidations.get(i).doInvalidate(); + mPendingInvalidations.get(i).run(); } mPendingInvalidations.clear(); }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/compositor/Invalidator.java b/chrome/android/java/src/org/chromium/chrome/browser/compositor/Invalidator.java index 7849468..65c3098 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/compositor/Invalidator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/compositor/Invalidator.java
@@ -9,25 +9,15 @@ */ public class Invalidator { /** - * Interface for the client that gets invalidated. - */ - public interface Client { - /** - * Do the invalidation. - */ - void doInvalidate(); - } - - /** * Interface for the host that drives the invalidations. */ public interface Host { /** * Requests an invalidation of the view. * - * @param view The {@link View} to invalidate. + * @param invalidator {@link Runnable} that invalidates the view. */ - void deferInvalidate(Client view); + void deferInvalidate(Runnable invalidator); } private Host mHost; @@ -43,13 +33,13 @@ * Invalidates either immediately (if no host is specified) or at time * triggered by the host. * - * @param client The {@link Client} to invalidate, most likely a view. + * @param invalidator The {@link Runnable} performing invalidation. */ - public void invalidate(Client client) { + public void invalidate(Runnable invalidator) { if (mHost != null) { - mHost.deferInvalidate(client); + mHost.deferInvalidate(invalidator); } else { - client.doInvalidate(); + invalidator.run(); } } }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/ChromeContextMenuPopulator.java b/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/ChromeContextMenuPopulator.java index 09af504..3eb9fe9f 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/ChromeContextMenuPopulator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/ChromeContextMenuPopulator.java
@@ -389,7 +389,8 @@ // being loaded. Only use native URL formatting methods // if the native libraries have been loaded. if (BrowserStartupController.getInstance().isFullBrowserStarted()) { - return UrlFormatter.formatUrlForDisplayOmitHTTPScheme(params.getLinkUrl()); + return UrlFormatter.formatUrlForDisplayOmitSchemeOmitTrivialSubdomains( + params.getLinkUrl()); } return params.getLinkUrl(); }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/OWNERS b/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/OWNERS index aacc1b6..0170aa21 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/OWNERS +++ b/chrome/android/java/src/org/chromium/chrome/browser/contextmenu/OWNERS
@@ -1,4 +1,5 @@ twellington@chromium.org +sinansahin@google.com # COMPONENT: UI>Browser>Mobile>ContextMenu # TEAM: chrome-android-app@chromium.org
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/IncognitoCustomTabIntentDataProvider.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/IncognitoCustomTabIntentDataProvider.java index 9a179fd..4d526552 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/IncognitoCustomTabIntentDataProvider.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/IncognitoCustomTabIntentDataProvider.java
@@ -11,10 +11,13 @@ import static org.chromium.chrome.browser.customtabs.CustomTabIntentDataProvider.EXTRA_UI_TYPE; import static org.chromium.chrome.browser.customtabs.CustomTabIntentDataProvider.isTrustedCustomTab; +import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.graphics.drawable.Drawable; import android.os.Bundle; +import android.text.TextUtils; +import android.util.Pair; import androidx.annotation.Nullable; import androidx.browser.customtabs.CustomTabsIntent; @@ -29,6 +32,9 @@ import org.chromium.components.browser_ui.styles.ChromeColors; import org.chromium.components.browser_ui.widget.TintedDrawable; +import java.util.ArrayList; +import java.util.List; + /** * A model class that parses the incoming intent for incognito Custom Tabs specific customization * data. @@ -38,21 +44,26 @@ * to activity re-creation. */ public class IncognitoCustomTabIntentDataProvider extends BrowserServicesIntentDataProvider { + private static final int MAX_CUSTOM_MENU_ITEMS = 5; + private final Intent mIntent; private final CustomTabsSessionToken mSession; private final boolean mIsTrustedIntent; private final Bundle mAnimationBundle; - @Nullable - private final String mUrlToLoad; - private final int mToolbarColor; private final int mBottomBarColor; private final Drawable mCloseButtonIcon; private final boolean mShowShareItem; + private final List<Pair<String, PendingIntent>> mMenuEntries = new ArrayList<>(); + + @Nullable + private final String mUrlToLoad; /** Whether this CustomTabActivity was explicitly started by another Chrome Activity. */ private final boolean mIsOpenedByChrome; + private final @CustomTabsUiType int mUiType; + /** * Constructs a {@link IncognitoCustomTabIntentDataProvider}. * Incognito CCT would have a fix color scheme. @@ -74,6 +85,16 @@ mCloseButtonIcon = TintedDrawable.constructTintedDrawable(context, R.drawable.btn_close); mShowShareItem = IntentUtils.safeGetBooleanExtra( intent, CustomTabsIntent.EXTRA_DEFAULT_SHARE_MENU_ITEM, false); + + mUiType = getUiType(intent); + updateExtraMenuItemsIfNecessary(intent); + } + + private static @CustomTabsUiType int getUiType(Intent intent) { + if (isForPaymentsFlow(intent)) return CustomTabsUiType.PAYMENT_REQUEST; + if (isForReaderMode(intent)) return CustomTabsUiType.READER_MODE; + + return CustomTabsUiType.DEFAULT; } private static boolean isIncognitoRequested(Intent intent) { @@ -82,13 +103,44 @@ } private static boolean isForPaymentsFlow(Intent intent) { + final int requestedUiType = + IntentUtils.safeGetIntExtra(intent, EXTRA_UI_TYPE, CustomTabsUiType.DEFAULT); + return (isTrustedIntent(intent) && (requestedUiType == CustomTabsUiType.PAYMENT_REQUEST)); + } + + private static boolean isForReaderMode(Intent intent) { + final int requestedUiType = + IntentUtils.safeGetIntExtra(intent, EXTRA_UI_TYPE, CustomTabsUiType.DEFAULT); + return (isTrustedIntent(intent) && (requestedUiType == CustomTabsUiType.READER_MODE)); + } + + private static boolean isTrustedIntent(Intent intent) { CustomTabsSessionToken session = CustomTabsSessionToken.getSessionTokenFromIntent(intent); boolean isOpenedByChrome = IntentUtils.safeGetBooleanExtra(intent, EXTRA_IS_OPENED_BY_CHROME, false); - final int requestedUiType = - IntentUtils.safeGetIntExtra(intent, EXTRA_UI_TYPE, CustomTabsUiType.DEFAULT); - return (isTrustedCustomTab(intent, session) && isOpenedByChrome - && (requestedUiType == CustomTabsUiType.PAYMENT_REQUEST)); + return isTrustedCustomTab(intent, session) && isOpenedByChrome; + } + + private static boolean isAllowedToAddCustomMenuItem(Intent intent) { + // Only READER_MODE is supported for now. + return isForReaderMode(intent); + } + + private void updateExtraMenuItemsIfNecessary(Intent intent) { + if (!isAllowedToAddCustomMenuItem(intent)) return; + + List<Bundle> menuItems = + IntentUtils.getParcelableArrayListExtra(intent, CustomTabsIntent.EXTRA_MENU_ITEMS); + if (menuItems == null) return; + + for (int i = 0; i < Math.min(MAX_CUSTOM_MENU_ITEMS, menuItems.size()); i++) { + Bundle bundle = menuItems.get(i); + String title = IntentUtils.safeGetString(bundle, CustomTabsIntent.KEY_MENU_ITEM_TITLE); + PendingIntent pendingIntent = + IntentUtils.safeGetParcelable(bundle, CustomTabsIntent.KEY_PENDING_INTENT); + if (TextUtils.isEmpty(title) || pendingIntent == null) continue; + mMenuEntries.add(new Pair<String, PendingIntent>(title, pendingIntent)); + } } // TODO(https://crbug.com/1023759): Remove this function and enable @@ -204,4 +256,19 @@ public boolean isIncognito() { return true; } + + @Override + @CustomTabsUiType + public int getUiType() { + return mUiType; + } + + @Override + public List<String> getMenuTitles() { + ArrayList<String> list = new ArrayList<>(); + for (Pair<String, PendingIntent> pair : mMenuEntries) { + list.add(pair.first); + } + return list; + } }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/identity_disc/IdentityDiscController.java b/chrome/android/java/src/org/chromium/chrome/browser/identity_disc/IdentityDiscController.java index 9c5260e..6f26b53 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/identity_disc/IdentityDiscController.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/identity_disc/IdentityDiscController.java
@@ -169,7 +169,7 @@ return; } - String email = CoreAccountInfo.getEmailFrom(getSyncAccountInfo()); + String email = CoreAccountInfo.getEmailFrom(getSignedInAccountInfo()); mState = email == null ? IdentityDiscState.NONE : IdentityDiscState.SMALL; ensureProfileDataCache(email, mState); @@ -235,7 +235,7 @@ if (mState == IdentityDiscState.NONE) return; assert mProfileDataCache[mState] != null; - if (accountEmail.equals(CoreAccountInfo.getEmailFrom(getSyncAccountInfo()))) { + if (accountEmail.equals(CoreAccountInfo.getEmailFrom(getSignedInAccountInfo()))) { notifyObservers(true); } } @@ -295,8 +295,13 @@ * null for off-the-record ones. * @return account info for the current profile. Returns null for OTR profile. */ - private CoreAccountInfo getSyncAccountInfo() { - return mIdentityManager != null ? mIdentityManager.getPrimaryAccountInfo(ConsentLevel.SYNC) + private CoreAccountInfo getSignedInAccountInfo() { + @ConsentLevel + int consentLevel = + ChromeFeatureList.isEnabled(ChromeFeatureList.MOBILE_IDENTITY_CONSISTENCY) + ? ConsentLevel.NOT_REQUIRED + : ConsentLevel.SYNC; + return mIdentityManager != null ? mIdentityManager.getPrimaryAccountInfo(consentLevel) : null; }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/AutocompleteController.java b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/AutocompleteController.java index e7a1e0d..f57dc34 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/AutocompleteController.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/AutocompleteController.java
@@ -23,6 +23,7 @@ import org.chromium.chrome.browser.omnibox.OmniboxSuggestionType; import org.chromium.chrome.browser.omnibox.suggestions.AutocompleteResult.GroupDetails; import org.chromium.chrome.browser.omnibox.suggestions.OmniboxSuggestion.MatchClassification; +import org.chromium.chrome.browser.omnibox.suggestions.OmniboxSuggestion.NavsuggestTile; import org.chromium.chrome.browser.omnibox.voice.VoiceRecognitionHandler.VoiceResult; import org.chromium.chrome.browser.profiles.Profile; import org.chromium.chrome.browser.tab.Tab; @@ -353,7 +354,8 @@ int[] descriptionClassificationStyles, SuggestionAnswer answer, String fillIntoEdit, GURL url, GURL imageUrl, String imageDominantColor, boolean isStarred, boolean isDeletable, String postContentType, byte[] postData, int groupId, - List<QueryTile> tiles, byte[] clipboardImageData, boolean hasTabMatch) { + List<QueryTile> tiles, byte[] clipboardImageData, boolean hasTabMatch, + List<NavsuggestTile> navsuggestTiles) { assert contentClassificationOffsets.length == contentClassificationStyles.length; List<MatchClassification> contentClassifications = new ArrayList<>(); for (int i = 0; i < contentClassificationOffsets.length; i++) { @@ -376,7 +378,19 @@ return new OmniboxSuggestion(nativeType, subtypes, isSearchType, relevance, transition, contents, contentClassifications, description, descriptionClassifications, answer, fillIntoEdit, url, imageUrl, imageDominantColor, isStarred, isDeletable, - postContentType, postData, groupId, tiles, clipboardImageData, hasTabMatch); + postContentType, postData, groupId, tiles, clipboardImageData, hasTabMatch, + navsuggestTiles); + } + + @CalledByNative + private static List<NavsuggestTile> buildOmniboxNavsuggestTileList(int capacity) { + return new ArrayList<>(capacity); + } + + @CalledByNative + private static void addOmniboxNavsuggestTile( + List<NavsuggestTile> tiles, String title, GURL url) { + tiles.add(new NavsuggestTile(title, url)); } /**
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/CachedZeroSuggestionsManager.java b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/CachedZeroSuggestionsManager.java index 167d09b8..abd9d88 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/CachedZeroSuggestionsManager.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/CachedZeroSuggestionsManager.java
@@ -185,7 +185,7 @@ OmniboxSuggestion suggestion = new OmniboxSuggestion(nativeType, subtypes, isSearchType, 0, 0, displayText, classifications, description, classifications, null, null, url, GURL.emptyGURL(), null, isStarred, isDeletable, postContentType, postData, - groupId, null, null, false); + groupId, null, null, false, null); suggestions.add(suggestion); } @@ -280,7 +280,8 @@ return !suggestion.hasAnswer() && suggestion.getType() != OmniboxSuggestionType.CLIPBOARD_URL && suggestion.getType() != OmniboxSuggestionType.CLIPBOARD_TEXT - && suggestion.getType() != OmniboxSuggestionType.CLIPBOARD_IMAGE; + && suggestion.getType() != OmniboxSuggestionType.CLIPBOARD_IMAGE + && suggestion.getType() != OmniboxSuggestionType.TILE_NAVSUGGEST; } /**
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestion.java b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestion.java index cded0596..fa0cfe5 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestion.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestion.java
@@ -28,6 +28,25 @@ public static final int INVALID_TYPE = -1; /** + * Specifies an individual tile for TILE_NAVSUGGEST suggestions. + */ + public static class NavsuggestTile { + /** + * Title of the website the tile points to. + */ + public final String title; + /** + * URL of the website the tile points to. + */ + public final GURL url; + + public NavsuggestTile(String title, GURL url) { + this.title = title; + this.url = url; + } + } + + /** * Specifies the style of portions of the suggestion text. * <p> * ACMatchClassification (as defined in C++) further describes the fields and usage. @@ -79,6 +98,7 @@ private final List<QueryTile> mQueryTiles; private final byte[] mClipboardImageData; private final boolean mHasTabMatch; + private final @Nullable List<NavsuggestTile> mNavsuggestTiles; public OmniboxSuggestion(int nativeType, Set<Integer> subtypes, boolean isSearchType, int relevance, int transition, String displayText, @@ -86,8 +106,8 @@ List<MatchClassification> descriptionClassifications, SuggestionAnswer answer, String fillIntoEdit, GURL url, GURL imageUrl, String imageDominantColor, boolean isStarred, boolean isDeletable, String postContentType, byte[] postData, - int groupId, List<QueryTile> queryTiles, byte[] clipboardImageData, - boolean hasTabMatch) { + int groupId, List<QueryTile> queryTiles, byte[] clipboardImageData, boolean hasTabMatch, + List<NavsuggestTile> navsuggestTiles) { if (subtypes == null) { subtypes = Collections.emptySet(); } @@ -115,6 +135,7 @@ mQueryTiles = queryTiles; mClipboardImageData = clipboardImageData; mHasTabMatch = hasTabMatch; + mNavsuggestTiles = navsuggestTiles; } public int getType() { @@ -263,6 +284,13 @@ return mGroupId; } + /** + * @return List of tiles for TILE_NAVSUGGEST suggestion. + */ + public @Nullable List<NavsuggestTile> getNavsuggestTiles() { + return mNavsuggestTiles; + } + @Override public String toString() { List<String> pieces = Arrays.asList("mType=" + mType, "mSubtypes=" + mSubtypes.toString(),
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/VoiceSuggestionProvider.java b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/VoiceSuggestionProvider.java index 55845c2..f4c4466d 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/VoiceSuggestionProvider.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/omnibox/suggestions/VoiceSuggestionProvider.java
@@ -124,7 +124,7 @@ suggestions.add(new OmniboxSuggestion(OmniboxSuggestionType.VOICE_SUGGEST, null, true, 0, 1, result.getMatch(), classifications, null, classifications, null, null, voiceUrl, GURL.emptyGURL(), null, false, false, null, null, OmniboxSuggestion.INVALID_GROUP, - null, null, false)); + null, null, false, null)); } private boolean doesVoiceResultHaveMatch(
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/sync/AndroidSyncSettings.java b/chrome/android/java/src/org/chromium/chrome/browser/sync/AndroidSyncSettings.java index ab8bea9..ff9f5cc 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/sync/AndroidSyncSettings.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/sync/AndroidSyncSettings.java
@@ -56,6 +56,8 @@ private boolean mMasterSyncEnabled; + private boolean mShouldDecoupleSyncFromMasterSync; + private final ObserverList<AndroidSyncSettingsObserver> mObservers = new ObserverList<>(); /** @@ -87,14 +89,16 @@ sInstance = instance; } - /** - * @param account The sync account if sync is enabled, null otherwise. - */ // TODO(crbug.com/1125622): Exposing these testing constructors that don't register the // singleton instance can be dangerous when there's code that explicitly calls |get()| // (in that case, a new object would be returned, not the one constructed by the test). // Consider exposing them as static methods that also register a singleton instance. + /** + * WARNING: Consider using |overrideForTests()| to inject a mock instead. + * @param account The sync account if sync is enabled, null otherwise. + */ @VisibleForTesting + @Deprecated public AndroidSyncSettings(@Nullable Account account) { ThreadUtils.assertOnUiThread(); mContractAuthority = getContractAuthority(); @@ -104,6 +108,14 @@ updateCachedSettings(); updateSyncability(); + ProfileSyncService syncService = ProfileSyncService.get(); + if (syncService != null + && ChromeFeatureList.isEnabled( + ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC)) { + // Read initial persisted value. + mShouldDecoupleSyncFromMasterSync = syncService.getDecoupledFromAndroidMasterSync(); + } + SyncStatusObserver androidOsListener = new SyncStatusObserver() { @Override public void onStatusChanged(int which) { @@ -153,9 +165,7 @@ */ public boolean doesMasterSyncSettingAllowChromeSync() { ThreadUtils.assertOnUiThread(); - return mMasterSyncEnabled - || ChromeFeatureList.isEnabled( - ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC); + return mMasterSyncEnabled || mShouldDecoupleSyncFromMasterSync; } /** @@ -200,6 +210,7 @@ * Add a new AndroidSyncSettingsObserver. */ public void registerObserver(AndroidSyncSettingsObserver observer) { + ThreadUtils.assertOnUiThread(); mObservers.addObserver(observer); } @@ -207,6 +218,7 @@ * Remove an AndroidSyncSettingsObserver that was previously added. */ public void unregisterObserver(AndroidSyncSettingsObserver observer) { + ThreadUtils.assertOnUiThread(); mObservers.removeObserver(observer); } @@ -262,7 +274,8 @@ } /** - * Update the three cached settings from the content resolver. + * Update the three cached settings from the content resolver and the + * master sync decoupling setting. * * @return Whether either chromeSyncEnabled or masterSyncEnabled changed. */ @@ -284,6 +297,17 @@ mMasterSyncEnabled = mSyncContentResolverDelegate.getMasterSyncAutomatically(); } + if (mAccount != null && ProfileSyncService.get() != null + && ChromeFeatureList.isEnabled( + ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC) + && mMasterSyncEnabled && !mShouldDecoupleSyncFromMasterSync) { + // Re-enabling master sync at least once should cause Sync to no longer care whether + // the former is enabled or not. This fact should be persisted via ProfileSyncService + // so it's known on the next startup. + mShouldDecoupleSyncFromMasterSync = true; + ProfileSyncService.get().setDecoupledFromAndroidMasterSync(); + } + return oldChromeSyncEnabled != mChromeSyncEnabled || oldMasterSyncEnabled != mMasterSyncEnabled; }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/sync/ProfileSyncService.java b/chrome/android/java/src/org/chromium/chrome/browser/sync/ProfileSyncService.java index ae05364..83b9815 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/sync/ProfileSyncService.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/sync/ProfileSyncService.java
@@ -88,6 +88,7 @@ */ @VisibleForTesting public static void overrideForTests(ProfileSyncService profileSyncService) { + ThreadUtils.assertOnUiThread(); sProfileSyncService = profileSyncService; sInitialized = true; }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarManager.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarManager.java index 111bd9c..bc7991c5 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarManager.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/ToolbarManager.java
@@ -24,6 +24,7 @@ import org.chromium.base.CallbackController; import org.chromium.base.TraceEvent; import org.chromium.base.supplier.ObservableSupplier; +import org.chromium.base.supplier.ObservableSupplierImpl; import org.chromium.base.supplier.OneshotSupplier; import org.chromium.base.supplier.Supplier; import org.chromium.chrome.R; @@ -50,6 +51,7 @@ import org.chromium.chrome.browser.findinpage.FindToolbarObserver; import org.chromium.chrome.browser.fullscreen.FullscreenManager; import org.chromium.chrome.browser.fullscreen.FullscreenOptions; +import org.chromium.chrome.browser.homepage.HomepageManager; import org.chromium.chrome.browser.identity_disc.IdentityDiscController; import org.chromium.chrome.browser.ntp.FakeboxDelegate; import org.chromium.chrome.browser.ntp.IncognitoNewTabPage; @@ -83,6 +85,7 @@ import org.chromium.chrome.browser.toolbar.top.ToolbarActionModeCallback; import org.chromium.chrome.browser.toolbar.top.ToolbarControlContainer; import org.chromium.chrome.browser.toolbar.top.ToolbarLayout; +import org.chromium.chrome.browser.toolbar.top.ToolbarPhone; import org.chromium.chrome.browser.toolbar.top.TopToolbarCoordinator; import org.chromium.chrome.browser.toolbar.top.ViewShiftingActionBarDelegate; import org.chromium.chrome.browser.ui.TabObscuringHandler; @@ -121,6 +124,10 @@ private final ToolbarControlContainer mControlContainer; private final BrowserControlsStateProvider.Observer mBrowserControlsObserver; private final FullscreenManager.Observer mFullscreenObserver; + private final ObservableSupplierImpl<Boolean> mHomeButtonVisibilitySupplier = + new ObservableSupplierImpl<>(); + private final ObservableSupplierImpl<Boolean> mIdentityDiscStateSupplier = + new ObservableSupplierImpl<>(); private BottomControlsCoordinator mBottomControlsCoordinator; private TabModelSelector mTabModelSelector; @@ -142,6 +149,7 @@ private BookmarkBridge.BookmarkModelObserver mBookmarksObserver; private FindToolbarObserver mFindToolbarObserver; private OverviewModeObserver mOverviewModeObserver; + private @OverviewModeState int mOverviewModeState = OverviewModeState.NOT_SHOWN; private OverviewModeBehavior mOverviewModeBehavior; private OneshotSupplier<OverviewModeBehavior> mOverviewModeBehaviorSupplier; @@ -160,6 +168,7 @@ private final LoadProgressCoordinator mProgressBarCoordinator; private final ToolbarTabControllerImpl mToolbarTabController; private MenuButtonCoordinator mMenuButtonCoordinator; + private HomepageManager.HomepageStateListener mHomepageStateListener; private BrowserStateBrowserControlsVisibilityDelegate mControlsVisibilityDelegate; private int mFullscreenFocusToken = TokenHolder.INVALID_TOKEN; @@ -309,17 +318,13 @@ mActivity.getCompositorViewHolder()::requestFocus, shouldShowUpdateBadge, mActivity::isInOverviewMode, overviewModeThemeColorProvider, R.id.none); - mToolbar = new TopToolbarCoordinator(controlContainer, toolbarLayout, - identityDiscController, mLocationBarModel, mToolbarTabController, - new UserEducationHelper(mActivity, mHandler), buttonDataProviders, - mOverviewModeBehaviorSupplier, browsingModeThemeColorProvider, - mAppThemeColorProvider, mMenuButtonCoordinator, startSurfaceMenuButtonCoordinator, - mMenuButtonCoordinator.getMenuButtonHelperSupplier(), mActivity, - mTabModelSelectorSupplier); + mToolbar = createTopToolbarCoordinator(controlContainer, toolbarLayout, buttonDataProviders, + browsingModeThemeColorProvider, startSurfaceMenuButtonCoordinator, invalidator, + identityDiscController); + mActionModeController = new ActionModeController(mActivity, mActionBarDelegate, toolbarActionModeCallback); - mToolbar.setPaintInvalidator(invalidator); mActionModeController.setTabStripHeight(mToolbar.getTabStripHeight()); mLocationBar = mToolbar.getLocationBar(); mLocationBar.setProfileSupplier(profileSupplier); @@ -573,6 +578,7 @@ public void onOverviewModeStateChanged( @OverviewModeState int overviewModeState, boolean showTabSwitcherToolbar) { assert StartSurfaceConfiguration.isStartSurfaceEnabled(); + mOverviewModeState = overviewModeState; mToolbar.updateTabSwitcherToolbarState(showTabSwitcherToolbar); } @@ -618,6 +624,36 @@ TraceEvent.end("ToolbarManager.ToolbarManager"); } + private TopToolbarCoordinator createTopToolbarCoordinator( + ToolbarControlContainer controlContainer, ToolbarLayout toolbarLayout, + List<ButtonDataProvider> buttonDataProviders, + ThemeColorProvider browsingModeThemeColorProvider, + MenuButtonCoordinator startSurfaceMenuButtonCoordinator, Invalidator invalidator, + IdentityDiscController identityDiscController) { + TopToolbarCoordinator toolbar = new TopToolbarCoordinator(controlContainer, toolbarLayout, + mLocationBarModel, mToolbarTabController, + new UserEducationHelper(mActivity, mHandler), buttonDataProviders, + mOverviewModeBehaviorSupplier, browsingModeThemeColorProvider, + mAppThemeColorProvider, mMenuButtonCoordinator, startSurfaceMenuButtonCoordinator, + mMenuButtonCoordinator.getMenuButtonHelperSupplier(), mTabModelSelectorSupplier, + mHomeButtonVisibilitySupplier, mIdentityDiscStateSupplier, (client) -> { + if (invalidator != null) { + invalidator.invalidate(client); + } else { + client.run(); + } + }, () -> identityDiscController.getForStartSurface(mOverviewModeState)); + mHomepageStateListener = + () -> mHomeButtonVisibilitySupplier.set(HomepageManager.isHomepageEnabled()); + HomepageManager.getInstance().addListener(mHomepageStateListener); + if (toolbarLayout instanceof ToolbarPhone + && StartSurfaceConfiguration.isStartSurfaceEnabled()) { + identityDiscController.addObserver( + (canShowHint) -> mIdentityDiscStateSupplier.set(canShowHint)); + } + return toolbar; + } + /** * Called when the contextual action bar's visibility has changed (i.e. the widget shown * when you can copy/paste text after long press). @@ -693,7 +729,7 @@ TabSwitcherActionMenuCoordinator.createOnLongClickListener( (id) -> mActivity.onOptionsItemSelected(id, null)); - mToolbar.initializeWithNative(layoutManager, tabSwitcherClickHandler, + mToolbar.initializeWithNative(layoutManager::requestUpdate, tabSwitcherClickHandler, tabSwitcherLongClickHandler, newTabClickHandler, bookmarkClickHandler, customTabsBackClickHandler); @@ -843,6 +879,8 @@ mLayoutManager = null; } + HomepageManager.getInstance().removeListener(mHomepageStateListener); + if (mBottomControlsCoordinator != null) { mBottomControlsCoordinator.destroy(); mBottomControlsCoordinator = null;
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarCoordinator.java index 771d8dc..70ae814 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarCoordinator.java
@@ -13,13 +13,15 @@ import org.chromium.base.CallbackController; import org.chromium.base.library_loader.LibraryLoader; +import org.chromium.base.supplier.ObservableSupplier; import org.chromium.base.supplier.OneshotSupplier; +import org.chromium.base.supplier.Supplier; import org.chromium.chrome.R; import org.chromium.chrome.browser.ThemeColorProvider; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior; -import org.chromium.chrome.browser.identity_disc.IdentityDiscController; import org.chromium.chrome.browser.incognito.IncognitoUtils; import org.chromium.chrome.browser.tabmodel.TabModelSelector; +import org.chromium.chrome.browser.toolbar.ButtonData; import org.chromium.chrome.browser.toolbar.IncognitoStateProvider; import org.chromium.chrome.browser.toolbar.TabCountProvider; import org.chromium.chrome.browser.toolbar.TabSwitcherButtonCoordinator; @@ -53,9 +55,11 @@ private CallbackController mCallbackController = new CallbackController(); StartSurfaceToolbarCoordinator(ViewStub startSurfaceToolbarStub, - IdentityDiscController identityDiscController, UserEducationHelper userEducationHelper, + UserEducationHelper userEducationHelper, OneshotSupplier<OverviewModeBehavior> overviewModeBehaviorSupplier, - ThemeColorProvider provider, MenuButtonCoordinator menuButtonCoordinator) { + ObservableSupplier<Boolean> identityDiscStateSupplier, ThemeColorProvider provider, + MenuButtonCoordinator menuButtonCoordinator, + Supplier<ButtonData> identityDiscButtonSupplier) { mStub = startSurfaceToolbarStub; overviewModeBehaviorSupplier.onAvailable( @@ -78,7 +82,7 @@ // should not be both true. assert !(StartSurfaceConfiguration.START_SURFACE_HIDE_INCOGNITO_SWITCH_NO_TAB.getValue() && StartSurfaceConfiguration.START_SURFACE_SHOW_STACK_TAB_SWITCHER.getValue()); - mToolbarMediator = new StartSurfaceToolbarMediator(mPropertyModel, identityDiscController, + mToolbarMediator = new StartSurfaceToolbarMediator(mPropertyModel, (iphCommandBuilder) -> { // TODO(crbug.com/865801): Replace the null check with an assert after fixing or @@ -90,7 +94,7 @@ StartSurfaceConfiguration.START_SURFACE_HIDE_INCOGNITO_SWITCH_NO_TAB.getValue(), StartSurfaceConfiguration.START_SURFACE_HIDE_INCOGNITO_SWITCH.getValue(), StartSurfaceConfiguration.START_SURFACE_SHOW_STACK_TAB_SWITCHER.getValue(), - menuButtonCoordinator); + menuButtonCoordinator, identityDiscStateSupplier, identityDiscButtonSupplier); mThemeColorProvider = provider; mMenuButtonCoordinator = menuButtonCoordinator;
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediator.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediator.java index 1e8945f..b8d689b 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediator.java
@@ -26,11 +26,12 @@ import androidx.annotation.VisibleForTesting; import org.chromium.base.Callback; +import org.chromium.base.supplier.ObservableSupplier; +import org.chromium.base.supplier.Supplier; import org.chromium.chrome.browser.compositor.layouts.EmptyOverviewModeObserver; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior.OverviewModeObserver; import org.chromium.chrome.browser.compositor.layouts.OverviewModeState; -import org.chromium.chrome.browser.identity_disc.IdentityDiscController; import org.chromium.chrome.browser.search_engines.TemplateUrlServiceFactory; import org.chromium.chrome.browser.tabmodel.EmptyTabModelSelectorObserver; import org.chromium.chrome.browser.tabmodel.TabModel; @@ -47,11 +48,11 @@ /** The mediator implements interacts between the views and the caller. */ class StartSurfaceToolbarMediator { private final PropertyModel mPropertyModel; - private final IdentityDiscController mIdentityDiscController; private final Callback<IPHCommandBuilder> mShowIPHCallback; private final boolean mHideIncognitoSwitchWhenNoTabs; private final boolean mHideIncognitoSwitchOnHomePage; private final boolean mShowNewTabAndIdentityDiscAtStart; + private final Supplier<ButtonData> mIdentityDiscButtonSupplier; private TabModelSelector mTabModelSelector; private TemplateUrlServiceObserver mTemplateUrlObserver; @@ -63,19 +64,24 @@ private int mOverviewModeState; private boolean mIsGoogleSearchEngine; - StartSurfaceToolbarMediator(PropertyModel model, IdentityDiscController identityDiscController, - Callback<IPHCommandBuilder> showIPHCallback, boolean hideIncognitoSwitchWhenNoTabs, - boolean hideIncognitoSwitchOnHomePage, boolean showNewTabAndIdentityDiscAtStart, - MenuButtonCoordinator menuButtonCoordinator) { + StartSurfaceToolbarMediator(PropertyModel model, Callback<IPHCommandBuilder> showIPHCallback, + boolean hideIncognitoSwitchWhenNoTabs, boolean hideIncognitoSwitchOnHomePage, + boolean showNewTabAndIdentityDiscAtStart, MenuButtonCoordinator menuButtonCoordinator, + ObservableSupplier<Boolean> identityDiscStateSupplier, + Supplier<ButtonData> identityDiscButtonSupplier) { mPropertyModel = model; mOverviewModeState = OverviewModeState.NOT_SHOWN; - mIdentityDiscController = identityDiscController; - mIdentityDiscController.addObserver(this::identityDiscStateChanged); mShowIPHCallback = showIPHCallback; mHideIncognitoSwitchWhenNoTabs = hideIncognitoSwitchWhenNoTabs; mHideIncognitoSwitchOnHomePage = hideIncognitoSwitchOnHomePage; mShowNewTabAndIdentityDiscAtStart = showNewTabAndIdentityDiscAtStart; mMenuButtonCoordinator = menuButtonCoordinator; + mIdentityDiscButtonSupplier = identityDiscButtonSupplier; + identityDiscStateSupplier.addObserver((canShowHint) -> { + // If the identity disc wants to be hidden and is hidden, there's nothing we need to do. + if (!canShowHint && !mPropertyModel.get(IDENTITY_DISC_IS_VISIBLE)) return; + updateIdentityDisc(mIdentityDiscButtonSupplier.get()); + }); } void onNativeLibraryReady() { @@ -117,14 +123,13 @@ @Override public void onTabModelSelected(TabModel newModel, TabModel oldModel) { mPropertyModel.set(IS_INCOGNITO, mTabModelSelector.isIncognitoSelected()); - updateIdentityDisc( - mIdentityDiscController.getForStartSurface(mOverviewModeState)); + updateIdentityDisc(mIdentityDiscButtonSupplier.get()); updateIncognitoSwitchVisibility(); } }; } mPropertyModel.set(IS_INCOGNITO, mTabModelSelector.isIncognitoSelected()); - updateIdentityDisc(mIdentityDiscController.getForStartSurface(mOverviewModeState)); + updateIdentityDisc(mIdentityDiscButtonSupplier.get()); mTabModelSelector.addObserver(mTabModelSelectorObserver); } @@ -186,7 +191,7 @@ updateIncognitoSwitchVisibility(); updateNewTabButtonVisibility(); updateLogoVisibility(mIsGoogleSearchEngine); - updateIdentityDisc(mIdentityDiscController.getForStartSurface(mOverviewModeState)); + updateIdentityDisc(mIdentityDiscButtonSupplier.get()); } @Override public void onOverviewModeStartedShowing(boolean showToolbar) { @@ -225,14 +230,7 @@ mPropertyModel.set(LOGO_IS_VISIBLE, shouldShowLogo); } - @VisibleForTesting - void identityDiscStateChanged(boolean canShowHint) { - // If the identity disc wants to be hidden and is hidden, there's nothing we need to do. - if (!canShowHint && !mPropertyModel.get(IDENTITY_DISC_IS_VISIBLE)) return; - updateIdentityDisc(mIdentityDiscController.getForStartSurface(mOverviewModeState)); - } - - @VisibleForTesting + @VisibleForTesting(otherwise = VisibleForTesting.PRIVATE) void updateIdentityDisc(ButtonData buttonData) { boolean shouldShow = buttonData.canShow && !mTabModelSelector.isIncognitoSelected(); if (shouldShow) { @@ -259,4 +257,10 @@ || ChromeAccessibilityUtil.get().isAccessibilityEnabled(); mPropertyModel.set(NEW_TAB_BUTTON_IS_VISIBLE, isShownTabswitcherState); } + + @VisibleForTesting + @OverviewModeState + int getOverviewModeStateForTesting() { + return mOverviewModeState; + } }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarLayout.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarLayout.java index c0688b1f..193518d 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarLayout.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarLayout.java
@@ -17,20 +17,20 @@ import android.view.ViewGroup; import android.widget.FrameLayout; import android.widget.ProgressBar; + import androidx.annotation.CallSuper; import androidx.annotation.ColorRes; import androidx.annotation.Nullable; import androidx.annotation.VisibleForTesting; + +import org.chromium.base.Callback; import org.chromium.base.ObserverList; import org.chromium.base.TraceEvent; import org.chromium.chrome.R; import org.chromium.chrome.browser.ThemeColorProvider; import org.chromium.chrome.browser.ThemeColorProvider.ThemeColorObserver; import org.chromium.chrome.browser.ThemeColorProvider.TintObserver; -import org.chromium.chrome.browser.compositor.Invalidator; -import org.chromium.chrome.browser.compositor.layouts.LayoutUpdateHost; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior; -import org.chromium.chrome.browser.findinpage.FindToolbar; import org.chromium.chrome.browser.ntp.NewTabPage; import org.chromium.chrome.browser.omnibox.LocationBar; import org.chromium.chrome.browser.omnibox.UrlBarData; @@ -58,7 +58,7 @@ */ public abstract class ToolbarLayout extends FrameLayout implements TintObserver, ThemeColorObserver { - private Invalidator mInvalidator; + private Callback<Runnable> mInvalidator; protected final ObserverList<UrlExpansionObserver> mUrlExpansionObservers = new ObserverList<>(); @@ -411,7 +411,7 @@ * {@link Invalidator} a chance to defer the actual invalidate to sync drawing. * @param invalidator An {@link Invalidator} instance. */ - void setPaintInvalidator(Invalidator invalidator) { + void setInvalidatorCallback(Callback<Runnable> invalidator) { mInvalidator = invalidator; } @@ -420,12 +420,8 @@ * {@link #setPaintInvalidator(Invalidator)} to decide when to actually invalidate. * @param client A {@link Invalidator.Client} instance that wants to be invalidated. */ - void triggerPaintInvalidate(Invalidator.Client client) { - if (mInvalidator == null) { - client.doInvalidate(); - } else { - mInvalidator.invalidate(client); - } + protected void triggerPaintInvalidate(Runnable clientInvalidator) { + mInvalidator.onResult(clientInvalidator); } /** @@ -603,7 +599,7 @@ return false; } - void setLayoutUpdateHost(LayoutUpdateHost layoutUpdateHost) {} + void setLayoutUpdater(Runnable layoutUpdater) {} void setOverviewModeBehavior(OverviewModeBehavior overviewModeBehavior) {}
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java index 2b196cc..9e5c1a4e 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/ToolbarPhone.java
@@ -49,8 +49,6 @@ import org.chromium.base.MathUtils; import org.chromium.base.TraceEvent; import org.chromium.chrome.R; -import org.chromium.chrome.browser.compositor.Invalidator; -import org.chromium.chrome.browser.compositor.layouts.LayoutUpdateHost; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior; import org.chromium.chrome.browser.device.DeviceClassManager; import org.chromium.chrome.browser.feature_engagement.TrackerFactory; @@ -90,9 +88,8 @@ /** * Phone specific toolbar implementation. */ -public class ToolbarPhone extends ToolbarLayout implements Invalidator.Client, OnClickListener, - NewTabPage.OnSearchBoxScrollListener, - TabCountObserver { +public class ToolbarPhone extends ToolbarLayout + implements OnClickListener, NewTabPage.OnSearchBoxScrollListener, TabCountObserver { /** The amount of time transitioning from one theme color to another should take in ms. */ public static final long THEME_COLOR_TRANSITION_DURATION = 250; @@ -240,7 +237,7 @@ private boolean mIsHomeButtonEnabled; - private LayoutUpdateHost mLayoutUpdateHost; + private Runnable mLayoutUpdater; /** The vertical inset of the location bar background. */ private int mLocationBarBackgroundVerticalInset; @@ -311,7 +308,7 @@ @Override public void set(ToolbarPhone object, Float value) { object.mTabSwitcherModePercent = value; - triggerPaintInvalidate(ToolbarPhone.this); + triggerPaintInvalidate(ToolbarPhone.this::postInvalidateOnAnimation); } }; @@ -1322,11 +1319,6 @@ canvas.restore(); } - @Override - public void doInvalidate() { - postInvalidateOnAnimation(); - } - /** * Translates the canvas to ensure the specified view's coordinates are at 0, 0. * @@ -1576,8 +1568,8 @@ } @Override - public void setLayoutUpdateHost(LayoutUpdateHost layoutUpdateHost) { - mLayoutUpdateHost = layoutUpdateHost; + public void setLayoutUpdater(Runnable layoutUpdater) { + mLayoutUpdater = layoutUpdater; } @Override @@ -1654,7 +1646,7 @@ // TODO(amaralp): Have the LocationBar listen to tint changes. if (mLocationBar != null) mLocationBar.updateVisualsForState(); - if (mLayoutUpdateHost != null) mLayoutUpdateHost.requestUpdate(); + if (mLayoutUpdater != null) mLayoutUpdater.run(); } @Override @@ -1730,7 +1722,7 @@ // Request a texture update to ensure a texture is captured before the user // re-enters the tab switcher. postInvalidate(); - mLayoutUpdateHost.requestUpdate(); + mLayoutUpdater.run(); } @Override @@ -2294,7 +2286,7 @@ }); mBrandColorTransitionAnimation.start(); mBrandColorTransitionActive = true; - if (mLayoutUpdateHost != null) mLayoutUpdateHost.requestUpdate(); + if (mLayoutUpdater != null) mLayoutUpdater.run(); } private void updateNtpAnimationState() { @@ -2462,8 +2454,8 @@ // Refresh the toolbar texture. if ((mVisualState == VisualState.BRAND_COLOR || visualStateChanged) - && mLayoutUpdateHost != null) { - mLayoutUpdateHost.requestUpdate(); + && mLayoutUpdater != null) { + mLayoutUpdater.run(); } updateShadowVisibility(); updateUrlExpansionAnimation(); @@ -2602,7 +2594,7 @@ } private void requestLayoutHostUpdateForOptionalButton() { - if (mLayoutUpdateHost != null) mLayoutUpdateHost.requestUpdate(); + if (mLayoutUpdater != null) mLayoutUpdater.run(); getViewTreeObserver().removeOnGlobalLayoutListener(mOptionalButtonLayoutListener); }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/TopToolbarCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/TopToolbarCoordinator.java index e087893..aee3306 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/TopToolbarCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/toolbar/top/TopToolbarCoordinator.java
@@ -4,7 +4,6 @@ package org.chromium.chrome.browser.toolbar.top; -import android.content.Context; import android.graphics.Rect; import android.graphics.drawable.Drawable; import android.view.View; @@ -14,20 +13,18 @@ import androidx.annotation.Nullable; import androidx.annotation.VisibleForTesting; +import org.chromium.base.Callback; import org.chromium.base.CallbackController; import org.chromium.base.supplier.ObservableSupplier; import org.chromium.base.supplier.OneShotCallback; import org.chromium.base.supplier.OneshotSupplier; +import org.chromium.base.supplier.Supplier; import org.chromium.chrome.R; import org.chromium.chrome.browser.ThemeColorProvider; -import org.chromium.chrome.browser.compositor.Invalidator; -import org.chromium.chrome.browser.compositor.layouts.LayoutManager; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior; -import org.chromium.chrome.browser.findinpage.FindToolbar; -import org.chromium.chrome.browser.homepage.HomepageManager; -import org.chromium.chrome.browser.identity_disc.IdentityDiscController; import org.chromium.chrome.browser.omnibox.LocationBar; import org.chromium.chrome.browser.tabmodel.TabModelSelector; +import org.chromium.chrome.browser.toolbar.ButtonData; import org.chromium.chrome.browser.toolbar.ButtonDataProvider; import org.chromium.chrome.browser.toolbar.IncognitoStateProvider; import org.chromium.chrome.browser.toolbar.TabCountProvider; @@ -75,7 +72,6 @@ */ private @Nullable StartSurfaceToolbarCoordinator mStartSurfaceToolbarCoordinator; - private final IdentityDiscController mIdentityDiscController; private OptionalBrowsingModeButtonController mOptionalButtonController; private MenuButtonCoordinator mMenuButtonCoordinator; @@ -83,19 +79,10 @@ private CallbackController mCallbackController = new CallbackController(); private ObservableSupplier<TabModelSelector> mTabModelSelectorSupplier; - private HomepageManager.HomepageStateListener mHomepageStateListener = - new HomepageManager.HomepageStateListener() { - @Override - public void onHomepageStateUpdated() { - mToolbarLayout.onHomeButtonUpdate(HomepageManager.isHomepageEnabled()); - } - }; - /** * Creates a new {@link TopToolbarCoordinator}. * @param controlContainer The {@link ToolbarControlContainer} for the containing activity. * @param toolbarLayout The {@link ToolbarLayout}. - * @param identityDiscController Class that controls the state of the identity disc. * @param userEducationHelper Helper class for showing in-product help text bubbles. * @param buttonDataProviders List of classes that wish to display an optional button in the * browsing mode toolbar. @@ -104,20 +91,29 @@ * @param normalThemeColorProvider The {@link ThemeColorProvider} for normal mode. * @param overviewThemeColorProvider The {@link ThemeColorProvider} for overview mode. * @param tabModelSelectorSupplier Supplier of the {@link TabModelSelector}. + * @param homeButtonVisibilitySupplier Supplier of the visibility change of Home button. + * @param identityDiscStateSupplier Supplier of the state change of identity disc button. + * @param invalidatorCallback Callback that will be invoked when the toolbar attempts to + * invalidate the drawing surface. This will give the object that registers as the host + * for the {@link Invalidator} a chance to defer the actual invalidate to sync drawing. + * @param identityDiscButtonSupplier Supplier of Identity Disc button. */ public TopToolbarCoordinator(ToolbarControlContainer controlContainer, - ToolbarLayout toolbarLayout, IdentityDiscController identityDiscController, - ToolbarDataProvider toolbarDataProvider, ToolbarTabController tabController, - UserEducationHelper userEducationHelper, List<ButtonDataProvider> buttonDataProviders, + ToolbarLayout toolbarLayout, ToolbarDataProvider toolbarDataProvider, + ToolbarTabController tabController, UserEducationHelper userEducationHelper, + List<ButtonDataProvider> buttonDataProviders, OneshotSupplier<OverviewModeBehavior> overviewModeBehaviorSupplier, ThemeColorProvider normalThemeColorProvider, ThemeColorProvider overviewThemeColorProvider, MenuButtonCoordinator browsingModeMenuButtonCoordinator, MenuButtonCoordinator startSurfaceMenuButtonCoordinator, - ObservableSupplier<AppMenuButtonHelper> appMenuButtonHelperSupplier, Context context, - ObservableSupplier<TabModelSelector> tabModelSelectorSupplier) { + ObservableSupplier<AppMenuButtonHelper> appMenuButtonHelperSupplier, + ObservableSupplier<TabModelSelector> tabModelSelectorSupplier, + ObservableSupplier<Boolean> homeButtonVisibilitySupplier, + ObservableSupplier<Boolean> identityDiscStateSupplier, + Callback<Runnable> invalidatorCallback, + Supplier<ButtonData> identityDiscButtonSupplier) { mToolbarLayout = toolbarLayout; - mIdentityDiscController = identityDiscController; mMenuButtonCoordinator = browsingModeMenuButtonCoordinator; mOptionalButtonController = new OptionalBrowsingModeButtonController(buttonDataProviders, userEducationHelper, mToolbarLayout, () -> toolbarDataProvider.getTab()); @@ -131,8 +127,9 @@ if (StartSurfaceConfiguration.isStartSurfaceEnabled()) { mStartSurfaceToolbarCoordinator = new StartSurfaceToolbarCoordinator( controlContainer.getRootView().findViewById(R.id.tab_switcher_toolbar_stub), - mIdentityDiscController, userEducationHelper, overviewModeBehaviorSupplier, - overviewThemeColorProvider, startSurfaceMenuButtonCoordinator); + userEducationHelper, overviewModeBehaviorSupplier, + identityDiscStateSupplier, overviewThemeColorProvider, + startSurfaceMenuButtonCoordinator, identityDiscButtonSupplier); } else { mTabSwitcherModeCoordinatorPhone = new TabSwitcherModeTTCoordinatorPhone( controlContainer.getRootView().findViewById( @@ -140,12 +137,13 @@ } } controlContainer.setToolbar(this); - HomepageManager.getInstance().addListener(mHomepageStateListener); mToolbarLayout.initialize(toolbarDataProvider, tabController, mMenuButtonCoordinator); mToolbarLayout.setThemeColorProvider(normalThemeColorProvider); mAppMenuButtonHelperSupplier = appMenuButtonHelperSupplier; new OneShotCallback<>(mAppMenuButtonHelperSupplier, this::setAppMenuButtonHelper); + homeButtonVisibilitySupplier.addObserver((show) -> mToolbarLayout.onHomeButtonUpdate(show)); + mToolbarLayout.setInvalidatorCallback(invalidatorCallback); } /** @@ -163,14 +161,14 @@ * <p> * Calling this must occur after the native library have completely loaded. * - * @param layoutManager A {@link LayoutManager} instance used to watch for scene changes. + * @param layoutUpdater A {@link Runnable} used to request layout update upon scene change. * @param tabSwitcherClickHandler The click handler for the tab switcher button. * @param tabSwitcherLongClickHandler The long click handler for the tab switcher button. * @param newTabClickHandler The click handler for the new tab button. * @param bookmarkClickHandler The click handler for the bookmarks button. * @param customTabsBackClickHandler The click handler for the custom tabs back button. */ - public void initializeWithNative(LayoutManager layoutManager, + public void initializeWithNative(Runnable layoutUpdater, OnClickListener tabSwitcherClickHandler, OnLongClickListener tabSwitcherLongClickHandler, OnClickListener newTabClickHandler, OnClickListener bookmarkClickHandler, OnClickListener customTabsBackClickHandler) { @@ -195,7 +193,7 @@ mToolbarLayout.setOnTabSwitcherLongClickHandler(tabSwitcherLongClickHandler); mToolbarLayout.setBookmarkClickHandler(bookmarkClickHandler); mToolbarLayout.setCustomTabCloseClickHandler(customTabsBackClickHandler); - mToolbarLayout.setLayoutUpdateHost(layoutManager); + mToolbarLayout.setLayoutUpdater(layoutUpdater); mToolbarLayout.onNativeLibraryReady(); } @@ -230,7 +228,6 @@ * Cleans up any code as necessary. */ public void destroy() { - HomepageManager.getInstance().removeListener(mHomepageStateListener); mToolbarLayout.destroy(); if (mTabSwitcherModeCoordinatorPhone != null) { mTabSwitcherModeCoordinatorPhone.destroy(); @@ -302,8 +299,8 @@ * {@link Invalidator} a chance to defer the actual invalidate to sync drawing. * @param invalidator An {@link Invalidator} instance. */ - public void setPaintInvalidator(Invalidator invalidator) { - mToolbarLayout.setPaintInvalidator(invalidator); + public void setInvalidatorCallback(Callback<Runnable> callback) { + mToolbarLayout.setInvalidatorCallback(callback); } /**
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java index a6e0d0b..7e1b010f 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java
@@ -42,6 +42,8 @@ import org.chromium.chrome.browser.findinpage.FindToolbarManager; import org.chromium.chrome.browser.findinpage.FindToolbarObserver; import org.chromium.chrome.browser.flags.ActivityType; +import org.chromium.chrome.browser.flags.CachedFeatureFlags; +import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.fullscreen.BrowserControlsManager; import org.chromium.chrome.browser.identity_disc.IdentityDiscController; import org.chromium.chrome.browser.lifecycle.Destroyable; @@ -76,6 +78,8 @@ import org.chromium.components.browser_ui.widget.MenuOrKeyboardActionController; import org.chromium.components.browser_ui.widget.scrim.ScrimCoordinator; import org.chromium.components.feature_engagement.EventConstants; +import org.chromium.components.messages.MessageQueueManager; +import org.chromium.components.messages.MessagesFactory; import org.chromium.content_public.browser.ActionModeCallbackHelper; import org.chromium.content_public.browser.LoadUrlParams; import org.chromium.ui.base.DeviceFormFactor; @@ -149,6 +153,8 @@ @Nullable private BrowserControlsManager mBrowserControlsManager; private ObservableSupplier<TabModelSelector> mTabModelSelectorSupplier; + @Nullable + private MessageQueueManager mMessageQueueManager; /** * Create a new {@link RootUiCoordinator} for the given activity. @@ -202,6 +208,11 @@ mOverviewModeBehaviorSupplier = overviewModeBehaviorSupplier; mOverviewModeBehaviorSupplier.onAvailable( mCallbackController.makeCancelable(this::setOverviewModeBehavior)); + + if (CachedFeatureFlags.isEnabled(ChromeFeatureList.MESSAGES_FOR_ANDROID_INFRASTRUCTURE)) { + mMessageQueueManager = + MessagesFactory.createMessageQueueManager(mActivity.getWindowAndroid()); + } } // TODO(pnoland, crbug.com/865801): remove this in favor of wiring it directly. @@ -216,6 +227,11 @@ mActivity.getLayoutManagerSupplier().removeObserver(mLayoutManagerSupplierCallback); + if (mMessageQueueManager != null) { + mMessageQueueManager.destroy(); + mMessageQueueManager = null; + } + if (mOverlayPanelManager != null) { mOverlayPanelManager.removeObserver(mOverlayPanelManagerObserver); }
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/autofill/settings/AutofillPaymentMethodsFragmentTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/autofill/settings/AutofillPaymentMethodsFragmentTest.java index ad6683a..3888ff8 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/autofill/settings/AutofillPaymentMethodsFragmentTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/autofill/settings/AutofillPaymentMethodsFragmentTest.java
@@ -96,23 +96,6 @@ @Test @MediumTest - @Features.DisableFeatures({ChromeFeatureList.AUTOFILL_ENABLE_SURFACING_SERVER_CARD_NICKNAME}) - public void testCreditCardWithNickname_nicknameExpOff_displayNetworkAndLastFourAsTitle() - throws Exception { - mAutofillTestHelper.addServerCreditCard( - SAMPLE_CARD_VISA, "Test nickname", CARD_ISSUER_UNKNOWN); - - SettingsActivity activity = mSettingsActivityTestRule.startSettingsActivity(); - - Preference cardPreference = getPreferenceScreen(activity).getPreference(1); - String title = cardPreference.getTitle().toString(); - assertThat(title).contains("Visa"); - assertThat(title).contains("1111"); - } - - @Test - @MediumTest - @Features.EnableFeatures({ChromeFeatureList.AUTOFILL_ENABLE_SURFACING_SERVER_CARD_NICKNAME}) public void testCreditCardWithNickname_displaysNicknameAndLastFourAsTitle() throws Exception { mAutofillTestHelper.addServerCreditCard( SAMPLE_CARD_VISA, "Test nickname", CARD_ISSUER_UNKNOWN); @@ -127,7 +110,6 @@ @Test @MediumTest - @Features.EnableFeatures({ChromeFeatureList.AUTOFILL_ENABLE_SURFACING_SERVER_CARD_NICKNAME}) public void testCreditCardWithLongNickname_displaysCompleteNicknameAndLastFourAsTitle() throws Exception { mAutofillTestHelper.addServerCreditCard( @@ -170,10 +152,9 @@ @Test @MediumTest - @Features.EnableFeatures({ChromeFeatureList.AUTOFILL_ENABLE_GOOGLE_ISSUED_CARD, - ChromeFeatureList.AUTOFILL_ENABLE_SURFACING_SERVER_CARD_NICKNAME}) - public void - testGoogleIssuedServerCardWithNickname_displaysNicknameAndLastFourAsTitle() throws Exception { + @Features.EnableFeatures({ChromeFeatureList.AUTOFILL_ENABLE_GOOGLE_ISSUED_CARD}) + public void testGoogleIssuedServerCardWithNickname_displaysNicknameAndLastFourAsTitle() + throws Exception { mAutofillTestHelper.addServerCreditCard( SAMPLE_CARD_VISA, "Test nickname", CARD_ISSUER_GOOGLE);
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/bookmarks/BookmarkTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/bookmarks/BookmarkTest.java index cffcaa9..665637d 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/bookmarks/BookmarkTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/bookmarks/BookmarkTest.java
@@ -9,6 +9,10 @@ import static androidx.test.espresso.assertion.ViewAssertions.doesNotExist; import static androidx.test.espresso.matcher.ViewMatchers.withText; +import static org.mockito.Mockito.any; +import static org.mockito.Mockito.doNothing; +import static org.mockito.Mockito.when; + import static org.chromium.components.browser_ui.widget.highlight.ViewHighlighterTestUtils.checkHighlightOff; import static org.chromium.components.browser_ui.widget.highlight.ViewHighlighterTestUtils.checkHighlightPulse; @@ -35,6 +39,9 @@ import org.junit.Rule; import org.junit.Test; import org.junit.runner.RunWith; +import org.mockito.Mock; +import org.mockito.junit.MockitoJUnit; +import org.mockito.junit.MockitoRule; import org.chromium.base.ActivityState; import org.chromium.base.ApplicationStatus; @@ -59,7 +66,8 @@ import org.chromium.chrome.browser.preferences.ChromePreferenceKeys; import org.chromium.chrome.browser.preferences.SharedPreferencesManager; import org.chromium.chrome.browser.profiles.Profile; -import org.chromium.chrome.browser.sync.AndroidSyncSettingsTestUtils; +import org.chromium.chrome.browser.sync.AndroidSyncSettings; +import org.chromium.chrome.browser.sync.AndroidSyncSettings.AndroidSyncSettingsObserver; import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.browser.ui.messages.snackbar.Snackbar; import org.chromium.chrome.browser.ui.messages.snackbar.SnackbarManager; @@ -106,6 +114,8 @@ @Rule public ChromeRenderTestRule mRenderTestRule = ChromeRenderTestRule.Builder.withPublicCorpus().build(); + @Rule + public final MockitoRule mMockitoRule = MockitoJUnit.rule(); private static final String TEST_PAGE_URL_GOOGLE = "/chrome/test/data/android/google.html"; private static final String TEST_PAGE_TITLE_GOOGLE = "The Google"; @@ -125,6 +135,8 @@ private String mTestPageFoo; private EmbeddedTestServer mTestServer; private @Nullable BookmarkActivity mBookmarkActivity; + @Mock + private AndroidSyncSettings mAndroidSyncSettings; @BeforeClass public static void setUpBeforeActivityLaunched() { @@ -145,8 +157,17 @@ mActivityTestRule.getActivity().getActivityTab().getWebContents())); mBookmarkBridge = mActivityTestRule.getActivity().getBookmarkBridgeForTesting(); - // Stub Android master sync state to make sure promos aren't suppressed. - AndroidSyncSettingsTestUtils.setUpAndroidSyncSettingsForTesting(); + // Stub AndroidSyncSettings state to make sure promos aren't suppressed. + when(mAndroidSyncSettings.doesMasterSyncSettingAllowChromeSync()).thenReturn(true); + when(mAndroidSyncSettings.isSyncEnabled()).thenReturn(false); + when(mAndroidSyncSettings.isChromeSyncEnabled()).thenReturn(false); + doNothing() + .when(mAndroidSyncSettings) + .registerObserver(any(AndroidSyncSettingsObserver.class)); + doNothing() + .when(mAndroidSyncSettings) + .unregisterObserver(any(AndroidSyncSettingsObserver.class)); + AndroidSyncSettings.overrideForTests(mAndroidSyncSettings); }); mTestServer = EmbeddedTestServer.createAndStartServer(InstrumentationRegistry.getContext()); mTestPage = mTestServer.getURL(TEST_PAGE_URL_GOOGLE);
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityIncognitoTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityIncognitoTest.java index 5a1aedb..d16f5f1f 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityIncognitoTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityIncognitoTest.java
@@ -138,7 +138,7 @@ assertTrue(item == null || !item.isVisible()); } - private void testTopActionIconsIsVisible(String screenshotName) throws Exception { + private void testTopActionIconsIsVisible() throws Exception { Menu menu = mCustomTabActivityTestRule.getMenu(); MenuItem iconRow = menu.findItem(R.id.icon_row_menu_id); @@ -261,7 +261,7 @@ @Features.EnableFeatures({ChromeFeatureList.CCT_INCOGNITO}) public void ensureOnlyFourTopIconsAreVisible() throws Exception { launchMenuItem(); - testTopActionIconsIsVisible("Forward, info, bookmark and reload is visible"); + testTopActionIconsIsVisible(); } @Test @@ -281,7 +281,26 @@ assertTrue(menu.findItem(R.id.request_desktop_site_row_menu_id).isVisible()); // Check top icons are still the same. - testTopActionIconsIsVisible("Custom menu items not visible"); + testTopActionIconsIsVisible(); + } + + @Test + @MediumTest + @Features.EnableFeatures({ChromeFeatureList.CCT_INCOGNITO}) + public void ensureAddCustomMenuItemIsEnabledForReaderMode() throws Exception { + Intent intent = createMinimalIncognitoCustomTabIntent(); + CustomTabIntentDataProvider.addReaderModeUIExtras(intent); + CustomTabActivity activity = launchIncognitoCustomTab(intent); + CustomTabsTestUtils.openAppMenuAndAssertMenuShown(activity); + + Menu menu = mCustomTabActivityTestRule.getMenu(); + // Check the menu items have only 2 items visible "not" including the top icon row menu. + assertEquals(2, CustomTabsTestUtils.getVisibleMenuSize(menu)); + assertTrue(menu.findItem(R.id.reader_mode_prefs_id).isVisible()); + assertTrue(menu.findItem(R.id.find_in_page_id).isVisible()); + + assertFalse(menu.findItem(R.id.icon_row_menu_id).isVisible()); + assertFalse(menu.findItem(R.id.request_desktop_site_row_menu_id).isVisible()); } @Test
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/FirstRunIntegrationTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/FirstRunIntegrationTest.java index 523ed8d..c036465 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/FirstRunIntegrationTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/FirstRunIntegrationTest.java
@@ -69,7 +69,7 @@ @Mock public FirstRunAppRestrictionInfo mMockAppRestrictionInfo; @Mock - public EnterpriseInfo mEntepriseInfo; + public EnterpriseInfo mEnterpriseInfo; private final Set<Class> mSupportedActivities = CollectionUtil.newHashSet(ChromeLauncherActivity.class, FirstRunActivity.class, @@ -85,6 +85,7 @@ public void setUp() { MockitoAnnotations.initMocks(this); FirstRunActivity.setObserverForTest(mTestObserver); + ToSAndUMAFirstRunFragment.setShowUmaCheckBoxForTesting(true); mInstrumentation = InstrumentationRegistry.getInstrumentation(); mContext = mInstrumentation.getTargetContext(); @@ -98,6 +99,7 @@ @After public void tearDown() { FirstRunAppRestrictionInfo.setInitializedInstanceForTest(null); + ToSAndUMAFirstRunFragment.setShowUmaCheckBoxForTesting(false); EnterpriseInfo.setInstanceForTest(null); if (mLastActivity != null) mLastActivity.finish(); } @@ -133,9 +135,17 @@ callback.onResult(new EnterpriseInfo.OwnedState(true, false)); return null; }) - .when(mEntepriseInfo) + .when(mEnterpriseInfo) .getDeviceEnterpriseInfo(any()); - EnterpriseInfo.setInstanceForTest(mEntepriseInfo); + EnterpriseInfo.setInstanceForTest(mEnterpriseInfo); + } + + private void setCctTosDialogEnabledPolicy(boolean enabled) { + setHasAppRestrictionForMock(); + Bundle restrictions = new Bundle(); + restrictions.putBoolean("CCTToSDialogEnabled", enabled); + AbstractAppRestrictionsProvider.setTestRestrictions(restrictions); + setDeviceOwnedForMock(); } @Test @@ -191,6 +201,14 @@ runSearchEnginePromptTest(LocaleManager.SearchEnginePromoType.SHOW_EXISTING); } + @Test + @MediumTest + public void testDefaultSearchEngine_WithCctPolicy() throws Exception { + setCctTosDialogEnabledPolicy(false); + + runSearchEnginePromptTest(LocaleManager.SearchEnginePromoType.SHOW_EXISTING); + } + private void runSearchEnginePromptTest(@SearchEnginePromoType final int searchPromoType) throws Exception { // Force the LocaleManager into a specific state. @@ -269,11 +287,7 @@ @Test @MediumTest public void testExitFirstRunWithPolicy() { - setHasAppRestrictionForMock(); - Bundle restrictions = new Bundle(); - restrictions.putBoolean("CCTToSDialogEnabled", false); - AbstractAppRestrictionsProvider.setTestRestrictions(restrictions); - setDeviceOwnedForMock(); + setCctTosDialogEnabledPolicy(false); Intent intent = CustomTabsTestUtils.createMinimalCustomTabIntent(mContext, "https://test.com"); @@ -287,9 +301,34 @@ "native never initialized."); waitForActivity(CustomTabActivity.class); - Assert.assertFalse("Usage and crash reporting pref was set to true after skip", PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); + Assert.assertTrue( + "FRE should be skipped for CCT.", FirstRunStatus.isEphemeralSkipFirstRun()); + } + + @Test + @MediumTest + // TODO(https://crbug.com/1111490): Change this test case when policy can handle cases when ToS + // is accepted in Browser App. + public void testSkipTosPage_WithCctPolicy() throws Exception { + setCctTosDialogEnabledPolicy(false); + FirstRunStatus.setSkipWelcomePage(true); + + Intent intent = + CustomTabsTestUtils.createMinimalCustomTabIntent(mContext, "https://test.com"); + mContext.startActivity(intent); + + FirstRunActivity freActivity = waitForActivity(FirstRunActivity.class); + CriteriaHelper.pollUiThread( + () -> freActivity.getSupportFragmentManager().getFragments().size() > 0); + + // A page skip should happen, while we are still staying at FRE. + mTestObserver.jumpToPageCallback.waitForCallback("Welcome page should be skipped.", 0); + Assert.assertFalse( + "FRE should not be skipped for CCT.", FirstRunStatus.isEphemeralSkipFirstRun()); + Assert.assertFalse( + "FreActivity should still be alive.", freActivity.isActivityFinishingOrDestroyed()); } @Test
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/TosAndUmaFirstRunFragmentWithEnterpriseSupportTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/TosAndUmaFirstRunFragmentWithEnterpriseSupportTest.java index 3c25fdbb..4bad010d 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/TosAndUmaFirstRunFragmentWithEnterpriseSupportTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/firstrun/TosAndUmaFirstRunFragmentWithEnterpriseSupportTest.java
@@ -12,6 +12,7 @@ import android.content.Context; import android.content.Intent; import android.os.Bundle; +import android.os.SystemClock; import android.support.test.InstrumentationRegistry; import android.view.View; import android.widget.CheckBox; @@ -33,11 +34,15 @@ import org.chromium.base.Callback; import org.chromium.base.CommandLine; import org.chromium.base.metrics.RecordHistogram; +import org.chromium.base.test.util.CallbackHelper; import org.chromium.chrome.R; import org.chromium.chrome.browser.customtabs.CustomTabsTestUtils; import org.chromium.chrome.browser.flags.ChromeSwitches; import org.chromium.chrome.browser.policy.EnterpriseInfo; import org.chromium.chrome.browser.policy.PolicyServiceFactory; +import org.chromium.chrome.browser.preferences.ChromePreferenceKeys; +import org.chromium.chrome.browser.preferences.SharedPreferencesManager; +import org.chromium.chrome.browser.privacy.settings.PrivacyPreferencesManager; import org.chromium.chrome.test.ChromeJUnit4ClassRunner; import org.chromium.components.policy.PolicyService; import org.chromium.content_public.browser.test.util.Criteria; @@ -65,6 +70,15 @@ int HAS_POLICY = 2; } + @IntDef({SpeedComparedToInflation.NOT_RECORDED, SpeedComparedToInflation.FASTER, + SpeedComparedToInflation.SLOWER}) + @Retention(RetentionPolicy.SOURCE) + @interface SpeedComparedToInflation { + int NOT_RECORDED = 0; + int FASTER = 1; + int SLOWER = 2; + } + @Rule public DisableAnimationsTestRule mDisableAnimationsTestRule = new DisableAnimationsTestRule(); @@ -79,9 +93,11 @@ private FirstRunActivity mActivity; private final List<PolicyService.Observer> mPolicyServiceObservers = new ArrayList<>(); - private final List<Callback<Boolean>> mAppRestrictonsCallbacks = new ArrayList<>(); + private final List<Callback<Boolean>> mAppRestrictionsCallbacks = new ArrayList<>(); + private final List<Callback<Long>> mAppRestrictionsDurationCallbacks = new ArrayList<>(); private final List<Callback<EnterpriseInfo.OwnedState>> mOwnedStateCallbacks = new ArrayList<>(); + private final CallbackHelper mAcceptTosCallbackHelper = new CallbackHelper(); private int mExitCount; private View mTosText; @@ -114,7 +130,9 @@ public void onFlowIsKnown(Bundle freProperties) {} @Override - public void onAcceptTermsOfService() {} + public void onAcceptTermsOfService() { + mAcceptTosCallbackHelper.notifyCalled(); + } @Override public void onJumpToPage(int position) {} @@ -139,6 +157,8 @@ PolicyServiceFactory.setPolicyServiceForTest(null); FirstRunUtilsJni.TEST_HOOKS.setInstanceForTesting(mFirstRunUtils); EnterpriseInfo.setInstanceForTest(null); + SharedPreferencesManager.getInstance().writeBoolean( + ChromePreferenceKeys.PRIVACY_METRICS_REPORTING, false); if (mActivity != null) mActivity.finish(); } @@ -151,9 +171,24 @@ setAppRestrictionsMockInitialized(false); assertUIState(FragmentState.NO_POLICY); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.LoadingDuration")); + assertHistograms(true, SpeedComparedToInflation.SLOWER, + SpeedComparedToInflation.NOT_RECORDED, SpeedComparedToInflation.NOT_RECORDED); + + // Try to accept Tos. + TestThreadUtils.runOnUiThreadBlocking((Runnable) mAcceptButton::performClick); + Assert.assertTrue("Crash report should be enabled.", + PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); + } + + @Test + @SmallTest + public void testNoRestriction_BeforeInflation() { + setAppRestrictionsMockInitialized(false); + launchFirstRunThroughCustomTab(); + assertUIState(FragmentState.NO_POLICY); + + assertHistograms(false, SpeedComparedToInflation.FASTER, + SpeedComparedToInflation.NOT_RECORDED, SpeedComparedToInflation.NOT_RECORDED); } @Test @@ -167,12 +202,42 @@ setPolicyServiceMockInitializedWithDialogEnabled(true); assertUIState(FragmentState.NO_POLICY); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.LoadingDuration")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.EnterprisePolicyCheckSpeed.SlowerThanInflation")); + + assertHistograms(true, SpeedComparedToInflation.FASTER, + SpeedComparedToInflation.NOT_RECORDED, SpeedComparedToInflation.SLOWER); + + // Try to accept Tos. + TestThreadUtils.runOnUiThreadBlocking((Runnable) mAcceptButton::performClick); + Assert.assertTrue("Crash report should be enabled.", + PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); + } + + @Test + @SmallTest + public void testDialogEnabled_BeforeAppRestrictions() { + launchFirstRunThroughCustomTab(); + assertUIState(FragmentState.LOADING); + + // When policy is loaded on fully managed device, we don't need app restriction. + setPolicyServiceMockInitializedWithDialogEnabled(true); + assertUIState(FragmentState.NO_POLICY); + + assertHistograms(true, SpeedComparedToInflation.NOT_RECORDED, + SpeedComparedToInflation.NOT_RECORDED, SpeedComparedToInflation.SLOWER); + } + + @Test + @SmallTest + public void testDialogDisabled_NoRestriction() { + setPolicyServiceMockInitializedWithDialogEnabled(false); + launchFirstRunThroughCustomTab(); + assertUIState(FragmentState.LOADING); + + setAppRestrictionsMockInitialized(false); + assertUIState(FragmentState.NO_POLICY); + + assertHistograms(true, SpeedComparedToInflation.SLOWER, + SpeedComparedToInflation.NOT_RECORDED, SpeedComparedToInflation.SLOWER); } @Test @@ -184,12 +249,14 @@ setEnterpriseInfoInitializedWithDeviceOwner(false); assertUIState(FragmentState.NO_POLICY); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.LoadingDuration")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation")); + + assertHistograms(true, SpeedComparedToInflation.FASTER, SpeedComparedToInflation.SLOWER, + SpeedComparedToInflation.NOT_RECORDED); + + // Try to accept Tos. + TestThreadUtils.runOnUiThreadBlocking((Runnable) mAcceptButton::performClick); + Assert.assertTrue("Crash report should be enabled.", + PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); } @Test @@ -201,12 +268,39 @@ launchFirstRunThroughCustomTab(); assertUIState(FragmentState.NO_POLICY); - Assert.assertEquals(0, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.LoadingDuration")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.FasterThanInflation")); + assertHistograms(false, SpeedComparedToInflation.FASTER, SpeedComparedToInflation.FASTER, + SpeedComparedToInflation.NOT_RECORDED); + } + + @Test + @SmallTest + public void testOwnedDevice_NoRestriction() { + setEnterpriseInfoInitializedWithDeviceOwner(true); + launchFirstRunThroughCustomTab(); + assertUIState(FragmentState.LOADING); + + setAppRestrictionsMockInitialized(false); + assertUIState(FragmentState.NO_POLICY); + + assertHistograms(true, SpeedComparedToInflation.SLOWER, SpeedComparedToInflation.FASTER, + SpeedComparedToInflation.NOT_RECORDED); + } + + @Test + @SmallTest + public void testOwnedDevice_NoPolicy() { + setEnterpriseInfoInitializedWithDeviceOwner(true); + launchFirstRunThroughCustomTab(); + assertUIState(FragmentState.LOADING); + + setAppRestrictionsMockInitialized(true); + assertUIState(FragmentState.LOADING); + + setPolicyServiceMockInitializedWithDialogEnabled(true); + assertUIState(FragmentState.NO_POLICY); + + assertHistograms(true, SpeedComparedToInflation.SLOWER, SpeedComparedToInflation.FASTER, + SpeedComparedToInflation.SLOWER); } @Test @@ -222,15 +316,10 @@ setPolicyServiceMockInitializedWithDialogEnabled(false); assertUIState(FragmentState.HAS_POLICY); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.LoadingDuration")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation")); + assertHistograms(true, SpeedComparedToInflation.FASTER, SpeedComparedToInflation.SLOWER, + SpeedComparedToInflation.SLOWER); + Assert.assertFalse("Crash report should not be enabled.", + PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); } @Test @@ -246,15 +335,10 @@ setEnterpriseInfoInitializedWithDeviceOwner(true); assertUIState(FragmentState.HAS_POLICY); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.LoadingDuration")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation")); + assertHistograms(true, SpeedComparedToInflation.FASTER, SpeedComparedToInflation.SLOWER, + SpeedComparedToInflation.SLOWER); + Assert.assertFalse("Crash report should not be enabled.", + PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); } @Test @@ -270,19 +354,17 @@ setEnterpriseInfoInitializedWithDeviceOwner(true); assertUIState(FragmentState.HAS_POLICY); + assertHistograms(true, SpeedComparedToInflation.NOT_RECORDED, + SpeedComparedToInflation.SLOWER, SpeedComparedToInflation.SLOWER); + // assertUIState will verify that exit was not called a second time. setAppRestrictionsMockInitialized(true); assertUIState(FragmentState.HAS_POLICY); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.LoadingDuration")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation")); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - "MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation")); + assertHistograms(true, SpeedComparedToInflation.SLOWER, SpeedComparedToInflation.SLOWER, + SpeedComparedToInflation.SLOWER); + Assert.assertFalse("Crash report should not be enabled.", + PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); } @Test @@ -299,6 +381,27 @@ assertUIState(FragmentState.NO_POLICY); } + @Test + @SmallTest + public void testAcceptTosWithoutCrashUpload() throws Exception { + setAppRestrictionsMockInitialized(true); + setEnterpriseInfoInitializedWithDeviceOwner(true); + setPolicyServiceMockInitializedWithDialogEnabled(true); + + launchFirstRunThroughCustomTab(); + assertUIState(FragmentState.NO_POLICY); + + // Accept ToS without check on UMA. + TestThreadUtils.runOnUiThreadBlocking(() -> { + mUmaCheckBox.setChecked(false); + mAcceptButton.performClick(); + }); + + mAcceptTosCallbackHelper.waitForCallback("Accept Tos is never called.", 0); + Assert.assertFalse("Crash report should not be enabled.", + PrivacyPreferencesManager.getInstance().isUsageAndCrashReportingPermittedByUser()); + } + /** * Launch chrome through custom tab and trigger first run. */ @@ -334,7 +437,7 @@ mTosText = mActivity.findViewById(R.id.tos_and_privacy); mUmaCheckBox = mActivity.findViewById(R.id.send_report_checkbox); - mAcceptButton = mActivity.findViewById(R.id.tos_and_privacy); + mAcceptButton = mActivity.findViewById(R.id.terms_accept); mLargeSpinner = mActivity.findViewById(R.id.progress_spinner_large); } @@ -361,6 +464,50 @@ Assert.assertEquals(expectedExitCount, mExitCount); } + /** + * Asserts the speed histograms related to FirstRunAppRestrictions and TosAndUmaFirstRunFragment + * are recorded correctly. Noting that with the current test setup, it is possible that the + * FragmentInflationSpeedCheck might be flaky. + * + * TODO(https://crbug.com/1120859): Move to a different setup once this test file moves to + * robolectric. + * + * @param didLoading If Welcome screen ever attempts to wait and load for policies. + * @param appRestrictionMetricsState {@link SpeedComparedToInflation} for checks regarding + * {@link FirstRunAppRestrictionInfo#getHasAppRestriction(Callback)} + * @param deviceOwnershipMetricsState {@link SpeedComparedToInflation} for checks regarding + * {@link EnterpriseInfo#getDeviceEnterpriseInfo(Callback)}} + * @param policyCheckMetricsState {@link SpeedComparedToInflation} for checks regarding {@link + * PolicyService#isInitializationComplete()} + */ + private void assertHistograms(boolean didLoading, + @SpeedComparedToInflation int appRestrictionMetricsState, + @SpeedComparedToInflation int deviceOwnershipMetricsState, + @SpeedComparedToInflation int policyCheckMetricsState) { + assertSingleHistogram("MobileFre.CctTos.LoadingDuration", didLoading); + + // WARNING: These two checks might be flaky with current test setup. + assertSingleHistogram("MobileFre.FragmentInflationSpeed.FasterThanAppRestriction", + appRestrictionMetricsState == SpeedComparedToInflation.SLOWER); + assertSingleHistogram("MobileFre.FragmentInflationSpeed.SlowerThanAppRestriction", + appRestrictionMetricsState == SpeedComparedToInflation.FASTER); + + assertSingleHistogram("MobileFre.CctTos.IsDeviceOwnedCheckSpeed.FasterThanInflation", + deviceOwnershipMetricsState == SpeedComparedToInflation.FASTER); + assertSingleHistogram("MobileFre.CctTos.IsDeviceOwnedCheckSpeed.SlowerThanInflation", + deviceOwnershipMetricsState == SpeedComparedToInflation.SLOWER); + + assertSingleHistogram("MobileFre.CctTos.EnterprisePolicyCheckSpeed.FasterThanInflation", + policyCheckMetricsState == SpeedComparedToInflation.FASTER); + assertSingleHistogram("MobileFre.CctTos.EnterprisePolicyCheckSpeed.SlowerThanInflation", + policyCheckMetricsState == SpeedComparedToInflation.SLOWER); + } + + private void assertSingleHistogram(String histogram, boolean recorded) { + Assert.assertEquals("Histogram <" + histogram + "> is not recorded correctly.", + recorded ? 1 : 0, RecordHistogram.getHistogramTotalCountForTesting(histogram)); + } + private void waitUntilNativeLoaded() { CriteriaHelper.pollUiThread( (() -> mActivity.isNativeSideIsInitializedForTest()), "native never initialized."); @@ -369,25 +516,46 @@ private void setAppRestrictionsMockNotInitialized() { Mockito.doAnswer(invocation -> { Callback<Boolean> callback = invocation.getArgument(0); - mAppRestrictonsCallbacks.add(callback); + mAppRestrictionsCallbacks.add(callback); return null; }) .when(mMockAppRestrictionInfo) .getHasAppRestriction(any()); + + Mockito.doAnswer(invocation -> { + Callback<Long> callback = invocation.getArgument(0); + mAppRestrictionsDurationCallbacks.add(callback); + return null; + }) + .when(mMockAppRestrictionInfo) + .getCompletionElapsedRealtimeMs(any()); } - private void setAppRestrictionsMockInitialized(boolean hasAppRestrictons) { + private void setAppRestrictionsMockInitialized(boolean hasAppRestrictions) { Mockito.doAnswer(invocation -> { Callback<Boolean> callback = invocation.getArgument(0); - callback.onResult(hasAppRestrictons); + callback.onResult(hasAppRestrictions); return null; }) .when(mMockAppRestrictionInfo) .getHasAppRestriction(any()); + long resolvingTime = SystemClock.elapsedRealtime(); + Mockito.doAnswer(invocation -> { + Callback<Long> callback = invocation.getArgument(0); + callback.onResult(resolvingTime); + return null; + }) + .when(mMockAppRestrictionInfo) + .getCompletionElapsedRealtimeMs(any()); + TestThreadUtils.runOnUiThreadBlocking(() -> { - for (Callback<Boolean> callback : mAppRestrictonsCallbacks) { - callback.onResult(hasAppRestrictons); + for (Callback<Boolean> callback : mAppRestrictionsCallbacks) { + callback.onResult(hasAppRestrictions); + } + + for (Callback<Long> callback : mAppRestrictionsDurationCallbacks) { + callback.onResult(resolvingTime); } }); }
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java index a2fabc6..28ed320 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/identity_disc/IdentityDiscControllerTest.java
@@ -31,12 +31,14 @@ import org.chromium.base.test.util.CommandLineFlags; import org.chromium.chrome.R; +import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.flags.ChromeSwitches; import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.test.ChromeJUnit4ClassRunner; import org.chromium.chrome.test.ChromeTabbedActivityTestRule; import org.chromium.chrome.test.util.ChromeTabUtils; import org.chromium.chrome.test.util.NewTabPageTestUtils; +import org.chromium.chrome.test.util.browser.Features; import org.chromium.chrome.test.util.browser.signin.AccountManagerTestRule; import org.chromium.components.embedder_support.util.UrlConstants; import org.chromium.content_public.common.ContentUrlConstants; @@ -46,6 +48,7 @@ */ @RunWith(ChromeJUnit4ClassRunner.class) @CommandLineFlags.Add({ChromeSwitches.DISABLE_FIRST_RUN_EXPERIENCE}) +@Features.DisableFeatures({ChromeFeatureList.MOBILE_IDENTITY_CONSISTENCY}) public class IdentityDiscControllerTest { private final ChromeTabbedActivityTestRule mActivityTestRule = new ChromeTabbedActivityTestRule();
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageUtilsTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageUtilsTest.java index 8eaff60..89ed7ca 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageUtilsTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/offlinepages/OfflinePageUtilsTest.java
@@ -202,7 +202,7 @@ @Override public void onResult(ShareParams shareParams) { - mText = shareParams.getText(); + mText = shareParams.getTextAndUrl(); mSemaphore.release(); }
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestionBuilderForTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestionBuilderForTest.java index afc12a1..2f45ee3 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestionBuilderForTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/omnibox/suggestions/OmniboxSuggestionBuilderForTest.java
@@ -44,6 +44,7 @@ private List<QueryTile> mQueryTiles; private byte[] mClipboardImageData; private boolean mHasTabMatch; + private List<OmniboxSuggestion.NavsuggestTile> mNavsuggestTiles; /** * Create a suggestion builder for a search suggestion. @@ -88,7 +89,7 @@ mDisplayText, mDisplayTextClassifications, mDescription, mDescriptionClassifications, mAnswer, mFillIntoEdit, mUrl, mImageUrl, mImageDominantColor, mIsStarred, mIsDeletable, mPostContentType, mPostData, - mGroupId, mQueryTiles, mClipboardImageData, mHasTabMatch); + mGroupId, mQueryTiles, mClipboardImageData, mHasTabMatch, mNavsuggestTiles); } /**
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/share/ShareDelegateImplIntegrationTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/share/ShareDelegateImplIntegrationTest.java index b4afb16..176f8f5 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/share/ShareDelegateImplIntegrationTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/share/ShareDelegateImplIntegrationTest.java
@@ -108,7 +108,7 @@ HistogramDelta urlResultDelta = new HistogramDelta( ShareDelegateImpl.CANONICAL_URL_RESULT_HISTOGRAM, expectedUrlResult); ShareParams params = triggerShare(); - Assert.assertTrue(params.getText().contains(expectedShareUrl)); + Assert.assertTrue(params.getTextAndUrl().contains(expectedShareUrl)); Assert.assertEquals(1, urlResultDelta.getDelta()); }
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTest.java index 8228f3bf..7e5ea517 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTest.java
@@ -4,6 +4,10 @@ package org.chromium.chrome.browser.sync; +import static org.mockito.Mockito.doNothing; +import static org.mockito.Mockito.verify; +import static org.mockito.Mockito.when; + import static org.chromium.chrome.browser.sync.AndroidSyncSettingsTestUtils.getDoesMasterSyncAllowSyncOnUiThread; import static org.chromium.chrome.browser.sync.AndroidSyncSettingsTestUtils.getIsChromeSyncEnabledOnUiThread; import static org.chromium.chrome.browser.sync.AndroidSyncSettingsTestUtils.getIsSyncEnabledOnUiThread; @@ -20,8 +24,10 @@ import org.junit.Test; import org.junit.rules.TestRule; import org.junit.runner.RunWith; +import org.mockito.Mock; +import org.mockito.junit.MockitoJUnit; +import org.mockito.junit.MockitoRule; -import org.chromium.base.FeatureList; import org.chromium.base.test.BaseJUnit4ClassRunner; import org.chromium.base.test.util.Feature; import org.chromium.chrome.browser.flags.ChromeFeatureList; @@ -116,21 +122,25 @@ @Rule public TestRule mChromeBrowserRule = new ChromeBrowserTestRule(); @Rule - public TestRule mProcessorRule = new Features.JUnitProcessor(); + public TestRule mProcessorRule = new Features.InstrumentationProcessor(); + @Rule + public final MockitoRule mMockitoRule = MockitoJUnit.rule(); private AndroidSyncSettings mAndroidSyncSettings; private CountingMockSyncContentResolverDelegate mSyncContentResolverDelegate; + @Mock + private ProfileSyncService mProfileSyncService; private Account mAccount; private Account mAlternateAccount; private String mAuthority = AndroidSyncSettings.getContractAuthority(); @Before public void setUp() { - FeatureList.setTestCanUseDefaultsForTesting(); - mSyncContentResolverDelegate = new CountingMockSyncContentResolverDelegate(); - TestThreadUtils.runOnUiThreadBlocking( - () -> SyncContentResolverDelegate.overrideForTests(mSyncContentResolverDelegate)); + TestThreadUtils.runOnUiThreadBlocking(() -> { + SyncContentResolverDelegate.overrideForTests(mSyncContentResolverDelegate); + ProfileSyncService.overrideForTests(mProfileSyncService); + }); FakeAccountManagerFacade fakeAccountManagerFacade = new FakeAccountManagerFacade(null); AccountManagerFacadeProvider.setInstanceForTests(fakeAccountManagerFacade); @@ -156,16 +166,6 @@ } } - private void setMasterSyncAllowsChromeSync() { - if (!ChromeFeatureList.isEnabled( - ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC)) { - mSyncContentResolverDelegate.setMasterSyncAutomatically(true); - Assert.assertTrue(getDoesMasterSyncAllowSyncOnUiThread()); - } - // If DecoupleSyncFromAndroidMasterSync is enabled, no need for any - // setup since master sync doesn't influence sync. - } - @After public void tearDown() { AccountManagerFacadeProvider.resetInstanceForTests(); @@ -174,6 +174,7 @@ @Test @SmallTest @Feature({"Sync"}) + @Features.DisableFeatures(ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC) public void testAccountInitialization() { createAndroidSyncSettings(); @@ -250,9 +251,9 @@ @SmallTest @Feature({"Sync"}) public void testToggleAccountSyncFromApplication() { - createAndroidSyncSettings(); + mSyncContentResolverDelegate.setMasterSyncAutomatically(true); - setMasterSyncAllowsChromeSync(); + createAndroidSyncSettings(); TestThreadUtils.runOnUiThreadBlocking(() -> mAndroidSyncSettings.enableChromeSync()); Assert.assertTrue(getIsSyncEnabledOnUiThread()); @@ -265,9 +266,9 @@ @SmallTest @Feature({"Sync"}) public void testToggleSyncabilityForMultipleAccounts() { - createAndroidSyncSettings(); + mSyncContentResolverDelegate.setMasterSyncAutomatically(true); - setMasterSyncAllowsChromeSync(); + createAndroidSyncSettings(); TestThreadUtils.runOnUiThreadBlocking(() -> { mAndroidSyncSettings.enableChromeSync(); @@ -292,9 +293,9 @@ @SmallTest @Feature({"Sync"}) public void testSyncSettingsCaching() { - createAndroidSyncSettings(); + mSyncContentResolverDelegate.setMasterSyncAutomatically(true); - setMasterSyncAllowsChromeSync(); + createAndroidSyncSettings(); TestThreadUtils.runOnUiThreadBlocking(() -> { mAndroidSyncSettings.enableChromeSync(); @@ -418,20 +419,71 @@ @SmallTest @Feature({"Sync"}) @Features.EnableFeatures(ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC) - // TODO(crbug.com/1105795): Remove this test after DecoupleSyncFromAndroidMasterSync has - // launched, since testToggleChromeSyncFromSettings() covers the same functionality. - public void testSyncStateDoesNotDependOnMasterSync() { + public void testMasterSyncAllowsSyncIfReEnabledOnce() { + // Master sync is disabled on startup and the user hasn't gone through the decoupling flow + // in the past. mSyncContentResolverDelegate.setMasterSyncAutomatically(false); - createAndroidSyncSettings(); - mSyncContentResolverDelegate.setSyncAutomatically(mAccount, mAuthority, true); - Assert.assertTrue(getIsChromeSyncEnabledOnUiThread()); + TestThreadUtils.runOnUiThreadBlocking(() -> { + when(mProfileSyncService.getDecoupledFromAndroidMasterSync()).thenReturn(false); + }); + + // Sync must remain disabled as long as master sync is not re-enabled. + createAndroidSyncSettings(); + Assert.assertFalse(getDoesMasterSyncAllowSyncOnUiThread()); + Assert.assertFalse(getIsSyncEnabledOnUiThread()); + + // Re-enable master sync at least once. Sync is now re-enabled and decoupled from master + // sync. + TestThreadUtils.runOnUiThreadBlocking( + () -> doNothing().when(mProfileSyncService).setDecoupledFromAndroidMasterSync()); + mSyncContentResolverDelegate.setMasterSyncAutomatically(true); Assert.assertTrue(getDoesMasterSyncAllowSyncOnUiThread()); Assert.assertTrue(getIsSyncEnabledOnUiThread()); - - mSyncContentResolverDelegate.setSyncAutomatically(mAccount, mAuthority, false); - Assert.assertFalse(getIsChromeSyncEnabledOnUiThread()); + TestThreadUtils.runOnUiThreadBlocking( + () -> verify(mProfileSyncService).setDecoupledFromAndroidMasterSync()); + mSyncContentResolverDelegate.setMasterSyncAutomatically(false); Assert.assertTrue(getDoesMasterSyncAllowSyncOnUiThread()); + Assert.assertTrue(getIsSyncEnabledOnUiThread()); + } + + @Test + @SmallTest + @Feature({"Sync"}) + @Features.EnableFeatures(ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC) + public void testSyncStateRespectsPersistedDecouplingStateIfFeatureEnabled() { + // Master sync is disabled on startup, but the user has gone through the decoupling flow in + // the past and has the DecoupleSyncFromAndroidMasterSync feature enabled. + mSyncContentResolverDelegate.setMasterSyncAutomatically(false); + mSyncContentResolverDelegate.setSyncAutomatically(mAccount, mAuthority, true); + TestThreadUtils.runOnUiThreadBlocking(() -> { + when(mProfileSyncService.getDecoupledFromAndroidMasterSync()).thenReturn(true); + }); + + // Chrome becomes aware of the previous decoupling, so Sync can be enabled despite master + // sync being disabled. + createAndroidSyncSettings(); + Assert.assertTrue(getDoesMasterSyncAllowSyncOnUiThread()); + Assert.assertTrue(getIsSyncEnabledOnUiThread()); + } + + @Test + @SmallTest + @Feature({"Sync"}) + @Features.DisableFeatures(ChromeFeatureList.DECOUPLE_SYNC_FROM_ANDROID_MASTER_SYNC) + public void testSyncStateDoesNotRespectPersistedDecouplingStateIfFeatureDisabled() { + // The user went through the master sync decoupling flow in the past, but has the + // DecoupleSyncFromAndroidMasterSync feature disabled. + mSyncContentResolverDelegate.setMasterSyncAutomatically(false); + mSyncContentResolverDelegate.setSyncAutomatically(mAccount, mAuthority, true); + TestThreadUtils.runOnUiThreadBlocking(() -> { + when(mProfileSyncService.getDecoupledFromAndroidMasterSync()).thenReturn(true); + }); + + // Chrome should ignore that a previous decoupling happened. Sync should again respect + // master sync and stay disabled. + createAndroidSyncSettings(); + Assert.assertFalse(getDoesMasterSyncAllowSyncOnUiThread()); Assert.assertFalse(getIsSyncEnabledOnUiThread()); } }
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTestUtils.java b/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTestUtils.java index 2f9edfca..0d3e9fc 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTestUtils.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/sync/AndroidSyncSettingsTestUtils.java
@@ -9,16 +9,13 @@ import org.chromium.base.annotations.CalledByNative; import org.chromium.content_public.browser.test.util.TestThreadUtils; -import java.util.concurrent.Callable; - /** * A utility class for mocking AndroidSyncSettings. */ public class AndroidSyncSettingsTestUtils { /** - * Sets up AndroidSyncSettings with a mock SyncContentResolverDelegate and with Android's master - * sync setting enabled. (This setting is found, e.g., under Settings > Accounts & Sync > - * Auto-sync data.) + * Sets up a MockSyncContentResolverDelegate with Android's master sync setting enabled. + * (This setting is found, e.g., under Settings > Accounts & Sync > Auto-sync data.) */ @CalledByNative @VisibleForTesting @@ -27,36 +24,20 @@ delegate.setMasterSyncAutomatically(true); TestThreadUtils.runOnUiThreadBlocking( () -> SyncContentResolverDelegate.overrideForTests(delegate)); - // Explicitly pass null account to AndroidSyncSettings ctor. Normally, AndroidSyncSettings - // ctor uses IdentityManager to get the sync account, but some native tests call this method - // before profiles are initialized (when IdentityManager doesn't exist yet). - AndroidSyncSettings.overrideForTests(new AndroidSyncSettings(null)); } public static boolean getIsSyncEnabledOnUiThread() { - return TestThreadUtils.runOnUiThreadBlockingNoException(new Callable<Boolean>() { - @Override - public Boolean call() { - return AndroidSyncSettings.get().isSyncEnabled(); - } - }); + return TestThreadUtils.runOnUiThreadBlockingNoException( + () -> AndroidSyncSettings.get().isSyncEnabled()); } public static boolean getIsChromeSyncEnabledOnUiThread() { - return TestThreadUtils.runOnUiThreadBlockingNoException(new Callable<Boolean>() { - @Override - public Boolean call() { - return AndroidSyncSettings.get().isChromeSyncEnabled(); - } - }); + return TestThreadUtils.runOnUiThreadBlockingNoException( + () -> AndroidSyncSettings.get().isChromeSyncEnabled()); } public static boolean getDoesMasterSyncAllowSyncOnUiThread() { - return TestThreadUtils.runOnUiThreadBlockingNoException(new Callable<Boolean>() { - @Override - public Boolean call() { - return AndroidSyncSettings.get().doesMasterSyncSettingAllowChromeSync(); - } - }); + return TestThreadUtils.runOnUiThreadBlockingNoException( + () -> AndroidSyncSettings.get().doesMasterSyncSettingAllowChromeSync()); } }
diff --git a/chrome/android/junit/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediatorUnitTest.java b/chrome/android/junit/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediatorUnitTest.java index 185f5d1..773983afc9 100644 --- a/chrome/android/junit/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediatorUnitTest.java +++ b/chrome/android/junit/src/org/chromium/chrome/browser/toolbar/top/StartSurfaceToolbarMediatorUnitTest.java
@@ -41,6 +41,7 @@ import org.robolectric.annotation.Config; import org.chromium.base.Callback; +import org.chromium.base.supplier.ObservableSupplierImpl; import org.chromium.base.test.BaseRobolectricTestRunner; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior; import org.chromium.chrome.browser.compositor.layouts.OverviewModeBehavior.OverviewModeObserver; @@ -99,6 +100,7 @@ private ButtonData mButtonData; private ButtonData mDisabledButtonData; + private ObservableSupplierImpl<Boolean> mIdentityDiscStateSupplier; @Before public void setUp() { @@ -113,6 +115,7 @@ .build(); mButtonData = new ButtonData(false, mDrawable, mOnClickListener, 0, false, null, true); mDisabledButtonData = new ButtonData(false, null, null, 0, false, null, true); + mIdentityDiscStateSupplier = new ObservableSupplierImpl<>(); doReturn(mButtonData) .when(mIdentityDiscController) .getForStartSurface(OverviewModeState.SHOWN_HOMEPAGE); @@ -589,17 +592,17 @@ assertEquals(mPropertyModel.get(IDENTITY_DISC_IS_VISIBLE), false); mButtonData.canShow = true; - mMediator.identityDiscStateChanged(true); + mIdentityDiscStateSupplier.set(true); assertEquals(mPropertyModel.get(IDENTITY_DISC_IS_VISIBLE), true); mButtonData.canShow = false; - mMediator.identityDiscStateChanged(false); + mIdentityDiscStateSupplier.set(false); assertEquals(mPropertyModel.get(IDENTITY_DISC_IS_VISIBLE), false); // updateIdentityDisc() should properly handle a hint that contradicts the true value of // canShow. mButtonData.canShow = false; - mMediator.identityDiscStateChanged(true); + mIdentityDiscStateSupplier.set(true); assertEquals(mPropertyModel.get(IDENTITY_DISC_IS_VISIBLE), false); } @@ -720,9 +723,12 @@ private void createMediator(boolean hideIncognitoSwitchWhenNoTabs, boolean hideIncognitoSwitchOnHomePage, boolean showNewTabAndIdentityDiscAtStart) { - mMediator = new StartSurfaceToolbarMediator(mPropertyModel, mIdentityDiscController, - mMockCallback, hideIncognitoSwitchWhenNoTabs, hideIncognitoSwitchOnHomePage, - showNewTabAndIdentityDiscAtStart, mMenuButtonCoordinator); + mMediator = new StartSurfaceToolbarMediator(mPropertyModel, mMockCallback, + hideIncognitoSwitchWhenNoTabs, hideIncognitoSwitchOnHomePage, + showNewTabAndIdentityDiscAtStart, mMenuButtonCoordinator, + mIdentityDiscStateSupplier, + () -> mIdentityDiscController.getForStartSurface( + mMediator.getOverviewModeStateForTesting())); mMediator.setOverviewModeBehavior(mOverviewModeBehavior); verify(mOverviewModeBehavior) .addOverviewModeObserver(mOverviewModeObserverCaptor.capture());
diff --git a/chrome/app/chromium_strings.grd b/chrome/app/chromium_strings.grd index 7dfc7d9ca..34f4b52 100644 --- a/chrome/app/chromium_strings.grd +++ b/chrome/app/chromium_strings.grd
@@ -328,7 +328,7 @@ Make Chromium the default browser </message> <if expr="chromeos"> - <message name="IDS_EXTERNAL_PROTOCOL_TITLE" desc="External Protocol Dialog Title"> + <message name="IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE" desc="External Protocol Dialog Title"> Chromium OS can't open this page. </message> </if>
diff --git a/chrome/app/chromium_strings_grd/IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE.png.sha1 b/chrome/app/chromium_strings_grd/IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE.png.sha1 new file mode 100644 index 0000000..57fd0855 --- /dev/null +++ b/chrome/app/chromium_strings_grd/IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE.png.sha1
@@ -0,0 +1 @@ +d4b444ab2d88cb4bd11e21e52b7246de60c8bf71 \ No newline at end of file
diff --git a/chrome/app/generated_resources.grd b/chrome/app/generated_resources.grd index 73c5a61c..c9456357 100644 --- a/chrome/app/generated_resources.grd +++ b/chrome/app/generated_resources.grd
@@ -5683,10 +5683,17 @@ </message> </if> - <!-- Read Later menu --> - <message name="IDS_READ_LATER_MENU_TITLE" desc="Title of the Read later menu"> - Read later - </message> + <!-- Read Later button and menu --> + <if expr="use_titlecase"> + <message name="IDS_READ_LATER_TITLE" desc="Title of the Read later menu"> + Reading List + </message> + </if> + <if expr="not use_titlecase"> + <message name="IDS_READ_LATER_TITLE" desc="Title of the Read later menu"> + Reading list + </message> + </if> <message name="IDS_READ_LATER_MENU_UNREAD_HEADER" desc="Header for section of unread Read later items."> UNREAD </message> @@ -5742,9 +5749,6 @@ <message name="IDS_TOOLTIP_MIC_SEARCH" desc="The tooltip for search-by-voice button"> Search by voice </message> - <message name="IDS_TOOLTIP_READ_LATER_BUTTON" desc="The tooltip for the read-later button"> - Read later - </message> <message name="IDS_TOOLTIP_SAVE_CREDIT_CARD" desc="The tooltip for the icon that shows the save credit card bubble"> Save card </message> @@ -8028,28 +8032,26 @@ </message> <!-- External Protocol Dialog --> - <if expr="not chromeos"> - <message name="IDS_EXTERNAL_PROTOCOL_TITLE" desc="External Protocol Dialog Title"> - Open <ph name="APPLICATION">$1<ex>Adobe Acrobat</ex></ph>? - </message> - <message name="IDS_EXTERNAL_PROTOCOL_MESSAGE_WITH_INITIATING_ORIGIN" desc="External Protocol Dialog message when initiated by another website"> - <ph name="ORIGIN">$1<ex>https://google.com</ex></ph> wants to open this application. - </message> - <message name="IDS_EXTERNAL_PROTOCOL_MESSAGE" desc="External Protocol Dialog message when the initiating website is unknown"> - A website wants to open this application. - </message> - <message name="IDS_EXTERNAL_PROTOCOL_OK_BUTTON_TEXT" desc="Button in External Protocol Dialog that launches the application associated with the protocol"> - Open <ph name="APPLICATION">$1<ex>Adobe Acrobat</ex></ph> - </message> - <message name="IDS_EXTERNAL_PROTOCOL_CANCEL_BUTTON_TEXT" desc="Button in External Protocol Dialog that does not launch the application associated with the protocol"> - Cancel - </message> - <message name="IDS_EXTERNAL_PROTOCOL_CHECKBOX_PER_ORIGIN_TEXT" desc="The External Protocol Dialog is shown when a navigation is started from a webpage, such as https://google.com, to a URL where the protocol indicates that a different software application on the machine should be opened, external to the browser. For example, 'skype:' may indicate that the Skype application be opened. This string describes a checkbox that allows the user to opt out of seeing this confirmation dialog in the future from pages with the same origin as the current page, when trying to launch the same protocol currently being launched"> - Always allow <ph name="ORIGIN">$1<ex>https://google.com</ex></ph> to open links of this type in the associated app - </message> - </if> + <message name="IDS_EXTERNAL_PROTOCOL_TITLE" desc="External Protocol Dialog Title"> + Open <ph name="APPLICATION">$1<ex>Adobe Acrobat</ex></ph>? + </message> + <message name="IDS_EXTERNAL_PROTOCOL_MESSAGE_WITH_INITIATING_ORIGIN" desc="External Protocol Dialog message when initiated by another website"> + <ph name="ORIGIN">$1<ex>https://google.com</ex></ph> wants to open this application. + </message> + <message name="IDS_EXTERNAL_PROTOCOL_MESSAGE" desc="External Protocol Dialog message when the initiating website is unknown"> + A website wants to open this application. + </message> + <message name="IDS_EXTERNAL_PROTOCOL_OK_BUTTON_TEXT" desc="Button in External Protocol Dialog that launches the application associated with the protocol"> + Open <ph name="APPLICATION">$1<ex>Adobe Acrobat</ex></ph> + </message> + <message name="IDS_EXTERNAL_PROTOCOL_CANCEL_BUTTON_TEXT" desc="Button in External Protocol Dialog that does not launch the application associated with the protocol"> + Cancel + </message> + <message name="IDS_EXTERNAL_PROTOCOL_CHECKBOX_PER_ORIGIN_TEXT" desc="The External Protocol Dialog is shown when a navigation is started from a webpage, such as https://google.com, to a URL where the protocol indicates that a different software application on the machine should be opened, external to the browser. For example, 'skype:' may indicate that the Skype application be opened. This string describes a checkbox that allows the user to opt out of seeing this confirmation dialog in the future from pages with the same origin as the current page, when trying to launch the same protocol currently being launched"> + Always allow <ph name="ORIGIN">$1<ex>https://google.com</ex></ph> to open links of this type in the associated app + </message> <if expr="chromeos"> - <message name="IDS_EXTERNAL_PROTOCOL_OK_BUTTON_TEXT" desc="Button in External Protocol Dialog that closes the dialog"> + <message name="IDS_EXTERNAL_PROTOCOL_CLOSE_BUTTON_TEXT" desc="Button in External Protocol Dialog that closes the dialog"> Close </message> </if>
diff --git a/chrome/app/generated_resources_grd/IDS_EXTERNAL_PROTOCOL_CLOSE_BUTTON_TEXT.png.sha1 b/chrome/app/generated_resources_grd/IDS_EXTERNAL_PROTOCOL_CLOSE_BUTTON_TEXT.png.sha1 new file mode 100644 index 0000000..57fd0855 --- /dev/null +++ b/chrome/app/generated_resources_grd/IDS_EXTERNAL_PROTOCOL_CLOSE_BUTTON_TEXT.png.sha1
@@ -0,0 +1 @@ +d4b444ab2d88cb4bd11e21e52b7246de60c8bf71 \ No newline at end of file
diff --git a/chrome/app/generated_resources_grd/IDS_EXTERNAL_PROTOCOL_OK_BUTTON_TEXT.png.sha1 b/chrome/app/generated_resources_grd/IDS_EXTERNAL_PROTOCOL_OK_BUTTON_TEXT.png.sha1 new file mode 100644 index 0000000..931c9d5 --- /dev/null +++ b/chrome/app/generated_resources_grd/IDS_EXTERNAL_PROTOCOL_OK_BUTTON_TEXT.png.sha1
@@ -0,0 +1 @@ +0a0bc6ca1f1985c5c25a726a8ef123c27c33c7e1 \ No newline at end of file
diff --git a/chrome/app/generated_resources_grd/IDS_READ_LATER_MENU_TITLE.png.sha1 b/chrome/app/generated_resources_grd/IDS_READ_LATER_MENU_TITLE.png.sha1 deleted file mode 100644 index fee408a..0000000 --- a/chrome/app/generated_resources_grd/IDS_READ_LATER_MENU_TITLE.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -97cc37ef9726d64172b7cfdd8bf251cb5b66d645 \ No newline at end of file
diff --git a/chrome/app/generated_resources_grd/IDS_READ_LATER_TITLE.png.sha1 b/chrome/app/generated_resources_grd/IDS_READ_LATER_TITLE.png.sha1 new file mode 100644 index 0000000..d550252 --- /dev/null +++ b/chrome/app/generated_resources_grd/IDS_READ_LATER_TITLE.png.sha1
@@ -0,0 +1 @@ +07fc3d80481bd9c45c4ce4dc913d9ca6a11cae78 \ No newline at end of file
diff --git a/chrome/app/generated_resources_grd/IDS_TOOLTIP_READ_LATER_BUTTON.png.sha1 b/chrome/app/generated_resources_grd/IDS_TOOLTIP_READ_LATER_BUTTON.png.sha1 deleted file mode 100644 index 6b01db7..0000000 --- a/chrome/app/generated_resources_grd/IDS_TOOLTIP_READ_LATER_BUTTON.png.sha1 +++ /dev/null
@@ -1 +0,0 @@ -5b3b3031843ec01ec012ee1c6ee2c48729910490 \ No newline at end of file
diff --git a/chrome/app/google_chrome_strings.grd b/chrome/app/google_chrome_strings.grd index 930f416..d45430e1e 100644 --- a/chrome/app/google_chrome_strings.grd +++ b/chrome/app/google_chrome_strings.grd
@@ -334,7 +334,7 @@ Make Google Chrome the default browser </message> <if expr="chromeos"> - <message name="IDS_EXTERNAL_PROTOCOL_TITLE" desc="External Protocol Dialog Title"> + <message name="IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE" desc="External Protocol Dialog Title"> Google Chrome OS can't open this page. </message> </if>
diff --git a/chrome/app/google_chrome_strings_grd/IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE.png.sha1 b/chrome/app/google_chrome_strings_grd/IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE.png.sha1 new file mode 100644 index 0000000..57fd0855 --- /dev/null +++ b/chrome/app/google_chrome_strings_grd/IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE.png.sha1
@@ -0,0 +1 @@ +d4b444ab2d88cb4bd11e21e52b7246de60c8bf71 \ No newline at end of file
diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn index 282ed55..f609c4c3 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn
@@ -3726,6 +3726,12 @@ "search/search_suggest/search_suggest_service_factory.cc", "search/search_suggest/search_suggest_service_factory.h", "search/search_suggest/search_suggest_service_observer.h", + "search/shopping_tasks/shopping_tasks_data.cc", + "search/shopping_tasks/shopping_tasks_data.h", + "search/shopping_tasks/shopping_tasks_service.cc", + "search/shopping_tasks/shopping_tasks_service.h", + "search/shopping_tasks/shopping_tasks_service_factory.cc", + "search/shopping_tasks/shopping_tasks_service_factory.h", "send_tab_to_self/desktop_notification_handler.cc", "send_tab_to_self/desktop_notification_handler.h", "send_tab_to_self/send_tab_to_self_desktop_util.cc",
diff --git a/chrome/browser/about_flags.cc b/chrome/browser/about_flags.cc index 9e556682..2f40d67a 100644 --- a/chrome/browser/about_flags.cc +++ b/chrome/browser/about_flags.cc
@@ -2935,6 +2935,10 @@ {"crostini-enable-dlc", flag_descriptions::kCrostiniEnableDlcName, flag_descriptions::kCrostiniEnableDlcDescription, kOsCrOS, FEATURE_VALUE_TYPE(chromeos::features::kCrostiniEnableDlc)}, + {"guest-os-external-protocol", + flag_descriptions::kGuestOsExternalProtocolName, + flag_descriptions::kGuestOsExternalProtocolDescription, kOsCrOS, + FEATURE_VALUE_TYPE(chromeos::features::kGuestOsExternalProtocol)}, {"pluginvm-show-camera-permissions", flag_descriptions::kPluginVmShowCameraPermissionsName, flag_descriptions::kPluginVmShowCameraPermissionsDescription, kOsCrOS, @@ -6084,12 +6088,6 @@ flag_descriptions::kAndroidMultipleDisplayDescription, kOsAndroid, FEATURE_VALUE_TYPE(chrome::android::kAndroidMultipleDisplay)}, #endif // defined(OS_ANDROID) - {"autofill-enable-surfacing-server-card-nickname", - flag_descriptions::kAutofillEnableSurfacingServerCardNicknameName, - flag_descriptions::kAutofillEnableSurfacingServerCardNicknameDescription, - kOsAll, - FEATURE_VALUE_TYPE( - autofill::features::kAutofillEnableSurfacingServerCardNickname)}, {"app-cache", flag_descriptions::kAppCacheName, flag_descriptions::kAppCacheDescription, kOsAll,
diff --git a/chrome/browser/accessibility/accessibility_labels_service.cc b/chrome/browser/accessibility/accessibility_labels_service.cc index 30426788..64c783f 100644 --- a/chrome/browser/accessibility/accessibility_labels_service.cc +++ b/chrome/browser/accessibility/accessibility_labels_service.cc
@@ -11,7 +11,6 @@ #include "chrome/browser/accessibility/accessibility_state_utils.h" #include "chrome/browser/language/url_language_histogram_factory.h" #include "chrome/browser/profiles/profile.h" -#include "chrome/browser/ui/tab_contents/tab_contents_iterator.h" #include "chrome/common/channel_info.h" #include "chrome/common/pref_names.h" #include "components/language/core/browser/pref_names.h" @@ -33,6 +32,7 @@ #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_finder.h" #include "chrome/browser/ui/browser_list.h" +#include "chrome/browser/ui/tab_contents/tab_contents_iterator.h" #endif using LanguageInfo = language::UrlLanguageHistogram::LanguageInfo;
diff --git a/chrome/browser/android/autofill_assistant/client_android.cc b/chrome/browser/android/autofill_assistant/client_android.cc index e866bdb3..f9e81cd 100644 --- a/chrome/browser/android/autofill_assistant/client_android.cc +++ b/chrome/browser/android/autofill_assistant/client_android.cc
@@ -31,8 +31,6 @@ #include "components/autofill_assistant/browser/features.h" #include "components/autofill_assistant/browser/switches.h" #include "components/autofill_assistant/browser/website_login_manager_impl.h" -#include "components/password_manager/content/browser/content_password_manager_driver.h" -#include "components/password_manager/content/browser/content_password_manager_driver_factory.h" #include "components/password_manager/core/browser/password_manager_client.h" #include "components/signin/public/identity_manager/account_info.h" #include "components/signin/public/identity_manager/identity_manager.h" @@ -485,15 +483,8 @@ WebsiteLoginManager* ClientAndroid::GetWebsiteLoginManager() const { if (!website_login_manager_) { auto* client = GetPasswordManagerClient(); - auto* factory = - password_manager::ContentPasswordManagerDriverFactory::FromWebContents( - web_contents_); - // TODO(crbug.com/1043132): Add support for non-main frames. If another - // frame has a different origin than the main frame, passwords-related - // features may not work. - auto* driver = factory->GetDriverForFrame(web_contents_->GetMainFrame()); website_login_manager_ = - std::make_unique<WebsiteLoginManagerImpl>(client, driver); + std::make_unique<WebsiteLoginManagerImpl>(client, web_contents_); } return website_login_manager_.get(); }
diff --git a/chrome/browser/android/omnibox/OWNERS b/chrome/browser/android/omnibox/OWNERS new file mode 100644 index 0000000..da1fa59 --- /dev/null +++ b/chrome/browser/android/omnibox/OWNERS
@@ -0,0 +1,3 @@ +file://components/omnibox/OWNERS + +# COMPONENT: UI>Browser>Omnibox \ No newline at end of file
diff --git a/chrome/browser/android/omnibox/autocomplete_controller_android.cc b/chrome/browser/android/omnibox/autocomplete_controller_android.cc index c38f57b7..72e044b 100644 --- a/chrome/browser/android/omnibox/autocomplete_controller_android.cc +++ b/chrome/browser/android/omnibox/autocomplete_controller_android.cc
@@ -615,6 +615,8 @@ ScopedJavaLocalRef<jobject> j_query_tiles = query_tiles::TileConversionBridge::CreateJavaTiles(env, match.query_tiles); + ScopedJavaLocalRef<jobject> j_navsuggest_tiles = + BuildNavsuggestTilesList(env, match.navsuggest_tiles); BookmarkModel* bookmark_model = BookmarkModelFactory::GetForBrowserContext(profile_); @@ -633,7 +635,27 @@ match.suggestion_group_id.value_or( SearchSuggestionParser::kNoSuggestionGroupId), j_query_tiles, ToJavaByteArray(env, clipboard_image_data), - match.has_tab_match); + match.has_tab_match, j_navsuggest_tiles); +} + +base::android::ScopedJavaLocalRef<jobject> +AutocompleteControllerAndroid::BuildNavsuggestTilesList( + JNIEnv* env, + const std::vector<AutocompleteMatch::NavsuggestTile>& tiles) { + if (tiles.empty()) + return ScopedJavaLocalRef<jobject>(); + ScopedJavaLocalRef<jobject> j_navsuggest_tiles = + Java_AutocompleteController_buildOmniboxNavsuggestTileList(env, + tiles.size()); + for (const auto& tile : tiles) { + ScopedJavaLocalRef<jstring> title = + ConvertUTF16ToJavaString(env, tile.title); + ScopedJavaLocalRef<jobject> url = + url::GURLAndroid::FromNativeGURL(env, tile.url); + Java_AutocompleteController_addOmniboxNavsuggestTile( + env, j_navsuggest_tiles, title, url); + } + return j_navsuggest_tiles; } void AutocompleteControllerAndroid::PopulateOmniboxGroupsDetails(
diff --git a/chrome/browser/android/omnibox/autocomplete_controller_android.h b/chrome/browser/android/omnibox/autocomplete_controller_android.h index 3fc0388..2ffd7ded 100644 --- a/chrome/browser/android/omnibox/autocomplete_controller_android.h +++ b/chrome/browser/android/omnibox/autocomplete_controller_android.h
@@ -134,6 +134,11 @@ base::android::ScopedJavaLocalRef<jobject> BuildOmniboxSuggestion( JNIEnv* env, const AutocompleteMatch& match); + // Construct Java list of NavsuggestTile objects. + base::android::ScopedJavaLocalRef<jobject> BuildNavsuggestTilesList( + JNIEnv* env, + const std::vector<AutocompleteMatch::NavsuggestTile>& tiles); + // Construct Java GroupDetails map from supplied HeadersMap and expanded // state. void PopulateOmniboxGroupsDetails(
diff --git a/chrome/browser/apps/platform_apps/BUILD.gn b/chrome/browser/apps/platform_apps/BUILD.gn index 1208c1a..bb34b1e5 100644 --- a/chrome/browser/apps/platform_apps/BUILD.gn +++ b/chrome/browser/apps/platform_apps/BUILD.gn
@@ -4,6 +4,13 @@ import("//extensions/buildflags/buildflags.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + assert(enable_extensions) source_set("platform_apps") {
diff --git a/chrome/browser/autofill/autofill_save_card_infobar_delegate_mobile_unittest.cc b/chrome/browser/autofill/autofill_save_card_infobar_delegate_mobile_unittest.cc index ce080bd..1f31f933 100644 --- a/chrome/browser/autofill/autofill_save_card_infobar_delegate_mobile_unittest.cc +++ b/chrome/browser/autofill/autofill_save_card_infobar_delegate_mobile_unittest.cc
@@ -395,42 +395,17 @@ } } -// Tests to ensure the card nickname is correctly shown in the Upstream infobar. -// The param here indicates whether the nickname experiment is enabled. -class AutofillSaveCardInfoBarDelegateMobileTestForNickname - : public AutofillSaveCardInfoBarDelegateMobileTest, - public ::testing::WithParamInterface<bool> { - protected: - void SetUp() override { - scoped_feature_list_.InitWithFeatureState( - features::kAutofillEnableSurfacingServerCardNickname, GetParam()); - - AutofillSaveCardInfoBarDelegateMobileTest::SetUp(); - } - - private: - base::test::ScopedFeatureList scoped_feature_list_; -}; - -INSTANTIATE_TEST_SUITE_P(, - AutofillSaveCardInfoBarDelegateMobileTestForNickname, - testing::Bool()); - -TEST_P(AutofillSaveCardInfoBarDelegateMobileTestForNickname, - LocalCardHasNickname) { +TEST_F(AutofillSaveCardInfoBarDelegateMobileTest, LocalCardHasNickname) { CreditCard card = test::GetCreditCard(); card.SetNickname(base::ASCIIToUTF16("Nickname")); std::unique_ptr<AutofillSaveCardInfoBarDelegateMobile> delegate = CreateDelegate(/*is_uploading=*/true, prefs::PREVIOUS_SAVE_CREDIT_CARD_PROMPT_USER_DECISION_NONE, card); - EXPECT_EQ(delegate->card_label(), - GetParam() ? card.NicknameAndLastFourDigitsForTesting() - : card.NetworkAndLastFourDigits()); + EXPECT_EQ(delegate->card_label(), card.NicknameAndLastFourDigitsForTesting()); } -TEST_P(AutofillSaveCardInfoBarDelegateMobileTestForNickname, - LocalCardHasNoNickname) { +TEST_F(AutofillSaveCardInfoBarDelegateMobileTest, LocalCardHasNoNickname) { CreditCard card = test::GetCreditCard(); std::unique_ptr<AutofillSaveCardInfoBarDelegateMobile> delegate = CreateDelegate(/*is_uploading=*/true,
diff --git a/chrome/browser/browser_process_impl.cc b/chrome/browser/browser_process_impl.cc index 2ef25c4..55182e17 100644 --- a/chrome/browser/browser_process_impl.cc +++ b/chrome/browser/browser_process_impl.cc
@@ -41,7 +41,6 @@ #include "chrome/browser/chrome_notification_types.h" #include "chrome/browser/component_updater/chrome_component_updater_configurator.h" #include "chrome/browser/defaults.h" -#include "chrome/browser/devtools/devtools_auto_opener.h" #include "chrome/browser/devtools/remote_debugging_server.h" #include "chrome/browser/download/download_request_limiter.h" #include "chrome/browser/download/download_status_updater.h" @@ -76,7 +75,6 @@ #include "chrome/browser/startup_data.h" #include "chrome/browser/status_icons/status_tray.h" #include "chrome/browser/ui/browser_dialogs.h" -#include "chrome/browser/ui/browser_list.h" #include "chrome/browser/update_client/chrome_update_query_params_delegate.h" #include "chrome/common/buildflags.h" #include "chrome/common/channel_info.h" @@ -161,9 +159,11 @@ #include "chrome/browser/flags/android/chrome_feature_list.h" #include "chrome/browser/ssl/chrome_security_state_client.h" #else +#include "chrome/browser/devtools/devtools_auto_opener.h" #include "chrome/browser/gcm/gcm_product_util.h" #include "chrome/browser/resource_coordinator/tab_manager.h" #include "chrome/browser/ui/browser_finder.h" +#include "chrome/browser/ui/browser_list.h" #include "components/gcm_driver/gcm_client_factory.h" #include "components/gcm_driver/gcm_desktop_utils.h" #include "components/keep_alive_registry/keep_alive_registry.h"
diff --git a/chrome/browser/chrome_browser_main.cc b/chrome/browser/chrome_browser_main.cc index b75b2249..cd80a6b 100644 --- a/chrome/browser/chrome_browser_main.cc +++ b/chrome/browser/chrome_browser_main.cc
@@ -93,7 +93,6 @@ #include "chrome/browser/ui/profile_error_dialog.h" #include "chrome/browser/ui/startup/bad_flags_prompt.h" #include "chrome/browser/ui/startup/startup_browser_creator.h" -#include "chrome/browser/ui/uma_browsing_activity_observer.h" #include "chrome/browser/ui/webui/chrome_web_ui_controller_factory.h" #include "chrome/common/buildflags.h" #include "chrome/common/channel_info.h" @@ -188,6 +187,7 @@ #include "chrome/browser/resource_coordinator/tab_manager.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_finder.h" +#include "chrome/browser/ui/uma_browsing_activity_observer.h" #include "chrome/browser/upgrade_detector/upgrade_detector.h" #include "chrome/browser/usb/web_usb_detector.h" #include "ui/base/l10n/l10n_util.h"
diff --git a/chrome/browser/chromeos/BUILD.gn b/chrome/browser/chromeos/BUILD.gn index afc4df3..4cbe804 100644 --- a/chrome/browser/chromeos/BUILD.gn +++ b/chrome/browser/chromeos/BUILD.gn
@@ -375,7 +375,10 @@ "//url", ] if (is_cfm) { - deps += [ "//chromeos/dbus/cfm" ] + deps += [ + "//chrome/browser/chromeos/cfm", + "//chromeos/dbus/cfm", + ] } data_deps = [ ":dbus_service_files" ] @@ -1334,6 +1337,8 @@ "first_run/steps/app_list_step.h", "first_run/steps/tray_step.cc", "first_run/steps/tray_step.h", + "guest_os/guest_os_external_protocol_handler.cc", + "guest_os/guest_os_external_protocol_handler.h", "guest_os/guest_os_pref_names.cc", "guest_os/guest_os_pref_names.h", "guest_os/guest_os_registry_service.cc", @@ -3313,6 +3318,7 @@ "fileapi/recent_disk_source_unittest.cc", "fileapi/recent_model_unittest.cc", "fileapi/test/fake_recent_source.cc", + "guest_os/guest_os_external_protocol_handler_unittest.cc", "guest_os/guest_os_registry_service_unittest.cc", "guest_os/guest_os_share_path_unittest.cc", "hats/hats_finch_helper_unittest.cc",
diff --git a/chrome/browser/chromeos/DEPS b/chrome/browser/chromeos/DEPS index 9984e3a8..6c315c5 100644 --- a/chrome/browser/chromeos/DEPS +++ b/chrome/browser/chromeos/DEPS
@@ -48,6 +48,9 @@ "event_rewriter_unittest\.cc": [ "+ui/events/devices/device_data_manager.h", ], + "external_protocol_dialog\.cc": [ + "+chrome/browser/ui/views/external_protocol_dialog.h", + ], "file_manager_browsertest_base.cc": [ "+chrome/browser/ui/views/extensions/extension_dialog.h", "+chrome/browser/ui/views/select_file_dialog_extension.h",
diff --git a/chrome/browser/chromeos/attestation/enrollment_certificate_uploader_impl.cc b/chrome/browser/chromeos/attestation/enrollment_certificate_uploader_impl.cc index fbe00bb6..6f764af 100644 --- a/chrome/browser/chromeos/attestation/enrollment_certificate_uploader_impl.cc +++ b/chrome/browser/chromeos/attestation/enrollment_certificate_uploader_impl.cc
@@ -11,7 +11,6 @@ #include "base/time/time.h" #include "chrome/browser/chromeos/attestation/attestation_ca_client.h" #include "chromeos/attestation/attestation_flow.h" -#include "chromeos/attestation/attestation_flow_integrated.h" #include "chromeos/cryptohome/async_method_caller.h" #include "chromeos/cryptohome/cryptohome_parameters.h" #include "chromeos/dbus/cryptohome/cryptohome_client.h" @@ -95,7 +94,11 @@ cryptohome_client_ = CryptohomeClient::Get(); if (!attestation_flow_) { - default_attestation_flow_ = std::make_unique<AttestationFlowIntegrated>(); + std::unique_ptr<ServerProxy> attestation_ca_client( + new AttestationCAClient()); + default_attestation_flow_.reset(new AttestationFlow( + cryptohome::AsyncMethodCaller::GetInstance(), cryptohome_client_, + std::move(attestation_ca_client))); attestation_flow_ = default_attestation_flow_.get(); }
diff --git a/chrome/browser/chromeos/attestation/machine_certificate_uploader_impl.cc b/chrome/browser/chromeos/attestation/machine_certificate_uploader_impl.cc index 73a5ac24..14034e7 100644 --- a/chrome/browser/chromeos/attestation/machine_certificate_uploader_impl.cc +++ b/chrome/browser/chromeos/attestation/machine_certificate_uploader_impl.cc
@@ -17,7 +17,6 @@ #include "chrome/browser/chromeos/attestation/attestation_key_payload.pb.h" #include "chrome/browser/chromeos/settings/cros_settings.h" #include "chromeos/attestation/attestation_flow.h" -#include "chromeos/attestation/attestation_flow_integrated.h" #include "chromeos/cryptohome/async_method_caller.h" #include "chromeos/cryptohome/cryptohome_parameters.h" #include "chromeos/dbus/cryptohome/cryptohome_client.h" @@ -164,7 +163,11 @@ cryptohome_client_ = CryptohomeClient::Get(); if (!attestation_flow_) { - default_attestation_flow_ = std::make_unique<AttestationFlowIntegrated>(); + std::unique_ptr<ServerProxy> attestation_ca_client( + new AttestationCAClient()); + default_attestation_flow_.reset(new AttestationFlow( + cryptohome::AsyncMethodCaller::GetInstance(), cryptohome_client_, + std::move(attestation_ca_client))); attestation_flow_ = default_attestation_flow_.get(); }
diff --git a/chrome/browser/chromeos/attestation/platform_verification_flow.cc b/chrome/browser/chromeos/attestation/platform_verification_flow.cc index d758e4c..f4260e0 100644 --- a/chrome/browser/chromeos/attestation/platform_verification_flow.cc +++ b/chrome/browser/chromeos/attestation/platform_verification_flow.cc
@@ -19,7 +19,6 @@ #include "chrome/browser/permissions/permission_manager_factory.h" #include "chrome/browser/profiles/profile.h" #include "chromeos/attestation/attestation_flow.h" -#include "chromeos/attestation/attestation_flow_integrated.h" #include "chromeos/constants/chromeos_switches.h" #include "chromeos/cryptohome/async_method_caller.h" #include "chromeos/cryptohome/cryptohome_parameters.h" @@ -157,7 +156,9 @@ delegate_(NULL), timeout_delay_(base::TimeDelta::FromSeconds(kTimeoutInSeconds)) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); - default_attestation_flow_ = std::make_unique<AttestationFlowIntegrated>(); + std::unique_ptr<ServerProxy> attestation_ca_client(new AttestationCAClient()); + default_attestation_flow_.reset(new AttestationFlow( + async_caller_, cryptohome_client_, std::move(attestation_ca_client))); attestation_flow_ = default_attestation_flow_.get(); default_delegate_.reset(new DefaultDelegate()); delegate_ = default_delegate_.get();
diff --git a/chrome/browser/chromeos/attestation/tpm_challenge_key_subtle.cc b/chrome/browser/chromeos/attestation/tpm_challenge_key_subtle.cc index 6ec6b15..c8697d0b 100644 --- a/chrome/browser/chromeos/attestation/tpm_challenge_key_subtle.cc +++ b/chrome/browser/chromeos/attestation/tpm_challenge_key_subtle.cc
@@ -19,7 +19,6 @@ #include "chrome/browser/extensions/chrome_extension_function_details.h" #include "chrome/browser/profiles/profile.h" #include "chrome/common/pref_names.h" -#include "chromeos/attestation/attestation_flow_integrated.h" #include "chromeos/cryptohome/async_method_caller.h" #include "chromeos/cryptohome/cryptohome_parameters.h" #include "chromeos/dbus/constants/attestation_constants.h" @@ -116,7 +115,10 @@ } // namespace TpmChallengeKeySubtleImpl::TpmChallengeKeySubtleImpl() - : default_attestation_flow_(std::make_unique<AttestationFlowIntegrated>()), + : default_attestation_flow_(std::make_unique<AttestationFlow>( + cryptohome::AsyncMethodCaller::GetInstance(), + CryptohomeClient::Get(), + std::make_unique<AttestationCAClient>())), attestation_flow_(default_attestation_flow_.get()) {} TpmChallengeKeySubtleImpl::TpmChallengeKeySubtleImpl(
diff --git a/chrome/browser/chromeos/cfm/BUILD.gn b/chrome/browser/chromeos/cfm/BUILD.gn new file mode 100644 index 0000000..4783459 --- /dev/null +++ b/chrome/browser/chromeos/cfm/BUILD.gn
@@ -0,0 +1,21 @@ +# Copyright 2020 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("//chromeos/services/cfm/public/buildflags/buildflags.gni") + +assert(is_chromeos, "Non-ChromeOS builds cannot depend on //chromeos") +assert(is_cfm, "Non-CfM builds cannot depend on this library") + +source_set("cfm") { + sources = [ + "cfm_chrome_services.cc", + "cfm_chrome_services.h", + ] + deps = [ + "//chromeos/dbus/cfm", + "//chromeos/services/cfm/public/features", + "//chromeos/services/cfm/public/mojom", + ] + public_deps = [ "//base" ] +}
diff --git a/chrome/browser/chromeos/cfm/DEPS b/chrome/browser/chromeos/cfm/DEPS new file mode 100644 index 0000000..1ca82d5 --- /dev/null +++ b/chrome/browser/chromeos/cfm/DEPS
@@ -0,0 +1,5 @@ +include_rules = [ + "+chromeos/dbus/cfm", + "+chromeos/services/cfm/public/buildflags", + "+chromeos/services/cfm/public/features", +]
diff --git a/chrome/browser/chromeos/cfm/cfm_chrome_services.cc b/chrome/browser/chromeos/cfm/cfm_chrome_services.cc new file mode 100644 index 0000000..cf8525e --- /dev/null +++ b/chrome/browser/chromeos/cfm/cfm_chrome_services.cc
@@ -0,0 +1,24 @@ +// Copyright 2020 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/cfm/cfm_chrome_services.h" + +#include "chromeos/dbus/cfm/cfm_hotline_client.h" +#include "chromeos/services/cfm/public/features/features.h" + +namespace chromeos { +namespace cfm { + +void InitializeCfmServices() { + if (!base::FeatureList::IsEnabled( + chromeos::cfm::features::kCfmMojoServices) && + CfmHotlineClient::Get()) { + return; + } + + // TODO(kdgwill) Add Initial CfM Chromium Service +} + +} // namespace cfm +} // namespace chromeos
diff --git a/chrome/browser/chromeos/cfm/cfm_chrome_services.h b/chrome/browser/chromeos/cfm/cfm_chrome_services.h new file mode 100644 index 0000000..6fa5365 --- /dev/null +++ b/chrome/browser/chromeos/cfm/cfm_chrome_services.h
@@ -0,0 +1,23 @@ +// Copyright 2020 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_CFM_CFM_CHROME_SERVICES_H_ +#define CHROME_BROWSER_CHROMEOS_CFM_CFM_CHROME_SERVICES_H_ + +#include <string> + +#include "base/observer_list.h" +#include "base/observer_list_types.h" + +namespace chromeos { +namespace cfm { + +// Registers the observers for service interface requests by the +// |CfmServiceContext| granting hotline access to services. +void InitializeCfmServices(); + +} // namespace cfm +} // namespace chromeos + +#endif // CHROME_BROWSER_CHROMEOS_CFM_CFM_CHROME_SERVICES_H_
diff --git a/chrome/browser/chromeos/chrome_browser_main_chromeos.cc b/chrome/browser/chromeos/chrome_browser_main_chromeos.cc index 835a7d2e..d99093b1 100644 --- a/chrome/browser/chromeos/chrome_browser_main_chromeos.cc +++ b/chrome/browser/chromeos/chrome_browser_main_chromeos.cc
@@ -166,6 +166,7 @@ #include "chromeos/network/network_cert_loader.h" #include "chromeos/network/network_handler.h" #include "chromeos/network/portal_detector/network_portal_detector_stub.h" +#include "chromeos/services/cfm/public/buildflags/buildflags.h" // PLATFORM_CFM #include "chromeos/services/cros_healthd/public/cpp/service_connection.h" #include "chromeos/system/statistics_provider.h" #include "chromeos/tpm/install_attributes.h" @@ -210,6 +211,10 @@ #include "ui/chromeos/events/pref_names.h" #include "ui/events/event_utils.h" +#if BUILDFLAG(PLATFORM_CFM) +#include "chrome/browser/chromeos/cfm/cfm_chrome_services.h" +#endif + #if BUILDFLAG(ENABLE_RLZ) #include "components/rlz/rlz_tracker.h" #endif @@ -630,6 +635,10 @@ system::BreakpadConsentWatcher::Initialize(stats_controller); } +#if BUILDFLAG(PLATFORM_CFM) + chromeos::cfm::InitializeCfmServices(); +#endif // BUILDFLAG(PLATFORM_CFM) + ChromeBrowserMainPartsLinux::PreMainMessageLoopRun(); }
diff --git a/chrome/browser/chromeos/crosapi/browser_util.cc b/chrome/browser/chromeos/crosapi/browser_util.cc index bf8f381a..b451bce 100644 --- a/chrome/browser/chromeos/crosapi/browser_util.cc +++ b/chrome/browser/chromeos/crosapi/browser_util.cc
@@ -15,6 +15,7 @@ #include "chrome/browser/browser_process.h" #include "chrome/common/channel_info.h" #include "chrome/common/chrome_paths.h" +#include "chromeos/crosapi/cpp/crosapi_constants.h" #include "chromeos/crosapi/mojom/crosapi.mojom.h" #include "components/exo/shell_surface_util.h" #include "components/metrics/metrics_pref_names.h" @@ -114,9 +115,6 @@ const std::string* app_id = exo::GetShellApplicationId(window); if (!app_id) return false; - // TODO(jamescook): Move this constant to //chromeos/crosapi/cpp and share it - // with //ui/ozone/wayland. - const char kLacrosAppIdPrefix[] = "org.chromium.lacros"; return base::StartsWith(*app_id, kLacrosAppIdPrefix); }
diff --git a/chrome/browser/chromeos/external_protocol_dialog.cc b/chrome/browser/chromeos/external_protocol_dialog.cc index 54e18354..41f7fac 100644 --- a/chrome/browser/chromeos/external_protocol_dialog.cc +++ b/chrome/browser/chromeos/external_protocol_dialog.cc
@@ -4,13 +4,18 @@ #include "chrome/browser/chromeos/external_protocol_dialog.h" +#include "base/feature_list.h" +#include "base/strings/utf_string_conversions.h" #include "chrome/browser/chromeos/arc/intent_helper/arc_external_protocol_dialog.h" +#include "chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.h" #include "chrome/browser/external_protocol/external_protocol_handler.h" #include "chrome/browser/sharing/click_to_call/feature.h" #include "chrome/browser/tab_contents/tab_util.h" #include "chrome/browser/ui/browser_dialogs.h" +#include "chrome/browser/ui/views/external_protocol_dialog.h" #include "chrome/grit/chromium_strings.h" #include "chrome/grit/generated_resources.h" +#include "chromeos/constants/chromeos_features.h" #include "content/public/browser/render_process_host.h" #include "content/public/browser/render_view_host.h" #include "content/public/browser/web_contents.h" @@ -27,9 +32,28 @@ const int kMessageWidth = 400; -void OnArcHandled(WebContents* web_contents, const GURL& url, bool handled) { - if (!handled) - new ExternalProtocolDialog(web_contents, url); +void OnArcHandled(WebContents* web_contents, + const GURL& url, + const base::Optional<url::Origin>& initiating_origin, + bool handled) { + if (handled) + return; + + // Display the standard ExternalProtocolDialog if Guest OS has a handler. + if (base::FeatureList::IsEnabled( + chromeos::features::kGuestOsExternalProtocol)) { + base::Optional<guest_os::GuestOsRegistryService::Registration> + registration = guest_os::GetHandler( + Profile::FromBrowserContext(web_contents->GetBrowserContext()), + url); + if (registration) { + new ExternalProtocolDialog(web_contents, url, + base::UTF8ToUTF16(registration->Name()), + initiating_origin); + return; + } + } + new ExternalProtocolNoHandlersDialog(web_contents, url); } } // namespace @@ -55,21 +79,22 @@ arc::RunArcExternalProtocolDialog( url, initiating_origin, render_process_host_id, routing_id, page_transition, has_user_gesture, - base::BindOnce(&OnArcHandled, web_contents, url)); + base::BindOnce(&OnArcHandled, web_contents, url, initiating_origin)); } /////////////////////////////////////////////////////////////////////////////// -// ExternalProtocolDialog +// ExternalProtocolNoHandlersDialog -ExternalProtocolDialog::ExternalProtocolDialog(WebContents* web_contents, - const GURL& url) +ExternalProtocolNoHandlersDialog::ExternalProtocolNoHandlersDialog( + WebContents* web_contents, + const GURL& url) : creation_time_(base::TimeTicks::Now()), scheme_(url.scheme()) { SetOwnedByWidget(true); views::DialogDelegate::SetButtons(ui::DIALOG_BUTTON_OK); views::DialogDelegate::SetButtonLabel( ui::DIALOG_BUTTON_OK, - l10n_util::GetStringUTF16(IDS_EXTERNAL_PROTOCOL_OK_BUTTON_TEXT)); + l10n_util::GetStringUTF16(IDS_EXTERNAL_PROTOCOL_CLOSE_BUTTON_TEXT)); message_box_view_ = new views::MessageBoxView(); message_box_view_->SetMessageWidth(kMessageWidth); @@ -87,9 +112,9 @@ chrome::DialogIdentifier::EXTERNAL_PROTOCOL_CHROMEOS); } -ExternalProtocolDialog::~ExternalProtocolDialog() = default; +ExternalProtocolNoHandlersDialog::~ExternalProtocolNoHandlersDialog() = default; -base::string16 ExternalProtocolDialog::GetWindowTitle() const { +base::string16 ExternalProtocolNoHandlersDialog::GetWindowTitle() const { // If click to call feature is available, we display a message to the user on // how to use the feature. // TODO(crbug.com/1007995) - This is a hotfix for M78 and we plan to use our @@ -101,17 +126,17 @@ l10n_util::GetStringUTF16( IDS_BROWSER_SHARING_CLICK_TO_CALL_DIALOG_TROUBLESHOOT_LINK)); } - return l10n_util::GetStringUTF16(IDS_EXTERNAL_PROTOCOL_TITLE); + return l10n_util::GetStringUTF16(IDS_EXTERNAL_PROTOCOL_NO_HANDLER_TITLE); } -views::View* ExternalProtocolDialog::GetContentsView() { +views::View* ExternalProtocolNoHandlersDialog::GetContentsView() { return message_box_view_; } -const views::Widget* ExternalProtocolDialog::GetWidget() const { +const views::Widget* ExternalProtocolNoHandlersDialog::GetWidget() const { return message_box_view_->GetWidget(); } -views::Widget* ExternalProtocolDialog::GetWidget() { +views::Widget* ExternalProtocolNoHandlersDialog::GetWidget() { return message_box_view_->GetWidget(); }
diff --git a/chrome/browser/chromeos/external_protocol_dialog.h b/chrome/browser/chromeos/external_protocol_dialog.h index c66703e..769c36b 100644 --- a/chrome/browser/chromeos/external_protocol_dialog.h +++ b/chrome/browser/chromeos/external_protocol_dialog.h
@@ -22,13 +22,12 @@ class MessageBoxView; } -// An external protocol dialog for ChromeOS. Unlike other platforms, -// ChromeOS does not support launching external program, therefore, -// this dialog simply says it is not supported. -class ExternalProtocolDialog : public views::DialogDelegate { +// The external protocol dialog for Chrome OS shown when there are no handlers. +class ExternalProtocolNoHandlersDialog : public views::DialogDelegate { public: - ExternalProtocolDialog(content::WebContents* web_contents, const GURL& url); - ~ExternalProtocolDialog() override; + ExternalProtocolNoHandlersDialog(content::WebContents* web_contents, + const GURL& url); + ~ExternalProtocolNoHandlersDialog() override; // views::DialogDelegate: base::string16 GetWindowTitle() const override; @@ -46,7 +45,7 @@ // The scheme of the url. std::string scheme_; - DISALLOW_COPY_AND_ASSIGN(ExternalProtocolDialog); + DISALLOW_COPY_AND_ASSIGN(ExternalProtocolNoHandlersDialog); }; #endif // CHROME_BROWSER_CHROMEOS_EXTERNAL_PROTOCOL_DIALOG_H_
diff --git a/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.cc b/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.cc new file mode 100644 index 0000000..225d6823 --- /dev/null +++ b/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.cc
@@ -0,0 +1,70 @@ +// Copyright 2020 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/guest_os/guest_os_external_protocol_handler.h" + +#include "base/time/time.h" +#include "chrome/browser/chromeos/crostini/crostini_util.h" +#include "chrome/browser/chromeos/guest_os/guest_os_registry_service_factory.h" +#include "chrome/browser/chromeos/plugin_vm/plugin_vm_files.h" +#include "chrome/browser/profiles/profile.h" +#include "ui/display/display.h" + +namespace guest_os { +namespace { + +using VmType = guest_os::GuestOsRegistryService::VmType; + +bool AppHandlesProtocol( + const guest_os::GuestOsRegistryService::Registration& app, + const std::string& scheme) { + return app.MimeTypes().count("x-scheme-handler/" + scheme) != 0; +} + +} // namespace + +base::Optional<GuestOsRegistryService::Registration> GetHandler( + Profile* profile, + const GURL& url) { + auto* registry_service = + guest_os::GuestOsRegistryServiceFactory::GetForProfile(profile); + + base::Optional<GuestOsRegistryService::Registration> result; + for (auto& pair : registry_service->GetEnabledApps()) { + auto& registration = pair.second; + if (AppHandlesProtocol(registration, url.scheme()) && + (!result || registration.LastLaunchTime() > result->LastLaunchTime())) { + result = std::move(registration); + } + } + return result; +} + +void Launch(Profile* profile, const GURL& url) { + base::Optional<GuestOsRegistryService::Registration> registration = + GetHandler(profile, url); + if (!registration) { + LOG(ERROR) << "No handler for " << url; + return; + } + + switch (registration->VmType()) { + case VmType::ApplicationList_VmType_TERMINA: + crostini::LaunchCrostiniApp(profile, registration->app_id(), + display::kInvalidDisplayId, {url.spec()}, + base::DoNothing()); + break; + + case VmType::ApplicationList_VmType_PLUGIN_VM: + plugin_vm::LaunchPluginVmApp(profile, registration->app_id(), + {url.spec()}, base::DoNothing()); + break; + + default: + LOG(ERROR) << "Unsupported VmType: " + << static_cast<int>(registration->VmType()); + } +} + +} // namespace guest_os
diff --git a/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.h b/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.h new file mode 100644 index 0000000..be51f3fe3 --- /dev/null +++ b/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.h
@@ -0,0 +1,25 @@ +// Copyright 2020 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_GUEST_OS_GUEST_OS_EXTERNAL_PROTOCOL_HANDLER_H_ +#define CHROME_BROWSER_CHROMEOS_GUEST_OS_GUEST_OS_EXTERNAL_PROTOCOL_HANDLER_H_ + +#include "base/optional.h" +#include "chrome/browser/chromeos/guest_os/guest_os_registry_service.h" + +class Profile; + +namespace guest_os { + +// Returns handler for |url| if one exists. +base::Optional<GuestOsRegistryService::Registration> GetHandler( + Profile* profile, + const GURL& url); + +// Launches the app configured to handle |url| if one exists. +void Launch(Profile* profile, const GURL& url); + +} // namespace guest_os + +#endif // CHROME_BROWSER_CHROMEOS_GUEST_OS_GUEST_OS_EXTERNAL_PROTOCOL_HANDLER_H_
diff --git a/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler_unittest.cc b/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler_unittest.cc new file mode 100644 index 0000000..20fd719 --- /dev/null +++ b/chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler_unittest.cc
@@ -0,0 +1,74 @@ +// Copyright 2020 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/guest_os/guest_os_external_protocol_handler.h" + +#include <vector> + +#include "base/time/time.h" +#include "chrome/browser/chromeos/crostini/fake_crostini_features.h" +#include "chrome/browser/chromeos/guest_os/guest_os_registry_service.h" +#include "chrome/test/base/testing_profile.h" +#include "chromeos/dbus/vm_applications/apps.pb.h" +#include "content/public/test/browser_task_environment.h" +#include "testing/gtest/include/gtest/gtest.h" +#include "url/gurl.h" + +namespace guest_os { + +class GuestOsExternalProtocolHandlerTest : public testing::Test { + void SetUp() override { + fake_crostini_features_.set_enabled(true); + + app_list_.set_vm_type(vm_tools::apps::ApplicationList::TERMINA); + app_list_.set_vm_name("vm_name"); + app_list_.set_container_name("container_name"); + } + + protected: + TestingProfile* profile() { return &profile_; } + vm_tools::apps::ApplicationList& app_list() { return app_list_; } + + void AddApp(const std::string& desktop_file_id, + const std::string& mime_type, + const base::Time last_launch) { + vm_tools::apps::App& app = *app_list_.add_apps(); + app.set_desktop_file_id(desktop_file_id); + app.mutable_name()->add_values(); + app.add_mime_types(mime_type); + } + + private: + content::BrowserTaskEnvironment task_environment_; + TestingProfile profile_; + crostini::FakeCrostiniFeatures fake_crostini_features_; + vm_tools::apps::ApplicationList app_list_; +}; + +TEST_F(GuestOsExternalProtocolHandlerTest, TestNoRegisteredApps) { + AddApp("id", "not-scheme", base::Time()); + GuestOsRegistryService(profile()).UpdateApplicationList(app_list()); + + EXPECT_FALSE(guest_os::GetHandler(profile(), GURL("testscheme:12341234"))); +} + +TEST_F(GuestOsExternalProtocolHandlerTest, SingleRegisteredApp) { + AddApp("id", "x-scheme-handler/testscheme", base::Time()); + GuestOsRegistryService(profile()).UpdateApplicationList(app_list()); + + EXPECT_TRUE(guest_os::GetHandler(profile(), GURL("testscheme:12341234"))); +} + +TEST_F(GuestOsExternalProtocolHandlerTest, MostRecent) { + AddApp("id1", "x-scheme-handler/testscheme", base::Time::FromTimeT(1)); + AddApp("id2", "x-scheme-handler/testscheme", base::Time::FromTimeT(2)); + GuestOsRegistryService(profile()).UpdateApplicationList(app_list()); + + base::Optional<GuestOsRegistryService::Registration> registration = + GetHandler(profile(), GURL("testscheme:12341234")); + EXPECT_TRUE(registration); + EXPECT_EQ("id2", registration->DesktopFileId()); +} + +} // namespace guest_os
diff --git a/chrome/browser/chromeos/net/network_portal_detector_impl.cc b/chrome/browser/chromeos/net/network_portal_detector_impl.cc index 8684a73..3a52dcda 100644 --- a/chrome/browser/chromeos/net/network_portal_detector_impl.cc +++ b/chrome/browser/chromeos/net/network_portal_detector_impl.cc
@@ -377,7 +377,7 @@ DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); DCHECK(is_checking_for_portal()); - NET_LOG(ERROR) << "Portal detection timeout: " + NET_LOG(EVENT) << "Portal detection timeout: " << " id=" << NetworkGuidId(default_network_id_); captive_portal_detector_->Cancel();
diff --git a/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc b/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc index ee6a2f0..cf0ecbc 100644 --- a/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc +++ b/chrome/browser/chromeos/policy/browser_policy_connector_chromeos.cc
@@ -60,11 +60,11 @@ #include "chrome/common/chrome_features.h" #include "chrome/common/pref_names.h" #include "chromeos/attestation/attestation_flow.h" -#include "chromeos/attestation/attestation_flow_integrated.h" #include "chromeos/constants/chromeos_paths.h" #include "chromeos/constants/chromeos_switches.h" #include "chromeos/cryptohome/async_method_caller.h" #include "chromeos/cryptohome/system_salt_getter.h" +#include "chromeos/dbus/cryptohome/cryptohome_client.h" #include "chromeos/dbus/dbus_thread_manager.h" #include "chromeos/dbus/session_manager/session_manager_client.h" #include "chromeos/dbus/upstart/upstart_client.h" @@ -522,7 +522,10 @@ std::unique_ptr<chromeos::attestation::AttestationFlow> BrowserPolicyConnectorChromeOS::CreateAttestationFlow() { - return std::make_unique<chromeos::attestation::AttestationFlowIntegrated>(); + return std::make_unique<chromeos::attestation::AttestationFlow>( + cryptohome::AsyncMethodCaller::GetInstance(), + chromeos::CryptohomeClient::Get(), + std::make_unique<chromeos::attestation::AttestationCAClient>()); } chromeos::AffiliationIDSet
diff --git a/chrome/browser/contextmenu/OWNERS b/chrome/browser/contextmenu/OWNERS index 8aa316f3..c7ac92b6 100644 --- a/chrome/browser/contextmenu/OWNERS +++ b/chrome/browser/contextmenu/OWNERS
@@ -1,6 +1,6 @@ jinsukkim@chromium.org -sinansahin@chromium.org +sinansahin@google.com # TEAM: clank-modularization@chromium.org -# COMPONENT: UI>Browser>Mobile +# COMPONENT: UI>Browser>Mobile>ContextMenu # OS: Android
diff --git a/chrome/browser/extensions/extension_resource_request_policy_apitest.cc b/chrome/browser/extensions/extension_resource_request_policy_apitest.cc index 3d5554b..d774223f 100644 --- a/chrome/browser/extensions/extension_resource_request_policy_apitest.cc +++ b/chrome/browser/extensions/extension_resource_request_policy_apitest.cc
@@ -229,27 +229,14 @@ << message_; } -#if defined(OS_MAC) || defined(OS_WIN) -// http://crbug.com/238733 - Video is flaky on Mac and Win. -#define MAYBE_Video DISABLED_Video -#else -#define MAYBE_Video Video -#endif - -IN_PROC_BROWSER_TEST_F(ExtensionResourceRequestPolicyTest, MAYBE_Video) { +IN_PROC_BROWSER_TEST_F(ExtensionResourceRequestPolicyTest, Video) { EXPECT_TRUE(RunExtensionSubtest( "extension_resource_request_policy/extension2", "video.html")) << message_; } -// This test times out regularly on win_rel trybots. See http://crbug.com/122154 -#if defined(OS_WIN) -#define MAYBE_WebAccessibleResources DISABLED_WebAccessibleResources -#else -#define MAYBE_WebAccessibleResources WebAccessibleResources -#endif IN_PROC_BROWSER_TEST_F(ExtensionResourceRequestPolicyTest, - MAYBE_WebAccessibleResources) { + WebAccessibleResources) { std::string result; ASSERT_TRUE(LoadExtension(test_data_dir_ .AppendASCII("extension_resource_request_policy")
diff --git a/chrome/browser/flag-metadata.json b/chrome/browser/flag-metadata.json index 6740bee..0e2b6bf 100644 --- a/chrome/browser/flag-metadata.json +++ b/chrome/browser/flag-metadata.json
@@ -297,11 +297,6 @@ "expiry_milestone": 90 }, { - "name": "autofill-enable-surfacing-server-card-nickname", - "owners": [ "sujiezhu@google.com", "jsaul@google.com" ], - "expiry_milestone": 90 - }, - { "name": "autofill-enable-toolbar-status-chip", "owners": [ "siyua" ], "expiry_milestone": 88 @@ -2719,6 +2714,11 @@ "expiry_milestone": 93 }, { + "name": "guest-os-external-protocol", + "owners": [ "joelhockey", "crostini-syd" ], + "expiry_milestone": 93 + }, + { "name": "h264-decoder-is-buffer-complete-frame", "owners": [ "jkardatzke", "mcasas" ], "expiry_milestone": 89 @@ -4268,7 +4268,7 @@ { "name": "system-keyboard-lock", "owners": [ "joedow", "garykac", "jamiewalch" ], - "expiry_milestone": 86 + "expiry_milestone": 95 }, { "name": "system-tray-mic-gain",
diff --git a/chrome/browser/flag_descriptions.cc b/chrome/browser/flag_descriptions.cc index b01f6d0b..6eae2c6 100644 --- a/chrome/browser/flag_descriptions.cc +++ b/chrome/browser/flag_descriptions.cc
@@ -241,12 +241,6 @@ "When enabled, all Autofill payments bubbles will not be dismissed upon " "navigation."; -const char kAutofillEnableSurfacingServerCardNicknameName[] = - "Enable surfacing masked server card nicknames"; -const char kAutofillEnableSurfacingServerCardNicknameDescription[] = - "When enabled, if Google Payments cards were given nicknames in a Google " - "Pay app, Autofill will surface these nicknames in suggestions."; - const char kAutofillEnableToolbarStatusChipName[] = "Move Autofill omnibox icons next to the profile avatar icon"; const char kAutofillEnableToolbarStatusChipDescription[] = @@ -756,6 +750,10 @@ const char kEnableGpuServiceLoggingDescription[] = "Enable printing the actual GL driver calls."; +const char kGuestOsExternalProtocolName[] = "Guest OS External Protocol"; +const char kGuestOsExternalProtocolDescription[] = + "Enable Guest OS external protocol handlers"; + const char kEnableImplicitRootScrollerName[] = "Implicit Root Scroller"; const char kEnableImplicitRootScrollerDescription[] = "Enables implicitly choosing which scroller on a page is the 'root "
diff --git a/chrome/browser/flag_descriptions.h b/chrome/browser/flag_descriptions.h index 2dd3b13..fc91426 100644 --- a/chrome/browser/flag_descriptions.h +++ b/chrome/browser/flag_descriptions.h
@@ -153,9 +153,6 @@ extern const char kAutofillEnableStickyPaymentsBubbleName[]; extern const char kAutofillEnableStickyPaymentsBubbleDescription[]; -extern const char kAutofillEnableSurfacingServerCardNicknameName[]; -extern const char kAutofillEnableSurfacingServerCardNicknameDescription[]; - extern const char kAutofillEnableToolbarStatusChipName[]; extern const char kAutofillEnableToolbarStatusChipDescription[]; @@ -715,6 +712,9 @@ extern const char kGpuRasterizationName[]; extern const char kGpuRasterizationDescription[]; +extern const char kGuestOsExternalProtocolName[]; +extern const char kGuestOsExternalProtocolDescription[]; + extern const char kH264DecoderBufferIsCompleteFrameName[]; extern const char kH264DecoderBufferIsCompleteFrameDescription[];
diff --git a/chrome/browser/flags/android/chrome_feature_list.cc b/chrome/browser/flags/android/chrome_feature_list.cc index b942e70..840e455 100644 --- a/chrome/browser/flags/android/chrome_feature_list.cc +++ b/chrome/browser/flags/android/chrome_feature_list.cc
@@ -73,7 +73,6 @@ &autofill::features::kAutofillEnableCardNicknameManagement, &autofill::features::kAutofillEnableCompanyName, &autofill::features::kAutofillEnableGoogleIssuedCard, - &autofill::features::kAutofillEnableSurfacingServerCardNickname, &autofill_assistant::features::kAutofillAssistant, &autofill_assistant::features::kAutofillAssistantChromeEntry, &autofill_assistant::features::kAutofillAssistantDirectActions,
diff --git a/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/CachedFeatureFlags.java b/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/CachedFeatureFlags.java index 1ef4cdd..07e77d6 100644 --- a/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/CachedFeatureFlags.java +++ b/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/CachedFeatureFlags.java
@@ -78,6 +78,7 @@ put(ChromeFeatureList.INTEREST_FEED_V2, false); put(ChromeFeatureList.TABBED_APP_OVERFLOW_MENU_ICONS, false); put(ChromeFeatureList.TABBED_APP_OVERFLOW_MENU_REGROUP, false); + put(ChromeFeatureList.MESSAGES_FOR_ANDROID_INFRASTRUCTURE, false); } };
diff --git a/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java b/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java index 2e45424..04a4a656 100644 --- a/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java +++ b/chrome/browser/flags/android/java/src/org/chromium/chrome/browser/flags/ChromeFeatureList.java
@@ -202,8 +202,6 @@ public static final String AUTOFILL_ENABLE_COMPANY_NAME = "AutofillEnableCompanyName"; public static final String AUTOFILL_ENABLE_GOOGLE_ISSUED_CARD = "AutofillEnableGoogleIssuedCard"; - public static final String AUTOFILL_ENABLE_SURFACING_SERVER_CARD_NICKNAME = - "AutofillEnableSurfacingServerCardNickname"; public static final String ADJUST_WEBAPK_INSTALLATION_SPACE = "AdjustWebApkInstallationSpace"; public static final String ANDROID_DEFAULT_BROWSER_PROMO = "AndroidDefaultBrowserPromo"; public static final String ANDROID_MANAGED_BY_MENU_ITEM = "AndroidManagedByMenuItem";
diff --git a/chrome/browser/media/kaleidoscope/kaleidoscope_service.cc b/chrome/browser/media/kaleidoscope/kaleidoscope_service.cc index 37c75cb1..0137554 100644 --- a/chrome/browser/media/kaleidoscope/kaleidoscope_service.cc +++ b/chrome/browser/media/kaleidoscope/kaleidoscope_service.cc
@@ -9,6 +9,7 @@ #include "base/feature_list.h" #include "base/metrics/histogram_functions.h" #include "base/strings/strcat.h" +#include "base/time/default_clock.h" #include "chrome/browser/media/history/media_history_store.h" #include "chrome/browser/media/kaleidoscope/constants.h" #include "chrome/browser/media/kaleidoscope/kaleidoscope_prefs.h" @@ -39,8 +40,9 @@ const std::string& gaia_id, const std::string& request_b64, scoped_refptr<::network::SharedURLLoaderFactory> url_loader_factory, - base::OnceCallback<void(std::unique_ptr<std::string>)> callback) - : gaia_id_(gaia_id) { + base::Clock* clock, + base::OnceCallback<void(const std::string&)> callback) + : gaia_id_(gaia_id), clock_(clock), start_time_(clock->Now()) { const auto base_url = GetGoogleAPIBaseURL(*base::CommandLine::ForCurrentProcess()); @@ -100,7 +102,9 @@ pending_request_->SetAllowHttpErrorResults(true); pending_request_->AttachStringForUpload(request_body, kRequestContentType); pending_request_->DownloadToStringOfUnboundedSizeUntilCrashAndDie( - url_loader_factory.get(), std::move(callback)); + url_loader_factory.get(), + base::BindOnce(&GetCollectionsRequest::OnDataLoaded, + base::Unretained(this), std::move(callback))); } ~GetCollectionsRequest() = default; @@ -122,6 +126,20 @@ } private: + void OnDataLoaded(base::OnceCallback<void(const std::string&)> callback, + std::unique_ptr<std::string> data) { + base::TimeDelta time_taken = clock_->Now() - start_time_; + base::UmaHistogramTimes( + KaleidoscopeService::kNTPModuleServerFetchTimeHistogramName, + time_taken); + + if (data) { + std::move(callback).Run(*data); + } else { + std::move(callback).Run(std::string()); + } + } + int response_code() const { if (url_loader().ResponseInfo() && url_loader().ResponseInfo()->headers) { return url_loader().ResponseInfo()->headers->response_code(); @@ -131,6 +149,8 @@ } std::string const gaia_id_; + base::Clock* const clock_; + base::Time const start_time_; std::unique_ptr<::network::SimpleURLLoader> pending_request_; }; @@ -140,8 +160,13 @@ const char KaleidoscopeService::kNTPModuleCacheHitHistogramName[] = "Media.Kaleidoscope.NewTabPage.CacheHitWhenForced"; -KaleidoscopeService::KaleidoscopeService(Profile* profile) : profile_(profile) { +const char KaleidoscopeService::kNTPModuleServerFetchTimeHistogramName[] = + "Media.Kaleidoscope.NewTabPage.ServerFetchTime"; + +KaleidoscopeService::KaleidoscopeService(Profile* profile) + : profile_(profile), clock_(base::DefaultClock::GetInstance()) { DCHECK(!profile->IsOffTheRecord()); + DCHECK(clock_); } // static @@ -241,15 +266,14 @@ if (!request_) { request_ = std::make_unique<GetCollectionsRequest>( std::move(credentials), gaia_id, request, - GetURLLoaderFactoryForFetcher(), + GetURLLoaderFactoryForFetcher(), clock_, base::BindOnce(&KaleidoscopeService::OnURLFetchComplete, base::Unretained(this), gaia_id)); } } -void KaleidoscopeService::OnURLFetchComplete( - const std::string& gaia_id, - std::unique_ptr<std::string> data) { +void KaleidoscopeService::OnURLFetchComplete(const std::string& gaia_id, + const std::string& data) { auto response = media::mojom::GetCollectionsResponse::New(); if (request_->not_available()) { response->result = media::mojom::GetCollectionsResult::kNotAvailable; @@ -262,7 +286,7 @@ response->result = media::mojom::GetCollectionsResult::kFirstRun; } else { response->result = media::mojom::GetCollectionsResult::kSuccess; - response->response = *data; + response->response = data; } for (auto& callback : pending_callbacks_) {
diff --git a/chrome/browser/media/kaleidoscope/kaleidoscope_service.h b/chrome/browser/media/kaleidoscope/kaleidoscope_service.h index 0f492289..0db6ac9 100644 --- a/chrome/browser/media/kaleidoscope/kaleidoscope_service.h +++ b/chrome/browser/media/kaleidoscope/kaleidoscope_service.h
@@ -14,6 +14,10 @@ class Profile; +namespace base { +class Clock; +} // namespace base + namespace kaleidoscope { namespace { @@ -23,6 +27,7 @@ class KaleidoscopeService : public KeyedService { public: static const char kNTPModuleCacheHitHistogramName[]; + static const char kNTPModuleServerFetchTimeHistogramName[]; // When we try and ger Kaleidoscope data we store whether we hit the cache in // |kNTPModuleCacheHitHistogramName|. Do not change the numbering since this @@ -63,8 +68,7 @@ GetCollectionsCallback callback, media::mojom::GetCollectionsResponsePtr cached); - void OnURLFetchComplete(const std::string& gaia_id, - std::unique_ptr<std::string> data); + void OnURLFetchComplete(const std::string& gaia_id, const std::string& data); scoped_refptr<::network::SharedURLLoaderFactory> GetURLLoaderFactoryForFetcher(); @@ -78,6 +82,8 @@ std::vector<GetCollectionsCallback> pending_callbacks_; + base::Clock* clock_; + base::WeakPtrFactory<KaleidoscopeService> weak_ptr_factory_{this}; };
diff --git a/chrome/browser/media/kaleidoscope/kaleidoscope_service_unittest.cc b/chrome/browser/media/kaleidoscope/kaleidoscope_service_unittest.cc index 88176e7..17928bc6 100644 --- a/chrome/browser/media/kaleidoscope/kaleidoscope_service_unittest.cc +++ b/chrome/browser/media/kaleidoscope/kaleidoscope_service_unittest.cc
@@ -10,6 +10,7 @@ #include "base/test/bind_test_util.h" #include "base/test/metrics/histogram_tester.h" #include "base/test/scoped_feature_list.h" +#include "base/test/simple_test_clock.h" #include "base/test/task_environment.h" #include "chrome/browser/media/kaleidoscope/constants.h" #include "chrome/browser/media/kaleidoscope/kaleidoscope_prefs.h" @@ -50,6 +51,7 @@ GetService()->test_url_loader_factory_for_fetcher_ = base::MakeRefCounted<::network::WeakWrapperSharedURLLoaderFactory>( &url_loader_factory_); + GetService()->clock_ = &clock_; feature_list_.InitWithFeatures({}, {media::kKaleidoscopeModuleCacheOnly}); } @@ -99,6 +101,8 @@ kKaleidoscopeFirstRunLatestVersion); } + base::SimpleTestClock& clock() { return clock_; } + private: std::string GetCurrentlyQueriedHeaderValue(const base::StringPiece& key) { std::string out; @@ -112,12 +116,16 @@ ::network::TestURLLoaderFactory url_loader_factory_; + base::SimpleTestClock clock_; + base::test::ScopedFeatureList feature_list_; }; TEST_F(KaleidoscopeServiceTest, Success) { MarkFirstRunAsComplete(); + base::HistogramTester histogram_tester; + GetService()->GetCollections( CreateCredentials(), "123", "abcd", base::BindLambdaForTesting( @@ -128,8 +136,14 @@ })); WaitForRequest(); + clock().Advance(base::TimeDelta::FromSeconds(5)); ASSERT_TRUE(RespondToFetch(kTestData)); + // Wait for the callback to be called. + histogram_tester.ExpectUniqueTimeSample( + KaleidoscopeService::kNTPModuleServerFetchTimeHistogramName, + base::TimeDelta::FromSeconds(5), 1); + // If we call again then we should hit the cache. GetService()->GetCollections( CreateCredentials(), "123", "abcd",
diff --git a/chrome/browser/metrics/chrome_metrics_services_manager_client.cc b/chrome/browser/metrics/chrome_metrics_services_manager_client.cc index 36396922..5bc58e3 100644 --- a/chrome/browser/metrics/chrome_metrics_services_manager_client.cc +++ b/chrome/browser/metrics/chrome_metrics_services_manager_client.cc
@@ -21,7 +21,6 @@ #include "chrome/browser/metrics/variations/chrome_variations_service_client.h" #include "chrome/browser/metrics/variations/ui_string_overrider_factory.h" #include "chrome/browser/net/system_network_context_manager.h" -#include "chrome/browser/ui/browser_list.h" #include "chrome/browser/ui/browser_otr_state.h" #include "chrome/common/chrome_switches.h" #include "chrome/installer/util/google_update_settings.h" @@ -39,7 +38,9 @@ #if defined(OS_ANDROID) #include "chrome/browser/ui/android/tab_model/tab_model.h" #include "chrome/browser/ui/android/tab_model/tab_model_list.h" -#endif // OS_ANDROID +#else +#include "chrome/browser/ui/browser_list.h" +#endif // defined(OS_ANDROID) #if defined(OS_WIN) #include "base/win/registry.h"
diff --git a/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl.cc b/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl.cc index eeafab4..93ff42d 100644 --- a/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl.cc +++ b/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl.cc
@@ -621,6 +621,7 @@ if (!dict) { return false; } + public_certificate_expirations_.reserve(dict->DictSize()); for (const std::pair<const std::string&, const base::Value&>& pair : dict->DictItems()) { @@ -631,6 +632,9 @@ public_certificate_expirations_.emplace_back(*id, *expiration); } + std::sort(public_certificate_expirations_.begin(), + public_certificate_expirations_.end(), SortBySecond); + return true; }
diff --git a/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl_unittest.cc b/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl_unittest.cc index 83e0d8f..74c71146 100644 --- a/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl_unittest.cc +++ b/chrome/browser/nearby_sharing/certificates/nearby_share_certificate_storage_impl_unittest.cc
@@ -24,7 +24,9 @@ namespace { -const char kSecretId1[] = "secretid1"; +// NOTE: Make sure secret ID alphabetical ordering does not match the 1,2,3,.. +// ordering to test sorting expiration times. +const char kSecretId1[] = "b_secretid1"; const char kSecretKey1[] = "secretkey1"; const char kPublicKey1[] = "publickey1"; const int64_t kStartSeconds1 = 0; @@ -35,7 +37,7 @@ const char kMetadataEncryptionKey1[] = "metadataencryptionkey1"; const char kEncryptedMetadataBytes1[] = "encryptedmetadatabytes1"; const char kMetadataEncryptionKeyTag1[] = "metadataencryptionkeytag1"; -const char kSecretId2[] = "secretid2"; +const char kSecretId2[] = "c_secretid2"; const char kSecretKey2[] = "secretkey2"; const char kPublicKey2[] = "publickey2"; const int64_t kStartSeconds2 = 0; @@ -46,7 +48,7 @@ const char kMetadataEncryptionKey2[] = "metadataencryptionkey2"; const char kEncryptedMetadataBytes2[] = "encryptedmetadatabytes2"; const char kMetadataEncryptionKeyTag2[] = "metadataencryptionkeytag2"; -const char kSecretId3[] = "secretid3"; +const char kSecretId3[] = "a_secretid3"; const char kSecretKey3[] = "secretkey3"; const char kPublicKey3[] = "publickey3"; const int64_t kStartSeconds3 = 0; @@ -57,7 +59,7 @@ const char kMetadataEncryptionKey3[] = "metadataencryptionkey3"; const char kEncryptedMetadataBytes3[] = "encryptedmetadatabytes3"; const char kMetadataEncryptionKeyTag3[] = "metadataencryptionkeytag3"; -const char kSecretId4[] = "secretid4"; +const char kSecretId4[] = "d_secretid4"; const char kSecretKey4[] = "secretkey4"; const char kPublicKey4[] = "publickey4"; const int64_t kStartSeconds4 = 0;
diff --git a/chrome/browser/net/dns_over_https_browsertest.cc b/chrome/browser/net/dns_over_https_browsertest.cc index 0d4ce20..f7123475 100644 --- a/chrome/browser/net/dns_over_https_browsertest.cc +++ b/chrome/browser/net/dns_over_https_browsertest.cc
@@ -14,6 +14,7 @@ #include "content/public/test/browser_test.h" #include "content/public/test/test_navigation_observer.h" #include "net/dns/public/doh_provider_entry.h" +#include "net/dns/public/secure_dns_mode.h" #include "testing/gtest/include/gtest/gtest.h" #include "url/gurl.h" @@ -71,7 +72,7 @@ ->GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); // Ensure that DoH is enabled in secure mode - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kSecure, secure_dns_config.mode()); content::TestNavigationObserver nav_observer( browser()->tab_strip_model()->GetActiveWebContents(), 1);
diff --git a/chrome/browser/net/dns_probe_service_factory.cc b/chrome/browser/net/dns_probe_service_factory.cc index aca02f2..e369edf2 100644 --- a/chrome/browser/net/dns_probe_service_factory.cc +++ b/chrome/browser/net/dns_probe_service_factory.cc
@@ -32,6 +32,7 @@ #include "net/base/ip_endpoint.h" #include "net/dns/public/dns_over_https_server_config.h" #include "net/dns/public/dns_protocol.h" +#include "net/dns/public/secure_dns_mode.h" #include "services/network/public/mojom/network_service.mojom.h" namespace chrome_browser_net { @@ -81,7 +82,7 @@ net::IPEndPoint(net::IPAddress(kGooglePublicDns2), net::dns_protocol::kDefaultPort)}; overrides.attempts = 1; - overrides.secure_dns_mode = net::DnsConfig::SecureDnsMode::OFF; + overrides.secure_dns_mode = net::SecureDnsMode::kOff; return overrides; } @@ -147,8 +148,7 @@ NetworkContextGetter network_context_getter_; DnsConfigChangeManagerGetter dns_config_change_manager_getter_; mojo::Receiver<network::mojom::DnsConfigChangeManagerClient> receiver_{this}; - net::DnsConfig::SecureDnsMode current_config_secure_dns_mode_ = - net::DnsConfig::SecureDnsMode::OFF; + net::SecureDnsMode current_config_secure_dns_mode_ = net::SecureDnsMode::kOff; // DnsProbeRunners for the current DNS configuration and a Google DNS // configuration. Both runners will have the insecure async resolver enabled @@ -234,20 +234,17 @@ current_config_overrides.search = std::vector<std::string>(); current_config_overrides.attempts = 1; - if (current_config_secure_dns_mode_ == - net::DnsConfig::SecureDnsMode::SECURE) { + if (current_config_secure_dns_mode_ == net::SecureDnsMode::kSecure) { if (!secure_dns_config.servers().empty()) { current_config_overrides.dns_over_https_servers.emplace( secure_dns_config.servers()); } - current_config_overrides.secure_dns_mode = - net::DnsConfig::SecureDnsMode::SECURE; + current_config_overrides.secure_dns_mode = net::SecureDnsMode::kSecure; } else { // A DNS error that occurred in automatic mode must have had an insecure // DNS failure. For efficiency, probe queries in this case can just be // issued in OFF mode. - current_config_overrides.secure_dns_mode = - net::DnsConfig::SecureDnsMode::OFF; + current_config_overrides.secure_dns_mode = net::SecureDnsMode::kOff; } current_config_runner_ = std::make_unique<DnsProbeRunner>( @@ -311,8 +308,7 @@ // current DNS config is in secure mode, return an error indicating that this // is a secure DNS config issue. if (google_config_result == DnsProbeRunner::CORRECT) { - return (current_config_secure_dns_mode_ == - net::DnsConfig::SecureDnsMode::SECURE) + return (current_config_secure_dns_mode_ == net::SecureDnsMode::kSecure) ? error_page::DNS_PROBE_FINISHED_BAD_SECURE_CONFIG : error_page::DNS_PROBE_FINISHED_BAD_CONFIG; }
diff --git a/chrome/browser/net/dns_probe_service_factory_unittest.cc b/chrome/browser/net/dns_probe_service_factory_unittest.cc index c8574bfb..74f8a4d 100644 --- a/chrome/browser/net/dns_probe_service_factory_unittest.cc +++ b/chrome/browser/net/dns_probe_service_factory_unittest.cc
@@ -27,6 +27,7 @@ #include "components/prefs/pref_service.h" #include "content/public/test/browser_task_environment.h" #include "mojo/public/cpp/bindings/remote.h" +#include "net/dns/public/secure_dns_mode.h" #include "testing/gtest/include/gtest/gtest.h" using base::RunLoop; @@ -317,8 +318,7 @@ EXPECT_EQ(1, overrides.attempts.value()); EXPECT_TRUE(overrides.secure_dns_mode.has_value()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, - overrides.secure_dns_mode.value()); + EXPECT_EQ(net::SecureDnsMode::kOff, overrides.secure_dns_mode.value()); EXPECT_FALSE(overrides.dns_over_https_servers.has_value()); } @@ -341,8 +341,7 @@ EXPECT_EQ(1, overrides.attempts.value()); EXPECT_TRUE(overrides.secure_dns_mode.has_value()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, - overrides.secure_dns_mode.value()); + EXPECT_EQ(net::SecureDnsMode::kSecure, overrides.secure_dns_mode.value()); EXPECT_TRUE(overrides.dns_over_https_servers.has_value()); ASSERT_EQ(2u, overrides.dns_over_https_servers->size()); EXPECT_EQ(kDohTemplateGet,
diff --git a/chrome/browser/net/secure_dns_config.cc b/chrome/browser/net/secure_dns_config.cc index 7f1390dd..350e856 100644 --- a/chrome/browser/net/secure_dns_config.cc +++ b/chrome/browser/net/secure_dns_config.cc
@@ -10,7 +10,7 @@ constexpr char SecureDnsConfig::kModeSecure[]; SecureDnsConfig::SecureDnsConfig( - net::DnsConfig::SecureDnsMode mode, + net::SecureDnsMode mode, std::vector<net::DnsOverHttpsServerConfig> servers, ManagementMode management_mode) : mode_(mode), @@ -21,26 +21,26 @@ SecureDnsConfig::~SecureDnsConfig() = default; // static -base::Optional<net::DnsConfig::SecureDnsMode> SecureDnsConfig::ParseMode( +base::Optional<net::SecureDnsMode> SecureDnsConfig::ParseMode( base::StringPiece name) { if (name == kModeSecure) { - return net::DnsConfig::SecureDnsMode::SECURE; + return net::SecureDnsMode::kSecure; } else if (name == kModeAutomatic) { - return net::DnsConfig::SecureDnsMode::AUTOMATIC; + return net::SecureDnsMode::kAutomatic; } else if (name == kModeOff) { - return net::DnsConfig::SecureDnsMode::OFF; + return net::SecureDnsMode::kOff; } return base::nullopt; } // static -const char* SecureDnsConfig::ModeToString(net::DnsConfig::SecureDnsMode mode) { +const char* SecureDnsConfig::ModeToString(net::SecureDnsMode mode) { switch (mode) { - case net::DnsConfig::SecureDnsMode::SECURE: + case net::SecureDnsMode::kSecure: return kModeSecure; - case net::DnsConfig::SecureDnsMode::AUTOMATIC: + case net::SecureDnsMode::kAutomatic: return kModeAutomatic; - case net::DnsConfig::SecureDnsMode::OFF: + case net::SecureDnsMode::kOff: return kModeOff; } }
diff --git a/chrome/browser/net/secure_dns_config.h b/chrome/browser/net/secure_dns_config.h index 3a65827a..4e884cf 100644 --- a/chrome/browser/net/secure_dns_config.h +++ b/chrome/browser/net/secure_dns_config.h
@@ -9,11 +9,8 @@ #include "base/optional.h" #include "base/strings/string_piece.h" -#include "net/dns/dns_config.h" - -namespace net { -struct DnsOverHttpsServerConfig; -} // namespace net +#include "net/dns/public/dns_over_https_server_config.h" +#include "net/dns/public/secure_dns_mode.h" // Representation of a complete Secure DNS configuration. class SecureDnsConfig { @@ -31,13 +28,13 @@ kDisabledParentalControls, }; - // String representations for net::DnsConfig::SecureDnsMode. Used for both - // configuration storage and UI state. + // String representations for net::SecureDnsMode. Used for both configuration + // storage and UI state. static constexpr char kModeOff[] = "off"; static constexpr char kModeAutomatic[] = "automatic"; static constexpr char kModeSecure[] = "secure"; - SecureDnsConfig(net::DnsConfig::SecureDnsMode mode, + SecureDnsConfig(net::SecureDnsMode mode, std::vector<net::DnsOverHttpsServerConfig> servers, ManagementMode management_mode); // This class is move-only to avoid any accidental copying. @@ -47,19 +44,18 @@ // Identifies the SecureDnsMode corresponding to one of the above names, or // returns nullopt if the name is unrecognized. - static base::Optional<net::DnsConfig::SecureDnsMode> ParseMode( - base::StringPiece name); + static base::Optional<net::SecureDnsMode> ParseMode(base::StringPiece name); // Converts a secure DNS mode to one of the above names. - static const char* ModeToString(net::DnsConfig::SecureDnsMode mode); + static const char* ModeToString(net::SecureDnsMode mode); - net::DnsConfig::SecureDnsMode mode() { return mode_; } + net::SecureDnsMode mode() { return mode_; } const std::vector<net::DnsOverHttpsServerConfig>& servers() { return servers_; } ManagementMode management_mode() { return management_mode_; } private: - net::DnsConfig::SecureDnsMode mode_; + net::SecureDnsMode mode_; std::vector<net::DnsOverHttpsServerConfig> servers_; ManagementMode management_mode_; };
diff --git a/chrome/browser/net/secure_dns_config_unittest.cc b/chrome/browser/net/secure_dns_config_unittest.cc index d950956d..1b5feaa 100644 --- a/chrome/browser/net/secure_dns_config_unittest.cc +++ b/chrome/browser/net/secure_dns_config_unittest.cc
@@ -8,11 +8,11 @@ #include "testing/gtest/include/gtest/gtest.h" TEST(SecureDnsConfig, ParseMode) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, SecureDnsConfig::ParseMode("off").value()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, + EXPECT_EQ(net::SecureDnsMode::kAutomatic, SecureDnsConfig::ParseMode("automatic").value()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, + EXPECT_EQ(net::SecureDnsMode::kSecure, SecureDnsConfig::ParseMode("secure").value()); EXPECT_FALSE(SecureDnsConfig::ParseMode("foo").has_value()); @@ -21,21 +21,20 @@ TEST(SecureDnsConfig, ModeToString) { EXPECT_EQ(std::string("off"), - SecureDnsConfig::ModeToString(net::DnsConfig::SecureDnsMode::OFF)); - EXPECT_EQ( - std::string("automatic"), - SecureDnsConfig::ModeToString(net::DnsConfig::SecureDnsMode::AUTOMATIC)); - EXPECT_EQ(std::string("secure"), SecureDnsConfig::ModeToString( - net::DnsConfig::SecureDnsMode::SECURE)); + SecureDnsConfig::ModeToString(net::SecureDnsMode::kOff)); + EXPECT_EQ(std::string("automatic"), + SecureDnsConfig::ModeToString(net::SecureDnsMode::kAutomatic)); + EXPECT_EQ(std::string("secure"), + SecureDnsConfig::ModeToString(net::SecureDnsMode::kSecure)); } TEST(SecureDnsConfig, Constructor) { std::vector<net::DnsOverHttpsServerConfig> servers{ {{"https://template1", false}, {"https://template2", true}}}; SecureDnsConfig config( - net::DnsConfig::SecureDnsMode::SECURE, servers, + net::SecureDnsMode::kSecure, servers, SecureDnsConfig::ManagementMode::kDisabledParentalControls); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, config.mode()); + EXPECT_EQ(net::SecureDnsMode::kSecure, config.mode()); EXPECT_THAT(config.servers(), testing::ElementsAreArray(servers)); EXPECT_EQ(SecureDnsConfig::ManagementMode::kDisabledParentalControls, config.management_mode());
diff --git a/chrome/browser/net/stub_resolver_config_reader.cc b/chrome/browser/net/stub_resolver_config_reader.cc index fd6f5bf..2bddf0be 100644 --- a/chrome/browser/net/stub_resolver_config_reader.cc +++ b/chrome/browser/net/stub_resolver_config_reader.cc
@@ -30,6 +30,7 @@ #include "components/prefs/pref_registry_simple.h" #include "components/prefs/pref_service.h" #include "content/public/browser/network_service_instance.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/dns/public/util.h" #include "services/network/public/mojom/host_resolver.mojom.h" #include "services/network/public/mojom/network_service.mojom.h" @@ -125,14 +126,13 @@ if (set_up_pref_defaults) { local_state_->SetDefaultPrefValue(prefs::kBuiltInDnsClientEnabled, base::Value(ShouldEnableAsyncDns())); - net::DnsConfig::SecureDnsMode default_secure_dns_mode = - net::DnsConfig::SecureDnsMode::OFF; + net::SecureDnsMode default_secure_dns_mode = net::SecureDnsMode::kOff; std::string default_doh_templates; if (base::FeatureList::IsEnabled(features::kDnsOverHttps)) { if (features::kDnsOverHttpsFallbackParam.Get()) { - default_secure_dns_mode = net::DnsConfig::SecureDnsMode::AUTOMATIC; + default_secure_dns_mode = net::SecureDnsMode::kAutomatic; } else { - default_secure_dns_mode = net::DnsConfig::SecureDnsMode::SECURE; + default_secure_dns_mode = net::SecureDnsMode::kSecure; } default_doh_templates = features::kDnsOverHttpsTemplatesParam.Get(); } @@ -265,23 +265,23 @@ bool update_network_service) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - net::DnsConfig::SecureDnsMode secure_dns_mode; + net::SecureDnsMode secure_dns_mode; SecureDnsModeDetailsForHistogram mode_details; SecureDnsConfig::ManagementMode forced_management_mode = SecureDnsConfig::ManagementMode::kNoOverride; bool is_managed = local_state_->FindPreference(prefs::kDnsOverHttpsMode)->IsManaged(); if (!is_managed && ShouldDisableDohForManaged()) { - secure_dns_mode = net::DnsConfig::SecureDnsMode::OFF; + secure_dns_mode = net::SecureDnsMode::kOff; forced_management_mode = SecureDnsConfig::ManagementMode::kDisabledManaged; } else { secure_dns_mode = SecureDnsConfig::ParseMode( local_state_->GetString(prefs::kDnsOverHttpsMode)) - .value_or(net::DnsConfig::SecureDnsMode::OFF); + .value_or(net::SecureDnsMode::kOff); } bool check_parental_controls = false; - if (secure_dns_mode == net::DnsConfig::SecureDnsMode::SECURE) { + if (secure_dns_mode == net::SecureDnsMode::kSecure) { mode_details = is_managed ? SecureDnsModeDetailsForHistogram::kSecureByEnterprisePolicy : SecureDnsModeDetailsForHistogram::kSecureByUser; @@ -290,7 +290,7 @@ // enabled through policy, which takes precedence over parental controls) // because the mode allows sending DoH requests immediately. check_parental_controls = !is_managed; - } else if (secure_dns_mode == net::DnsConfig::SecureDnsMode::AUTOMATIC) { + } else if (secure_dns_mode == net::SecureDnsMode::kAutomatic) { mode_details = is_managed ? SecureDnsModeDetailsForHistogram::kAutomaticByEnterprisePolicy @@ -333,7 +333,7 @@ if (ShouldDisableDohForParentalControls()) { forced_management_mode = SecureDnsConfig::ManagementMode::kDisabledParentalControls; - secure_dns_mode = net::DnsConfig::SecureDnsMode::OFF; + secure_dns_mode = net::SecureDnsMode::kOff; mode_details = SecureDnsModeDetailsForHistogram::kOffByDetectedParentalControls; @@ -356,8 +356,7 @@ std::vector<net::DnsOverHttpsServerConfig> dns_over_https_servers; base::Optional<std::vector<network::mojom::DnsOverHttpsServerPtr>> servers_mojo; - if (!doh_templates.empty() && - secure_dns_mode != net::DnsConfig::SecureDnsMode::OFF) { + if (!doh_templates.empty() && secure_dns_mode != net::SecureDnsMode::kOff) { for (base::StringPiece server_template : chrome_browser_net::secure_dns::SplitGroup(doh_templates)) { if (!net::dns_util::IsValidDohTemplate(server_template, &server_method)) {
diff --git a/chrome/browser/net/stub_resolver_config_reader_unittest.cc b/chrome/browser/net/stub_resolver_config_reader_unittest.cc index 3952d2e..5c5aa75 100644 --- a/chrome/browser/net/stub_resolver_config_reader_unittest.cc +++ b/chrome/browser/net/stub_resolver_config_reader_unittest.cc
@@ -15,8 +15,8 @@ #include "components/prefs/pref_service.h" #include "components/prefs/testing_pref_service.h" #include "content/public/test/browser_task_environment.h" -#include "net/dns/dns_config.h" #include "net/dns/public/dns_over_https_server_config.h" +#include "net/dns/public/secure_dns_mode.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" @@ -75,7 +75,7 @@ true /* force_check_parental_controls_for_automatic_mode */); EXPECT_FALSE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); // Parental controls should not be checked when DoH otherwise disabled. @@ -94,7 +94,7 @@ true /* force_check_parental_controls_for_automatic_mode */); EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); EXPECT_THAT(secure_dns_config.servers(), testing::ElementsAre( net::DnsOverHttpsServerConfig("https://doh1.test", @@ -117,7 +117,7 @@ false /* force_check_parental_controls_for_automatic_mode */); EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kSecure, secure_dns_config.mode()); EXPECT_THAT(secure_dns_config.servers(), testing::ElementsAre( net::DnsOverHttpsServerConfig("https://doh1.test", @@ -142,7 +142,7 @@ true /* force_check_parental_controls_for_automatic_mode */); EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); // Parental controls should not be checked when DoH otherwise disabled. @@ -161,7 +161,7 @@ false /* force_check_parental_controls_for_automatic_mode */); EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); // Parental controls should not be checked when DoH otherwise disabled. @@ -182,7 +182,7 @@ true /* force_check_parental_controls_for_automatic_mode */); EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); EXPECT_TRUE(config_reader_->parental_controls_checked()); @@ -202,7 +202,7 @@ false /* force_check_parental_controls_for_automatic_mode */); EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); EXPECT_TRUE(config_reader_->parental_controls_checked()); @@ -221,7 +221,7 @@ // Parental controls check initially skipped. EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); EXPECT_THAT(secure_dns_config.servers(), testing::ElementsAre( net::DnsOverHttpsServerConfig("https://doh1.test", @@ -240,7 +240,7 @@ false /* force_check_parental_controls_for_automatic_mode */); EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); } @@ -262,7 +262,7 @@ // Parental controls check initially skipped, and managed prefs take // precedence over disables. EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); EXPECT_THAT(secure_dns_config.servers(), testing::ElementsAre( net::DnsOverHttpsServerConfig("https://doh1.test", @@ -283,7 +283,7 @@ // Expect DoH still enabled after parental controls check because managed // prefs have precedence. EXPECT_TRUE(config_reader_->GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); EXPECT_THAT(secure_dns_config.servers(), testing::ElementsAre( net::DnsOverHttpsServerConfig("https://doh1.test",
diff --git a/chrome/browser/net/system_network_context_manager_browsertest.cc b/chrome/browser/net/system_network_context_manager_browsertest.cc index 2cc046d..859e4bd 100644 --- a/chrome/browser/net/system_network_context_manager_browsertest.cc +++ b/chrome/browser/net/system_network_context_manager_browsertest.cc
@@ -24,6 +24,7 @@ #include "content/public/browser/network_service_instance.h" #include "content/public/common/user_agent.h" #include "content/public/test/browser_test.h" +#include "net/dns/public/secure_dns_mode.h" #include "services/cert_verifier/test_cert_verifier_service_factory.h" #include "services/network/public/cpp/features.h" #include "services/network/public/cpp/network_service_buildflags.h" @@ -72,10 +73,9 @@ false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); if (base::FeatureList::IsEnabled(features::kDnsOverHttps)) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, - secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); } else { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); } EXPECT_TRUE(secure_dns_config.servers().empty()); @@ -94,14 +94,14 @@ secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kSecure, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); local_state->SetString(prefs::kDnsOverHttpsTemplates, good_post_template); secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kSecure, secure_dns_config.mode()); ASSERT_EQ(1u, secure_dns_config.servers().size()); EXPECT_EQ(good_post_template, secure_dns_config.servers().at(0).server_template); @@ -113,14 +113,14 @@ secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); local_state->SetString(prefs::kDnsOverHttpsTemplates, good_then_bad_template); secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); ASSERT_EQ(1u, secure_dns_config.servers().size()); EXPECT_EQ(good_get_template, secure_dns_config.servers().at(0).server_template); @@ -130,7 +130,7 @@ secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); ASSERT_EQ(1u, secure_dns_config.servers().size()); EXPECT_EQ(good_get_template, secure_dns_config.servers().at(0).server_template); @@ -141,7 +141,7 @@ secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kAutomatic, secure_dns_config.mode()); ASSERT_EQ(2u, secure_dns_config.servers().size()); EXPECT_EQ(good_get_template, secure_dns_config.servers().at(0).server_template); @@ -155,14 +155,14 @@ secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); local_state->SetString(prefs::kDnsOverHttpsMode, "no_match"); secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); // Test case with policy BuiltInDnsClientEnabled enabled. The DoH fields @@ -172,7 +172,7 @@ secure_dns_config = GetSecureDnsConfiguration( false /* force_check_parental_controls_for_automatic_mode */); EXPECT_EQ(!async_dns_feature_enabled, GetInsecureStubResolverEnabled()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, secure_dns_config.mode()); + EXPECT_EQ(net::SecureDnsMode::kOff, secure_dns_config.mode()); EXPECT_TRUE(secure_dns_config.servers().empty()); }
diff --git a/chrome/browser/payments/android/payment_app_service_bridge.cc b/chrome/browser/payments/android/payment_app_service_bridge.cc index 938ac7f..bf1c795 100644 --- a/chrome/browser/payments/android/payment_app_service_bridge.cc +++ b/chrome/browser/payments/android/payment_app_service_bridge.cc
@@ -206,7 +206,7 @@ frame_origin_(url_formatter::FormatUrlForSecurityDisplay( render_frame_host->GetLastCommittedURL())), frame_security_origin_(render_frame_host->GetLastCommittedOrigin()), - spec_(spec), + spec_(spec->GetWeakPtr()), twa_package_name_(twa_package_name), payment_manifest_web_data_service_(web_data_service), may_crawl_for_installable_payment_apps_( @@ -247,6 +247,7 @@ const std::vector<PaymentMethodDataPtr>& PaymentAppServiceBridge::GetMethodData() const { + DCHECK(spec_); return spec_->method_data(); } @@ -301,7 +302,7 @@ } PaymentRequestSpec* PaymentAppServiceBridge::GetSpec() const { - return spec_; + return spec_.get(); } std::string PaymentAppServiceBridge::GetTwaPackageName() const {
diff --git a/chrome/browser/payments/android/payment_app_service_bridge.h b/chrome/browser/payments/android/payment_app_service_bridge.h index d954ebd..e64fde2 100644 --- a/chrome/browser/payments/android/payment_app_service_bridge.h +++ b/chrome/browser/payments/android/payment_app_service_bridge.h
@@ -38,7 +38,7 @@ // Creates a new PaymentAppServiceBridge. This object is self-deleting; its // memory is freed when OnDoneCreatingPaymentApps() is called - // |number_of_factories| times. + // `number_of_factories` times. The `spec` parameter should not be null. static PaymentAppServiceBridge* Create( size_t number_of_factories, content::RenderFrameHost* render_frame_host, @@ -87,7 +87,8 @@ void SetCanMakePaymentEvenWithoutApps() override; private: - // Prevents direct instantiation. Callers should use Create() instead. + // Prevents direct instantiation. Callers should use Create() instead. The + // `spec` parameter should not be null. PaymentAppServiceBridge( size_t number_of_factories, content::RenderFrameHost* render_frame_host, @@ -107,7 +108,7 @@ const GURL top_origin_; const GURL frame_origin_; const url::Origin frame_security_origin_; - PaymentRequestSpec* spec_; + base::WeakPtr<PaymentRequestSpec> spec_; const std::string twa_package_name_; scoped_refptr<PaymentManifestWebDataService> payment_manifest_web_data_service_;
diff --git a/chrome/browser/platform_util_chromeos.cc b/chrome/browser/platform_util_chromeos.cc index 65a5513..2379948 100644 --- a/chrome/browser/platform_util_chromeos.cc +++ b/chrome/browser/platform_util_chromeos.cc
@@ -9,11 +9,10 @@ #include "base/bind.h" #include "base/files/file_path.h" #include "chrome/browser/chromeos/file_manager/open_util.h" +#include "chrome/browser/chromeos/guest_os/guest_os_external_protocol_handler.h" #include "chrome/browser/platform_util_internal.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_finder.h" -#include "chrome/browser/ui/browser_navigator.h" -#include "chrome/browser/ui/browser_navigator_params.h" #include "chrome/browser/ui/browser_window.h" #include "chrome/browser/ui/simple_message_box.h" #include "chromeos/strings/grit/chromeos_strings.h" @@ -29,9 +28,6 @@ namespace { -const char kGmailComposeUrl[] = - "https://mail.google.com/mail/?extsrc=mailto&url="; - void ShowWarningOnOpenOperationResult(Profile* profile, const base::FilePath& path, OpenOperationResult result) { @@ -101,26 +97,7 @@ void OpenExternal(Profile* profile, const GURL& url) { DCHECK_CURRENTLY_ON(BrowserThread::UI); - - // This code should be obsolete since we have default handlers in ChromeOS - // which should handle this. However - there are two things which make it - // necessary to keep it in: - // a.) The user might have deleted the default handler in this session. - // In this case we would need to have this in place. - // b.) There are several code paths which are not clear if they would call - // this function directly and which would therefore break (e.g. - // "Browser::EmailPageLocation" (to name only one). - // As such we should keep this code here. - NavigateParams params(profile, url, ui::PAGE_TRANSITION_LINK); - params.disposition = WindowOpenDisposition::NEW_FOREGROUND_TAB; - - if (url.SchemeIs("mailto")) { - std::string string_url = kGmailComposeUrl; - string_url.append(url.spec()); - params.url = GURL(url); - } - - Navigate(¶ms); + guest_os::Launch(profile, url); } bool IsBrowserLockedFullscreen(const Browser* browser) {
diff --git a/chrome/browser/printing/print_preview_sticky_settings_unittest.cc b/chrome/browser/printing/print_preview_sticky_settings_unittest.cc index f303b4b..5c08d6b 100644 --- a/chrome/browser/printing/print_preview_sticky_settings_unittest.cc +++ b/chrome/browser/printing/print_preview_sticky_settings_unittest.cc
@@ -22,8 +22,8 @@ PrintPreviewStickySettings sticky_settings_; }; -TEST_F(PrintPreviewStickySettingsUnittest, GetPrinterRecentlyUsedRanks) { - std::string recently_used_ranks_str = R"({ +TEST_F(PrintPreviewStickySettingsUnittest, GetPrinterRecentlyUsed) { + const std::string kRecentlyUsedRanksStr = R"({ "version": 2, "recentDestinations": [ { @@ -36,19 +36,22 @@ } ] })"; - sticky_settings_.StoreAppState(recently_used_ranks_str); - base::flat_map<std::string, int> recently_used_ranks = - sticky_settings_.GetPrinterRecentlyUsedRanks(); - base::flat_map<std::string, int> expected_recently_used_ranks( + sticky_settings_.StoreAppState(kRecentlyUsedRanksStr); + const base::flat_map<std::string, int> kExpectedRecentlyUsedRanks( {{"id1", 0}, {"id2", 1}}); - EXPECT_EQ(expected_recently_used_ranks, recently_used_ranks); + EXPECT_EQ(kExpectedRecentlyUsedRanks, + sticky_settings_.GetPrinterRecentlyUsedRanks()); + const std::vector<std::string> kExpectedRecentlyUsedPrinters({"id1", "id2"}); + EXPECT_EQ(kExpectedRecentlyUsedPrinters, + sticky_settings_.GetRecentlyUsedPrinters()); } TEST_F(PrintPreviewStickySettingsUnittest, - GetPrinterRecentlyUsedRanks_NoRecentDestinations) { - std::string recently_used_ranks_str = R"({"version": 2})"; - sticky_settings_.StoreAppState(recently_used_ranks_str); + GetPrinterRecentlyUsed_NoRecentDestinations) { + const std::string kRecentlyUsedRanksStr = R"({"version": 2})"; + sticky_settings_.StoreAppState(kRecentlyUsedRanksStr); EXPECT_TRUE(sticky_settings_.GetPrinterRecentlyUsedRanks().empty()); + EXPECT_TRUE(sticky_settings_.GetRecentlyUsedPrinters().empty()); } } // namespace printing
diff --git a/chrome/browser/privacy/BUILD.gn b/chrome/browser/privacy/BUILD.gn index 1b21a762..b5d03ba 100644 --- a/chrome/browser/privacy/BUILD.gn +++ b/chrome/browser/privacy/BUILD.gn
@@ -27,7 +27,7 @@ "//chrome/browser/settings:java", "//components/browser_ui/settings/android:java", "//components/browser_ui/widget/android:java", - "//net/dns:secure_dns_mode_generated_enum", + "//net/dns/public:secure_dns_mode_generated_enum", "//third_party/android_deps:androidx_annotation_annotation_java", "//third_party/android_deps:androidx_fragment_fragment_java", "//third_party/android_deps:androidx_preference_preference_java", @@ -35,7 +35,7 @@ ] srcjar_deps = [ "//chrome/browser/net:secure_dns_management_mode_generated_enum", - "//net/dns:secure_dns_mode_generated_enum", + "//net/dns/public:secure_dns_mode_generated_enum", ] annotation_processor_deps = [ "//base/android/jni_generator:jni_processor" ] resources_package = "org.chromium.chrome.browser.privacy.secure_dns"
diff --git a/chrome/browser/privacy/secure_dns_bridge.cc b/chrome/browser/privacy/secure_dns_bridge.cc index 15ea13b..d42c607 100644 --- a/chrome/browser/privacy/secure_dns_bridge.cc +++ b/chrome/browser/privacy/secure_dns_bridge.cc
@@ -20,6 +20,7 @@ #include "components/country_codes/country_codes.h" #include "components/prefs/pref_service.h" #include "net/dns/public/doh_provider_entry.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/dns/public/util.h" #include "base/bind.h" @@ -79,9 +80,9 @@ static void JNI_SecureDnsBridge_SetMode(JNIEnv* env, jint mode) { PrefService* local_state = g_browser_process->local_state(); - local_state->SetString(prefs::kDnsOverHttpsMode, - SecureDnsConfig::ModeToString( - static_cast<net::DnsConfig::SecureDnsMode>(mode))); + local_state->SetString( + prefs::kDnsOverHttpsMode, + SecureDnsConfig::ModeToString(static_cast<net::SecureDnsMode>(mode))); } static jboolean JNI_SecureDnsBridge_IsModeManaged(JNIEnv* env) { @@ -167,7 +168,7 @@ net::DnsConfigOverrides overrides; overrides.search = std::vector<std::string>(); overrides.attempts = 1; - overrides.secure_dns_mode = net::DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = net::SecureDnsMode::kSecure; secure_dns::ApplyTemplate(&overrides, base::android::ConvertJavaStringToUTF8(jtemplate));
diff --git a/chrome/browser/profiles/off_the_record_profile_impl.h b/chrome/browser/profiles/off_the_record_profile_impl.h index 792935a..8185a68d 100644 --- a/chrome/browser/profiles/off_the_record_profile_impl.h +++ b/chrome/browser/profiles/off_the_record_profile_impl.h
@@ -13,7 +13,6 @@ #include "build/build_config.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/profiles/profile_io_data_handle.h" -#include "chrome/browser/ui/browser_list.h" #include "components/domain_reliability/clear_mode.h" #include "content/public/browser/content_browser_client.h"
diff --git a/chrome/browser/profiles/profile_manager.h b/chrome/browser/profiles/profile_manager.h index f27f425..8d079373 100644 --- a/chrome/browser/profiles/profile_manager.h +++ b/chrome/browser/profiles/profile_manager.h
@@ -23,11 +23,14 @@ #include "chrome/browser/profiles/profile.h" #include "chrome/browser/profiles/profile_metrics.h" #include "chrome/browser/profiles/profile_shortcut_manager.h" -#include "chrome/browser/ui/browser_list_observer.h" #include "chrome/common/buildflags.h" #include "content/public/browser/notification_observer.h" #include "content/public/browser/notification_registrar.h" +#if !defined(OS_ANDROID) +#include "chrome/browser/ui/browser_list_observer.h" +#endif // !defined(OS_ANDROID) + class ProfileAttributesStorage; class ProfileInfoCache; class ProfileManagerObserver;
diff --git a/chrome/browser/resource_coordinator/tab_helper.cc b/chrome/browser/resource_coordinator/tab_helper.cc index ccf38154..7e157ea8 100644 --- a/chrome/browser/resource_coordinator/tab_helper.cc +++ b/chrome/browser/resource_coordinator/tab_helper.cc
@@ -15,8 +15,6 @@ #include "chrome/browser/browser_process.h" #include "chrome/browser/resource_coordinator/lifecycle_unit_state.mojom-shared.h" #include "chrome/browser/resource_coordinator/resource_coordinator_parts.h" -#include "chrome/browser/resource_coordinator/tab_lifecycle_unit_external.h" -#include "chrome/browser/resource_coordinator/tab_lifecycle_unit_source.h" #include "chrome/browser/resource_coordinator/tab_load_tracker.h" #include "chrome/browser/resource_coordinator/tab_memory_metrics_reporter.h" #include "chrome/browser/resource_coordinator/utils.h"
diff --git a/chrome/browser/resources/chromeos/wallpaper_manager/images/icon192.png b/chrome/browser/resources/chromeos/wallpaper_manager/images/icon192.png index 95aecff..86cc40b1 100644 --- a/chrome/browser/resources/chromeos/wallpaper_manager/images/icon192.png +++ b/chrome/browser/resources/chromeos/wallpaper_manager/images/icon192.png Binary files differ
diff --git a/chrome/browser/resources/settings/chromeos/internet_page/BUILD.gn b/chrome/browser/resources/settings/chromeos/internet_page/BUILD.gn index 2bb6a511..d79361c5 100644 --- a/chrome/browser/resources/settings/chromeos/internet_page/BUILD.gn +++ b/chrome/browser/resources/settings/chromeos/internet_page/BUILD.gn
@@ -189,7 +189,7 @@ ":internet_page_browser_proxy.m", ":internet_shared_css.m", # ":internet_subpage.m", -# ":network_proxy_section.m", + ":network_proxy_section.m", # ":network_summary.m", # ":network_summary_item.m", # ":tether_connection_dialog.m" @@ -285,7 +285,20 @@ js_library("network_proxy_section.m") { sources = [ "$root_gen_dir/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.m.js" ] deps = [ - # TODO: Fill those in. + ":internet_shared_css.m", + "//chrome/browser/resources/settings/chromeos:os_route.m", + "//chrome/browser/resources/settings/controls:extension_controlled_indicator.m", + "//chrome/browser/resources/settings/controls:settings_toggle_button.m", + "//chrome/browser/resources/settings/prefs:prefs_behavior.m", + "//chrome/browser/resources/settings:router.m", + "//third_party/polymer/v3_0/components-chromium/iron-flex-layout:iron-flex-layout-classes", + "//third_party/polymer/v3_0/components-chromium/polymer:polymer_bundled", + "//ui/webui/resources/cr_components/chromeos/network:cr_policy_network_behavior_mojo.m", + "//ui/webui/resources/cr_components/chromeos/network:cr_policy_network_indicator_mojo.m", + "//ui/webui/resources/cr_components/chromeos/network:network_proxy.m", + "//ui/webui/resources/cr_elements/cr_button:cr_button.m", + "//ui/webui/resources/cr_elements/cr_dialog:cr_dialog.m", + "//ui/webui/resources/js:i18n_behavior.m", ] extra_deps = [ ":network_proxy_section_module" ] } @@ -377,6 +390,8 @@ js_file = "network_proxy_section.js" html_file = "network_proxy_section.html" html_type = "dom-module" + auto_imports = os_settings_auto_imports + namespace_rewrites = os_settings_namespace_rewrites } polymer_modulizer("network_summary") {
diff --git a/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.html b/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.html index 6cfe1d4f..677c5a6 100644 --- a/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.html +++ b/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.html
@@ -6,15 +6,14 @@ <link rel="import" href="chrome://resources/cr_elements/cr_button/cr_button.html"> <link rel="import" href="chrome://resources/cr_elements/cr_dialog/cr_dialog.html"> <link rel="import" href="chrome://resources/cr_elements/hidden_style_css.html"> -<link rel="import" href="chrome://resources/html/assert.html"> -<link rel="import" href="chrome://resources/html/cr/ui/focus_without_ink.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="../../controls/extension_controlled_indicator.html"> <link rel="import" href="../../controls/settings_toggle_button.html"> -<link rel="import" href="../../i18n_setup.html"> <link rel="import" href="../../prefs/prefs_behavior.html"> +<link rel="import" href="../../router.html"> <link rel="import" href="../../settings_vars_css.html"> +<link rel="import" href="../os_route.html"> <link rel="import" href="internet_shared_css.html"> <dom-module id="network-proxy-section">
diff --git a/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.js b/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.js index d8f7f25..25367d1 100644 --- a/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.js +++ b/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.js
@@ -7,10 +7,6 @@ * detail page. This element is responsible for setting 'Allow proxies for * shared networks'. */ -(function() { -'use strict'; - -const mojom = chromeos.networkConfig.mojom; Polymer({ is: 'network-proxy-section', @@ -63,12 +59,13 @@ * @private */ isShared_() { + const mojom = chromeos.networkConfig.mojom; return this.managedProperties.source == mojom.OncSource.kDevice || this.managedProperties.source == mojom.OncSource.kDevicePolicy; }, /** - * @return {!mojom.ManagedString|undefined} + * @return {!chromeos.networkConfig.mojom.ManagedString|undefined} * @private */ getProxySettingsTypeProperty_() { @@ -158,4 +155,3 @@ this.$.allowShared.focus(); }, }); -})();
diff --git a/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.html b/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.html index 8b8fb73..6ba623e 100644 --- a/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.html +++ b/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.html
@@ -36,6 +36,10 @@ min-height: 36px; } + cr-policy-indicator { + margin-inline-end: 8px; + } + .bottom-margin { margin-bottom: var(--cr-section-vertical-margin); } @@ -62,13 +66,23 @@ [[getLanguageDisplayName_(languages.prospectiveUILanguage)]] </div> </div> - <cr-button id="changeDeviceLanguage" - on-click="onChangeDeviceLanguageClick_" - aria-label="[[getChangeDeviceLanguageButtonDescription_( - languages.prospectiveUILanguage)]]" - deep-link-focus-id$="[[Setting.kChangeDeviceLanguage]]"> - $i18n{changeDeviceLanguageLabel} - </cr-button> + <template is="dom-if" if="[[isSecondaryUser_]]"> + <cr-policy-indicator id="changeDeviceLanguagePolicyIndicator" + indicator-type="primary_user" + indicator-source-name="[[primaryUserEmail_]]"> + </cr-policy-indicator> + </template> + <template is="dom-if" if="[[!isGuest_]]"> + <cr-button id="changeDeviceLanguage" + on-click="onChangeDeviceLanguageClick_" + disabled="[[isSecondaryUser_]]" + aria-label="[[getChangeDeviceLanguageButtonDescription_( + languages.prospectiveUILanguage)]]" + deep-link-focus-id$="[[Setting.kChangeDeviceLanguage]]"> + $i18n{changeDeviceLanguageLabel} + </cr-button> + </template> + </div> <div class="hr bottom-margin">
diff --git a/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.js b/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.js index 9d347e5..5f408f3 100644 --- a/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.js +++ b/chrome/browser/resources/settings/chromeos/os_languages_page/os_languages_page_v2.js
@@ -55,6 +55,30 @@ value: false, }, + /** @private */ + isGuest_: { + type: Boolean, + value() { + return loadTimeData.getBoolean('isGuest'); + }, + }, + + /** @private */ + isSecondaryUser_: { + type: Boolean, + value() { + return loadTimeData.getBoolean('isSecondaryUser'); + }, + }, + + /** @private */ + primaryUserEmail_: { + type: String, + value() { + return loadTimeData.getString('primaryUserEmail'); + }, + }, + /** * Used by DeepLinkingBehavior to focus this page's deep links. * @type {!Set<!chromeos.settings.mojom.Setting>} @@ -108,7 +132,7 @@ /** @private */ onChangeDeviceLanguageDialogClose_() { this.showChangeDeviceLanguageDialog_ = false; - cr.ui.focusWithoutInk(assert(this.$.changeDeviceLanguage)); + cr.ui.focusWithoutInk(assert(this.$$('#changeDeviceLanguage'))); }, /**
diff --git a/chrome/browser/resources/settings/chromeos/os_settings.js b/chrome/browser/resources/settings/chromeos/os_settings.js index 1eb19a8..7f8a256 100644 --- a/chrome/browser/resources/settings/chromeos/os_settings.js +++ b/chrome/browser/resources/settings/chromeos/os_settings.js
@@ -10,6 +10,7 @@ import './internet_page/cellular_setup_dialog.m.js'; import './internet_page/internet_config.m.js'; import './internet_page/internet_known_networks_page.m.js'; +import './internet_page/network_proxy_section.m.js'; import './nearby_share_page/nearby_share_receive_dialog.m.js'; import './nearby_share_page/nearby_share_subpage.m.js'; import './multidevice_page/multidevice_page.m.js';
diff --git a/chrome/browser/resources/settings/chromeos/os_settings_resources_v3.grdp b/chrome/browser/resources/settings/chromeos/os_settings_resources_v3.grdp index e795836..ebb2f4e 100644 --- a/chrome/browser/resources/settings/chromeos/os_settings_resources_v3.grdp +++ b/chrome/browser/resources/settings/chromeos/os_settings_resources_v3.grdp
@@ -55,6 +55,11 @@ use_base_dir="false" compress="false" type="BINDATA" /> + <include name="IDR_OS_SETTINGS_NETWORK_PROXY_SECTION_M_JS" + file="${root_gen_dir}/chrome/browser/resources/settings/chromeos/internet_page/network_proxy_section.m.js" + use_base_dir="false" + compress="false" + type="BINDATA" /> <include name="IDR_OS_SETTINGS_PERSONALIZATION_PAGE_M_JS" file="${root_gen_dir}/chrome/browser/resources/settings/chromeos/personalization_page/personalization_page.m.js" use_base_dir="false" @@ -87,6 +92,11 @@ use_base_dir="false" compress="false" type="BINDATA" /> + <include name="IDR_OS_SETTINGS_EXTENSION_CONTROLLED_INDICATOR_M_JS" + file="${root_gen_dir}/chrome/browser/resources/settings/controls/extension_controlled_indicator.m.js" + use_base_dir="false" + compress="false" + type="BINDATA" /> <include name="IDR_OS_SETTINGS_SETTINGS_RADIO_GROUP_M_JS" file="${root_gen_dir}/chrome/browser/resources/settings/controls/settings_radio_group.m.js" use_base_dir="false" @@ -102,6 +112,11 @@ use_base_dir="false" compress="false" type="BINDATA" /> + <include name="IDR_OS_SETTINGS_EXTENSION_CONTROL_BROWSER_PROXY_M_JS" + file="${root_gen_dir}/chrome/browser/resources/settings/extension_control_browser_proxy.m.js" + use_base_dir="false" + compress="false" + type="BINDATA" /> <include name="IDR_OS_SETTINGS_LANGUAGES_PAGE_LANGUAGES_BROWSER_PROXY_M_JS" file="${root_gen_dir}/chrome/browser/resources/settings/languages_page/languages_browser_proxy.m.js" use_base_dir="false"
diff --git a/chrome/browser/resources/settings/privacy_page/privacy_page.html b/chrome/browser/resources/settings/privacy_page/privacy_page.html index d8d14c3..94dae1df 100644 --- a/chrome/browser/resources/settings/privacy_page/privacy_page.html +++ b/chrome/browser/resources/settings/privacy_page/privacy_page.html
@@ -234,22 +234,20 @@ </category-setting-exceptions> </settings-subpage> </template> - <template is="dom-if" if="[[enableInsecureContentContentSetting_]]"> - <template is="dom-if" route-path="/content/insecureContent" no-search> - <settings-subpage - page-title="$i18n{siteSettingsCategoryInsecureContent}" - search-label="$i18n{siteSettingsAllSitesSearch}" - search-term="{{searchFilter_}}"> - <div class="cr-row first"> - $i18n{siteSettingsInsecureContentBlock} - </div> - <category-setting-exceptions - category="[[ContentSettingsTypes.MIXEDSCRIPT]]" - block-header="$i18n{siteSettingsBlock}" - search-filter="[[searchFilter_]]"> - </category-setting-exceptions> - </settings-subpage> - </template> + <template is="dom-if" route-path="/content/insecureContent" no-search> + <settings-subpage + page-title="$i18n{siteSettingsCategoryInsecureContent}" + search-label="$i18n{siteSettingsAllSitesSearch}" + search-term="{{searchFilter_}}"> + <div class="cr-row first"> + $i18n{siteSettingsInsecureContentBlock} + </div> + <category-setting-exceptions + category="[[ContentSettingsTypes.MIXEDSCRIPT]]" + block-header="$i18n{siteSettingsBlock}" + search-filter="[[searchFilter_]]"> + </category-setting-exceptions> + </settings-subpage> </template> <template is="dom-if" route-path="/content/location" no-search> <settings-subpage page-title="$i18n{siteSettingsCategoryLocation}"
diff --git a/chrome/browser/resources/settings/privacy_page/privacy_page.js b/chrome/browser/resources/settings/privacy_page/privacy_page.js index f835de5..f3c5ae1 100644 --- a/chrome/browser/resources/settings/privacy_page/privacy_page.js +++ b/chrome/browser/resources/settings/privacy_page/privacy_page.js
@@ -144,14 +144,6 @@ }, /** @private */ - enableInsecureContentContentSetting_: { - type: Boolean, - value() { - return loadTimeData.getBoolean('enableInsecureContentContentSetting'); - } - }, - - /** @private */ enableFileSystemWriteContentSetting_: { type: Boolean, value() {
diff --git a/chrome/browser/resources/settings/route.js b/chrome/browser/resources/settings/route.js index 9caa01c..f8dbb8bd 100644 --- a/chrome/browser/resources/settings/route.js +++ b/chrome/browser/resources/settings/route.js
@@ -47,10 +47,7 @@ r.SITE_SETTINGS_SITE_DATA.createChild('/cookies/detail'); r.SITE_SETTINGS_IDLE_DETECTION = r.SITE_SETTINGS.createChild('idleDetection'); r.SITE_SETTINGS_IMAGES = r.SITE_SETTINGS.createChild('images'); - if (loadTimeData.getBoolean('enableInsecureContentContentSetting')) { - r.SITE_SETTINGS_MIXEDSCRIPT = - r.SITE_SETTINGS.createChild('insecureContent'); - } + r.SITE_SETTINGS_MIXEDSCRIPT = r.SITE_SETTINGS.createChild('insecureContent'); r.SITE_SETTINGS_JAVASCRIPT = r.SITE_SETTINGS.createChild('javascript'); r.SITE_SETTINGS_SOUND = r.SITE_SETTINGS.createChild('sound'); r.SITE_SETTINGS_SENSORS = r.SITE_SETTINGS.createChild('sensors');
diff --git a/chrome/browser/resources/settings/site_settings/site_details.html b/chrome/browser/resources/settings/site_settings/site_details.html index 161b726b..e22ec5e 100644 --- a/chrome/browser/resources/settings/site_settings/site_details.html +++ b/chrome/browser/resources/settings/site_settings/site_details.html
@@ -217,13 +217,11 @@ label="$i18n{siteSettingsBluetoothScanning}"> </site-details-permission> </template> - <template is="dom-if" if="[[enableInsecureContentContentSetting_]]"> - <site-details-permission - category="[[ContentSettingsTypes.MIXEDSCRIPT]]" - icon="settings:insecure-content" - label="$i18n{siteSettingsInsecureContent}"> - </site-details-permission> - </template> + <site-details-permission + category="[[ContentSettingsTypes.MIXEDSCRIPT]]" + icon="settings:insecure-content" + label="$i18n{siteSettingsInsecureContent}"> + </site-details-permission> <site-details-permission category="[[ContentSettingsTypes.AR]]" icon="settings:vr-headset" label="$i18n{siteSettingsAr}"> </site-details-permission>
diff --git a/chrome/browser/resources/settings/site_settings/site_details.js b/chrome/browser/resources/settings/site_settings/site_details.js index 94dbde12..0482ad33 100644 --- a/chrome/browser/resources/settings/site_settings/site_details.js +++ b/chrome/browser/resources/settings/site_settings/site_details.js
@@ -111,14 +111,6 @@ }, /** @private */ - enableInsecureContentContentSetting_: { - type: Boolean, - value() { - return loadTimeData.getBoolean('enableInsecureContentContentSetting'); - } - }, - - /** @private */ storagePressureFlagEnabled_: { type: Boolean, value: () => loadTimeData.getBoolean('enableStoragePressureUI'),
diff --git a/chrome/browser/resources/settings/site_settings/site_settings_behavior.js b/chrome/browser/resources/settings/site_settings/site_settings_behavior.js index 89815160..09b65fd 100644 --- a/chrome/browser/resources/settings/site_settings/site_settings_behavior.js +++ b/chrome/browser/resources/settings/site_settings/site_settings_behavior.js
@@ -226,9 +226,6 @@ ContentSettingsTypes.FILE_SYSTEM_WRITE, 'enableFileSystemWriteContentSetting'); addOrRemoveSettingWithFlag( - ContentSettingsTypes.MIXEDSCRIPT, - 'enableInsecureContentContentSetting'); - addOrRemoveSettingWithFlag( ContentSettingsTypes.BLUETOOTH_DEVICES, 'enableWebBluetoothNewPermissionsBackend'); addOrRemoveSettingWithFlag(
diff --git a/chrome/browser/resources/settings/site_settings_page/site_settings_page.js b/chrome/browser/resources/settings/site_settings_page/site_settings_page.js index cbbddf3..0d972b6 100644 --- a/chrome/browser/resources/settings/site_settings_page/site_settings_page.js +++ b/chrome/browser/resources/settings/site_settings_page/site_settings_page.js
@@ -185,8 +185,6 @@ label: 'siteSettingsInsecureContent', icon: 'settings:insecure-content', disabledLabel: 'siteSettingsInsecureContentBlock', - shouldShow: () => - loadTimeData.getBoolean('enableInsecureContentContentSetting'), }, { route: routes.SITE_SETTINGS_FILE_SYSTEM_WRITE,
diff --git a/chrome/browser/safe_browsing/chrome_password_protection_service.cc b/chrome/browser/safe_browsing/chrome_password_protection_service.cc index 689e6fa..e29e1db2 100644 --- a/chrome/browser/safe_browsing/chrome_password_protection_service.cc +++ b/chrome/browser/safe_browsing/chrome_password_protection_service.cc
@@ -34,7 +34,6 @@ #include "chrome/browser/signin/identity_manager_factory.h" #include "chrome/browser/sync/profile_sync_service_factory.h" #include "chrome/browser/sync/user_event_service_factory.h" -#include "chrome/browser/ui/browser_list.h" #include "chrome/common/pref_names.h" #include "chrome/common/url_constants.h" #include "components/content_settings/core/browser/host_content_settings_map.h" @@ -91,6 +90,8 @@ #if defined(OS_ANDROID) #include "chrome/browser/safe_browsing/android/password_reuse_controller_android.h" +#else +#include "chrome/browser/ui/browser_list.h" #endif using base::RecordAction;
diff --git a/chrome/browser/search/shopping_tasks/shopping_tasks_data.cc b/chrome/browser/search/shopping_tasks/shopping_tasks_data.cc new file mode 100644 index 0000000..c2ca51a --- /dev/null +++ b/chrome/browser/search/shopping_tasks/shopping_tasks_data.cc
@@ -0,0 +1,15 @@ +// Copyright 2020 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/search/shopping_tasks/shopping_tasks_data.h" + +ShoppingTasksData::Product::Product() = default; +ShoppingTasksData::Product::Product(const Product&) = default; +ShoppingTasksData::Product::~Product() = default; +ShoppingTasksData::RelatedSearch::RelatedSearch() = default; +ShoppingTasksData::RelatedSearch::RelatedSearch(const RelatedSearch&) = default; +ShoppingTasksData::RelatedSearch::~RelatedSearch() = default; +ShoppingTasksData::ShoppingTasksData() = default; +ShoppingTasksData::ShoppingTasksData(const ShoppingTasksData&) = default; +ShoppingTasksData::~ShoppingTasksData() = default;
diff --git a/chrome/browser/search/shopping_tasks/shopping_tasks_data.h b/chrome/browser/search/shopping_tasks/shopping_tasks_data.h new file mode 100644 index 0000000..1c2348de --- /dev/null +++ b/chrome/browser/search/shopping_tasks/shopping_tasks_data.h
@@ -0,0 +1,44 @@ +// Copyright 2020 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_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_DATA_H_ +#define CHROME_BROWSER_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_DATA_H_ + +#include <string> + +#include "url/gurl.h" + +// Represents a single shopping task. +struct ShoppingTasksData { + struct Product { + Product(); + Product(const Product&); + ~Product(); + + std::string name; + GURL image_url; + std::string price; + std::string info; + GURL target_url; + }; + + struct RelatedSearch { + RelatedSearch(); + RelatedSearch(const RelatedSearch&); + ~RelatedSearch(); + + std::string text; + GURL target_url; + }; + + ShoppingTasksData(); + ShoppingTasksData(const ShoppingTasksData&); + ~ShoppingTasksData(); + + std::string title; + std::vector<Product> products; + std::vector<RelatedSearch> related_searches; +}; + +#endif // CHROME_BROWSER_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_DATA_H_
diff --git a/chrome/browser/search/shopping_tasks/shopping_tasks_service.cc b/chrome/browser/search/shopping_tasks/shopping_tasks_service.cc new file mode 100644 index 0000000..e3a9335 --- /dev/null +++ b/chrome/browser/search/shopping_tasks/shopping_tasks_service.cc
@@ -0,0 +1,173 @@ +// Copyright 2020 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/search/shopping_tasks/shopping_tasks_service.h" + +#include "chrome/common/webui_url_constants.h" +#include "components/google/core/common/google_util.h" +#include "services/network/public/cpp/resource_request.h" +#include "services/network/public/cpp/shared_url_loader_factory.h" +#include "services/network/public/cpp/simple_url_loader.h" + +namespace { +const char kNewTabShoppingTasksApiPath[] = "/async/newtab_shopping_tasks"; +const char kXSSIResponsePreamble[] = ")]}'"; + +GURL GetApiUrl() { + GURL google_base_url = google_util::CommandLineGoogleBaseURL(); + if (!google_base_url.is_valid()) { + google_base_url = GURL(google_util::kGoogleHomepageURL); + } + return google_base_url.Resolve(kNewTabShoppingTasksApiPath); +} +} // namespace + +ShoppingTasksService::ShoppingTasksService( + scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, + Profile* profile) + : url_loader_factory_(url_loader_factory) {} + +ShoppingTasksService::~ShoppingTasksService() = default; + +void ShoppingTasksService::Shutdown() {} + +void ShoppingTasksService::GetPrimaryShoppingTask( + ShoppingTaskCallback callback) { + net::NetworkTrafficAnnotationTag traffic_annotation = + net::DefineNetworkTrafficAnnotation("shopping_tasks_service", R"( + semantics { + sender: "Shopping Tasks Service" + description: "This service downloads shopping tasks, which is " + "information related to the user's currently active shopping " + "search journeys such as visisted and recommended products. " + "Shopping tasks will be displayed on the new tab page to help the " + "user to continue their search journey. Shopping tasks are queried " + "on every new tab page load." + trigger: + "Displaying the new tab page on Desktop, if Google is the " + "configured search provider and the user is signed in." + data: "Credentials if user is signed in." + destination: GOOGLE_OWNED_SERVICE + } + policy { + cookies_allowed: YES + cookies_store: "user" + setting: + "Users can control this feature via selecting a non-Google default " + "search engine in Chrome settings under 'Search Engine' or by " + "signing out." + chrome_policy { + DefaultSearchProviderEnabled { + policy_options {mode: MANDATORY} + DefaultSearchProviderEnabled: false + } + BrowserSignin { + policy_options {mode: MANDATORY} + BrowserSignin: 0 + } + } + })"); + + auto resource_request = std::make_unique<network::ResourceRequest>(); + resource_request->url = GetApiUrl(); + resource_request->credentials_mode = + network::mojom::CredentialsMode::kInclude; + resource_request->request_initiator = + url::Origin::Create(GURL(chrome::kChromeUINewTabURL)); + + loaders_.push_back(network::SimpleURLLoader::Create( + std::move(resource_request), traffic_annotation)); + loaders_.back()->DownloadToString( + url_loader_factory_.get(), + base::BindOnce(&ShoppingTasksService::OnDataLoaded, + weak_ptr_factory_.GetWeakPtr(), loaders_.back().get(), + std::move(callback)), + network::SimpleURLLoader::kMaxBoundedStringDownloadSize); +} + +void ShoppingTasksService::OnDataLoaded(network::SimpleURLLoader* loader, + ShoppingTaskCallback callback, + std::unique_ptr<std::string> response) { + auto net_error = loader->NetError(); + base::EraseIf(loaders_, [loader](const auto& target) { + return loader == target.get(); + }); + + if (net_error != net::OK || !response) { + std::move(callback).Run(base::nullopt); + return; + } + + if (base::StartsWith(*response, kXSSIResponsePreamble, + base::CompareCase::SENSITIVE)) { + *response = response->substr(strlen(kXSSIResponsePreamble)); + } + + data_decoder::DataDecoder::ParseJsonIsolated( + *response, + base::BindOnce(&ShoppingTasksService::OnJsonParsed, + weak_ptr_factory_.GetWeakPtr(), std::move(callback))); +} + +void ShoppingTasksService::OnJsonParsed( + ShoppingTaskCallback callback, + data_decoder::DataDecoder::ValueOrError result) { + if (!result.value) { + std::move(callback).Run(base::nullopt); + return; + } + // We receive a list of shopping tasks ordered from highest to lowest + // priority. We only support showing a single task though. Therefore, pick the + // first task. + auto* shopping_tasks = result.value->FindListPath("update.shopping_tasks"); + if (!shopping_tasks || shopping_tasks->GetList().size() == 0) { + std::move(callback).Run(base::nullopt); + return; + } + auto* title = shopping_tasks->GetList()[0].FindStringPath("title"); + auto* products = shopping_tasks->GetList()[0].FindListPath("products"); + auto* related_searches = + shopping_tasks->GetList()[0].FindListPath("related_searches"); + if (!title || !products || !related_searches) { + std::move(callback).Run(base::nullopt); + return; + } + std::vector<ShoppingTasksData::Product> products_list; + for (const auto& product : products->GetList()) { + auto* name = product.FindStringPath("name"); + auto* image_url = product.FindStringPath("image_url"); + auto* price = product.FindStringPath("price"); + auto* info = product.FindStringPath("info"); + auto* target_url = product.FindStringPath("target_url"); + if (!name || !image_url || !price || !info || !target_url) { + std::move(callback).Run(base::nullopt); + return; + } + ShoppingTasksData::Product product_struct; + product_struct.name = *name; + product_struct.image_url = GURL(*image_url); + product_struct.price = *price; + product_struct.info = *info; + product_struct.target_url = GURL(*target_url); + products_list.push_back(product_struct); + } + std::vector<ShoppingTasksData::RelatedSearch> related_searches_list; + for (const auto& related_search : related_searches->GetList()) { + auto* text = related_search.FindStringPath("text"); + auto* target_url = related_search.FindStringPath("target_url"); + if (!text || !target_url) { + std::move(callback).Run(base::nullopt); + return; + } + ShoppingTasksData::RelatedSearch related_search_struct; + related_search_struct.text = *text; + related_search_struct.target_url = GURL(*target_url); + related_searches_list.push_back(related_search_struct); + } + ShoppingTasksData data; + data.title = *title; + data.products = products_list; + data.related_searches = related_searches_list; + std::move(callback).Run(data); +}
diff --git a/chrome/browser/search/shopping_tasks/shopping_tasks_service.h b/chrome/browser/search/shopping_tasks/shopping_tasks_service.h new file mode 100644 index 0000000..eed0687 --- /dev/null +++ b/chrome/browser/search/shopping_tasks/shopping_tasks_service.h
@@ -0,0 +1,57 @@ +// Copyright 2020 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_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_SERVICE_H_ +#define CHROME_BROWSER_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_SERVICE_H_ + +#include <list> +#include <memory> + +#include "base/callback.h" +#include "base/memory/scoped_refptr.h" +#include "base/memory/weak_ptr.h" +#include "chrome/browser/search/shopping_tasks/shopping_tasks_data.h" +#include "components/keyed_service/core/keyed_service.h" +#include "services/data_decoder/public/cpp/data_decoder.h" + +class Profile; +namespace network { +class SharedURLLoaderFactory; +class SimpleURLLoader; +} // namespace network + +// Downloads shopping tasks for current user from GWS. +class ShoppingTasksService : public KeyedService { + public: + ShoppingTasksService( + scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, + Profile* profile); + ShoppingTasksService(const ShoppingTasksService&) = delete; + ~ShoppingTasksService() override; + + // KeyedService: + void Shutdown() override; + + using ShoppingTaskCallback = base::OnceCallback<void( + const base::Optional<ShoppingTasksData>& shopping_tasks_data)>; + // Downloads and parses shopping tasks and calls |callback| when done. + // On success |callback| is called with a populated |ShoppingTasksData| object + // of the highest priority shopping task. On failure, it is called with + // base::nullopt. + void GetPrimaryShoppingTask(ShoppingTaskCallback callback); + + private: + void OnDataLoaded(network::SimpleURLLoader* loader, + ShoppingTaskCallback callback, + std::unique_ptr<std::string> response); + void OnJsonParsed(ShoppingTaskCallback callback, + data_decoder::DataDecoder::ValueOrError result); + + scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory_; + std::list<std::unique_ptr<network::SimpleURLLoader>> loaders_; + + base::WeakPtrFactory<ShoppingTasksService> weak_ptr_factory_{this}; +}; + +#endif // CHROME_BROWSER_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_SERVICE_H_
diff --git a/chrome/browser/search/shopping_tasks/shopping_tasks_service_factory.cc b/chrome/browser/search/shopping_tasks/shopping_tasks_service_factory.cc new file mode 100644 index 0000000..82ae0b2 --- /dev/null +++ b/chrome/browser/search/shopping_tasks/shopping_tasks_service_factory.cc
@@ -0,0 +1,42 @@ +// Copyright 2020 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/search/shopping_tasks/shopping_tasks_service_factory.h" + +#include "chrome/browser/content_settings/cookie_settings_factory.h" +#include "chrome/browser/profiles/profile.h" +#include "chrome/browser/search/shopping_tasks/shopping_tasks_service.h" +#include "components/keyed_service/content/browser_context_dependency_manager.h" +#include "content/public/browser/browser_context.h" +#include "content/public/browser/storage_partition.h" + +// static +ShoppingTasksService* ShoppingTasksServiceFactory::GetForProfile( + Profile* profile) { + return static_cast<ShoppingTasksService*>( + GetInstance()->GetServiceForBrowserContext(profile, true)); +} + +// static +ShoppingTasksServiceFactory* ShoppingTasksServiceFactory::GetInstance() { + return base::Singleton<ShoppingTasksServiceFactory>::get(); +} + +ShoppingTasksServiceFactory::ShoppingTasksServiceFactory() + : BrowserContextKeyedServiceFactory( + "ShoppingTasksService", + BrowserContextDependencyManager::GetInstance()) { + DependsOn(CookieSettingsFactory::GetInstance()); +} + +ShoppingTasksServiceFactory::~ShoppingTasksServiceFactory() = default; + +KeyedService* ShoppingTasksServiceFactory::BuildServiceInstanceFor( + content::BrowserContext* context) const { + auto url_loader_factory = + content::BrowserContext::GetDefaultStoragePartition(context) + ->GetURLLoaderFactoryForBrowserProcess(); + return new ShoppingTasksService(url_loader_factory, + Profile::FromBrowserContext(context)); +}
diff --git a/chrome/browser/search/shopping_tasks/shopping_tasks_service_factory.h b/chrome/browser/search/shopping_tasks/shopping_tasks_service_factory.h new file mode 100644 index 0000000..8f10f20 --- /dev/null +++ b/chrome/browser/search/shopping_tasks/shopping_tasks_service_factory.h
@@ -0,0 +1,33 @@ +// Copyright 2020 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_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_SERVICE_FACTORY_H_ +#define CHROME_BROWSER_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_SERVICE_FACTORY_H_ + +#include "base/memory/singleton.h" +#include "components/keyed_service/content/browser_context_keyed_service_factory.h" + +class Profile; +class ShoppingTasksService; + +// Factory to access the shopping task service for the current profile. +class ShoppingTasksServiceFactory : public BrowserContextKeyedServiceFactory { + public: + static ShoppingTasksService* GetForProfile(Profile* profile); + static ShoppingTasksServiceFactory* GetInstance(); + + ShoppingTasksServiceFactory(const ShoppingTasksServiceFactory&) = delete; + + private: + friend struct base::DefaultSingletonTraits<ShoppingTasksServiceFactory>; + + ShoppingTasksServiceFactory(); + ~ShoppingTasksServiceFactory() override; + + // BrowserContextKeyedServiceFactory: + KeyedService* BuildServiceInstanceFor( + content::BrowserContext* profile) const override; +}; + +#endif // CHROME_BROWSER_SEARCH_SHOPPING_TASKS_SHOPPING_TASKS_SERVICE_FACTORY_H_
diff --git a/chrome/browser/search/shopping_tasks/shopping_tasks_service_unittest.cc b/chrome/browser/search/shopping_tasks/shopping_tasks_service_unittest.cc new file mode 100644 index 0000000..ee74dd56 --- /dev/null +++ b/chrome/browser/search/shopping_tasks/shopping_tasks_service_unittest.cc
@@ -0,0 +1,205 @@ +// Copyright 2020 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 <memory> + +#include "base/memory/scoped_refptr.h" +#include "base/test/bind_test_util.h" +#include "base/test/mock_callback.h" +#include "chrome/browser/search/shopping_tasks/shopping_tasks_service.h" +#include "chrome/test/base/testing_profile.h" +#include "content/public/test/browser_task_environment.h" +#include "services/data_decoder/public/cpp/test_support/in_process_data_decoder.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_url_loader_factory.h" +#include "testing/gmock/include/gmock/gmock.h" +#include "testing/gtest/include/gtest/gtest.h" + +class ShoppingTasksServiceTest : public testing::Test { + public: + ShoppingTasksServiceTest() + : task_environment_(content::BrowserTaskEnvironment::IO_MAINLOOP) {} + + void SetUp() override { + testing::Test::SetUp(); + + service_ = std::make_unique<ShoppingTasksService>( + base::MakeRefCounted<network::WeakWrapperSharedURLLoaderFactory>( + &test_url_loader_factory_), + &profile_); + } + + void TearDown() override { + service_.reset(); + test_url_loader_factory_.ClearResponses(); + } + + protected: + // Required to run tests from UI thread. + content::BrowserTaskEnvironment task_environment_; + TestingProfile profile_; + network::TestURLLoaderFactory test_url_loader_factory_; + data_decoder::test::InProcessDataDecoder in_process_data_decoder_; + scoped_refptr<network::SharedURLLoaderFactory> test_shared_loader_factory_; + std::unique_ptr<ShoppingTasksService> service_; +}; + +// Verifies correct parsing of well-formed JSON. +TEST_F(ShoppingTasksServiceTest, GoodResponse) { + test_url_loader_factory_.AddResponse( + "https://www.google.com/async/newtab_shopping_tasks", + R"()]}' +{ + "update": { + "shopping_tasks": [ + { + "title": "hello world", + "products": [ + { + "name": "foo", + "image_url": "https://foo.com", + "price": "$500", + "info": "visited 5 days ago", + "target_url": "https://google.com/foo" + },{ + "name": "bar", + "image_url": "https://bar.com", + "price": "$400", + "info": "visited 1 day ago", + "target_url": "https://google.com/bar" + } + ], + "related_searches": [ + { + "text": "baz", + "target_url": "https://google.com/baz" + }, + { + "text": "blub", + "target_url": "https://google.com/blub" + } + ] + } + ] + } +})"); + + base::Optional<ShoppingTasksData> result; + base::MockCallback<ShoppingTasksService::ShoppingTaskCallback> callback; + EXPECT_CALL(callback, Run(testing::_)) + .Times(1) + .WillOnce(testing::SaveArg<0>(&result)); + + service_->GetPrimaryShoppingTask(callback.Get()); + base::RunLoop().RunUntilIdle(); + + ASSERT_TRUE(result.has_value()); + EXPECT_EQ("hello world", result->title); + EXPECT_EQ(2ul, result->products.size()); + EXPECT_EQ(2ul, result->related_searches.size()); + EXPECT_EQ("foo", result->products[0].name); + EXPECT_EQ("https://foo.com/", result->products[0].image_url.spec()); + EXPECT_EQ("$500", result->products[0].price); + EXPECT_EQ("visited 5 days ago", result->products[0].info); + EXPECT_EQ("https://google.com/bar", result->products[1].target_url.spec()); + EXPECT_EQ("bar", result->products[1].name); + EXPECT_EQ("https://bar.com/", result->products[1].image_url.spec()); + EXPECT_EQ("$400", result->products[1].price); + EXPECT_EQ("visited 1 day ago", result->products[1].info); + EXPECT_EQ("https://google.com/bar", result->products[1].target_url.spec()); + EXPECT_EQ("baz", result->related_searches[0].text); + EXPECT_EQ("https://google.com/baz", + result->related_searches[0].target_url.spec()); + EXPECT_EQ("blub", result->related_searches[1].text); + EXPECT_EQ("https://google.com/blub", + result->related_searches[1].target_url.spec()); +} + +// Verifies service can handle multiple in flight requests. +TEST_F(ShoppingTasksServiceTest, MultiRequest) { + test_url_loader_factory_.AddResponse( + "https://www.google.com/async/newtab_shopping_tasks", + R"()]}' +{ + "update": { + "shopping_tasks": [ + { + "title": "hello world", + "products": [ + { + "name": "foo", + "image_url": "https://foo.com", + "price": "$500", + "info": "visited 5 days ago", + "target_url": "https://google.com/foo" + } + ], + "related_searches": [ + { + "text": "baz", + "target_url": "https://google.com/baz" + } + ] + } + ] + } +})"); + + base::Optional<ShoppingTasksData> result1; + base::MockCallback<ShoppingTasksService::ShoppingTaskCallback> callback1; + EXPECT_CALL(callback1, Run(testing::_)) + .Times(1) + .WillOnce(testing::SaveArg<0>(&result1)); + service_->GetPrimaryShoppingTask(callback1.Get()); + + base::Optional<ShoppingTasksData> result2; + base::MockCallback<ShoppingTasksService::ShoppingTaskCallback> callback2; + EXPECT_CALL(callback2, Run(testing::_)) + .Times(1) + .WillOnce(testing::SaveArg<0>(&result2)); + service_->GetPrimaryShoppingTask(callback2.Get()); + + base::RunLoop().RunUntilIdle(); + + EXPECT_TRUE(result1.has_value()); + EXPECT_TRUE(result2.has_value()); +} + +// Verifies error of JSON is malformed. +TEST_F(ShoppingTasksServiceTest, BadResponse) { + test_url_loader_factory_.AddResponse( + "https://www.google.com/async/newtab_shopping_tasks", + ")]}'{\"update\":{\"promotions\":{}}}"); + + base::Optional<ShoppingTasksData> result; + base::MockCallback<ShoppingTasksService::ShoppingTaskCallback> callback; + EXPECT_CALL(callback, Run(testing::_)) + .Times(1) + .WillOnce(testing::SaveArg<0>(&result)); + + service_->GetPrimaryShoppingTask(callback.Get()); + base::RunLoop().RunUntilIdle(); + + ASSERT_FALSE(result.has_value()); +} + +// Verifies error if download fails. +TEST_F(ShoppingTasksServiceTest, ErrorResponse) { + test_url_loader_factory_.AddResponse( + GURL("https://www.google.com/async/newtab_shopping_tasks"), + network::mojom::URLResponseHead::New(), std::string(), + network::URLLoaderCompletionStatus(net::HTTP_NOT_FOUND)); + + base::Optional<ShoppingTasksData> result; + base::MockCallback<ShoppingTasksService::ShoppingTaskCallback> callback; + EXPECT_CALL(callback, Run(testing::_)) + .Times(1) + .WillOnce(testing::SaveArg<0>(&result)); + + service_->GetPrimaryShoppingTask(callback.Get()); + base::RunLoop().RunUntilIdle(); + + ASSERT_FALSE(result.has_value()); +}
diff --git a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ShareSheetPropertyModelBuilder.java b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ShareSheetPropertyModelBuilder.java index 85b9a11..b462049 100644 --- a/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ShareSheetPropertyModelBuilder.java +++ b/chrome/browser/share/android/java/src/org/chromium/chrome/browser/share/share_sheet/ShareSheetPropertyModelBuilder.java
@@ -119,8 +119,7 @@ contentTypes.add(ContentType.LINK_PAGE_NOT_VISIBLE); } } - if (!TextUtils.isEmpty(params.getText()) - && !TextUtils.equals(params.getUrl(), params.getText())) { + if (!TextUtils.isEmpty(params.getText())) { if (chromeShareExtras.isUserHighlightedText()) { contentTypes.add(ContentType.HIGHLIGHTED_TEXT); } else {
diff --git a/chrome/browser/signin/chrome_signin_client.cc b/chrome/browser/signin/chrome_signin_client.cc index 68205183..640cdd4 100644 --- a/chrome/browser/signin/chrome_signin_client.cc +++ b/chrome/browser/signin/chrome_signin_client.cc
@@ -26,7 +26,6 @@ #include "chrome/browser/signin/force_signin_verifier.h" #include "chrome/browser/signin/identity_manager_factory.h" #include "chrome/browser/signin/signin_util.h" -#include "chrome/browser/ui/browser_list.h" #include "chrome/common/buildflags.h" #include "chrome/common/channel_info.h" #include "chrome/common/pref_names.h" @@ -61,6 +60,7 @@ #endif #if !defined(OS_ANDROID) && !defined(OS_CHROMEOS) +#include "chrome/browser/ui/browser_list.h" #include "chrome/browser/ui/user_manager.h" #endif
diff --git a/chrome/browser/signin/chrome_signin_status_metrics_provider_delegate.h b/chrome/browser/signin/chrome_signin_status_metrics_provider_delegate.h index 18b8e76..24e155c 100644 --- a/chrome/browser/signin/chrome_signin_status_metrics_provider_delegate.h +++ b/chrome/browser/signin/chrome_signin_status_metrics_provider_delegate.h
@@ -11,9 +11,12 @@ #include "base/macros.h" #include "build/build_config.h" #include "chrome/browser/signin/identity_manager_factory.h" -#include "chrome/browser/ui/browser_list_observer.h" #include "components/signin/core/browser/signin_status_metrics_provider_delegate.h" +#if !defined(OS_ANDROID) +#include "chrome/browser/ui/browser_list_observer.h" +#endif // !defined(OS_ANDROID) + class ChromeSigninStatusMetricsProviderDelegate : public SigninStatusMetricsProviderDelegate, #if !defined(OS_ANDROID)
diff --git a/chrome/browser/ssl/chrome_security_blocking_page_factory.cc b/chrome/browser/ssl/chrome_security_blocking_page_factory.cc index 368caa8b..2762202e 100644 --- a/chrome/browser/ssl/chrome_security_blocking_page_factory.cc +++ b/chrome/browser/ssl/chrome_security_blocking_page_factory.cc
@@ -51,7 +51,7 @@ #include "chrome/browser/ui/tabs/tab_strip_model.h" #include "components/captive_portal/content/captive_portal_tab_helper.h" #include "net/base/net_errors.h" -#include "net/dns/dns_config.h" +#include "net/dns/public/secure_dns_mode.h" #endif namespace { @@ -338,7 +338,7 @@ // If the DNS mode is SECURE, captive portal login tabs should be opened in // new popup windows where secure DNS will be disabled. - if (secure_dns_config.mode() == net::DnsConfig::SecureDnsMode::SECURE) { + if (secure_dns_config.mode() == net::SecureDnsMode::kSecure) { // If there is already a captive portal popup window, do not create another. for (auto* contents : AllTabContentses()) { captive_portal::CaptivePortalTabHelper* captive_portal_tab_helper =
diff --git a/chrome/browser/supervised_user/supervised_user_service.h b/chrome/browser/supervised_user/supervised_user_service.h index 46b355a..38672ab 100644 --- a/chrome/browser/supervised_user/supervised_user_service.h +++ b/chrome/browser/supervised_user/supervised_user_service.h
@@ -23,7 +23,6 @@ #include "chrome/browser/supervised_user/supervised_user_denylist.h" #include "chrome/browser/supervised_user/supervised_user_url_filter.h" #include "chrome/browser/supervised_user/supervised_users.h" -#include "chrome/browser/ui/browser_list_observer.h" #include "components/keyed_service/core/keyed_service.h" #include "components/prefs/pref_change_registrar.h" #include "components/sync/driver/sync_type_preference_provider.h" @@ -37,7 +36,10 @@ #include "extensions/browser/management_policy.h" #endif -class Browser; +#if !defined(OS_ANDROID) +#include "chrome/browser/ui/browser_list_observer.h" +#endif // !defined(OS_ANDROID) + class PermissionRequestCreator; class PrefService; class Profile; @@ -62,6 +64,10 @@ class PrefRegistrySyncable; } +#if !defined(OS_ANDROID) +class Browser; +#endif // !defined(OS_ANDROID) + // This class handles all the information related to a given supervised profile // (e.g. the installed content packs, the default URL filtering behavior, or // manual allowlist/denylist overrides).
diff --git a/chrome/browser/supervised_user/supervised_user_service_unittest.cc b/chrome/browser/supervised_user/supervised_user_service_unittest.cc index 29a5bfd..405cb3e9 100644 --- a/chrome/browser/supervised_user/supervised_user_service_unittest.cc +++ b/chrome/browser/supervised_user/supervised_user_service_unittest.cc
@@ -26,7 +26,6 @@ #include "chrome/browser/supervised_user/supervised_user_allowlist_service.h" #include "chrome/browser/supervised_user/supervised_user_features.h" #include "chrome/browser/supervised_user/supervised_user_service_factory.h" -#include "chrome/browser/ui/browser_list.h" #include "chrome/common/chrome_paths.h" #include "chrome/common/pref_names.h" #include "chrome/test/base/testing_profile.h"
diff --git a/chrome/browser/ui/BUILD.gn b/chrome/browser/ui/BUILD.gn index 0b2c471..8ccced6 100644 --- a/chrome/browser/ui/BUILD.gn +++ b/chrome/browser/ui/BUILD.gn
@@ -2723,6 +2723,8 @@ "views/autofill/payments/webauthn_dialog_view_impl.h", "views/close_bubble_on_tab_activation_helper.cc", "views/close_bubble_on_tab_activation_helper.h", + "views/external_protocol_dialog.cc", + "views/external_protocol_dialog.h", "views/hats/hats_bubble_view.cc", "views/hats/hats_bubble_view.h", "views/hats/hats_next_web_dialog.cc", @@ -2773,8 +2775,6 @@ "sync/one_click_signin_links_delegate_impl.h", "user_manager.cc", "user_manager.h", - "views/external_protocol_dialog.cc", - "views/external_protocol_dialog.h", "views/profiles/badged_profile_photo.cc", "views/profiles/badged_profile_photo.h", "views/profiles/profile_picker_view.cc",
diff --git a/chrome/browser/ui/android/default_browser_promo/java/src/org/chromium/chrome/browser/ui/default_browser_promo/DefaultBrowserPromoDeps.java b/chrome/browser/ui/android/default_browser_promo/java/src/org/chromium/chrome/browser/ui/default_browser_promo/DefaultBrowserPromoDeps.java index a9bdc37..abf74bf 100644 --- a/chrome/browser/ui/android/default_browser_promo/java/src/org/chromium/chrome/browser/ui/default_browser_promo/DefaultBrowserPromoDeps.java +++ b/chrome/browser/ui/android/default_browser_promo/java/src/org/chromium/chrome/browser/ui/default_browser_promo/DefaultBrowserPromoDeps.java
@@ -16,8 +16,6 @@ import android.provider.Settings; import android.text.TextUtils; -import androidx.annotation.NonNull; - import org.chromium.base.CommandLine; import org.chromium.base.ContextUtils; import org.chromium.base.PackageManagerUtils; @@ -125,8 +123,8 @@ } @DefaultBrowserState - int getCurrentDefaultBrowserState(@NonNull ResolveInfo info) { - if (info.match == 0) return DefaultBrowserState.NO_DEFAULT; // no default + int getCurrentDefaultBrowserState(ResolveInfo info) { + if (info == null || info.match == 0) return DefaultBrowserState.NO_DEFAULT; // no default if (TextUtils.equals(ContextUtils.getApplicationContext().getPackageName(), info.activityInfo.packageName)) { return DefaultBrowserState.CHROME_DEFAULT; // Already default
diff --git a/chrome/browser/ui/app_list/search/omnibox_result.cc b/chrome/browser/ui/app_list/search/omnibox_result.cc index 29de230..8356a32c 100644 --- a/chrome/browser/ui/app_list/search/omnibox_result.cc +++ b/chrome/browser/ui/app_list/search/omnibox_result.cc
@@ -116,6 +116,7 @@ case AutocompleteMatchType::EXTENSION_APP_DEPRECATED: case AutocompleteMatchType::TILE_SUGGESTION: + case AutocompleteMatchType::TILE_NAVSUGGEST: case AutocompleteMatchType::NUM_TYPES: NOTREACHED(); break; @@ -231,6 +232,7 @@ case AutocompleteMatchType::CLIPBOARD_IMAGE: case AutocompleteMatchType::HISTORY_BODY: case AutocompleteMatchType::TILE_SUGGESTION: + case AutocompleteMatchType::TILE_NAVSUGGEST: case AutocompleteMatchType::NUM_TYPES: // TODO(crbug.com/1028447): Add a NOTREACHED here once we are confident we // know all possible types for this result.
diff --git a/chrome/browser/ui/browser.cc b/chrome/browser/ui/browser.cc index 604d77d0..bf953c3 100644 --- a/chrome/browser/ui/browser.cc +++ b/chrome/browser/ui/browser.cc
@@ -1447,34 +1447,14 @@ if (allowed_per_prefs) return true; - if (base::FeatureList::IsEnabled(features::kMixedContentSiteSetting)) { - Profile* profile = - Profile::FromBrowserContext(web_contents->GetBrowserContext()); - HostContentSettingsMap* content_settings = - HostContentSettingsMapFactory::GetForProfile(profile); - return content_settings->GetContentSetting( - web_contents->GetLastCommittedURL(), GURL(), - ContentSettingsType::MIXEDSCRIPT, - std::string()) == CONTENT_SETTING_ALLOW; - } - MixedContentSettingsTabHelper* mixed_content_settings = - MixedContentSettingsTabHelper::FromWebContents(web_contents); - DCHECK(mixed_content_settings); - bool allowed = mixed_content_settings->IsRunningInsecureContentAllowed(); - if (!allowed && !origin.host().empty()) { - // Note: this is a browser-side-translation of the call to - // DidBlockContentType from inside - // ContentSettingsObserver::allowRunningInsecureContent. - // TODO(https://crbug.com/1103176): Plumb the actual frame reference here - // (MixedContentNavigationThrottle::ShouldBlockNavigation has - // |mixed_content_frame| reference) - content_settings::PageSpecificContentSettings* page_settings = - content_settings::PageSpecificContentSettings::GetForFrame( - web_contents->GetMainFrame()); - DCHECK(page_settings); - page_settings->OnContentBlocked(ContentSettingsType::MIXEDSCRIPT); - } - return allowed; + Profile* profile = + Profile::FromBrowserContext(web_contents->GetBrowserContext()); + HostContentSettingsMap* content_settings = + HostContentSettingsMapFactory::GetForProfile(profile); + return content_settings->GetContentSetting( + web_contents->GetLastCommittedURL(), GURL(), + ContentSettingsType::MIXEDSCRIPT, + std::string()) == CONTENT_SETTING_ALLOW; } void Browser::OnDidBlockNavigation(
diff --git a/chrome/browser/ui/browser_list.h b/chrome/browser/ui/browser_list.h index a376377..0abeb47 100644 --- a/chrome/browser/ui/browser_list.h +++ b/chrome/browser/ui/browser_list.h
@@ -14,6 +14,11 @@ #include "base/lazy_instance.h" #include "base/macros.h" #include "base/observer_list.h" +#include "build/build_config.h" + +#if defined(OS_ANDROID) +#error This file should only be included on desktop. +#endif class Browser; class Profile;
diff --git a/chrome/browser/ui/browser_list_observer.h b/chrome/browser/ui/browser_list_observer.h index 6879a58..c700a6b7 100644 --- a/chrome/browser/ui/browser_list_observer.h +++ b/chrome/browser/ui/browser_list_observer.h
@@ -5,6 +5,12 @@ #ifndef CHROME_BROWSER_UI_BROWSER_LIST_OBSERVER_H_ #define CHROME_BROWSER_UI_BROWSER_LIST_OBSERVER_H_ +#include "build/build_config.h" + +#if defined(OS_ANDROID) +#error This file should only be included on desktop. +#endif + class Browser; class BrowserListObserver {
diff --git a/chrome/browser/ui/content_settings/content_setting_bubble_model_browsertest.cc b/chrome/browser/ui/content_settings/content_setting_bubble_model_browsertest.cc index 6c1f86d2..9b67165 100644 --- a/chrome/browser/ui/content_settings/content_setting_bubble_model_browsertest.cc +++ b/chrome/browser/ui/content_settings/content_setting_bubble_model_browsertest.cc
@@ -40,120 +40,6 @@ using content_settings::PageSpecificContentSettings; -class ContentSettingBubbleModelMixedScriptTest : public InProcessBrowserTest { - public: - void SetUpCommandLine(base::CommandLine* command_line) override { - feature_list.InitWithFeatures( - /* enabled_features */ {}, - /* disabled_features */ {blink::features::kMixedContentAutoupgrade, - features::kMixedContentSiteSetting}); - } - - protected: - void SetUpInProcessBrowserTestFixture() override { - https_server_.reset( - new net::EmbeddedTestServer(net::EmbeddedTestServer::TYPE_HTTPS)); - https_server_->ServeFilesFromSourceDirectory(GetChromeTestDataDir()); - ASSERT_TRUE(https_server_->Start()); - } - - PageSpecificContentSettings* GetActivePageSpecificContentSettings() { - return PageSpecificContentSettings::GetForFrame( - browser()->tab_strip_model()->GetActiveWebContents()->GetMainFrame()); - } - - std::unique_ptr<net::EmbeddedTestServer> https_server_; - base::test::ScopedFeatureList feature_list; -}; - -// Tests that a MIXEDSCRIPT type ContentSettingBubbleModel sends appropriate -// IPCs to allow the renderer to load unsafe scripts and refresh the page -// automatically. -IN_PROC_BROWSER_TEST_F(ContentSettingBubbleModelMixedScriptTest, MainFrame) { - GURL url(https_server_->GetURL("/content_setting_bubble/mixed_script.html")); - - // Load a page with mixed content and do quick verification by looking at - // the title string. - ui_test_utils::NavigateToURL(browser(), url); - - EXPECT_TRUE(GetActivePageSpecificContentSettings()->IsContentBlocked( - ContentSettingsType::MIXEDSCRIPT)); - - // Emulate link clicking on the mixed script bubble. - std::unique_ptr<ContentSettingBubbleModel> model( - ContentSettingBubbleModel::CreateContentSettingBubbleModel( - browser()->content_setting_bubble_model_delegate(), - browser()->tab_strip_model()->GetActiveWebContents(), - ContentSettingsType::MIXEDSCRIPT)); - model->OnCustomLinkClicked(); - - // Wait for reload - content::TestNavigationObserver observer( - browser()->tab_strip_model()->GetActiveWebContents()); - observer.Wait(); - - EXPECT_FALSE(GetActivePageSpecificContentSettings()->IsContentBlocked( - ContentSettingsType::MIXEDSCRIPT)); -} - -class ContentSettingsMixedScriptIgnoreCertErrorsTest - : public ContentSettingBubbleModelMixedScriptTest { - protected: - void SetUpCommandLine(base::CommandLine* command_line) override { - ContentSettingBubbleModelMixedScriptTest::SetUpCommandLine(command_line); - command_line->AppendSwitch(switches::kIgnoreCertificateErrors); - } -}; - -// Tests that a MIXEDSCRIPT type ContentSettingBubbleModel records UMA -// metrics when the content is allowed to run. -IN_PROC_BROWSER_TEST_F(ContentSettingsMixedScriptIgnoreCertErrorsTest, - MainFrameMetrics) { - GURL url(https_server_->GetURL("/content_setting_bubble/mixed_script.html")); - - base::HistogramTester histograms; - histograms.ExpectTotalCount("ContentSettings.MixedScript", 0); - - // Load a page with mixed content and do quick verification by looking at - // the title string. - ui_test_utils::NavigateToURL(browser(), url); - - EXPECT_TRUE(GetActivePageSpecificContentSettings()->IsContentBlocked( - ContentSettingsType::MIXEDSCRIPT)); - - // Emulate link clicking on the mixed script bubble. - std::unique_ptr<ContentSettingBubbleModel> model( - ContentSettingBubbleModel::CreateContentSettingBubbleModel( - browser()->content_setting_bubble_model_delegate(), - browser()->tab_strip_model()->GetActiveWebContents(), - ContentSettingsType::MIXEDSCRIPT)); - model->OnCustomLinkClicked(); - - // Wait for reload - content::TestNavigationObserver observer( - browser()->tab_strip_model()->GetActiveWebContents()); - observer.Wait(); - - EXPECT_FALSE(GetActivePageSpecificContentSettings()->IsContentBlocked( - ContentSettingsType::MIXEDSCRIPT)); -} - -// Tests that a MIXEDSCRIPT type ContentSettingBubbleModel does not work -// for an iframe (mixed script in iframes is never allowed and the mixed -// content shield isn't shown for it). -IN_PROC_BROWSER_TEST_F(ContentSettingBubbleModelMixedScriptTest, Iframe) { - GURL url(https_server_->GetURL( - "/content_setting_bubble/mixed_script_in_iframe.html")); - - ui_test_utils::NavigateToURL(browser(), url); - - // Blink does not ask the browser to handle mixed content in the case - // of active subresources in an iframe, so the content type should not - // be marked as blocked. - EXPECT_FALSE(GetActivePageSpecificContentSettings()->IsContentBlocked( - ContentSettingsType::MIXEDSCRIPT)); -} - class ContentSettingBubbleModelMediaStreamTest : public InProcessBrowserTest { public: void ManageMediaStreamSettings( @@ -350,71 +236,3 @@ histograms.ExpectTotalCount("ContentSettings.Popups", 5); } - -class ContentSettingBubbleModelMixedScriptOopifTest - : public ContentSettingBubbleModelMixedScriptTest { - protected: - void SetUpCommandLine(base::CommandLine* command_line) override { - ContentSettingBubbleModelMixedScriptTest::SetUpCommandLine(command_line); - content::IsolateAllSitesForTesting(command_line); - } - - void SetUpInProcessBrowserTestFixture() override { - ContentSettingBubbleModelMixedScriptTest:: - SetUpInProcessBrowserTestFixture(); - host_resolver()->AddRule("*", "127.0.0.1"); - ASSERT_TRUE(embedded_test_server()->Start()); - } -}; - -// Tests that a MIXEDSCRIPT type ContentSettingBubbleModel sends appropriate -// IPCs to allow the renderer to load unsafe scripts inside out-of-processs -// iframes. -IN_PROC_BROWSER_TEST_F(ContentSettingBubbleModelMixedScriptOopifTest, - MixedContentInCrossSiteIframe) { - // Create a URL for the mixed content document and append it as a query - // string to the main URL. This approach is taken because the test servers - // run on random ports each time and it is not possible to use a static - // URL in the HTML for the main frame. The main document will use JS to - // navigate the iframe to the URL specified in the query string, which is - // determined at runtime and is known to be correct. - GURL foo_url(embedded_test_server()->GetURL( - "foo.com", "/content_setting_bubble/mixed_script.html")); - GURL main_url(https_server_->GetURL( - "/content_setting_bubble/mixed_script_in_cross_site_iframe.html?" + - foo_url.spec())); - - // Load a page with mixed content and verify that mixed content didn't get - // executed. - ui_test_utils::NavigateToURL(browser(), main_url); - EXPECT_TRUE(GetActivePageSpecificContentSettings()->IsContentBlocked( - ContentSettingsType::MIXEDSCRIPT)); - - std::string title; - content::WebContents* web_contents = - browser()->tab_strip_model()->GetActiveWebContents(); - EXPECT_TRUE(content::ExecuteScriptAndExtractString( - ChildFrameAt(web_contents->GetMainFrame(), 0), - "domAutomationController.send(document.title)", &title)); - EXPECT_EQ("", title); - - // Emulate link clicking on the mixed script bubble. - content::TestNavigationObserver observer(web_contents); - std::unique_ptr<ContentSettingBubbleModel> model( - ContentSettingBubbleModel::CreateContentSettingBubbleModel( - browser()->content_setting_bubble_model_delegate(), web_contents, - ContentSettingsType::MIXEDSCRIPT)); - model->OnCustomLinkClicked(); - - // Wait for reload and verify that mixed content is allowed. - observer.Wait(); - EXPECT_FALSE(GetActivePageSpecificContentSettings()->IsContentBlocked( - ContentSettingsType::MIXEDSCRIPT)); - - // Ensure that the script actually executed by checking the title of the - // document in the subframe. - EXPECT_TRUE(content::ExecuteScriptAndExtractString( - ChildFrameAt(web_contents->GetMainFrame(), 0), - "domAutomationController.send(document.title)", &title)); - EXPECT_EQ("mixed_script_ran_successfully", title); -}
diff --git a/chrome/browser/ui/tab_helpers.cc b/chrome/browser/ui/tab_helpers.cc index 440f669..5877e77 100644 --- a/chrome/browser/ui/tab_helpers.cc +++ b/chrome/browser/ui/tab_helpers.cc
@@ -83,7 +83,6 @@ #include "chrome/browser/ui/tab_dialogs.h" #include "chrome/browser/ui/tab_ui_helper.h" #include "chrome/browser/ui/thumbnails/thumbnail_tab_helper.h" -#include "chrome/browser/ui/web_applications/web_app_metrics.h" #include "chrome/browser/vr/vr_tab_helper.h" #include "chrome/common/buildflags.h" #include "chrome/common/chrome_features.h" @@ -166,6 +165,7 @@ #include "chrome/browser/extensions/api/web_navigation/web_navigation_api.h" #include "chrome/browser/extensions/chrome_extension_web_contents_observer.h" #include "chrome/browser/extensions/tab_helper.h" +#include "chrome/browser/ui/web_applications/web_app_metrics.h" #include "chrome/browser/web_applications/components/web_app_utils.h" #include "chrome/browser/web_applications/web_app_tab_helper.h" #include "extensions/browser/view_type_utils.h"
diff --git a/chrome/browser/ui/tab_helpers.h b/chrome/browser/ui/tab_helpers.h index 7505c53..385279c 100644 --- a/chrome/browser/ui/tab_helpers.h +++ b/chrome/browser/ui/tab_helpers.h
@@ -5,28 +5,36 @@ #ifndef CHROME_BROWSER_UI_TAB_HELPERS_H_ #define CHROME_BROWSER_UI_TAB_HELPERS_H_ +#include "build/build_config.h" + +#if defined(OS_ANDROID) + namespace android { class TabWebContentsDelegateAndroid; } -namespace content { -class WebContents; -} - -namespace chrome { -class BrowserTabStripModelDelegate; -} - -namespace prerender { -class ChromePrerenderContentsDelegate; -} - namespace thin_webview { namespace android { class ChromeThinWebViewInitializer; } } // namespace thin_webview +#else + +namespace chrome { +class BrowserTabStripModelDelegate; +} + +#endif // defined(OS_ANDROID) + +namespace content { +class WebContents; +} + +namespace prerender { +class ChromePrerenderContentsDelegate; +} + // A "tab contents" is a WebContents that is used as a tab in a browser window // (or the equivalent on Android). The TabHelpers class allows specific classes // to attach the set of tab helpers that is used for tab contents. @@ -40,14 +48,17 @@ // only Browser and BrowserTabStripModelDelegate.) class TabHelpers { private: - // Browser and its TabStripModelDelegate have intimate control of tabs. - // TabAndroid is the equivalent on Android. - friend class Browser; - friend class chrome::BrowserTabStripModelDelegate; +#if defined(OS_ANDROID) + // ThinWebView is used to host WebContents on non-tab UIs in Android. Most + // clients of ThinWebView will need a major subset of the tab helpers. + friend class thin_webview::android::ChromeThinWebViewInitializer; - // These are the Android equivalents of the two classes above. friend class TabAndroid; friend class android::TabWebContentsDelegateAndroid; +#else + friend class Browser; + friend class chrome::BrowserTabStripModelDelegate; +#endif // defined(OS_ANDROID) // chrome::Navigate creates WebContents that are destined for the tab strip, // and that might have WebUI that immediately calls back into random tab @@ -58,10 +69,6 @@ // the full set of tab helpers to deal with it. friend class prerender::ChromePrerenderContentsDelegate; - // ThinWebView is used to host WebContents on non-tab UIs in Android. Most - // clients of ThinWebView will need a major subset of the tab helpers. - friend class thin_webview::android::ChromeThinWebViewInitializer; - // FYI: Do NOT add any more friends here. The functions above are the ONLY // ones that need to call AttachTabHelpers; if you think you do, re-read the // design document linked above, especially the section "Reusing tab helpers".
diff --git a/chrome/browser/ui/ui_features.cc b/chrome/browser/ui/ui_features.cc index b5fa53a..b4f9d7e3 100644 --- a/chrome/browser/ui/ui_features.cc +++ b/chrome/browser/ui/ui_features.cc
@@ -109,6 +109,18 @@ const base::Feature kTabSearchFixedEntrypoint{ "TabSearchFixedEntrypoint", base::FEATURE_DISABLED_BY_DEFAULT}; +const base::FeatureParam<bool> kTabSearchSearchIgnoreLocation{ + &kTabSearch, "TabSearchSearchIgnoreLocation", true}; + +const base::FeatureParam<int> kTabSearchSearchDistance{ + &kTabSearch, "TabSearchSearchDistance", 200}; + +const base::FeatureParam<double> kTabSearchSearchThreshold{ + &kTabSearch, "TabSearchSearchThreshold", 0.0}; + +const base::FeatureParam<double> kTabSearchTitleToHostnameWeightRatio{ + &kTabSearch, "TabSearchTitleToHostnameWeightRatio", 2.0}; + // Enables showing text next to the 3-dot menu when an update is available. // See https://crbug.com/1001731 const base::Feature kUseTextForUpdateButton{"UseTextForUpdateButton",
diff --git a/chrome/browser/ui/ui_features.h b/chrome/browser/ui/ui_features.h index b877de8..b0b7c2b 100644 --- a/chrome/browser/ui/ui_features.h +++ b/chrome/browser/ui/ui_features.h
@@ -9,6 +9,7 @@ #define CHROME_BROWSER_UI_UI_FEATURES_H_ #include "base/feature_list.h" +#include "base/metrics/field_trial_params.h" #include "build/build_config.h" #include "chrome/common/buildflags.h" #include "extensions/buildflags/buildflags.h" @@ -65,6 +66,28 @@ extern const base::Feature kTabSearchFixedEntrypoint; +// Setting this to true will ignore the distance parameter when finding matches. +// This means that it will not matter where in the string the pattern occurs. +extern const base::FeatureParam<bool> kTabSearchSearchIgnoreLocation; + +// Determines how close the match must be to the beginning of the string. Eg a +// distance of 100 and threshold of 0.8 would require a perfect match to be +// within 80 characters of the beginning of the string. +extern const base::FeatureParam<int> kTabSearchSearchDistance; + +// This determines how strong the match should be for the item to be included in +// the result set. Eg a threshold of 0.0 requires a perfect match, 1.0 would +// match anything. Permissible values are [0.0, 1.0]. +extern const base::FeatureParam<double> kTabSearchSearchThreshold; + +// These are the hardcoded minimum and maximum search threshold values for +// |kTabSearchSearchThreshold|. +constexpr double kTabSearchSearchThresholdMin = 0.0; +constexpr double kTabSearchSearchThresholdMax = 1.0; + +// Controls how heavily weighted the tab's title is relative to the hostname. +extern const base::FeatureParam<double> kTabSearchTitleToHostnameWeightRatio; + extern const base::Feature kUseTextForUpdateButton; extern const base::Feature kWebFooterExperiment;
diff --git a/chrome/browser/ui/views/autofill/payments/local_card_migration_browsertest.cc b/chrome/browser/ui/views/autofill/payments/local_card_migration_browsertest.cc index c9fac41..687f3fa 100644 --- a/chrome/browser/ui/views/autofill/payments/local_card_migration_browsertest.cc +++ b/chrome/browser/ui/views/autofill/payments/local_card_migration_browsertest.cc
@@ -1233,29 +1233,8 @@ } // Tests to ensure the card nickname is shown correctly in the local card -// migration dialog. The param indicates whether the nickname experiment is -// enabled. -class LocalCardMigrationBrowserTestForNickname - : public LocalCardMigrationBrowserTest, - public ::testing::WithParamInterface<bool> { - protected: - LocalCardMigrationBrowserTestForNickname() { - scoped_feature_list_.InitWithFeatureState( - features::kAutofillEnableSurfacingServerCardNickname, GetParam()); - } - - ~LocalCardMigrationBrowserTestForNickname() override = default; - - private: - base::test::ScopedFeatureList scoped_feature_list_; -}; - -INSTANTIATE_TEST_SUITE_P(, - LocalCardMigrationBrowserTestForNickname, - testing::Bool()); - -IN_PROC_BROWSER_TEST_P(LocalCardMigrationBrowserTestForNickname, - CardIdentifierString) { +// migration dialog. +IN_PROC_BROWSER_TEST_F(LocalCardMigrationBrowserTest, CardIdentifierString) { base::HistogramTester histogram_tester; CreditCard first_card = SaveLocalCard( @@ -1275,8 +1254,7 @@ second_card.NetworkAndLastFourDigits()); EXPECT_EQ(static_cast<MigratableCardView*>(card_list_view->children()[1]) ->GetCardIdentifierString(), - GetParam() ? first_card.NicknameAndLastFourDigitsForTesting() - : first_card.NetworkAndLastFourDigits()); + first_card.NicknameAndLastFourDigitsForTesting()); } // TODO(crbug.com/897998):
diff --git a/chrome/browser/ui/views/autofill/payments/save_card_bubble_views_browsertest.cc b/chrome/browser/ui/views/autofill/payments/save_card_bubble_views_browsertest.cc index 1cd0d5f..201b039 100644 --- a/chrome/browser/ui/views/autofill/payments/save_card_bubble_views_browsertest.cc +++ b/chrome/browser/ui/views/autofill/payments/save_card_bubble_views_browsertest.cc
@@ -2243,37 +2243,8 @@ } // Tests to ensure the card nickname is shown correctly in the Upstream bubble. -// The param indicates whether the experiment is enabled. -class SaveCardBubbleViewsFullFormBrowserTestWithUpstreamForNickname - : public SaveCardBubbleViewsFullFormBrowserTest, - public ::testing::WithParamInterface<bool> { - protected: - SaveCardBubbleViewsFullFormBrowserTestWithUpstreamForNickname() { - if (GetParam()) { - feature_list_.InitWithFeatures( - /*enabled_features=*/{features:: - kAutofillEnableSurfacingServerCardNickname, - features::kAutofillUpstream}, - /*disabled_features=*/{}); - } else { - feature_list_.InitWithFeatures( - /*enabled_features=*/{features::kAutofillUpstream}, - /*disabled_features=*/{ - features::kAutofillEnableSurfacingServerCardNickname}); - } - } - - private: - base::test::ScopedFeatureList scoped_feature_list_; -}; - -INSTANTIATE_TEST_SUITE_P( - , - SaveCardBubbleViewsFullFormBrowserTestWithUpstreamForNickname, - testing::Bool()); - -IN_PROC_BROWSER_TEST_P( - SaveCardBubbleViewsFullFormBrowserTestWithUpstreamForNickname, +IN_PROC_BROWSER_TEST_F( + SaveCardBubbleViewsFullFormBrowserTestWithAutofillUpstream, LocalCardHasNickname) { base::HistogramTester histogram_tester; CreditCard card = test::GetCreditCard(); @@ -2289,12 +2260,11 @@ SubmitFormAndWaitForCardUploadSaveBubble(); EXPECT_EQ(GetSaveCardBubbleViews()->GetCardIdentifierString(), - (GetParam() ? card.NicknameAndLastFourDigitsForTesting() - : card.NetworkAndLastFourDigits())); + card.NicknameAndLastFourDigitsForTesting()); } -IN_PROC_BROWSER_TEST_P( - SaveCardBubbleViewsFullFormBrowserTestWithUpstreamForNickname, +IN_PROC_BROWSER_TEST_F( + SaveCardBubbleViewsFullFormBrowserTestWithAutofillUpstream, LocalCardHasNoNickname) { base::HistogramTester histogram_tester; CreditCard card = test::GetCreditCard();
diff --git a/chrome/browser/ui/views/external_protocol_dialog.cc b/chrome/browser/ui/views/external_protocol_dialog.cc index 2babaa2e..be89aa5da 100644 --- a/chrome/browser/ui/views/external_protocol_dialog.cc +++ b/chrome/browser/ui/views/external_protocol_dialog.cc
@@ -7,6 +7,7 @@ #include <utility> #include "base/strings/string_util.h" +#include "build/build_config.h" #include "chrome/browser/external_protocol/external_protocol_handler.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/shell_integration.h" @@ -43,6 +44,7 @@ } // namespace +#if !defined(OS_CHROMEOS) // static void ExternalProtocolHandler::RunExternalProtocolDialog( const GURL& url, @@ -63,6 +65,7 @@ new ExternalProtocolDialog(web_contents, url, program_name, initiating_origin); } +#endif // !defined(OS_CHROMEOS) ExternalProtocolDialog::ExternalProtocolDialog( WebContents* web_contents,
diff --git a/chrome/browser/ui/views/omnibox/omnibox_view_views.cc b/chrome/browser/ui/views/omnibox/omnibox_view_views.cc index 994604d..58fbed1 100644 --- a/chrome/browser/ui/views/omnibox/omnibox_view_views.cc +++ b/chrome/browser/ui/views/omnibox/omnibox_view_views.cc
@@ -802,23 +802,23 @@ } } -void OmniboxViewViews::OnInputMethodChanged() { -#if defined(OS_WIN) +ui::TextInputType OmniboxViewViews::GetTextInputType() const { + ui::TextInputType input_type = views::Textfield::GetTextInputType(); // We'd like to set the text input type to TEXT_INPUT_TYPE_URL, because this // triggers URL-specific layout in software keyboards, e.g. adding top-level // "/" and ".com" keys for English. However, this also causes IMEs to default // to Latin character mode, which makes entering search queries difficult for // IME users. Therefore, we try to guess whether an IME will be used based on // the input language, and set the input type accordingly. - if (location_bar_view_) { +#if defined(OS_WIN) + if (input_type != ui::TEXT_INPUT_TYPE_NONE && location_bar_view_) { ui::InputMethod* input_method = location_bar_view_->GetWidget()->GetInputMethod(); if (input_method && input_method->IsInputLocaleCJK()) - SetTextInputType(ui::TEXT_INPUT_TYPE_SEARCH); - else - SetTextInputType(ui::TEXT_INPUT_TYPE_URL); + return ui::TEXT_INPUT_TYPE_SEARCH; } #endif + return input_type; } void OmniboxViewViews::AddedToWidget() {
diff --git a/chrome/browser/ui/views/omnibox/omnibox_view_views.h b/chrome/browser/ui/views/omnibox/omnibox_view_views.h index b868f96..1e99695 100644 --- a/chrome/browser/ui/views/omnibox/omnibox_view_views.h +++ b/chrome/browser/ui/views/omnibox/omnibox_view_views.h
@@ -153,7 +153,7 @@ void OnMouseReleased(const ui::MouseEvent& event) override; void OnPaint(gfx::Canvas* canvas) override; void ExecuteCommand(int command_id, int event_flags) override; - void OnInputMethodChanged() override; + ui::TextInputType GetTextInputType() const override; void AddedToWidget() override; void RemovedFromWidget() override; base::string16 GetLabelForCommandId(int command_id) const override;
diff --git a/chrome/browser/ui/views/omnibox/omnibox_view_views_browsertest.cc b/chrome/browser/ui/views/omnibox/omnibox_view_views_browsertest.cc index 60997cf..cbdfb6598 100644 --- a/chrome/browser/ui/views/omnibox/omnibox_view_views_browsertest.cc +++ b/chrome/browser/ui/views/omnibox/omnibox_view_views_browsertest.cc
@@ -36,9 +36,7 @@ #include "ui/accessibility/ax_node_data.h" #include "ui/base/clipboard/clipboard.h" #include "ui/base/clipboard/scoped_clipboard_writer.h" -#include "ui/base/ime/init/input_method_factory.h" #include "ui/base/ime/input_method.h" -#include "ui/base/ime/mock_input_method.h" #include "ui/base/ime/text_edit_commands.h" #include "ui/base/ime/text_input_client.h" #include "ui/base/test/ui_controls.h" @@ -826,55 +824,4 @@ close_waiter.Wait(); EXPECT_FALSE(omnibox_view->model()->popup_model()->IsOpen()); } - -namespace { - -// MockInputMethod ------------------------------------------------------------ -class OmniBoxMockInputMethod : public ui::MockInputMethod { - public: - OmniBoxMockInputMethod() : ui::MockInputMethod(nullptr) {} - bool IsInputLocaleCJK() const override { return input_locale_cjk; } - void SetInputLocaleCJK(bool is_cjk) { input_locale_cjk = is_cjk; } - - private: - bool input_locale_cjk = false; -}; - -} // namespace - -class OmniboxViewViewsIMETest : public OmniboxViewViewsTest { - public: - OmniboxViewViewsIMETest() {} - void SetUp() override { - input_method_ = new OmniBoxMockInputMethod(); - // transfers ownership. - ui::SetUpInputMethodForTesting(input_method_); - InProcessBrowserTest::SetUp(); - } - - protected: - void SetUpCommandLine(base::CommandLine* command_line) override { - OmniboxViewViewsTest::SetUpCommandLine(command_line); - command_line->AppendSwitch(switches::kEnableExperimentalUIAutomation); - } - OmniBoxMockInputMethod* input_method_ = nullptr; -}; - -IN_PROC_BROWSER_TEST_F(OmniboxViewViewsIMETest, TextInputTypeChangedTest) { - chrome::FocusLocationBar(browser()); - OmniboxView* view = nullptr; - ASSERT_NO_FATAL_FAILURE(GetOmniboxViewForBrowser(browser(), &view)); - OmniboxViewViews* omnibox_view_views = static_cast<OmniboxViewViews*>(view); - ui::InputMethod* input_method = - omnibox_view_views->GetWidget()->GetInputMethod(); - EXPECT_EQ(input_method, input_method_); - EXPECT_EQ(ui::TEXT_INPUT_TYPE_URL, omnibox_view_views->GetTextInputType()); - input_method_->SetInputLocaleCJK(/*is_cjk*/ true); - omnibox_view_views->OnInputMethodChanged(); - EXPECT_EQ(ui::TEXT_INPUT_TYPE_SEARCH, omnibox_view_views->GetTextInputType()); - - input_method_->SetInputLocaleCJK(/*is_cjk*/ false); - omnibox_view_views->OnInputMethodChanged(); - EXPECT_EQ(ui::TEXT_INPUT_TYPE_URL, omnibox_view_views->GetTextInputType()); -} #endif // OS_WIN
diff --git a/chrome/browser/ui/views/payments/contact_info_editor_view_controller.cc b/chrome/browser/ui/views/payments/contact_info_editor_view_controller.cc index 2b0bf42d..2ff9a99 100644 --- a/chrome/browser/ui/views/payments/contact_info_editor_view_controller.cc +++ b/chrome/browser/ui/views/payments/contact_info_editor_view_controller.cc
@@ -54,6 +54,9 @@ std::vector<EditorField> ContactInfoEditorViewController::GetFieldDefinitions() { std::vector<EditorField> fields; + if (!spec()) + return fields; + if (spec()->request_payer_name()) { fields.push_back(EditorField( autofill::NAME_FULL, @@ -200,7 +203,8 @@ bool ContactInfoEditorViewController::ContactInfoValidationDelegate:: ValidateTextfield(views::Textfield* textfield, base::string16* error_message) { - bool is_valid = true; + if (!controller_->spec()) + return false; // Show errors from merchant's retry() call. autofill::AutofillProfile* invalid_contact_profile = @@ -213,6 +217,7 @@ return false; } + bool is_valid = true; if (textfield->GetText().empty()) { is_valid = false; if (error_message) {
diff --git a/chrome/browser/ui/views/payments/credit_card_editor_view_controller.cc b/chrome/browser/ui/views/payments/credit_card_editor_view_controller.cc index 03281372..dbef7615 100644 --- a/chrome/browser/ui/views/payments/credit_card_editor_view_controller.cc +++ b/chrome/browser/ui/views/payments/credit_card_editor_view_controller.cc
@@ -186,6 +186,8 @@ std::unique_ptr<views::View> CreditCardEditorViewController::CreateHeaderView() { std::unique_ptr<views::View> view = std::make_unique<views::View>(); + if (!spec()) + return view; // 9dp is required between the first row (label) and second row (icons). constexpr int kRowVerticalSpacing = 9;
diff --git a/chrome/browser/ui/views/payments/order_summary_view_controller.cc b/chrome/browser/ui/views/payments/order_summary_view_controller.cc index 940cdfe..43bc332 100644 --- a/chrome/browser/ui/views/payments/order_summary_view_controller.cc +++ b/chrome/browser/ui/views/payments/order_summary_view_controller.cc
@@ -123,12 +123,16 @@ PaymentRequestState* state, PaymentRequestDialogView* dialog) : PaymentRequestSheetController(spec, state, dialog), pay_button_(nullptr) { + DCHECK(spec); + DCHECK(state); spec->AddObserver(this); state->AddObserver(this); } OrderSummaryViewController::~OrderSummaryViewController() { - spec()->RemoveObserver(this); + if (spec()) + spec()->RemoveObserver(this); + state()->RemoveObserver(this); } @@ -164,6 +168,9 @@ } void OrderSummaryViewController::FillContentView(views::View* content_view) { + if (!spec()) + return; + auto layout = std::make_unique<views::BoxLayout>( views::BoxLayout::Orientation::kVertical); layout->set_main_axis_alignment(views::BoxLayout::MainAxisAlignment::kStart);
diff --git a/chrome/browser/ui/views/payments/order_summary_view_controller.h b/chrome/browser/ui/views/payments/order_summary_view_controller.h index 7f2b3b2a..f2ef9f0e7 100644 --- a/chrome/browser/ui/views/payments/order_summary_view_controller.h +++ b/chrome/browser/ui/views/payments/order_summary_view_controller.h
@@ -25,6 +25,7 @@ public PaymentRequestState::Observer { public: // Does not take ownership of the arguments, which should outlive this object. + // The `spec` and `state` parameters should not be null. OrderSummaryViewController(PaymentRequestSpec* spec, PaymentRequestState* state, PaymentRequestDialogView* dialog);
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 791099c..2bf1db82 100644 --- a/chrome/browser/ui/views/payments/payment_request_dialog_view.cc +++ b/chrome/browser/ui/views/payments/payment_request_dialog_view.cc
@@ -120,7 +120,7 @@ } void PaymentRequestDialogView::ShowErrorMessage() { - if (being_closed_) + if (being_closed_ || !request_->spec()) return; view_stack_->Push(CreateViewAndInstallController( @@ -148,6 +148,9 @@ void PaymentRequestDialogView::ShowPaymentHandlerScreen( const GURL& url, PaymentHandlerOpenWindowCallback callback) { + if (!request_->spec()) + return; + if (PaymentsExperimentalFeatures::IsEnabled( features::kPaymentHandlerPopUpSizeWindow)) { is_showing_large_payment_handler_window_ = true; @@ -180,6 +183,9 @@ } void PaymentRequestDialogView::RetryDialog() { + if (!request_->spec()) + return; + HideProcessingSpinner(); GoBackToPaymentSheet(false /* animate */); @@ -222,6 +228,9 @@ } void PaymentRequestDialogView::OnSpecUpdated() { + if (!request_->spec()) + return; + if (request_->spec()->current_update_reason() != PaymentRequestSpec::UpdateReason::NONE) { HideProcessingSpinner(); @@ -287,6 +296,9 @@ } void PaymentRequestDialogView::ShowContactProfileSheet() { + if (!request_->spec()) + return; + view_stack_->Push( CreateViewAndInstallController( ProfileListViewController::GetContactProfileViewController( @@ -298,6 +310,9 @@ } void PaymentRequestDialogView::ShowOrderSummary() { + if (!request_->spec()) + return; + view_stack_->Push(CreateViewAndInstallController( std::make_unique<OrderSummaryViewController>( request_->spec(), request_->state(), this), @@ -308,6 +323,9 @@ } void PaymentRequestDialogView::ShowPaymentMethodSheet() { + if (!request_->spec()) + return; + view_stack_->Push(CreateViewAndInstallController( std::make_unique<PaymentMethodViewController>( request_->spec(), request_->state(), this), @@ -318,6 +336,9 @@ } void PaymentRequestDialogView::ShowShippingProfileSheet() { + if (!request_->spec()) + return; + view_stack_->Push( CreateViewAndInstallController( ProfileListViewController::GetShippingProfileViewController( @@ -329,6 +350,9 @@ } void PaymentRequestDialogView::ShowShippingOptionSheet() { + if (!request_->spec()) + return; + view_stack_->Push(CreateViewAndInstallController( std::make_unique<ShippingOptionViewController>( request_->spec(), request_->state(), this), @@ -343,6 +367,9 @@ base::WeakPtr<autofill::payments::FullCardRequest::ResultDelegate> result_delegate, content::WebContents* web_contents) { + if (!request_->spec()) + return; + view_stack_->Push(CreateViewAndInstallController( std::make_unique<CvcUnmaskViewController>( request_->spec(), request_->state(), this, @@ -359,6 +386,9 @@ base::OnceClosure on_edited, base::OnceCallback<void(const autofill::CreditCard&)> on_added, autofill::CreditCard* credit_card) { + if (!request_->spec()) + return; + view_stack_->Push( CreateViewAndInstallController( std::make_unique<CreditCardEditorViewController>( @@ -376,6 +406,9 @@ base::OnceClosure on_edited, base::OnceCallback<void(const autofill::AutofillProfile&)> on_added, autofill::AutofillProfile* profile) { + if (!request_->spec()) + return; + view_stack_->Push( CreateViewAndInstallController( std::make_unique<ShippingAddressEditorViewController>( @@ -393,6 +426,9 @@ base::OnceClosure on_edited, base::OnceCallback<void(const autofill::AutofillProfile&)> on_added, autofill::AutofillProfile* profile) { + if (!request_->spec()) + return; + view_stack_->Push( CreateViewAndInstallController( std::make_unique<ContactInfoEditorViewController>( @@ -427,6 +463,8 @@ PaymentRequestDialogView::ObserverForTest* observer) : request_(request), observer_for_testing_(observer) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + DCHECK(request); + DCHECK(request->spec()); SetButtons(ui::DIALOG_BUTTON_NONE); @@ -467,6 +505,9 @@ PaymentRequestDialogView::~PaymentRequestDialogView() = default; void PaymentRequestDialogView::OnDialogOpened() { + if (!request_->spec()) + return; + if (request_->spec()->request_shipping() && !request_->state()->selected_shipping_profile() && PaymentsExperimentalFeatures::IsEnabled( @@ -484,6 +525,9 @@ } void PaymentRequestDialogView::ShowInitialPaymentSheet() { + if (!request_->spec()) + return; + view_stack_->Push(CreateViewAndInstallController( std::make_unique<PaymentSheetViewController>( request_->spec(), request_->state(), this),
diff --git a/chrome/browser/ui/views/payments/payment_request_item_list.cc b/chrome/browser/ui/views/payments/payment_request_item_list.cc index b52a6a70..dce85312 100644 --- a/chrome/browser/ui/views/payments/payment_request_item_list.cc +++ b/chrome/browser/ui/views/payments/payment_request_item_list.cc
@@ -52,7 +52,7 @@ bool clickable, bool show_edit_button) : PaymentRequestRowView(this, clickable, kRowInsets), - spec_(spec), + spec_(spec->GetWeakPtr()), state_(state), list_(list), selected_(selected),
diff --git a/chrome/browser/ui/views/payments/payment_request_item_list.h b/chrome/browser/ui/views/payments/payment_request_item_list.h index 4e106300..4355702 100644 --- a/chrome/browser/ui/views/payments/payment_request_item_list.h +++ b/chrome/browser/ui/views/payments/payment_request_item_list.h
@@ -33,9 +33,9 @@ // Represents an item in the item list. class Item : public views::ButtonListener, public PaymentRequestRowView { public: - // Creates an item that will be owned by |list| with the initial state set - // to |selected|. |clickable| indicates whether or not the user can interact - // with this row. + // Creates an item that will be owned by `list` with the initial state set + // to `selected`. `clickable` indicates whether or not the user can interact + // with this row. The `spec` parameter should not be null. Item(PaymentRequestSpec* spec, PaymentRequestState* state, PaymentRequestItemList* list, @@ -54,7 +54,7 @@ // Returns a pointer to the PaymentRequestSpec/State objects associated with // this instance of the UI. - PaymentRequestSpec* spec() { return spec_; } + PaymentRequestSpec* spec() { return spec_.get(); } PaymentRequestState* state() { return state_; } protected: @@ -110,7 +110,7 @@ // status (selected/not). void UpdateAccessibleName(); - PaymentRequestSpec* spec_; + base::WeakPtr<PaymentRequestSpec> spec_; PaymentRequestState* state_; PaymentRequestItemList* list_; base::string16 accessible_item_description_;
diff --git a/chrome/browser/ui/views/payments/payment_request_item_list_unittest.cc b/chrome/browser/ui/views/payments/payment_request_item_list_unittest.cc index 1833cdbf..7cb5fc8 100644 --- a/chrome/browser/ui/views/payments/payment_request_item_list_unittest.cc +++ b/chrome/browser/ui/views/payments/payment_request_item_list_unittest.cc
@@ -8,18 +8,28 @@ #include <utility> #include <vector> +#include "components/payments/content/payment_request_spec.h" #include "testing/gtest/include/gtest/gtest.h" +#include "third_party/blink/public/mojom/payments/payment_request.mojom.h" #include "ui/views/view.h" namespace payments { - namespace { +std::unique_ptr<PaymentRequestSpec> BuildSpec() { + return std::make_unique<PaymentRequestSpec>( + mojom::PaymentOptions::New(), mojom::PaymentDetails::New(), + std::vector<mojom::PaymentMethodDataPtr>(), + /*observer=*/nullptr, /*app_locale=*/"en-US"); +} + class TestListItem : public PaymentRequestItemList::Item { public: - TestListItem(PaymentRequestItemList* list, bool selected) - : PaymentRequestItemList::Item(nullptr, - nullptr, + TestListItem(PaymentRequestSpec* spec, + PaymentRequestItemList* list, + bool selected) + : PaymentRequestItemList::Item(spec, + /*state=*/nullptr, list, selected, /*clickable=*/true, @@ -63,11 +73,12 @@ std::unique_ptr<views::View> list_view = list.CreateListView(); EXPECT_TRUE(list_view->children().empty()); + std::unique_ptr<PaymentRequestSpec> spec = BuildSpec(); std::vector<std::unique_ptr<TestListItem>> items; - items.push_back(std::make_unique<TestListItem>(&list, false)); - items.push_back(std::make_unique<TestListItem>(&list, true)); - items.push_back(std::make_unique<TestListItem>(&list, false)); - items.push_back(std::make_unique<TestListItem>(&list, true)); + items.push_back(std::make_unique<TestListItem>(spec.get(), &list, false)); + items.push_back(std::make_unique<TestListItem>(spec.get(), &list, true)); + items.push_back(std::make_unique<TestListItem>(spec.get(), &list, false)); + items.push_back(std::make_unique<TestListItem>(spec.get(), &list, true)); // The unique_ptr objects will become owned by |list|, but the underlying // pointers will be needed for assertions after the unique_ptr is moved. @@ -91,10 +102,11 @@ TEST(PaymentRequestItemListTest, TestSelectItemResultsInSingleItemSelected) { PaymentRequestItemList list(nullptr); + std::unique_ptr<PaymentRequestSpec> spec = BuildSpec(); std::vector<std::unique_ptr<TestListItem>> items; - items.push_back(std::make_unique<TestListItem>(&list, false)); - items.push_back(std::make_unique<TestListItem>(&list, false)); - items.push_back(std::make_unique<TestListItem>(&list, false)); + items.push_back(std::make_unique<TestListItem>(spec.get(), &list, false)); + items.push_back(std::make_unique<TestListItem>(spec.get(), &list, false)); + items.push_back(std::make_unique<TestListItem>(spec.get(), &list, false)); // The unique_ptr objects will become owned by |list|, but the underlying // pointers will be needed for assertions after the unique_ptr is moved.
diff --git a/chrome/browser/ui/views/payments/payment_request_sheet_controller.cc b/chrome/browser/ui/views/payments/payment_request_sheet_controller.cc index 6540ca5..f56db4e 100644 --- a/chrome/browser/ui/views/payments/payment_request_sheet_controller.cc +++ b/chrome/browser/ui/views/payments/payment_request_sheet_controller.cc
@@ -199,7 +199,7 @@ PaymentRequestSpec* spec, PaymentRequestState* state, PaymentRequestDialogView* dialog) - : spec_(spec), state_(state), dialog_(dialog) {} + : spec_(spec->GetWeakPtr()), state_(state), dialog_(dialog) {} PaymentRequestSheetController::~PaymentRequestSheetController() = default;
diff --git a/chrome/browser/ui/views/payments/payment_request_sheet_controller.h b/chrome/browser/ui/views/payments/payment_request_sheet_controller.h index ea0c2cc..f028d156 100644 --- a/chrome/browser/ui/views/payments/payment_request_sheet_controller.h +++ b/chrome/browser/ui/views/payments/payment_request_sheet_controller.h
@@ -52,7 +52,7 @@ // +---------------------------+ std::unique_ptr<views::View> CreateView(); - PaymentRequestSpec* spec() { return spec_; } + PaymentRequestSpec* spec() { return spec_.get(); } PaymentRequestState* state() { return state_; } // The dialog that contains and owns this object. @@ -181,8 +181,9 @@ void AddPrimaryButton(views::View* container); void AddSecondaryButton(views::View* container); + base::WeakPtr<PaymentRequestSpec> spec_; + // All these are not owned. Will outlive this. - PaymentRequestSpec* const spec_ = nullptr; PaymentRequestState* const state_ = nullptr; PaymentRequestDialogView* const dialog_ = nullptr;
diff --git a/chrome/browser/ui/views/payments/payment_request_views_util.cc b/chrome/browser/ui/views/payments/payment_request_views_util.cc index ad7be05..85d5eb3 100644 --- a/chrome/browser/ui/views/payments/payment_request_views_util.cc +++ b/chrome/browser/ui/views/payments/payment_request_views_util.cc
@@ -318,20 +318,22 @@ AddressStyleType type, const std::string& locale, const autofill::AutofillProfile& profile, - const PaymentOptionsProvider& options, + bool request_payer_name, + bool request_payer_email, + bool request_payer_phone, const PaymentsProfileComparator& comp, base::string16* accessible_content) { DCHECK(accessible_content); - base::string16 name = options.request_payer_name() + base::string16 name = request_payer_name ? profile.GetInfo(autofill::NAME_FULL, locale) : base::string16(); base::string16 phone = - options.request_payer_phone() + request_payer_phone ? autofill::i18n::GetFormattedPhoneNumberForDisplay(profile, locale) : base::string16(); - base::string16 email = options.request_payer_email() + base::string16 email = request_payer_email ? profile.GetInfo(autofill::EMAIL_ADDRESS, locale) : base::string16();
diff --git a/chrome/browser/ui/views/payments/payment_request_views_util.h b/chrome/browser/ui/views/payments/payment_request_views_util.h index 412c1cb..2812999 100644 --- a/chrome/browser/ui/views/payments/payment_request_views_util.h +++ b/chrome/browser/ui/views/payments/payment_request_views_util.h
@@ -26,11 +26,10 @@ class ImageView; class Label; class View; -} +} // namespace views namespace payments { -class PaymentOptionsProvider; class PaymentsProfileComparator; enum class PaymentShippingType; @@ -117,7 +116,9 @@ AddressStyleType type, const std::string& locale, const autofill::AutofillProfile& profile, - const PaymentOptionsProvider& options, + bool request_payer_name, + bool request_payer_email, + bool request_payer_phone, const PaymentsProfileComparator& comp, base::string16* accessible_content);
diff --git a/chrome/browser/ui/views/payments/payment_sheet_view_controller.cc b/chrome/browser/ui/views/payments/payment_sheet_view_controller.cc index cb78d7e..63e5b129 100644 --- a/chrome/browser/ui/views/payments/payment_sheet_view_controller.cc +++ b/chrome/browser/ui/views/payments/payment_sheet_view_controller.cc
@@ -384,12 +384,16 @@ PaymentRequestState* state, PaymentRequestDialogView* dialog) : PaymentRequestSheetController(spec, state, dialog) { + DCHECK(spec); + DCHECK(state); spec->AddObserver(this); state->AddObserver(this); } PaymentSheetViewController::~PaymentSheetViewController() { - spec()->RemoveObserver(this); + if (spec()) + spec()->RemoveObserver(this); + state()->RemoveObserver(this); } @@ -426,6 +430,9 @@ } void PaymentSheetViewController::FillContentView(views::View* content_view) { + if (!spec()) + return; + views::GridLayout* layout = content_view->SetLayoutManager(std::make_unique<views::GridLayout>()); views::ColumnSet* columns = layout->AddColumnSet(0); @@ -442,12 +449,18 @@ // The shipping address and contact info rows are optional. std::unique_ptr<PaymentRequestRowView> summary_row = CreatePaymentSheetSummaryRow(); + if (!summary_row) + return; + PaymentRequestRowView* previous_row = summary_row.get(); layout->StartRow(views::GridLayout::kFixedSize, 0); layout->AddView(std::move(summary_row)); if (state()->ShouldShowShippingSection()) { std::unique_ptr<PaymentRequestRowView> shipping_row = CreateShippingRow(); + if (!shipping_row) + return; + shipping_row->set_previous_row(previous_row->AsWeakPtr()); previous_row = shipping_row.get(); layout->StartRow(views::GridLayout::kFixedSize, 0); @@ -493,7 +506,7 @@ void PaymentSheetViewController::ButtonPressed(views::Button* sender, const ui::Event& event) { - if (!dialog()->IsInteractive()) + if (!dialog()->IsInteractive() || !spec()) return; bool should_reset_retry_error_message = true; @@ -575,7 +588,8 @@ } // Creates the Order Summary row, which contains an "Order Summary" label, -// an inline list of display items, a Total Amount label, and a Chevron. +// an inline list of display items, a Total Amount label, and a Chevron. Returns +// nullptr if WeakPtr<PaymentRequestSpec> has become null. // +----------------------------------------------+ // | Order Summary Item 1 $ 1.34 | // | Item 2 $ 2.00 > | @@ -584,6 +598,9 @@ // +----------------------------------------------+ std::unique_ptr<PaymentRequestRowView> PaymentSheetViewController::CreatePaymentSheetSummaryRow() { + if (!spec()) + return nullptr; + std::unique_ptr<views::View> inline_summary = std::make_unique<views::View>(); views::GridLayout* layout = inline_summary->SetLayoutManager(std::make_unique<views::GridLayout>()); @@ -681,7 +698,8 @@ } // Creates the Shipping row, which contains a "Shipping address" label, the -// user's selected shipping address, and a chevron. +// user's selected shipping address, and a chevron. Returns null if the +// WeakPtr<PaymentRequestSpec> has become null. // +----------------------------------------------+ // | Shipping Address Barack Obama | // | 1600 Pennsylvania Ave. > | @@ -689,6 +707,9 @@ // +----------------------------------------------+ std::unique_ptr<PaymentRequestRowView> PaymentSheetViewController::CreateShippingRow() { + if (!spec()) + return nullptr; + std::unique_ptr<views::Button> section; PaymentSheetRowBuilder builder( this, GetShippingAddressSectionString(spec()->shipping_type())); @@ -807,11 +828,18 @@ base::string16* accessible_content) { autofill::AutofillProfile* profile = state()->selected_contact_profile(); *accessible_content = base::string16(); - return profile ? payments::GetContactInfoLabel( - AddressStyleType::SUMMARY, - state()->GetApplicationLocale(), *profile, *spec(), - *(state()->profile_comparator()), accessible_content) - : std::make_unique<views::Label>(base::string16()); + return profile && spec() + ? payments::GetContactInfoLabel( + AddressStyleType::SUMMARY, state()->GetApplicationLocale(), + *profile, + /*request_payer_name=*/spec() && + spec()->request_payer_name(), + /*request_payer_email=*/spec() && + spec()->request_payer_email(), + /*request_payer_phone=*/spec() && + spec()->request_payer_phone(), + *(state()->profile_comparator()), accessible_content) + : std::make_unique<views::Label>(base::string16()); } // Creates the Contact Info row, which contains a "Contact info" label; the @@ -872,6 +900,9 @@ std::unique_ptr<PaymentRequestRowView> PaymentSheetViewController::CreateShippingOptionRow() { + if (!spec()) + return nullptr; + // The Shipping Options row has many different ways of being displayed // depending on the state of the dialog and Payment Request. // 1. There is a selected shipping address. The website updated the shipping
diff --git a/chrome/browser/ui/views/payments/payment_sheet_view_controller.h b/chrome/browser/ui/views/payments/payment_sheet_view_controller.h index a08d6c6..68680cd 100644 --- a/chrome/browser/ui/views/payments/payment_sheet_view_controller.h +++ b/chrome/browser/ui/views/payments/payment_sheet_view_controller.h
@@ -24,6 +24,7 @@ public PaymentRequestState::Observer { public: // Does not take ownership of the arguments, which should outlive this object. + // The `spec` and `state` objects should not be null. PaymentSheetViewController(PaymentRequestSpec* spec, PaymentRequestState* state, PaymentRequestDialogView* dialog);
diff --git a/chrome/browser/ui/views/payments/profile_list_view_controller.cc b/chrome/browser/ui/views/payments/profile_list_view_controller.cc index a6f13d5..7938e9a 100644 --- a/chrome/browser/ui/views/payments/profile_list_view_controller.cc +++ b/chrome/browser/ui/views/payments/profile_list_view_controller.cc
@@ -115,14 +115,20 @@ class ShippingProfileViewController : public ProfileListViewController, public PaymentRequestSpec::Observer { public: + // The `spec` parameter should not be null ShippingProfileViewController(PaymentRequestSpec* spec, PaymentRequestState* state, PaymentRequestDialogView* dialog) : ProfileListViewController(spec, state, dialog) { + DCHECK(spec); spec->AddObserver(this); PopulateList(); } - ~ShippingProfileViewController() override { spec()->RemoveObserver(this); } + + ~ShippingProfileViewController() override { + if (spec()) + spec()->RemoveObserver(this); + } protected: // ProfileListViewController: @@ -175,8 +181,8 @@ } std::unique_ptr<views::View> CreateHeaderView() override { - if (!spec()->GetShippingOptions().empty() && - spec()->selected_shipping_option_error().empty()) { + if (!spec() || (!spec()->GetShippingOptions().empty() && + spec()->selected_shipping_option_error().empty())) { return nullptr; } @@ -188,7 +194,8 @@ } base::string16 GetSheetTitle() override { - return GetShippingAddressSectionString(spec()->shipping_type()); + return spec() ? GetShippingAddressSectionString(spec()->shipping_type()) + : base::string16(); } base::string16 GetSecondaryButtonLabel() override { @@ -214,6 +221,9 @@ private: void OnSpecUpdated() override { + if (!spec()) + return; + // If there's an error, stay on this screen so the user can select a // different address. Otherwise, go back to the payment sheet. if (spec()->current_update_reason() == @@ -235,10 +245,12 @@ class ContactProfileViewController : public ProfileListViewController { public: + // The `spec` parameter should not be null. ContactProfileViewController(PaymentRequestSpec* spec, PaymentRequestState* state, PaymentRequestDialogView* dialog) : ProfileListViewController(spec, state, dialog) { + DCHECK(spec); PopulateList(); } ~ContactProfileViewController() override {} @@ -248,9 +260,13 @@ std::unique_ptr<views::View> GetLabel( autofill::AutofillProfile* profile, base::string16* accessible_content) override { + DCHECK(profile); return GetContactInfoLabel( AddressStyleType::DETAILED, state()->GetApplicationLocale(), *profile, - *spec(), *(state()->profile_comparator()), accessible_content); + /*request_payer_name=*/spec() && spec()->request_payer_name(), + /*request_payer_email=*/spec() && spec()->request_payer_email(), + /*request_payer_phone=*/spec() && spec()->request_payer_phone(), + *(state()->profile_comparator()), accessible_content); } void SelectProfile(autofill::AutofillProfile* profile) override { @@ -347,6 +363,9 @@ } void ProfileListViewController::PopulateList() { + if (!spec()) + return; + autofill::AutofillProfile* selected_profile = GetSelectedProfile(); list_.Clear();
diff --git a/chrome/browser/ui/views/payments/shipping_address_editor_view_controller.cc b/chrome/browser/ui/views/payments/shipping_address_editor_view_controller.cc index 1d5a0f04e..95cf8b8 100644 --- a/chrome/browser/ui/views/payments/shipping_address_editor_view_controller.cc +++ b/chrome/browser/ui/views/payments/shipping_address_editor_view_controller.cc
@@ -290,6 +290,9 @@ bool ShippingAddressEditorViewController::ShippingAddressValidationDelegate:: ValidateValue(const base::string16& value, base::string16* error_message) { + if (!controller_->spec()) + return false; + // Show errors from merchant's retry() call. Note that changing the selected // shipping address will clear the validation errors from retry(). autofill::AutofillProfile* invalid_shipping_profile =
diff --git a/chrome/browser/ui/views/payments/shipping_option_view_controller.cc b/chrome/browser/ui/views/payments/shipping_option_view_controller.cc index 3faccb6..953536d 100644 --- a/chrome/browser/ui/views/payments/shipping_option_view_controller.cc +++ b/chrome/browser/ui/views/payments/shipping_option_view_controller.cc
@@ -6,6 +6,7 @@ #include <memory> +#include "base/strings/string16.h" #include "chrome/browser/ui/views/payments/payment_request_dialog_view.h" #include "chrome/browser/ui/views/payments/payment_request_views_util.h" #include "components/payments/content/payment_request_spec.h" @@ -44,7 +45,9 @@ base::string16* accessible_content) override { return CreateShippingOptionLabel( shipping_option_, - spec()->GetFormattedCurrencyAmount(shipping_option_->amount), + /*formatted_amount=*/ + spec() ? spec()->GetFormattedCurrencyAmount(shipping_option_->amount) + : base::string16(), /*emphasize_label=*/true, accessible_content); } @@ -95,10 +98,14 @@ } ShippingOptionViewController::~ShippingOptionViewController() { - spec()->RemoveObserver(this); + if (spec()) + spec()->RemoveObserver(this); } void ShippingOptionViewController::OnSpecUpdated() { + if (!spec()) + return; + if (spec()->current_update_reason() == PaymentRequestSpec::UpdateReason::SHIPPING_OPTION) { dialog()->GoBack(); @@ -108,7 +115,8 @@ } base::string16 ShippingOptionViewController::GetSheetTitle() { - return GetShippingOptionSectionString(spec()->shipping_type()); + return spec() ? GetShippingOptionSectionString(spec()->shipping_type()) + : base::string16(); } void ShippingOptionViewController::FillContentView(views::View* content_view) {
diff --git a/chrome/browser/ui/views/read_later/read_later_button.cc b/chrome/browser/ui/views/read_later/read_later_button.cc index 216c232b..3814f931 100644 --- a/chrome/browser/ui/views/read_later/read_later_button.cc +++ b/chrome/browser/ui/views/read_later/read_later_button.cc
@@ -19,13 +19,17 @@ #include "ui/views/bubble/bubble_dialog_delegate_view.h" #include "ui/views/controls/button/button.h" #include "ui/views/controls/button/button_controller.h" +#include "ui/views/controls/button/label_button.h" ReadLaterButton::ReadLaterButton(Browser* browser) : ToolbarButton(this), browser_(browser) { - SetTooltipText(l10n_util::GetStringUTF16(IDS_TOOLTIP_READ_LATER_BUTTON)); + SetTooltipText(l10n_util::GetStringUTF16(IDS_READ_LATER_TITLE)); GetViewAccessibility().OverrideHasPopup(ax::mojom::HasPopup::kMenu); button_controller()->set_notify_action( views::ButtonController::NotifyAction::kOnPress); + // We don't want to use ToolbarButton::SetHighlight here because it adds a + // border around the button. + LabelButton::SetText(l10n_util::GetStringUTF16(IDS_READ_LATER_TITLE)); } ReadLaterButton::~ReadLaterButton() = default;
diff --git a/chrome/browser/ui/webui/read_later/read_later_ui.cc b/chrome/browser/ui/webui/read_later/read_later_ui.cc index c109d1eb..5535ada 100644 --- a/chrome/browser/ui/webui/read_later/read_later_ui.cc +++ b/chrome/browser/ui/webui/read_later/read_later_ui.cc
@@ -41,7 +41,7 @@ IDR_READ_LATER_MOJO_LITE_JS); static constexpr webui::LocalizedString kLocalizedStrings[] = { {"readHeader", IDS_READ_LATER_MENU_READ_HEADER}, - {"title", IDS_READ_LATER_MENU_TITLE}, + {"title", IDS_READ_LATER_TITLE}, {"tooltipDelete", IDS_DELETE}, {"tooltipMarkAsRead", IDS_READ_LATER_MENU_TOOLTIP_MARK_AS_READ}, {"tooltipMarkAsUnread", IDS_READ_LATER_MENU_TOOLTIP_MARK_AS_UNREAD},
diff --git a/chrome/browser/ui/webui/settings/chromeos/account_manager_handler_browsertest.cc b/chrome/browser/ui/webui/settings/chromeos/account_manager_handler_browsertest.cc index aa797a3..3cd2374 100644 --- a/chrome/browser/ui/webui/settings/chromeos/account_manager_handler_browsertest.cc +++ b/chrome/browser/ui/webui/settings/chromeos/account_manager_handler_browsertest.cc
@@ -226,8 +226,9 @@ std::unique_ptr<TestingAccountManagerUIHandler> handler_; }; +// TODO(https://crbug.com/1131834): Re-enable flaky test. IN_PROC_BROWSER_TEST_P(AccountManagerUIHandlerTest, - OnGetAccountsNoSecondaryAccounts) { + DISABLED_OnGetAccountsNoSecondaryAccounts) { const std::vector<AccountManager::Account> account_manager_accounts = GetAccountsFromAccountManager(); // Only Primary account. @@ -270,8 +271,9 @@ } } +// TODO(https://crbug.com/1131819): Re-enable flaky test. IN_PROC_BROWSER_TEST_P(AccountManagerUIHandlerTest, - OnGetAccountsWithSecondaryAccounts) { + DISABLED_OnGetAccountsWithSecondaryAccounts) { UpsertAccount("secondary1@example.com"); UpsertAccount("secondary2@example.com"); const std::vector<AccountManager::Account> account_manager_accounts =
diff --git a/chrome/browser/ui/webui/settings/settings_localized_strings_provider.cc b/chrome/browser/ui/webui/settings/settings_localized_strings_provider.cc index 0bb2f46..85dc34f 100644 --- a/chrome/browser/ui/webui/settings/settings_localized_strings_provider.cc +++ b/chrome/browser/ui/webui/settings/settings_localized_strings_provider.cc
@@ -2177,10 +2177,6 @@ browsing_data::features::kEnableRemovingAllThirdPartyCookies)); html_source->AddBoolean( - "enableInsecureContentContentSetting", - base::FeatureList::IsEnabled(features::kMixedContentSiteSetting)); - - html_source->AddBoolean( "enableStoragePressureUI", base::FeatureList::IsEnabled(features::kStoragePressureUI));
diff --git a/chrome/browser/ui/webui/settings/settings_secure_dns_handler.cc b/chrome/browser/ui/webui/settings/settings_secure_dns_handler.cc index 299fdea..4731bc7 100644 --- a/chrome/browser/ui/webui/settings/settings_secure_dns_handler.cc +++ b/chrome/browser/ui/webui/settings/settings_secure_dns_handler.cc
@@ -24,6 +24,7 @@ #include "content/public/browser/web_ui.h" #include "net/dns/public/dns_over_https_server_config.h" #include "net/dns/public/doh_provider_entry.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/dns/public/util.h" #include "ui/base/l10n/l10n_util.h" @@ -205,7 +206,7 @@ net::DnsConfigOverrides overrides; overrides.search = std::vector<std::string>(); overrides.attempts = 1; - overrides.secure_dns_mode = net::DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = net::SecureDnsMode::kSecure; secure_dns::ApplyTemplate(&overrides, server_template); DCHECK(!runner_); runner_ = std::make_unique<chrome_browser_net::DnsProbeRunner>(
diff --git a/chrome/browser/ui/webui/tab_search/tab_search.mojom b/chrome/browser/ui/webui/tab_search/tab_search.mojom index 7fa6d5f..0750704 100644 --- a/chrome/browser/ui/webui/tab_search/tab_search.mojom +++ b/chrome/browser/ui/webui/tab_search/tab_search.mojom
@@ -19,15 +19,38 @@ // Information about an existing open tab. struct Tab { + // Whether the tab is active. bool active; + + // The index of the tab in the current tab strip. int32 index; + + // The unique identifier of the tab. int32 tab_id; + + // The group identifier of the tab. string? group_id; + + // Whether the tab is pinned. bool pinned; + + // The title of the tab. string title; + + // The URL of the tab. string url; + + // The URL of the favicon in data scheme. + // Only used in OTR profile where chrome://favicon2 is not available. + string? favicon_url; + + // Whether the favicon is the default one. bool is_default_favicon; + + // Whether the tab strip should show the icon. bool show_icon; + + // Time ticks when the tab is last active. mojo_base.mojom.TimeTicks last_active_time_ticks; };
diff --git a/chrome/browser/ui/webui/tab_search/tab_search_page_handler.cc b/chrome/browser/ui/webui/tab_search/tab_search_page_handler.cc index f23e270..e494907d 100644 --- a/chrome/browser/ui/webui/tab_search/tab_search_page_handler.cc +++ b/chrome/browser/ui/webui/tab_search/tab_search_page_handler.cc
@@ -16,6 +16,7 @@ #include "base/trace_event/trace_event.h" #include "chrome/browser/extensions/extension_tab_util.h" #include "chrome/browser/favicon/favicon_utils.h" +#include "chrome/browser/profiles/profile.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_finder.h" #include "chrome/browser/ui/browser_list.h" @@ -32,10 +33,12 @@ TabSearchPageHandler::TabSearchPageHandler( mojo::PendingReceiver<tab_search::mojom::PageHandler> receiver, mojo::PendingRemote<tab_search::mojom::Page> page, + content::WebUI* web_ui, Delegate* delegate) : receiver_(this, std::move(receiver)), page_(std::move(page)), browser_(chrome::FindLastActive()), + web_ui_(web_ui), delegate_(delegate), debounce_timer_(std::make_unique<base::RetainingOneShotTimer>( FROM_HERE, @@ -182,6 +185,12 @@ if (tab_renderer_data.favicon.isNull()) { tab_data->is_default_favicon = true; } else { + // Only send favicon_url for OTR profile where chrome://favicon2 is not + // available. + if (browser_->profile()->IsOffTheRecord()) { + tab_data->favicon_url = webui::EncodePNGAndMakeDataURI( + tab_renderer_data.favicon, web_ui_->GetDeviceScaleFactor()); + } tab_data->is_default_favicon = tab_renderer_data.favicon.BackedBySameObjectAs( favicon::GetDefaultFavicon().AsImageSkia());
diff --git a/chrome/browser/ui/webui/tab_search/tab_search_page_handler.h b/chrome/browser/ui/webui/tab_search/tab_search_page_handler.h index 4b99364..05b13ad 100644 --- a/chrome/browser/ui/webui/tab_search/tab_search_page_handler.h +++ b/chrome/browser/ui/webui/tab_search/tab_search_page_handler.h
@@ -42,6 +42,7 @@ TabSearchPageHandler( mojo::PendingReceiver<tab_search::mojom::PageHandler> receiver, mojo::PendingRemote<tab_search::mojom::Page> page, + content::WebUI* web_ui, Delegate* delegate); TabSearchPageHandler(const TabSearchPageHandler&) = delete; TabSearchPageHandler& operator=(const TabSearchPageHandler&) = delete; @@ -99,6 +100,7 @@ mojo::Receiver<tab_search::mojom::PageHandler> receiver_; mojo::Remote<tab_search::mojom::Page> page_; Browser* const browser_; + content::WebUI* const web_ui_; Delegate* const delegate_; BrowserTabStripTracker browser_tab_strip_tracker_{this, this}; std::unique_ptr<base::RetainingOneShotTimer> debounce_timer_;
diff --git a/chrome/browser/ui/webui/tab_search/tab_search_page_handler_unittest.cc b/chrome/browser/ui/webui/tab_search/tab_search_page_handler_unittest.cc index e933883..68e8127 100644 --- a/chrome/browser/ui/webui/tab_search/tab_search_page_handler_unittest.cc +++ b/chrome/browser/ui/webui/tab_search/tab_search_page_handler_unittest.cc
@@ -60,6 +60,7 @@ EXPECT_FALSE(tab->pinned); EXPECT_EQ(title, tab->title); EXPECT_EQ(url, tab->url); + EXPECT_FALSE(tab->favicon_url.has_value()); EXPECT_TRUE(tab->is_default_favicon); EXPECT_TRUE(tab->show_icon); EXPECT_GT(tab->last_active_time_ticks, base::TimeTicks()); @@ -79,10 +80,12 @@ class TestTabSearchPageHandler : public TabSearchPageHandler { public: TestTabSearchPageHandler(mojo::PendingRemote<tab_search::mojom::Page> page, + content::WebUI* web_ui, TabSearchPageHandler::Delegate* delegate) : TabSearchPageHandler( mojo::PendingReceiver<tab_search::mojom::PageHandler>(), std::move(page), + web_ui, delegate) { mock_debounce_timer_ = new base::MockRetainingOneShotTimer(); SetTimerForTesting(base::WrapUnique(mock_debounce_timer_)); @@ -118,7 +121,7 @@ BrowserList::SetLastActive(browser1()); handler_delegate_ = std::make_unique<MockTabSearchPageHandlerDelegate>(); handler_ = std::make_unique<TestTabSearchPageHandler>( - page_.BindAndGetRemote(), handler_delegate_.get()); + page_.BindAndGetRemote(), web_ui(), handler_delegate_.get()); } void TearDown() override { @@ -357,4 +360,23 @@ handler()->CloseUI(); } +// OTR profile should have a non-empty base64 favicon_url for each tab +TEST_F(TabSearchPageHandlerTest, OTRProfileFaviconTest) { + AddTabWithTitle(browser3(), GURL(kTabUrl1), kTabName1); + BrowserList::SetLastActive(browser3()); + ASSERT_TRUE(browser3()->profile()->IsOffTheRecord()); + tab_search::mojom::PageHandler::GetProfileTabsCallback callback = + base::BindLambdaForTesting( + [&](tab_search::mojom::ProfileTabsPtr profile_tabs) { + ASSERT_EQ(1u, profile_tabs->windows.size()); + auto* window1 = profile_tabs->windows[0].get(); + ASSERT_EQ(1u, window1->tabs.size()); + ASSERT_TRUE(window1->tabs[0]->favicon_url.has_value()); + }); + testing::StrictMock<MockPage> page; + auto handler = std::make_unique<TestTabSearchPageHandler>( + page.BindAndGetRemote(), web_ui(), handler_delegate()); + handler->GetProfileTabs(std::move(callback)); +} + } // namespace
diff --git a/chrome/browser/ui/webui/tab_search/tab_search_ui.cc b/chrome/browser/ui/webui/tab_search/tab_search_ui.cc index cbf0efb..e20cca6 100644 --- a/chrome/browser/ui/webui/tab_search/tab_search_ui.cc +++ b/chrome/browser/ui/webui/tab_search/tab_search_ui.cc
@@ -4,6 +4,7 @@ #include "chrome/browser/ui/webui/tab_search/tab_search_ui.h" +#include "base/numerics/ranges.h" #include "build/branding_buildflags.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/ui/ui_features.h" @@ -57,6 +58,19 @@ "submitFeedbackEnabled", base::FeatureList::IsEnabled(features::kTabSearchFeedback)); + // Add the configuration parameters for fuzzy search. + source->AddBoolean("searchIgnoreLocation", + features::kTabSearchSearchIgnoreLocation.Get()); + source->AddInteger("searchDistance", + features::kTabSearchSearchDistance.Get()); + source->AddDouble( + "searchThreshold", + base::ClampToRange<double>(features::kTabSearchSearchThreshold.Get(), + features::kTabSearchSearchThresholdMin, + features::kTabSearchSearchThresholdMax)); + source->AddDouble("searchTitleToHostnameWeightRatio", + features::kTabSearchTitleToHostnameWeightRatio.Get()); + source->AddLocalizedString("close", IDS_CLOSE); source->AddResourcePath("tab_search.mojom-lite.js", IDR_TAB_SEARCH_MOJO_LITE_JS); @@ -104,6 +118,6 @@ mojo::PendingRemote<tab_search::mojom::Page> page, mojo::PendingReceiver<tab_search::mojom::PageHandler> receiver) { DCHECK(page); - page_handler_ = std::make_unique<TabSearchPageHandler>(std::move(receiver), - std::move(page), this); + page_handler_ = std::make_unique<TabSearchPageHandler>( + std::move(receiver), std::move(page), web_ui(), this); }
diff --git a/chrome/browser/web_applications/extensions/BUILD.gn b/chrome/browser/web_applications/extensions/BUILD.gn index 5b1492d7..83aaf79 100644 --- a/chrome/browser/web_applications/extensions/BUILD.gn +++ b/chrome/browser/web_applications/extensions/BUILD.gn
@@ -4,6 +4,13 @@ import("//extensions/buildflags/buildflags.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + assert(enable_extensions) source_set("extensions") {
diff --git a/chrome/common/chrome_features.cc b/chrome/common/chrome_features.cc index 07c6ee02..c8ba97b 100644 --- a/chrome/common/chrome_features.cc +++ b/chrome/common/chrome_features.cc
@@ -269,8 +269,15 @@ "DesktopPWAsWithoutExtensions", base::FEATURE_ENABLED_BY_DEFAULT}; // Enable DNS over HTTPS (DoH). -const base::Feature kDnsOverHttps{"DnsOverHttps", - base::FEATURE_DISABLED_BY_DEFAULT}; +const base::Feature kDnsOverHttps { + "DnsOverHttps", +#if defined(OS_WIN) || defined(OS_CHROMEOS) || defined(OS_MAC) || \ + defined(OS_ANDROID) + base::FEATURE_ENABLED_BY_DEFAULT +#else + base::FEATURE_DISABLED_BY_DEFAULT +#endif +}; // Provides a mechanism to remove providers from the dropdown list in the // settings UI. Separate multiple provider ids with commas. See the @@ -284,8 +291,15 @@ "Fallback", true}; // Sets whether the DoH setting is displayed in the settings UI. -const base::FeatureParam<bool> kDnsOverHttpsShowUiParam{&kDnsOverHttps, - "ShowUi", false}; +const base::FeatureParam<bool> kDnsOverHttpsShowUiParam { + &kDnsOverHttps, "ShowUi", +#if defined(OS_WIN) || defined(OS_CHROMEOS) || defined(OS_MAC) || \ + defined(OS_ANDROID) + true +#else + false +#endif +}; // Supply one or more space-separated DoH server URI templates to use when this // feature is enabled. If no templates are specified, then a hardcoded mapping @@ -520,13 +534,6 @@ base::FEATURE_DISABLED_BY_DEFAULT}; #endif -// Enables showing an entry for mixed content in site settings, which controls -// allowing blockable mixed content. When enabled, the mixed content shield is -// not shown on the omnibox, since its functionality is replaced by the -// setting. -const base::Feature kMixedContentSiteSetting{"MixedContentSiteSetting", - base::FEATURE_ENABLED_BY_DEFAULT}; - // Enables the use of native notification centers instead of using the Message // Center for displaying the toasts. The feature is hardcoded to enabled for // Chrome OS.
diff --git a/chrome/common/chrome_features.h b/chrome/common/chrome_features.h index 4132845b..24de7b8 100644 --- a/chrome/common/chrome_features.h +++ b/chrome/common/chrome_features.h
@@ -340,9 +340,6 @@ extern const base::Feature kMeteredShowToggle; #endif -COMPONENT_EXPORT(CHROME_FEATURES) -extern const base::Feature kMixedContentSiteSetting; - #if BUILDFLAG(ENABLE_NATIVE_NOTIFICATIONS) COMPONENT_EXPORT(CHROME_FEATURES) extern const base::Feature kNativeNotifications;
diff --git a/chrome/renderer/chrome_content_settings_agent_delegate.cc b/chrome/renderer/chrome_content_settings_agent_delegate.cc index 0c4dcfb..1517bc6 100644 --- a/chrome/renderer/chrome_content_settings_agent_delegate.cc +++ b/chrome/renderer/chrome_content_settings_agent_delegate.cc
@@ -107,32 +107,6 @@ return base::nullopt; } -base::Optional<bool> -ChromeContentSettingsAgentDelegate::AllowRunningInsecureContent( - bool allowed_per_settings, - const blink::WebURL& resource_url) { - // Note: this implementation is a mirror of - // Browser::ShouldAllowRunningInsecureContent. - FilteredReportInsecureContentRan(GURL(resource_url)); - - // TODO(crbug.com/987294): We may want to move this logic into - // ContentSettingsAgentImpl once this feature is launched. - if (base::FeatureList::IsEnabled(features::kMixedContentSiteSetting)) { - bool allow = allowed_per_settings; - auto* agent = - content_settings::ContentSettingsAgentImpl::Get(render_frame_); - if (agent->GetContentSettingRules()) { - auto setting = agent->GetContentSettingFromRules( - agent->GetContentSettingRules()->mixed_content_rules, - render_frame_->GetWebFrame(), GURL()); - allow |= (setting == CONTENT_SETTING_ALLOW); - } - return allow; - } - - return base::nullopt; -} - void ChromeContentSettingsAgentDelegate::PassiveInsecureContentFound( const blink::WebURL& resource_url) { // Note: this implementation is a mirror of
diff --git a/chrome/renderer/chrome_content_settings_agent_delegate.h b/chrome/renderer/chrome_content_settings_agent_delegate.h index b56cc2c..065ea60 100644 --- a/chrome/renderer/chrome_content_settings_agent_delegate.h +++ b/chrome/renderer/chrome_content_settings_agent_delegate.h
@@ -38,9 +38,6 @@ base::Optional<bool> AllowReadFromClipboard() override; base::Optional<bool> AllowWriteToClipboard() override; base::Optional<bool> AllowMutationEvents() override; - base::Optional<bool> AllowRunningInsecureContent( - bool allowed_per_settings, - const blink::WebURL& resource_url) override; void PassiveInsecureContentFound(const blink::WebURL&) override; private:
diff --git a/chrome/services/file_util/public/cpp/BUILD.gn b/chrome/services/file_util/public/cpp/BUILD.gn index 028b888..f40bcafe 100644 --- a/chrome/services/file_util/public/cpp/BUILD.gn +++ b/chrome/services/file_util/public/cpp/BUILD.gn
@@ -5,6 +5,13 @@ import("//build/config/features.gni") import("//components/safe_browsing/buildflags.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + source_set("cpp") { deps = [ "//chrome/common/safe_browsing:archive_analyzer_results" ] public_deps = [ "//chrome/services/file_util/public/mojom" ]
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn index 3b052e1..343d1c74 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn
@@ -4550,6 +4550,7 @@ # NTP is in native code on Android. "../browser/search/ntp_features_unittest.cc", + "../browser/search/shopping_tasks/shopping_tasks_service_unittest.cc", ] if (is_posix || is_fuchsia) { sources += [ "../browser/process_singleton_posix_unittest.cc" ]
diff --git a/chrome/test/chromedriver/BUILD.gn b/chrome/test/chromedriver/BUILD.gn index f4eed63..f99e0c6 100644 --- a/chrome/test/chromedriver/BUILD.gn +++ b/chrome/test/chromedriver/BUILD.gn
@@ -215,6 +215,7 @@ "command_listener_proxy.h", "commands.cc", "commands.h", + "connection_session_map.h", "constants/version.h", "devtools_events_logger.cc", "devtools_events_logger.h",
diff --git a/chrome/test/chromedriver/client/websocket_connection.py b/chrome/test/chromedriver/client/websocket_connection.py index 85bf699..494e16d 100644 --- a/chrome/test/chromedriver/client/websocket_connection.py +++ b/chrome/test/chromedriver/client/websocket_connection.py
@@ -19,7 +19,7 @@ class WebSocketCommands: CREATE_WEBSOCKET = \ - '/session/:sessionId/chromium/create_websocket' + '/session/:sessionId' SEND_OVER_WEBSOCKET = \ '/session/:sessionId/chromium/send_command_from_websocket' @@ -37,3 +37,6 @@ cmd_params['id'] = self._command_id self._command_id -= 1 self._websocket.send(json.dumps(cmd_params)) + + def Close(self): + self._websocket.close();
diff --git a/chrome/test/chromedriver/connection_session_map.h b/chrome/test/chromedriver/connection_session_map.h new file mode 100644 index 0000000..aa3be8ed --- /dev/null +++ b/chrome/test/chromedriver/connection_session_map.h
@@ -0,0 +1,13 @@ +// Copyright 2020 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_TEST_CHROMEDRIVER_CONNECTION_SESSION_MAP_H_ +#define CHROME_TEST_CHROMEDRIVER_CONNECTION_SESSION_MAP_H_ + +#include <string> +#include <unordered_map> + +using ConnectionSessionMap = std::unordered_map<int, std::string>; + +#endif // CHROME_TEST_CHROMEDRIVER_CONNECTION_SESSION_MAP_H_
diff --git a/chrome/test/chromedriver/server/http_handler.cc b/chrome/test/chromedriver/server/http_handler.cc index bdece95c..de5d68c 100644 --- a/chrome/test/chromedriver/server/http_handler.cc +++ b/chrome/test/chromedriver/server/http_handler.cc
@@ -66,6 +66,13 @@ return kW3CDefault; } +net::HttpServerResponseInfo createWebSocketRejectResponse( + net::HttpStatusCode code, + const std::string& msg) { + net::HttpServerResponseInfo response(code); + response.AddHeader("X-WebSocket-Reject-Reason", msg); + return response; +} } // namespace // WrapperURLLoaderFactory subclasses mojom::URLLoaderFactory as non-mojo, cross @@ -143,14 +150,17 @@ const scoped_refptr<base::SingleThreadTaskRunner> cmd_task_runner, const std::string& url_base, int adb_port) - : quit_func_(quit_func), url_base_(url_base), received_shutdown_(false) { + : quit_func_(quit_func), + io_task_runner_(io_task_runner), + url_base_(url_base), + received_shutdown_(false) { #if defined(OS_MAC) base::mac::ScopedNSAutoreleasePool autorelease_pool; #endif - context_getter_ = new URLRequestContextGetter(io_task_runner); + context_getter_ = new URLRequestContextGetter(io_task_runner_); socket_factory_ = CreateSyncWebSocketFactory(context_getter_.get()); - adb_.reset(new AdbImpl(io_task_runner, adb_port)); - device_manager_.reset(new DeviceManager(adb_.get())); + adb_ = std::make_unique<AdbImpl>(io_task_runner_, adb_port); + device_manager_ = std::make_unique<DeviceManager>(adb_.get()); url_loader_factory_owner_ = std::make_unique<network::TransitionalURLLoaderFactoryOwner>( context_getter_.get()); @@ -1296,10 +1306,67 @@ return response; } -void HttpHandler::OnWebSocketRequest(int connection_id, - const net::HttpServerRequestInfo& info) {} +void HttpHandler::OnWebSocketRequest(HttpServer* http_server, + int connection_id, + const net::HttpServerRequestInfo& info) { + std::string path = info.path; -void HttpHandler::OnClose(int connection_id) {} + std::vector<std::string> path_parts = base::SplitString( + path, "/", base::TRIM_WHITESPACE, base::SPLIT_WANT_NONEMPTY); + + if (path_parts.size() != 2 || path_parts[0] != "session") { + std::string err_msg = "bad request received path " + path; + VLOG(0) << "HttpHandler WebSocketRequest error " << err_msg; + SendWebSocketRejectResponse(http_server, connection_id, + net::HTTP_BAD_REQUEST, err_msg); + return; + } + + std::string session_id = path_parts[1]; + auto it = session_connection_map_.find(session_id); + if (it == session_connection_map_.end()) { + std::string err_msg = "bad request invalid session id " + session_id; + VLOG(0) << "HttpHandler WebSocketRequest error " << err_msg; + SendWebSocketRejectResponse(http_server, connection_id, + net::HTTP_BAD_REQUEST, err_msg); + return; + } else if (it->second != -1) { + std::string err_msg = "bad request only one connection for session id " + + session_id + " is allowed"; + VLOG(0) << "HttpHandler WebSocketRequest error " << err_msg; + SendWebSocketRejectResponse(http_server, connection_id, + net::HTTP_BAD_REQUEST, err_msg); + return; + } else { + session_connection_map_[session_id] = connection_id; + connection_session_map_[connection_id] = session_id; + io_task_runner_->PostTask( + FROM_HERE, + base::BindOnce(&HttpServer::AcceptWebSocket, + base::Unretained(http_server), connection_id, info)); + } +} + +void HttpHandler::OnClose(HttpServer* http_server, int connection_id) { + auto it = connection_session_map_.find(connection_id); + if (it == connection_session_map_.end()) { + return; + } + session_connection_map_[it->second] = -1; + connection_session_map_.erase(it); +} + +void HttpHandler::SendWebSocketRejectResponse(HttpServer* http_server, + int connection_id, + net::HttpStatusCode code, + const std::string& msg) { + io_task_runner_->PostTask( + FROM_HERE, + base::BindOnce(&HttpServer::SendResponse, base::Unretained(http_server), + connection_id, + createWebSocketRejectResponse(net::HTTP_BAD_REQUEST, msg), + TRAFFIC_ANNOTATION_FOR_TESTS)); +} namespace internal {
diff --git a/chrome/test/chromedriver/server/http_handler.h b/chrome/test/chromedriver/server/http_handler.h index 6595551..14b3d780 100644 --- a/chrome/test/chromedriver/server/http_handler.h +++ b/chrome/test/chromedriver/server/http_handler.h
@@ -18,12 +18,14 @@ #include "base/threading/thread_checker.h" #include "chrome/test/chromedriver/command.h" #include "chrome/test/chromedriver/commands.h" +#include "chrome/test/chromedriver/connection_session_map.h" #include "chrome/test/chromedriver/element_commands.h" #include "chrome/test/chromedriver/net/sync_websocket_factory.h" #include "chrome/test/chromedriver/session_commands.h" #include "chrome/test/chromedriver/session_connection_map.h" #include "chrome/test/chromedriver/session_thread_map.h" #include "chrome/test/chromedriver/window_commands.h" +#include "net/http/http_status_code.h" namespace base { class DictionaryValue; @@ -127,13 +129,20 @@ std::unique_ptr<base::Value> value, const std::string& session_id); - void OnWebSocketRequest(int connection_id, + void OnWebSocketRequest(HttpServer* http_server, + int connection_id, const net::HttpServerRequestInfo& info); - void OnClose(int connection_id); + void OnClose(HttpServer* http_server, int connection_id); + + void SendWebSocketRejectResponse(HttpServer* http_server, + int connection_id, + net::HttpStatusCode code, + const std::string& msg); base::ThreadChecker thread_checker_; base::RepeatingClosure quit_func_; + scoped_refptr<base::SingleThreadTaskRunner> io_task_runner_; std::string url_base_; bool received_shutdown_; scoped_refptr<URLRequestContextGetter> context_getter_; @@ -143,6 +152,7 @@ SyncWebSocketFactory socket_factory_; SessionThreadMap session_thread_map_; SessionConnectionMap session_connection_map_; + ConnectionSessionMap connection_session_map_; std::unique_ptr<CommandMap> command_map_; std::unique_ptr<Adb> adb_; std::unique_ptr<DeviceManager> device_manager_;
diff --git a/chrome/test/chromedriver/server/http_server.cc b/chrome/test/chromedriver/server/http_server.cc index a6b0575..8b02d15e 100644 --- a/chrome/test/chromedriver/server/http_server.cc +++ b/chrome/test/chromedriver/server/http_server.cc
@@ -133,69 +133,31 @@ const net::HttpServerRequestInfo& info) { cmd_runner_->PostTask( FROM_HERE, base::BindOnce(&HttpHandler::OnWebSocketRequest, handler_, - connection_id, info)); - - std::string path = info.path; - std::string session_id; - - if (!base::StartsWith(path, url_base_, base::CompareCase::SENSITIVE)) { - net::HttpServerResponseInfo response(net::HTTP_BAD_REQUEST); - response.SetBody("invalid websocket request url path", "text/plain"); - server_->SendResponse(connection_id, response, - TRAFFIC_ANNOTATION_FOR_TESTS); - return; - } - path.erase(0, url_base_.length()); - - std::vector<std::string> path_parts = - base::SplitString(path, "/", base::TRIM_WHITESPACE, base::SPLIT_WANT_ALL); - std::vector<std::string> command_path_parts = base::SplitString( - kCreateWebSocketPath, "/", base::TRIM_WHITESPACE, base::SPLIT_WANT_ALL); - - if (path_parts.size() != command_path_parts.size()) { - net::HttpServerResponseInfo response(net::HTTP_BAD_REQUEST); - response.SetBody("invalid websocket request url path", "text/plain"); - server_->SendResponse(connection_id, response, - TRAFFIC_ANNOTATION_FOR_TESTS); - return; - } - - for (size_t i = 0; i < path_parts.size(); ++i) { - if (command_path_parts[i][0] == ':') { - std::string name = command_path_parts[i]; - name.erase(0, 1); - CHECK(name.length()); - if (name == "sessionId") - session_id = path_parts[i]; - } else if (command_path_parts[i] != path_parts[i]) { - net::HttpServerResponseInfo response(net::HTTP_BAD_REQUEST); - response.SetBody("invalid websocket request url path", "text/plain"); - server_->SendResponse(connection_id, response, - TRAFFIC_ANNOTATION_FOR_TESTS); - return; - } - } - - server_->AcceptWebSocket(connection_id, info, TRAFFIC_ANNOTATION_FOR_TESTS); - connection_to_session_map[connection_id] = session_id; + this, connection_id, info)); } void HttpServer::OnWebSocketMessage(int connection_id, std::string data) { - base::Optional<base::Value> parsed_data = base::JSONReader::Read(data); - std::string path = url_base_ + kSendCommandFromWebSocket; - base::ReplaceFirstSubstringAfterOffset( - &path, 0, ":sessionId", connection_to_session_map[connection_id]); - - net::HttpServerRequestInfo request; - request.method = "post"; - request.path = path; - request.data = data; - OnHttpRequest(connection_id, request); + // TODO: Make use of WebSocket data + VLOG(0) << "HttpServer::OnWebSocketMessage received: " << data; } void HttpServer::OnClose(int connection_id) { - cmd_runner_->PostTask(FROM_HERE, base::BindOnce(&HttpHandler::OnClose, - handler_, connection_id)); + cmd_runner_->PostTask( + FROM_HERE, + base::BindOnce(&HttpHandler::OnClose, handler_, this, connection_id)); +} + +void HttpServer::AcceptWebSocket(int connection_id, + const net::HttpServerRequestInfo& request) { + server_->AcceptWebSocket(connection_id, request, + TRAFFIC_ANNOTATION_FOR_TESTS); +} + +void HttpServer::SendResponse( + int connection_id, + const net::HttpServerResponseInfo& response, + const net::NetworkTrafficAnnotationTag& traffic_annotation) { + server_->SendResponse(connection_id, response, traffic_annotation); } void HttpServer::OnResponse(
diff --git a/chrome/test/chromedriver/server/http_server.h b/chrome/test/chromedriver/server/http_server.h index c3fde562..72482b2 100644 --- a/chrome/test/chromedriver/server/http_server.h +++ b/chrome/test/chromedriver/server/http_server.h
@@ -43,6 +43,13 @@ void OnClose(int connection_id) override; + void AcceptWebSocket(int connection_id, + const net::HttpServerRequestInfo& request); + + void SendResponse(int connection_id, + const net::HttpServerResponseInfo& response, + const net::NetworkTrafficAnnotationTag& traffic_annotation); + private: void OnResponse(int connection_id, bool keep_alive,
diff --git a/chrome/test/chromedriver/test/run_py_tests.py b/chrome/test/chromedriver/test/run_py_tests.py index 90d471199..7fa258e 100755 --- a/chrome/test/chromedriver/test/run_py_tests.py +++ b/chrome/test/chromedriver/test/run_py_tests.py
@@ -45,6 +45,7 @@ sys.path.insert(1, _CLIENT_DIR) import chromedriver +import websocket_connection import webelement sys.path.remove(_CLIENT_DIR) @@ -98,6 +99,7 @@ 'ChromeDownloadDirTest.testFileDownloadAfterTabHeadless', 'ChromeDownloadDirTest.testFileDownloadWithClickHeadless', 'ChromeDownloadDirTest.testFileDownloadWithGetHeadless', + 'RemoteBrowserTest.testConnectToRemoteBrowserLiteralAddressHeadless', # HeadlessInvalidCertificateTest is sometimes flaky. 'HeadlessInvalidCertificateTest.*', # Similar issues with HeadlessChromeDriverTest. @@ -512,10 +514,14 @@ def testDefaultSession(self): driver = self.CreateDriver() self.assertFalse(driver.capabilities.has_key('webSocketUrl')) + self.assertRaises(Exception, websocket_connection.WebSocketConnection, + _CHROMEDRIVER_SERVER_URL, driver.GetSessionId()) def testWebSocketUrlFalse(self): driver = self.CreateDriver(web_socket_url=False) self.assertFalse(driver.capabilities.has_key('webSocketUrl')) + self.assertRaises(Exception, websocket_connection.WebSocketConnection, + _CHROMEDRIVER_SERVER_URL, driver.GetSessionId()) def testWebSocketUrlTrue(self): driver = self.CreateDriver(web_socket_url=True) @@ -524,11 +530,37 @@ self.assertEquals(driver.capabilities['webSocketUrl'], self.composeWebSocketUrl(_CHROMEDRIVER_SERVER_URL, driver.GetSessionId())) + websocket = websocket_connection.WebSocketConnection( + _CHROMEDRIVER_SERVER_URL, driver.GetSessionId()) + self.assertNotEqual(None, websocket) def testWebSocketUrlInvalid(self): self.assertRaises(chromedriver.InvalidArgument, self.CreateDriver, web_socket_url='Invalid') + def testWebSocketOneConnectionPerSession(self): + driver = self.CreateDriver(web_socket_url=True) + websocket = websocket_connection.WebSocketConnection( + _CHROMEDRIVER_SERVER_URL, driver.GetSessionId()) + self.assertNotEqual(None, websocket) + self.assertRaises(Exception, websocket_connection.WebSocketConnection, + _CHROMEDRIVER_SERVER_URL, driver.GetSessionId()) + + def testWebSocketInvalidSessionId(self): + driver = self.CreateDriver(web_socket_url=True) + self.assertRaises(Exception, websocket_connection.WebSocketConnection, + _CHROMEDRIVER_SERVER_URL, "random_session_id_123") + + def testWebSocketClosedCanReconnect(self): + driver = self.CreateDriver(web_socket_url=True) + websocket = websocket_connection.WebSocketConnection( + _CHROMEDRIVER_SERVER_URL, driver.GetSessionId()) + self.assertNotEqual(None, websocket) + websocket.Close() + websocket2 = websocket_connection.WebSocketConnection( + _CHROMEDRIVER_SERVER_URL, driver.GetSessionId()) + self.assertNotEqual(None, websocket2) + class ChromeDriverTest(ChromeDriverBaseTestWithWebServer): """End to end tests for ChromeDriver.""" @@ -4283,6 +4315,50 @@ else: # Else clause gets invoked if "break" never happens. raise # This re-raises the most recent exception. + def testConnectToRemoteBrowserLiteralAddressHeadless(self): + debug_addrs = ['127.0.0.1', '::1'] + debug_url_addrs = ['127.0.0.1', '[::1]'] + + for (debug_addr, debug_url_addr) in zip(debug_addrs, debug_url_addrs): + # Must use retries since there is an inherent race condition in port + # selection. + ports_generator = util.FindProbableFreePorts() + for _ in range(3): + port = ports_generator.next() + temp_dir = util.MakeTempDir() + print 'temp dir is ' + temp_dir + cmd = [_CHROME_BINARY, + '--headless', + '--remote-debugging-address=%s' % debug_addr, + '--remote-debugging-port=%d' % port, + '--user-data-dir=%s' % temp_dir, + '--use-mock-keychain'] + process = subprocess.Popen(cmd) + try: + driver = self.CreateDriver( + debugger_address='%s:%d' % (debug_url_addr, port)) + driver.ExecuteScript( + 'console.info("%s")' % 'connecting at %d!' % port) + driver.Quit() + except: + continue + finally: + if process.poll() is None: + process.terminate() + # Wait for Chrome to exit here to prevent a race with Chrome to + # delete/modify the temporary user-data-dir. + # Maximum wait ~1 second. + for _ in range(20): + if process.poll() is not None: + break + print 'continuing to wait for Chrome to exit' + time.sleep(.05) + else: + process.kill() + break + else: # Else clause gets invoked if "break" never happens. + raise # This re-raises the most recent exception. + class LaunchDesktopTest(ChromeDriverBaseTest): """Tests that launching desktop Chrome works."""
diff --git a/chrome/test/data/policy/policy_test_cases.json b/chrome/test/data/policy/policy_test_cases.json index a684940..02009bab5 100644 --- a/chrome/test/data/policy/policy_test_cases.json +++ b/chrome/test/data/policy/policy_test_cases.json
@@ -1761,7 +1761,7 @@ }, "DefaultSearchProviderEnabled": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { "DefaultSearchProviderEnabled": false }, @@ -1779,7 +1779,7 @@ }, "DefaultSearchProviderName": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1794,7 +1794,7 @@ }, "DefaultSearchProviderKeyword": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1808,7 +1808,7 @@ }, "DefaultSearchProviderSearchURL": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1822,7 +1822,7 @@ }, "DefaultSearchProviderSuggestURL": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1841,7 +1841,7 @@ }, "DefaultSearchProviderNewTabURL": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1856,7 +1856,7 @@ }, "DefaultSearchProviderIconURL": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1871,7 +1871,7 @@ }, "DefaultSearchProviderEncodings": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1888,7 +1888,7 @@ }, "DefaultSearchProviderAlternateURLs": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1910,7 +1910,7 @@ }, "DefaultSearchProviderImageURL": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1925,7 +1925,7 @@ }, "DefaultSearchProviderSearchURLPostParams": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1940,7 +1940,7 @@ }, "DefaultSearchProviderSuggestURLPostParams": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": { @@ -1959,7 +1959,7 @@ }, "DefaultSearchProviderImageURLPostParams": { - "os": ["win", "linux", "mac", "chromeos"], + "os": ["win", "linux", "mac", "chromeos", "android"], "policy_pref_mapping_test": [ { "policies": {
diff --git a/chrome/test/data/webui/BUILD.gn b/chrome/test/data/webui/BUILD.gn index 6e5b36f9..ae3d10e 100644 --- a/chrome/test/data/webui/BUILD.gn +++ b/chrome/test/data/webui/BUILD.gn
@@ -301,6 +301,7 @@ "$root_gen_dir/chrome/test/data/webui/settings/chromeos/multidevice_subpage_tests.m.js", "$root_gen_dir/chrome/test/data/webui/settings/chromeos/nearby_share_receive_dialog_tests.m.js", "$root_gen_dir/chrome/test/data/webui/settings/chromeos/nearby_share_subpage_tests.m.js", + "$root_gen_dir/chrome/test/data/webui/settings/chromeos/network_proxy_section_test.m.js", "$root_gen_dir/chrome/test/data/webui/settings/chromeos/os_edit_dictionary_page_test.m.js", "$root_gen_dir/chrome/test/data/webui/settings/chromeos/os_languages_page_tests.m.js", "$root_gen_dir/chrome/test/data/webui/settings/chromeos/os_languages_page_v2_tests.m.js",
diff --git a/chrome/test/data/webui/chromeos/diagnostics/diagnostics_test.js b/chrome/test/data/webui/chromeos/diagnostics/diagnostics_test.js index c7d8a44..d0033a5f 100644 --- a/chrome/test/data/webui/chromeos/diagnostics/diagnostics_test.js +++ b/chrome/test/data/webui/chromeos/diagnostics/diagnostics_test.js
@@ -4,7 +4,11 @@ // TODO(jimmyxgong): Use es6 module for mojo binding (crbug/1004256). import 'chrome://resources/mojo/mojo/public/js/mojo_bindings_lite.js'; +import 'chrome://diagnostics/battery_status_card.js'; +import 'chrome://diagnostics/cpu_card.js'; import 'chrome://diagnostics/diagnostics_app.js'; +import 'chrome://diagnostics/memory_card.js'; +import 'chrome://diagnostics/overview_card.js'; import {SystemDataProviderInterface} from 'chrome://diagnostics/diagnostics_types.js'; import {fakeBatteryChargeStatus, fakeBatteryHealth, fakeBatteryInfo, fakeCpuUsage, fakeMemoryUsage, fakeSystemInfo} from 'chrome://diagnostics/fake_data.js';
diff --git a/chrome/test/data/webui/settings/chromeos/BUILD.gn b/chrome/test/data/webui/settings/chromeos/BUILD.gn index 6d5782a..b009cfe5 100644 --- a/chrome/test/data/webui/settings/chromeos/BUILD.gn +++ b/chrome/test/data/webui/settings/chromeos/BUILD.gn
@@ -53,6 +53,7 @@ "multidevice_subpage_tests.js", "nearby_share_receive_dialog_tests.js", "nearby_share_subpage_tests.js", + "network_proxy_section_test.js", "os_edit_dictionary_page_test.js", "os_languages_page_tests.js", "os_languages_page_v2_tests.js",
diff --git a/chrome/test/data/webui/settings/chromeos/network_proxy_section_test.js b/chrome/test/data/webui/settings/chromeos/network_proxy_section_test.js new file mode 100644 index 0000000..78b390a --- /dev/null +++ b/chrome/test/data/webui/settings/chromeos/network_proxy_section_test.js
@@ -0,0 +1,63 @@ +// Copyright 2020 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. + +// clang-format off +// #import 'chrome://os-settings/chromeos/os_settings.js'; + +// #import {flush} from 'chrome://resources/polymer/v3_0/polymer/polymer_bundled.min.js'; +// clang-format on + +suite('NetworkProxySection', function() { + /** @type {!NetworkProxySectionElement|undefined} */ + let proxySection; + + setup(function() { + proxySection = document.createElement('network-proxy-section'); + proxySection.prefs = { + // prefs.settings.use_shared_proxies is set by the proxy service in CrOS, + // which does not run in the browser_tests environment. + 'settings': { + 'use_shared_proxies': { + key: 'use_shared_proxies', + type: chrome.settingsPrivate.PrefType.BOOLEAN, + value: true, + }, + }, + }; + document.body.appendChild(proxySection); + Polymer.dom.flush(); + }); + + test('Visibility of Allow Shared toggle', function() { + const mojom = chromeos.networkConfig.mojom; + + const allowSharedToggle = proxySection.$.allowShared; + assertTrue(!!allowSharedToggle); + + proxySection.managedProperties = { + source: mojom.OncSource.kNone, + }; + assertTrue(allowSharedToggle.hidden); + + proxySection.managedProperties = { + source: mojom.OncSource.kDevice, + }; + assertFalse(allowSharedToggle.hidden); + + proxySection.managedProperties = { + source: mojom.OncSource.kDevicePolicy, + }; + assertFalse(allowSharedToggle.hidden); + + proxySection.managedProperties = { + source: mojom.OncSource.kUser, + }; + assertTrue(allowSharedToggle.hidden); + + proxySection.managedProperties = { + source: mojom.OncSource.kUserPolicy, + }; + assertTrue(allowSharedToggle.hidden); + }); +});
diff --git a/chrome/test/data/webui/settings/chromeos/os_languages_page_v2_tests.js b/chrome/test/data/webui/settings/chromeos/os_languages_page_v2_tests.js index 95016b3..b4b14cc 100644 --- a/chrome/test/data/webui/settings/chromeos/os_languages_page_v2_tests.js +++ b/chrome/test/data/webui/settings/chromeos/os_languages_page_v2_tests.js
@@ -525,3 +525,51 @@ }); }); }); + +suite('change device language button', () => { + test('is hidden for guest users', () => { + loadTimeData.overrideValues({ + isGuest: true, + }); + const page = document.createElement('os-settings-languages-page-v2'); + document.body.appendChild(page); + Polymer.dom.flush(); + + assertFalse(!!page.$$('#changeDeviceLanguage')); + assertFalse(!!page.$$('#changeDeviceLanguagePolicyIndicator')); + }); + + test('is disabled for secondary users', () => { + loadTimeData.overrideValues( + {isGuest: false, isSecondaryUser: true, primaryUserEmail: 'test.com'}); + const page = document.createElement('os-settings-languages-page-v2'); + document.body.appendChild(page); + Polymer.dom.flush(); + + const changeDeviceLanguageButton = page.$$('#changeDeviceLanguage'); + assertTrue(changeDeviceLanguageButton.disabled); + assertFalse(changeDeviceLanguageButton.hidden); + + const changeDeviceLanguagePolicyIndicator = + page.$$('#changeDeviceLanguagePolicyIndicator'); + assertFalse(changeDeviceLanguagePolicyIndicator.hidden); + assertEquals( + 'test.com', changeDeviceLanguagePolicyIndicator.indicatorSourceName); + }); + + test('is enabled for primary users', () => { + loadTimeData.overrideValues({ + isGuest: false, + isSecondaryUser: false, + }); + const page = document.createElement('os-settings-languages-page-v2'); + document.body.appendChild(page); + Polymer.dom.flush(); + + const changeDeviceLanguageButton = page.$$('#changeDeviceLanguage'); + assertFalse(changeDeviceLanguageButton.disabled); + assertFalse(changeDeviceLanguageButton.hidden); + + assertFalse(!!page.$$('#changeDeviceLanguagePolicyIndicator')); + }); +});
diff --git a/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js b/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js index dc7fb57..cb33b9f 100644 --- a/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js +++ b/chrome/test/data/webui/settings/chromeos/os_settings_browsertest.js
@@ -1172,6 +1172,22 @@ mocha.run(); }); +// Test fixture for settings-internet-detail-page. +// eslint-disable-next-line no-var +var OSSettingsNetworkProxySectionTest = class extends OSSettingsBrowserTest { + /** @override */ + get extraLibraries() { + return super.extraLibraries.concat([ + BROWSER_SETTINGS_PATH + '../chromeos/fake_network_config_mojom.js', + 'network_proxy_section_test.js', + ]); + } +}; + +TEST_F('OSSettingsNetworkProxySectionTest', 'All', () => { + mocha.run(); +}); + // eslint-disable-next-line no-var var OSSettingsPeoplePageAccountManagerTest = class extends OSSettingsBrowserTest {
diff --git a/chrome/test/data/webui/settings/chromeos/os_settings_v3_browsertest.js b/chrome/test/data/webui/settings/chromeos/os_settings_v3_browsertest.js index 7299c010..50bce1be 100644 --- a/chrome/test/data/webui/settings/chromeos/os_settings_v3_browsertest.js +++ b/chrome/test/data/webui/settings/chromeos/os_settings_v3_browsertest.js
@@ -104,6 +104,7 @@ ['MultidevicePage', 'multidevice_page_tests.m.js'], ['MultideviceSmartLockSubPage', 'multidevice_smartlock_subpage_test.m.js'], ['MultideviceSubPage', 'multidevice_subpage_tests.m.js'], + ['NetworkProxySection', 'network_proxy_section_test.m.js'], ['OsEditDictionaryPage', 'os_edit_dictionary_page_test.m.js'], ['OsLanguagesPage', 'os_languages_page_tests.m.js'], ['NearbyShareReceiveDialog', 'nearby_share_receive_dialog_tests.m.js'],
diff --git a/chrome/test/data/webui/settings/site_details_tests.js b/chrome/test/data/webui/settings/site_details_tests.js index a2b25bd..8be1020 100644 --- a/chrome/test/data/webui/settings/site_details_tests.js +++ b/chrome/test/data/webui/settings/site_details_tests.js
@@ -219,8 +219,6 @@ optionalSiteDetailsContentSettingsTypes[ContentSettingsTypes .WINDOW_PLACEMENT] = 'enableExperimentalWebPlatformFeatures'; - optionalSiteDetailsContentSettingsTypes[ContentSettingsTypes.MIXEDSCRIPT] = - 'enableInsecureContentContentSetting'; optionalSiteDetailsContentSettingsTypes[ContentSettingsTypes .FILE_SYSTEM_WRITE] = 'enableFileSystemWriteContentSetting'; @@ -238,7 +236,6 @@ const controlledSettingsCount = /** @type{string : int } */ ({}); controlledSettingsCount['enableExperimentalWebPlatformFeatures'] = 2; - controlledSettingsCount['enableInsecureContentContentSetting'] = 1; controlledSettingsCount['enableFileSystemWriteContentSetting'] = 1; controlledSettingsCount['enableFontAccessContentSetting'] = 1; controlledSettingsCount['enablePaymentHandlerContentSetting'] = 1; @@ -370,7 +367,6 @@ // Make sure all the possible content settings are shown for this test. loadTimeData.overrideValues({ enableExperimentalWebPlatformFeatures: true, - enableInsecureContentContentSetting: true, enableFileSystemWriteContentSetting: true, enableFontAccessContentSetting: true, enablePaymentHandlerContentSetting: true,
diff --git a/chromecast/app/BUILD.gn b/chromecast/app/BUILD.gn index 17cf2a2..231b3f31 100644 --- a/chromecast/app/BUILD.gn +++ b/chromecast/app/BUILD.gn
@@ -6,6 +6,13 @@ import("//testing/test.gni") import("//tools/grit/grit_rule.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + cast_source_set("app") { sources = [ "cast_main_delegate.cc",
diff --git a/chromecast/base/BUILD.gn b/chromecast/base/BUILD.gn index cc3d792f..fe8ebd7 100644 --- a/chromecast/base/BUILD.gn +++ b/chromecast/base/BUILD.gn
@@ -10,6 +10,13 @@ import("//build/config/android/rules.gni") } +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + declare_args() { # Denotes the type of Cast product. This is #defined as CAST_PRODUCT_TYPE in # version.h. See //third_party/metrics_proto/cast_logs.proto for valid values.
diff --git a/chromecast/browser/android/apk/src/org/chromium/chromecast/shell/CastWebContentsScopes.java b/chromecast/browser/android/apk/src/org/chromium/chromecast/shell/CastWebContentsScopes.java index b815e33..8508ffc1 100644 --- a/chromecast/browser/android/apk/src/org/chromium/chromecast/shell/CastWebContentsScopes.java +++ b/chromecast/browser/android/apk/src/org/chromium/chromecast/shell/CastWebContentsScopes.java
@@ -13,6 +13,7 @@ import androidx.annotation.ColorInt; import androidx.annotation.Nullable; +import org.chromium.base.supplier.Supplier; import org.chromium.chromecast.base.Observer; import org.chromium.components.embedder_support.view.ContentView; import org.chromium.components.embedder_support.view.ContentViewRenderView; @@ -31,32 +32,34 @@ public static Observer<WebContents> onLayoutActivity( Activity activity, FrameLayout layout, @ColorInt int backgroundColor) { layout.setBackgroundColor(backgroundColor); - WindowAndroid window = new ActivityWindowAndroid(activity); - return onLayoutInternal(activity, layout, window, backgroundColor); + return onLayoutInternal( + activity, layout, () -> new ActivityWindowAndroid(activity), backgroundColor); } public static Observer<WebContents> onLayoutFragment( Activity activity, FrameLayout layout, @ColorInt int backgroundColor) { layout.setBackgroundColor(backgroundColor); - WindowAndroid window = new WindowAndroid(activity); - return onLayoutInternal(activity, layout, window, backgroundColor); + return onLayoutInternal( + activity, layout, () -> new WindowAndroid(activity), backgroundColor); } static Observer<WebContents> onLayoutView(Context context, FrameLayout layout, @ColorInt int backgroundColor, WindowTokenProvider windowTokenProvider) { layout.setBackgroundColor(backgroundColor); - WindowAndroid window = new WindowAndroid(context) { + return onLayoutInternal(context, layout, () -> new WindowAndroid(context) { @Override protected IBinder getWindowToken() { return windowTokenProvider.provideWindowToken(); } - }; - return onLayoutInternal(context, layout, window, backgroundColor); + }, backgroundColor); } + // Note: the |windowFactory| should create a new instance of a WindowAndroid each time it is + // invoked. private static Observer<WebContents> onLayoutInternal(Context context, FrameLayout layout, - WindowAndroid window, @ColorInt int backgroundColor) { + Supplier<WindowAndroid> windowFactory, @ColorInt int backgroundColor) { return (WebContents webContents) -> { + WindowAndroid window = windowFactory.get(); ContentViewRenderView contentViewRenderView = new ContentViewRenderView(context) { @Override protected void onReadyToRender() {
diff --git a/chromecast/crash/BUILD.gn b/chromecast/crash/BUILD.gn index d5fee555..38a71cb8 100644 --- a/chromecast/crash/BUILD.gn +++ b/chromecast/crash/BUILD.gn
@@ -5,15 +5,20 @@ import("//chromecast/chromecast.gni") import("//testing/test.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + cast_source_set("build_info") { sources = [ "build_info.cc", "build_info.h", ] - deps = [ - "//chromecast/base:cast_version", - ] + deps = [ "//chromecast/base:cast_version" ] } cast_source_set("crash_storage") {
diff --git a/chromecast/media/cma/decoder/cast_audio_decoder.cc b/chromecast/media/cma/decoder/cast_audio_decoder.cc index 92c04ee..8bbfc6c9 100644 --- a/chromecast/media/cma/decoder/cast_audio_decoder.cc +++ b/chromecast/media/cma/decoder/cast_audio_decoder.cc
@@ -184,15 +184,15 @@ } void OnDecodeStatus(base::TimeDelta buffer_timestamp, - ::media::DecodeStatus status) { + ::media::Status status) { DCHECK(pending_decode_callback_); Status result_status = kDecodeOk; scoped_refptr<media::DecoderBufferBase> decoded; - if (status == ::media::DecodeStatus::OK && !decoded_chunks_.empty()) { + if (status.is_ok() && !decoded_chunks_.empty()) { decoded = ConvertDecoded(); } else { - if (status != ::media::DecodeStatus::OK) + if (!status.is_ok()) result_status = kDecodeError; decoded = base::MakeRefCounted<media::DecoderBufferAdapter>( output_config_.id, base::MakeRefCounted<::media::DecoderBuffer>(0));
diff --git a/chromeos/components/diagnostics_ui/resources/fake_data.js b/chromeos/components/diagnostics_ui/resources/fake_data.js index ceb300c..31f2f5d 100644 --- a/chromeos/components/diagnostics_ui/resources/fake_data.js +++ b/chromeos/components/diagnostics_ui/resources/fake_data.js
@@ -5,13 +5,29 @@ import {BatteryChargeStatus, BatteryHealth, CpuUsage, ExternalPowerSource, MemoryUsage, SystemInfo} from './diagnostics_types.js' /* @type {!Array<!BatteryChargeStatus>} */ -export const fakeBatteryChargeStatus = [{ - charge_full_now_milliamp_hours: 6000, - charge_now_milliamp_hours: 4200, - current_now_milliamps: 1123, - power_adapter_status: ExternalPowerSource.kAc, - power_time: '3h 15m', -}]; +export const fakeBatteryChargeStatus = [ + { + charge_full_now_milliamp_hours: 5700, + charge_now_milliamp_hours: 4200, + current_now_milliamps: 1123, + power_adapter_status: ExternalPowerSource.kAc, + power_time: '3h 15m', + }, + { + charge_full_now_milliamp_hours: 5700, + charge_now_milliamp_hours: 4500, + current_now_milliamps: 1123, + power_adapter_status: ExternalPowerSource.kAc, + power_time: '3h 01m', + }, + { + charge_full_now_milliamp_hours: 5700, + charge_now_milliamp_hours: 4800, + current_now_milliamps: 1123, + power_adapter_status: ExternalPowerSource.kAc, + power_time: '2h 45m', + } +]; /* @type {!Array<!BatteryHealth>} */ export const fakeBatteryHealth = [{ @@ -28,18 +44,52 @@ }; /* @type {!Array<!CpuUsage>} */ -export const fakeCpuUsage = [{ - cpu_temp_degrees_celcius: 107, - percent_usage_system: 15, - percent_usage_user: 20, -}]; +export const fakeCpuUsage = [ + { + cpu_temp_degrees_celcius: 107, + percent_usage_system: 15, + percent_usage_user: 20, + }, + { + cpu_temp_degrees_celcius: 106, + percent_usage_system: 30, + percent_usage_user: 40, + }, + { + cpu_temp_degrees_celcius: 107, + percent_usage_system: 31, + percent_usage_user: 45, + }, + { + cpu_temp_degrees_celcius: 109, + percent_usage_system: 55, + percent_usage_user: 24, + } +]; /* @type {!Array<!MemoryUsage>} */ -export const fakeMemoryUsage = [{ - available_memory_kib: 57000, - free_memory_kib: 15000, - total_memory_kib: 128000, -}]; +export const fakeMemoryUsage = [ + { + available_memory_kib: 57000, + free_memory_kib: 15000, + total_memory_kib: 128000, + }, + { + available_memory_kib: 52000, + free_memory_kib: 15000, + total_memory_kib: 128000, + }, + { + available_memory_kib: 53000, + free_memory_kib: 15000, + total_memory_kib: 128000, + }, + { + available_memory_kib: 65000, + free_memory_kib: 15000, + total_memory_kib: 128000, + } +]; /* @type {!SystemInfo} */ export const fakeSystemInfo = {
diff --git a/chromeos/components/diagnostics_ui/resources/fake_observables.js b/chromeos/components/diagnostics_ui/resources/fake_observables.js index 3014160..2f094df 100644 --- a/chromeos/components/diagnostics_ui/resources/fake_observables.js +++ b/chromeos/components/diagnostics_ui/resources/fake_observables.js
@@ -33,6 +33,12 @@ * @private {number} **/ this.index_ = -1; + + /** + * Id of the timer if enabled. + * @private {number} + */ + this.timerId_ = -1; } /** @param {!Array<!T>} observations */ @@ -47,6 +53,31 @@ } /** + * Start firing the observers on a fixed interval. setObservableData() must + * already have been called. + * @param {number} intervalMs + */ + startTriggerOnInterval(intervalMs) { + assert(this.index_ >= 0); + if (this.timerId_ != -1) { + this.stopTriggerOnInterval(); + } + + assert(this.timerId_ == -1); + this.timerId_ = setInterval(this.trigger.bind(this), intervalMs); + } + + /** + * Disables the observer firing automatically on an interval. + */ + stopTriggerOnInterval() { + if (this.timerId_ != -1) { + clearInterval(this.timerId_); + this.timerId_ = -1; + } + } + + /** * Causes the observable to trigger and notify all observers of the next * observation value. */ @@ -106,6 +137,32 @@ setObservableData(methodName, observations) { this.getObservable_(methodName).setObservableData(observations); } + /** + * Start firing the observer on a fixed interval. setObservableData() must + * already have been called. + * @param {string} methodName + * @param {number} intervalMs + */ + startTriggerOnInterval(methodName, intervalMs) { + this.getObservable_(methodName).startTriggerOnInterval(intervalMs); + } + + /** + * Disables the observer firing automatically on an interval. + * @param {string} methodName + */ + stopTriggerOnInterval(methodName) { + this.getObservable_(methodName).stopTriggerOnInterval(); + } + + /** + * Disables all observers firing automatically on an interval. + */ + stopAllTriggerIntervals() { + for (let obs of this.observables_.values()) { + obs.stopTriggerOnInterval(); + } + } /** * Causes the observable to trigger and notify all observers of the next
diff --git a/chromeos/components/diagnostics_ui/resources/fake_system_data_provider.js b/chromeos/components/diagnostics_ui/resources/fake_system_data_provider.js index 5f37a3f..5d8ceff4 100644 --- a/chromeos/components/diagnostics_ui/resources/fake_system_data_provider.js +++ b/chromeos/components/diagnostics_ui/resources/fake_system_data_provider.js
@@ -172,4 +172,25 @@ this.observables_.setObservableData( 'MemoryUsageObserver_onMemoryUsageUpdated', memoryUsageList); } + + /** + * Make the observables fire automatically on various intervals. + */ + startTriggerIntervals() { + this.observables_.startTriggerOnInterval( + 'CpuUsageObserver_onCpuUsageUpdated', 1000); + this.observables_.startTriggerOnInterval( + 'MemoryUsageObserver_onMemoryUsageUpdated', 5000); + this.observables_.startTriggerOnInterval( + 'BatteryHealthObserver_onBatteryHealthUpdated', 30000); + this.observables_.startTriggerOnInterval( + 'BatteryChargeStatusObserver_onBatteryChargeStatusUpdated', 30000); + } + + /** + * Stop automatically triggering observables. + */ + stopTriggerIntervals() { + this.observables_.stopAllTriggerIntervals(); + } }
diff --git a/chromeos/components/diagnostics_ui/resources/mojo_interface_provider.js b/chromeos/components/diagnostics_ui/resources/mojo_interface_provider.js index edec27a..30e7291a 100644 --- a/chromeos/components/diagnostics_ui/resources/mojo_interface_provider.js +++ b/chromeos/components/diagnostics_ui/resources/mojo_interface_provider.js
@@ -29,6 +29,9 @@ provider.setFakeMemoryUsage(fakeMemoryUsage); provider.setFakeSystemInfo(fakeSystemInfo); + // Start the timers to generate some observations. + provider.startTriggerIntervals(); + // Set the fake provider. setSystemDataProviderForTesting(provider); }
diff --git a/chromeos/constants/chromeos_features.cc b/chromeos/constants/chromeos_features.cc index 0cc3dbe..e5338d7 100644 --- a/chromeos/constants/chromeos_features.cc +++ b/chromeos/constants/chromeos_features.cc
@@ -319,6 +319,10 @@ const base::Feature kGesturePropertiesDBusService{ "GesturePropertiesDBusService", base::FEATURE_DISABLED_BY_DEFAULT}; +// Enable Guest OS external protocol handling. +const base::Feature kGuestOsExternalProtocol{"GuestOsExternalProtocol", + base::FEATURE_DISABLED_BY_DEFAULT}; + // Enables editing with handwriting gestures within the virtual keyboard. const base::Feature kHandwritingGestureEditing{ "HandwritingGestureEditing", base::FEATURE_DISABLED_BY_DEFAULT};
diff --git a/chromeos/constants/chromeos_features.h b/chromeos/constants/chromeos_features.h index 2212bdf94..30d1afa5 100644 --- a/chromeos/constants/chromeos_features.h +++ b/chromeos/constants/chromeos_features.h
@@ -151,6 +151,8 @@ COMPONENT_EXPORT(CHROMEOS_CONSTANTS) extern const base::Feature kGesturePropertiesDBusService; COMPONENT_EXPORT(CHROMEOS_CONSTANTS) +extern const base::Feature kGuestOsExternalProtocol; +COMPONENT_EXPORT(CHROMEOS_CONSTANTS) extern const base::Feature kHelpAppFirstRun; COMPONENT_EXPORT(CHROMEOS_CONSTANTS) extern const base::Feature kHelpAppReleaseNotes;
diff --git a/chromeos/crosapi/cpp/BUILD.gn b/chromeos/crosapi/cpp/BUILD.gn index 20c74da..276fac2e 100644 --- a/chromeos/crosapi/cpp/BUILD.gn +++ b/chromeos/crosapi/cpp/BUILD.gn
@@ -14,6 +14,8 @@ "bitmap.h", "bitmap_util.cc", "bitmap_util.h", + "crosapi_constants.cc", + "crosapi_constants.h", ] configs += [ ":crosapi_implementation" ] deps = [
diff --git a/chromeos/crosapi/cpp/crosapi_constants.cc b/chromeos/crosapi/cpp/crosapi_constants.cc new file mode 100644 index 0000000..50f66b3 --- /dev/null +++ b/chromeos/crosapi/cpp/crosapi_constants.cc
@@ -0,0 +1,14 @@ +// Copyright 2020 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 "chromeos/crosapi/cpp/crosapi_constants.h" + +namespace crosapi { + +// The prefix for a Wayland app id for a Lacros browser window. The full ID is +// suffixed with a serialized unguessable token unique to each window. The +// trailing "." is intentional. +const char kLacrosAppIdPrefix[] = "org.chromium.lacros."; + +} // namespace crosapi
diff --git a/chromeos/crosapi/cpp/crosapi_constants.h b/chromeos/crosapi/cpp/crosapi_constants.h new file mode 100644 index 0000000..1d141f9 --- /dev/null +++ b/chromeos/crosapi/cpp/crosapi_constants.h
@@ -0,0 +1,16 @@ +// Copyright 2020 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 CHROMEOS_CROSAPI_CPP_CROSAPI_CONSTANTS_H_ +#define CHROMEOS_CROSAPI_CPP_CROSAPI_CONSTANTS_H_ + +#include "base/component_export.h" + +namespace crosapi { + +COMPONENT_EXPORT(CROSAPI) extern const char kLacrosAppIdPrefix[]; + +} // namespace crosapi + +#endif // CHROMEOS_CROSAPI_CPP_CROSAPI_CONSTANTS_H_
diff --git a/chromeos/dbus/cfm/BUILD.gn b/chromeos/dbus/cfm/BUILD.gn index 39a2c0eb..e81c8ba 100644 --- a/chromeos/dbus/cfm/BUILD.gn +++ b/chromeos/dbus/cfm/BUILD.gn
@@ -23,6 +23,7 @@ sources = [ "cfm_hotline_client.cc", "cfm_hotline_client.h", + "cfm_observer.h", "fake_cfm_hotline_client.cc", "fake_cfm_hotline_client.h", ]
diff --git a/chromeos/dbus/cfm/DEPS b/chromeos/dbus/cfm/DEPS index ca47467..386e0de 100644 --- a/chromeos/dbus/cfm/DEPS +++ b/chromeos/dbus/cfm/DEPS
@@ -1,4 +1,5 @@ include_rules = [ + # Do not add chrome here (use a delegate instead). "+chromeos/services/cfm/public/buildflags", "+chromeos/services/cfm/public/features", ]
diff --git a/chromeos/dbus/cfm/cfm_hotline_client.cc b/chromeos/dbus/cfm/cfm_hotline_client.cc index ddca563..40d496b3 100644 --- a/chromeos/dbus/cfm/cfm_hotline_client.cc +++ b/chromeos/dbus/cfm/cfm_hotline_client.cc
@@ -11,6 +11,8 @@ #include "base/logging.h" #include "base/macros.h" #include "base/memory/weak_ptr.h" +#include "base/observer_list.h" +#include "chromeos/dbus/cfm/cfm_observer.h" #include "chromeos/dbus/cfm/fake_cfm_hotline_client.h" #include "chromeos/services/cfm/public/features/features.h" #include "dbus/bus.h" @@ -34,6 +36,15 @@ dbus_proxy_ = bus->GetObjectProxy(::cfm::broker::kServiceName, dbus::ObjectPath(::cfm::broker::kServicePath)); + + dbus_proxy_->ConnectToSignal( + ::cfm::broker::kServiceInterfaceName, + ::cfm::broker::kMojoServiceRequestedSignal, + base::BindRepeating( + &CfmHotlineClientImpl::OnServiceRequestedSignalReceived, + weak_ptr_factory_.GetWeakPtr()), + base::BindRepeating(&CfmHotlineClientImpl::OnSignalConnected, + weak_ptr_factory_.GetWeakPtr())); } void WaitForServiceToBeAvailable( @@ -57,8 +68,39 @@ std::move(result_callback))); } + void AddObserver(cfm::CfmObserver* observer) override { + observer_list_.AddObserver(observer); + } + + void RemoveObserver(cfm::CfmObserver* observer) override { + observer_list_.RemoveObserver(observer); + } + private: - dbus::ObjectProxy* dbus_proxy_ = nullptr; + void OnServiceRequestedSignalReceived(dbus::Signal* signal) { + dbus::MessageReader reader(signal); + std::string service_id; + + if (!reader.PopString(&service_id)) { + LOG(ERROR) << "Invalid detection signal: " << signal->ToString(); + return; + } + + for (auto& observer : observer_list_) { + if (observer.ServiceRequestReceived(service_id)) { + // A service has been found that can fulfill the request + // Note: Only one service will match the requested service_id. + break; + } + } + } + + void OnSignalConnected(const std::string& interface, + const std::string& signal, + bool succeeded) { + LOG_IF(ERROR, !succeeded) + << "Connection to " << interface << " " << signal << " failed."; + } // Passes the invitation token of |dbus_response| on to |result_callback|. void OnBootstrapMojoConnectionResponse( @@ -67,7 +109,11 @@ std::move(result_callback).Run(response != nullptr); } - // Must be last class member. + dbus::ObjectProxy* dbus_proxy_ = nullptr; + cfm::CfmObserverList observer_list_; + + // Note: This should remain the last member so it'll be destroyed and + // invalidate its weak pointers before any other members are destroyed. base::WeakPtrFactory<CfmHotlineClientImpl> weak_ptr_factory_{this}; };
diff --git a/chromeos/dbus/cfm/cfm_hotline_client.h b/chromeos/dbus/cfm/cfm_hotline_client.h index e01415d..35dad1c 100644 --- a/chromeos/dbus/cfm/cfm_hotline_client.h +++ b/chromeos/dbus/cfm/cfm_hotline_client.h
@@ -12,6 +12,8 @@ #include "base/files/scoped_file.h" #include "dbus/object_proxy.h" +#include "chromeos/dbus/cfm/cfm_observer.h" + namespace dbus { class Bus; } @@ -64,6 +66,13 @@ base::ScopedFD fd, BootstrapMojoConnectionCallback result_callback) = 0; + // Adds an observer instance to the observers list to listen on changes like + // DLC state change, etc. + virtual void AddObserver(cfm::CfmObserver* observer) = 0; + + // Removes an observer from observers list. + virtual void RemoveObserver(cfm::CfmObserver* observer) = 0; + protected: // Initialize/Shutdown should be used instead. CfmHotlineClient();
diff --git a/chromeos/dbus/cfm/cfm_observer.h b/chromeos/dbus/cfm/cfm_observer.h new file mode 100644 index 0000000..a8a71e54 --- /dev/null +++ b/chromeos/dbus/cfm/cfm_observer.h
@@ -0,0 +1,33 @@ +// Copyright 2020 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 CHROMEOS_DBUS_CFM_CFM_OBSERVER_H_ +#define CHROMEOS_DBUS_CFM_CFM_OBSERVER_H_ + +#include <string> + +#include "base/observer_list.h" +#include "base/observer_list_types.h" + +namespace chromeos { +namespace cfm { + +class CfmObserver : public base::CheckedObserver { + public: + ~CfmObserver() override = default; + + // Called when Hotline is requesting a service to be connected. + // Returns |true| if |service_id| matches mojom interface name + virtual bool ServiceRequestReceived(const std::string& service_id) = 0; + + protected: + CfmObserver() = default; +}; + +using CfmObserverList = base::ObserverList<CfmObserver>; + +} // namespace cfm +} // namespace chromeos + +#endif // CHROMEOS_DBUS_CFM_CFM_OBSERVER_H_
diff --git a/chromeos/dbus/cfm/fake_cfm_hotline_client.cc b/chromeos/dbus/cfm/fake_cfm_hotline_client.cc index dd32b232..8f4f171 100644 --- a/chromeos/dbus/cfm/fake_cfm_hotline_client.cc +++ b/chromeos/dbus/cfm/fake_cfm_hotline_client.cc
@@ -28,4 +28,12 @@ FROM_HERE, base::BindOnce(std::move(result_callback), true)); } +void FakeCfmHotlineClient::AddObserver(cfm::CfmObserver* observer) { + observer_list_.AddObserver(observer); +} + +void FakeCfmHotlineClient::RemoveObserver(cfm::CfmObserver* observer) { + observer_list_.RemoveObserver(observer); +} + } // namespace chromeos
diff --git a/chromeos/dbus/cfm/fake_cfm_hotline_client.h b/chromeos/dbus/cfm/fake_cfm_hotline_client.h index d31bc790..00eaf05 100644 --- a/chromeos/dbus/cfm/fake_cfm_hotline_client.h +++ b/chromeos/dbus/cfm/fake_cfm_hotline_client.h
@@ -27,6 +27,12 @@ void BootstrapMojoConnection( base::ScopedFD fd, BootstrapMojoConnectionCallback result_callback) override; + void AddObserver(cfm::CfmObserver* observer) override; + void RemoveObserver(cfm::CfmObserver* observer) override; + + private: + // A list of observers that are listening on state changes, etc. + cfm::CfmObserverList observer_list_; }; } // namespace chromeos
diff --git a/chromeos/network/onc/onc_utils.cc b/chromeos/network/onc/onc_utils.cc index 8359b92..9934db5a2 100644 --- a/chromeos/network/onc/onc_utils.cc +++ b/chromeos/network/onc/onc_utils.cc
@@ -646,6 +646,11 @@ "\"Certificates\":[]}"; std::unique_ptr<base::Value> ReadDictionaryFromJson(const std::string& json) { + if (json.empty()) { + // Policy may contain empty values, just log a debug message. + NET_LOG(DEBUG) << "Empty json string"; + return nullptr; + } base::JSONReader::ValueWithError parsed_json = base::JSONReader::ReadAndReturnValueWithError( json, base::JSON_ALLOW_TRAILING_COMMAS);
diff --git a/chromeos/printing/uri.cc b/chromeos/printing/uri.cc index 3b5622d..27523353 100644 --- a/chromeos/printing/uri.cc +++ b/chromeos/printing/uri.cc
@@ -9,7 +9,6 @@ #include "base/check_op.h" #include "base/strings/string_number_conversions.h" #include "base/strings/string_util.h" - #include "chromeos/printing/uri_impl.h" namespace chromeos { @@ -126,8 +125,8 @@ } int Uri::GetDefaultPort(const std::string& scheme) { - auto it = Pim::kDefaultPorts.find(scheme); - if (it == Pim::kDefaultPorts.end()) + auto it = Pim::GetDefaultPorts().find(scheme); + if (it == Pim::GetDefaultPorts().end()) return -1; return it->second; } @@ -164,8 +163,8 @@ // Calculates a string representation of the Port number. std::string port; if (pim_->port() >= 0 && - (always_print_port || Pim::kDefaultPorts.count(pim_->scheme()) == 0 || - Pim::kDefaultPorts.at(pim_->scheme()) != pim_->port())) + (always_print_port || Pim::GetDefaultPorts().count(pim_->scheme()) == 0 || + Pim::GetDefaultPorts().at(pim_->scheme()) != pim_->port())) port = base::NumberToString(pim_->port()); // Output string. Adds Scheme.
diff --git a/chromeos/printing/uri_impl.cc b/chromeos/printing/uri_impl.cc index 98428f61..bf6110f 100644 --- a/chromeos/printing/uri_impl.cc +++ b/chromeos/printing/uri_impl.cc
@@ -11,6 +11,7 @@ #include "base/check_op.h" #include "base/i18n/streaming_utf8_validator.h" +#include "base/no_destructor.h" #include "base/strings/string_util.h" #include "base/strings/utf_string_conversion_utils.h" #include "chromeos/printing/uri.h" @@ -92,11 +93,20 @@ Iter FindFirstOf(Iter begin, Iter end, const std::string& chars) { return std::find_if(begin, end, Comparator(chars)); } + } // namespace -const std::map<std::string, int> Uri::Pim::kDefaultPorts = { - {"ipp", 631}, {"ipps", 443}, {"http", 80}, - {"https", 443}, {"lpd", 515}, {"socket", 9100}}; +// static +const std::map<std::string, int>& Uri::Pim::GetDefaultPorts() { + static const base::NoDestructor<std::map<std::string, int>> kDefaultPorts( + {{"ipp", 631}, + {"ipps", 443}, + {"http", 80}, + {"https", 443}, + {"lpd", 515}, + {"socket", 9100}}); + return *kDefaultPorts; +} template <bool encoded, bool case_insensitive> bool Uri::Pim::ParseString(const Iter& begin, @@ -185,8 +195,8 @@ parser_error_.status = ParserStatus::kInvalidPortNumber; return false; } - if (value == kPortUnspecified && kDefaultPorts.count(scheme_)) { - value = kDefaultPorts.at(scheme_); + if (value == kPortUnspecified && GetDefaultPorts().count(scheme_)) { + value = GetDefaultPorts().at(scheme_); } port_ = value; return true; @@ -297,8 +307,8 @@ scheme_ = std::move(out); // If the current Port is unspecified and the new Scheme has default port // number, set the default port number. - if (port_ == kPortUnspecified && kDefaultPorts.count(scheme_)) - port_ = kDefaultPorts.at(scheme_); + if (port_ == kPortUnspecified && GetDefaultPorts().count(scheme_)) + port_ = GetDefaultPorts().at(scheme_); return true; }
diff --git a/chromeos/printing/uri_impl.h b/chromeos/printing/uri_impl.h index 96e7fe49..8a2627a 100644 --- a/chromeos/printing/uri_impl.h +++ b/chromeos/printing/uri_impl.h
@@ -23,7 +23,7 @@ class Uri::Pim { public: // The map with pairs scheme -> default_port. - static const std::map<std::string, int> kDefaultPorts; + static const std::map<std::string, int>& GetDefaultPorts(); Pim(); Pim(const Pim&);
diff --git a/chromeos/services/cfm/public/cpp/appid_util.cc b/chromeos/services/cfm/public/cpp/appid_util.cc index 39bb730..c7699ef 100644 --- a/chromeos/services/cfm/public/cpp/appid_util.cc +++ b/chromeos/services/cfm/public/cpp/appid_util.cc
@@ -14,7 +14,7 @@ constexpr char const* kInternalHotrodAppIds[] = { "moklfjoegmpoolceggbebbmgbddlhdgp", // Stable "ldmpofkllgeicjiihkimgeccbhghhmfj", // Beta - "denipklgekfpcdmbahmbpnmokgajnhma" // Alpha + "denipklgekfpcdmbahmbpnmokgajnhma", // Alpha "kjfhgcncjdebkoofmbjoiemiboifnpbo", // Dev // Keep in sync with app_info.ts (go/googlehotrodappids). };
diff --git a/chromeos/services/secure_channel/BUILD.gn b/chromeos/services/secure_channel/BUILD.gn index 577fe7b..ed16a8e 100644 --- a/chromeos/services/secure_channel/BUILD.gn +++ b/chromeos/services/secure_channel/BUILD.gn
@@ -104,6 +104,8 @@ "multiplexed_channel.h", "multiplexed_channel_impl.cc", "multiplexed_channel_impl.h", + "nearby_connection.cc", + "nearby_connection.h", "nearby_connection_manager.cc", "nearby_connection_manager.h", "nearby_connection_manager_impl.cc",
diff --git a/chromeos/services/secure_channel/nearby_connection.cc b/chromeos/services/secure_channel/nearby_connection.cc new file mode 100644 index 0000000..edd1ba7 --- /dev/null +++ b/chromeos/services/secure_channel/nearby_connection.cc
@@ -0,0 +1,56 @@ +// Copyright 2020 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 "chromeos/services/secure_channel/nearby_connection.h" + +#include "base/memory/ptr_util.h" + +namespace chromeos { + +namespace secure_channel { + +// static +NearbyConnection::Factory* NearbyConnection::Factory::factory_instance_ = + nullptr; + +// static +std::unique_ptr<Connection> NearbyConnection::Factory::Create( + multidevice::RemoteDeviceRef remote_device) { + if (factory_instance_) + return factory_instance_->CreateInstance(remote_device); + + return base::WrapUnique(new NearbyConnection(remote_device)); +} + +// static +void NearbyConnection::Factory::SetFactoryForTesting(Factory* factory) { + factory_instance_ = factory; +} + +NearbyConnection::NearbyConnection(multidevice::RemoteDeviceRef remote_device) + : Connection(remote_device) {} + +NearbyConnection::~NearbyConnection() { + // TODO(https://crbug.com/1106937): Clean up potentially-lingering connection. +} + +void NearbyConnection::Connect() { + // TODO(https://crbug.com/1106937): Implement. +} + +void NearbyConnection::Disconnect() { + // TODO(https://crbug.com/1106937): Implement. +} + +std::string NearbyConnection::GetDeviceAddress() { + return remote_device().bluetooth_public_address(); +} + +void NearbyConnection::SendMessageImpl(std::unique_ptr<WireMessage> message) { + // TODO(https://crbug.com/1106937): Implement. +} + +} // namespace secure_channel + +} // namespace chromeos
diff --git a/chromeos/services/secure_channel/nearby_connection.h b/chromeos/services/secure_channel/nearby_connection.h new file mode 100644 index 0000000..70d1ad7b --- /dev/null +++ b/chromeos/services/secure_channel/nearby_connection.h
@@ -0,0 +1,50 @@ +// Copyright 2020 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 CHROMEOS_SERVICES_SECURE_CHANNEL_NEARBY_CONNECTION_H_ +#define CHROMEOS_SERVICES_SECURE_CHANNEL_NEARBY_CONNECTION_H_ + +#include "chromeos/services/secure_channel/connection.h" + +namespace chromeos { + +namespace secure_channel { + +// Connection implementation which creates a connection to a remote device via +// the Nearby Connections library. +// TODO(https://crbug.com/1106937): Add real implementation. +class NearbyConnection : public Connection { + public: + class Factory { + public: + static std::unique_ptr<Connection> Create( + multidevice::RemoteDeviceRef remote_device); + static void SetFactoryForTesting(Factory* factory); + virtual ~Factory() = default; + + protected: + virtual std::unique_ptr<Connection> CreateInstance( + multidevice::RemoteDeviceRef remote_device) = 0; + + private: + static Factory* factory_instance_; + }; + + ~NearbyConnection() override; + + private: + NearbyConnection(multidevice::RemoteDeviceRef remote_device); + + // Connection: + void Connect() override; + void Disconnect() override; + std::string GetDeviceAddress() override; + void SendMessageImpl(std::unique_ptr<WireMessage> message) override; +}; + +} // namespace secure_channel + +} // namespace chromeos + +#endif // CHROMEOS_SERVICES_SECURE_CHANNEL_NEARBY_CONNECTION_H_
diff --git a/chromeos/services/secure_channel/nearby_connection_manager_impl.cc b/chromeos/services/secure_channel/nearby_connection_manager_impl.cc index 4372c99..df64bb52 100644 --- a/chromeos/services/secure_channel/nearby_connection_manager_impl.cc +++ b/chromeos/services/secure_channel/nearby_connection_manager_impl.cc
@@ -5,6 +5,10 @@ #include "chromeos/services/secure_channel/nearby_connection_manager_impl.h" #include "base/memory/ptr_util.h" +#include "chromeos/components/multidevice/logging/logging.h" +#include "chromeos/services/secure_channel/authenticated_channel_impl.h" +#include "chromeos/services/secure_channel/nearby_connection.h" +#include "chromeos/services/secure_channel/secure_channel_disconnector.h" namespace chromeos { @@ -16,11 +20,16 @@ // static std::unique_ptr<NearbyConnectionManager> -NearbyConnectionManagerImpl::Factory::Create() { - if (test_factory_) - return test_factory_->CreateInstance(); +NearbyConnectionManagerImpl::Factory::Create( + BleScanner* ble_scanner, + SecureChannelDisconnector* secure_channel_disconnector) { + if (test_factory_) { + return test_factory_->CreateInstance(ble_scanner, + secure_channel_disconnector); + } - return base::WrapUnique(new NearbyConnectionManagerImpl()); + return base::WrapUnique(new NearbyConnectionManagerImpl( + ble_scanner, secure_channel_disconnector)); } // static @@ -31,15 +40,244 @@ NearbyConnectionManagerImpl::Factory::~Factory() = default; -NearbyConnectionManagerImpl::NearbyConnectionManagerImpl() = default; +NearbyConnectionManagerImpl::NearbyConnectionManagerImpl( + BleScanner* ble_scanner, + SecureChannelDisconnector* secure_channel_disconnector) + : ble_scanner_(ble_scanner), + secure_channel_disconnector_(secure_channel_disconnector) { + ble_scanner_->AddObserver(this); +} -NearbyConnectionManagerImpl::~NearbyConnectionManagerImpl() = default; +NearbyConnectionManagerImpl::~NearbyConnectionManagerImpl() { + ble_scanner_->RemoveObserver(this); +} void NearbyConnectionManagerImpl::PerformAttemptNearbyInitiatorConnection( - const DeviceIdPair& device_id_pair) {} + const DeviceIdPair& device_id_pair) { + if (DoesAuthenticatingChannelExist(device_id_pair.remote_device_id())) + return; + + ble_scanner_->AddScanRequest(ConnectionAttemptDetails( + device_id_pair, ConnectionMedium::kNearbyConnections, + ConnectionRole::kInitiatorRole)); +} void NearbyConnectionManagerImpl::PerformCancelNearbyInitiatorConnectionAttempt( - const DeviceIdPair& device_id_pair) {} + const DeviceIdPair& device_id_pair) { + if (DoesAuthenticatingChannelExist(device_id_pair.remote_device_id())) { + // Check to see if we are removing the final request for an active channel; + // if so, that channel needs to be disconnected. + ProcessPotentialLingeringChannel(device_id_pair.remote_device_id()); + return; + } + + // If a client canceled its request as a result of being notified of an + // authenticated channel, that request was not actually active. + if (notifying_remote_device_id_ == device_id_pair.remote_device_id()) + return; + + ble_scanner_->RemoveScanRequest(ConnectionAttemptDetails( + device_id_pair, ConnectionMedium::kNearbyConnections, + ConnectionRole::kInitiatorRole)); +} + +void NearbyConnectionManagerImpl::OnReceivedAdvertisement( + multidevice::RemoteDeviceRef remote_device, + device::BluetoothDevice* bluetooth_device, + ConnectionMedium connection_medium, + ConnectionRole connection_role) { + // Only process advertisements received as part of the Nearby Connections + // flow. + if (connection_medium != ConnectionMedium::kNearbyConnections) + return; + + // Create a connection to the device. + std::unique_ptr<Connection> connection = + NearbyConnection::Factory::Create(remote_device); + + SetAuthenticatingChannel( + remote_device.GetDeviceId(), + SecureChannel::Factory::Create(std::move(connection))); +} + +void NearbyConnectionManagerImpl::OnSecureChannelStatusChanged( + SecureChannel* secure_channel, + const SecureChannel::Status& old_status, + const SecureChannel::Status& new_status) { + std::string remote_device_id = + GetRemoteDeviceIdForSecureChannel(secure_channel); + + if (new_status == SecureChannel::Status::DISCONNECTED) { + bool was_authenticating = + old_status == SecureChannel::Status::AUTHENTICATING; + HandleSecureChannelDisconnection(remote_device_id, was_authenticating); + return; + } + + if (new_status == SecureChannel::Status::AUTHENTICATED) + HandleChannelAuthenticated(remote_device_id); +} + +bool NearbyConnectionManagerImpl::DoesAuthenticatingChannelExist( + const std::string& remote_device_id) { + return base::Contains(remote_device_id_to_secure_channel_map_, + remote_device_id); +} + +void NearbyConnectionManagerImpl::SetAuthenticatingChannel( + const std::string& remote_device_id, + std::unique_ptr<SecureChannel> secure_channel) { + // Since a channel has been established, all connection attempts to the device + // should be stopped. Otherwise, it would be possible to pick up additional + // scan results and try to start a new connection. Multiple simultaneous + // connections to the same device (e.g., one over BLE and one over Nearby) can + // interfere with each other. + PauseConnectionAttemptsToDevice(remote_device_id); + + if (DoesAuthenticatingChannelExist(remote_device_id)) { + PA_LOG(ERROR) << "A new channel was created, one already exists for the " + << "same remote device ID. ID: " + << multidevice::RemoteDeviceRef::TruncateDeviceIdForLogs( + remote_device_id); + NOTREACHED(); + } + + SecureChannel* secure_channel_raw = secure_channel.get(); + + PA_LOG(INFO) << "Advertisement received; establishing connection. " + << "Remote device ID: " + << multidevice::RemoteDeviceRef::TruncateDeviceIdForLogs( + remote_device_id); + remote_device_id_to_secure_channel_map_[remote_device_id] = + std::move(secure_channel); + + // Observe the channel to be notified of when either the channel authenticates + // successfully or faces connection instability and disconnects. + secure_channel_raw->AddObserver(this); + secure_channel_raw->Initialize(); +} + +void NearbyConnectionManagerImpl::PauseConnectionAttemptsToDevice( + const std::string& remote_device_id) { + for (const auto& pair : GetDeviceIdPairsForRemoteDevice(remote_device_id)) + PerformCancelNearbyInitiatorConnectionAttempt(pair); +} + +void NearbyConnectionManagerImpl::RestartPausedAttemptsToDevice( + const std::string& remote_device_id) { + for (const auto& pair : GetDeviceIdPairsForRemoteDevice(remote_device_id)) + PerformAttemptNearbyInitiatorConnection(pair); +} + +void NearbyConnectionManagerImpl::ProcessPotentialLingeringChannel( + const std::string& remote_device_id) { + // If there was no authenticating SecureChannel associated with + // |remote_device_id|, return early. + if (!DoesAuthenticatingChannelExist(remote_device_id)) + return; + + // If there is at least one active request, the channel should remain active. + if (!GetDeviceIdPairsForRemoteDevice(remote_device_id).empty()) + return; + + // Extract the map value and remove the entry from the map. + std::unique_ptr<SecureChannel> secure_channel = + std::move(remote_device_id_to_secure_channel_map_[remote_device_id]); + remote_device_id_to_secure_channel_map_.erase(remote_device_id); + + // Disconnect the channel, since it is lingering with no active request. + PA_LOG(VERBOSE) + << "Disconnecting lingering channel which is no longer associated with " + << "any active requests. Remote device ID: " + << multidevice::RemoteDeviceRef::TruncateDeviceIdForLogs( + remote_device_id); + secure_channel->RemoveObserver(this); + secure_channel_disconnector_->DisconnectSecureChannel( + std::move(secure_channel)); +} + +std::string NearbyConnectionManagerImpl::GetRemoteDeviceIdForSecureChannel( + SecureChannel* secure_channel) { + for (const auto& map_entry : remote_device_id_to_secure_channel_map_) { + if (map_entry.second.get() == secure_channel) + return map_entry.first; + } + + PA_LOG(ERROR) << "No remote device ID mapped to the provided SecureChannel."; + NOTREACHED(); + return std::string(); +} + +void NearbyConnectionManagerImpl::HandleSecureChannelDisconnection( + const std::string& remote_device_id, + bool was_authenticating) { + if (!DoesAuthenticatingChannelExist(remote_device_id)) { + PA_LOG(ERROR) << "HandleSecureChannelDisconnection(): Disconnected channel " + << "not present in map. Remote device ID: " + << multidevice::RemoteDeviceRef::TruncateDeviceIdForLogs( + remote_device_id); + NOTREACHED(); + } + + for (const auto& pair : GetDeviceIdPairsForRemoteDevice(remote_device_id)) { + NotifyNearbyInitiatorFailure( + pair, was_authenticating + ? NearbyInitiatorFailureType::kAuthenticationError + : NearbyInitiatorFailureType::kConnectivityError); + } + + auto it = remote_device_id_to_secure_channel_map_.find(remote_device_id); + + // It is possible that the NotifyNearbyInitiatorFailure() calls above resulted + // in observers responding to the failure by canceling the connection attempt. + // If all attempts to |remote_device_id| were cancelled, the disconnected + // channel will have already been cleaned up via + // ProcessPotentialLingeringChannel(). In that case, return early. + if (it == remote_device_id_to_secure_channel_map_.end()) + return; + + // Stop observing the disconnected channel and remove it from the map. + SecureChannel* secure_channel = it->second.get(); + secure_channel->RemoveObserver(this); + remote_device_id_to_secure_channel_map_.erase(it); + + // Since the previous connection failed, the connection attempts that were + // paused in SetAuthenticatingChannel() need to be started up again. + RestartPausedAttemptsToDevice(remote_device_id); +} + +void NearbyConnectionManagerImpl::HandleChannelAuthenticated( + const std::string& remote_device_id) { + // Extract the map value and remove the entry from the map. + std::unique_ptr<SecureChannel> secure_channel = + std::move(remote_device_id_to_secure_channel_map_[remote_device_id]); + remote_device_id_to_secure_channel_map_.erase(remote_device_id); + + // Stop observing the channel; it is about to be passed to a client. + secure_channel->RemoveObserver(this); + + // Before notifying clients, set |notifying_remote_device_id_|. This ensure + // that the PerformCancel*() functions can check to see whether requests need + // to be removed from BleScanner/BleAdvertiser. + notifying_remote_device_id_ = remote_device_id; + NotifyNearbyInitiatorConnectionSuccess( + ChooseChannelRecipient(remote_device_id), + AuthenticatedChannelImpl::Factory::Create( + std::vector<mojom::ConnectionCreationDetail>(), + std::move(secure_channel))); + notifying_remote_device_id_.reset(); + + // Restart any attempts which still exist. + RestartPausedAttemptsToDevice(remote_device_id); +} + +DeviceIdPair NearbyConnectionManagerImpl::ChooseChannelRecipient( + const std::string& remote_device_id) { + const base::flat_set<DeviceIdPair>& pairs = + GetDeviceIdPairsForRemoteDevice(remote_device_id); + DCHECK(!pairs.empty()); + return *pairs.begin(); +} } // namespace secure_channel
diff --git a/chromeos/services/secure_channel/nearby_connection_manager_impl.h b/chromeos/services/secure_channel/nearby_connection_manager_impl.h index 4e782c8..4906216 100644 --- a/chromeos/services/secure_channel/nearby_connection_manager_impl.h +++ b/chromeos/services/secure_channel/nearby_connection_manager_impl.h
@@ -5,23 +5,36 @@ #ifndef CHROMEOS_SERVICES_SECURE_CHANNEL_NEARBY_CONNECTION_MANAGER_IMPL_H_ #define CHROMEOS_SERVICES_SECURE_CHANNEL_NEARBY_CONNECTION_MANAGER_IMPL_H_ +#include "chromeos/services/secure_channel/ble_scanner.h" #include "chromeos/services/secure_channel/nearby_connection_manager.h" +#include "chromeos/services/secure_channel/secure_channel.h" namespace chromeos { namespace secure_channel { -// TODO(https://crbug.com/1106937): Add real implementation. -class NearbyConnectionManagerImpl : public NearbyConnectionManager { +class SecureChannelDisconnector; + +// NearbyConnectionManager implementation which uses BleScanner to determine +// whether the desired device is in proximity. If BleScanner discovers the +// device is nearby, it creates a new NearbyConnection to that device, then +// completes the authentication flow before returning it to the caller. +class NearbyConnectionManagerImpl : public NearbyConnectionManager, + public BleScanner::Observer, + public SecureChannel::Observer { public: class Factory { public: - static std::unique_ptr<NearbyConnectionManager> Create(); + static std::unique_ptr<NearbyConnectionManager> Create( + BleScanner* ble_scanner, + SecureChannelDisconnector* secure_channel_disconnector); static void SetFactoryForTesting(Factory* test_factory); protected: virtual ~Factory(); - virtual std::unique_ptr<NearbyConnectionManager> CreateInstance() = 0; + virtual std::unique_ptr<NearbyConnectionManager> CreateInstance( + BleScanner* ble_scanner, + SecureChannelDisconnector* secure_channel_disconnector) = 0; private: static Factory* test_factory_; @@ -33,13 +46,72 @@ ~NearbyConnectionManagerImpl() override; private: - NearbyConnectionManagerImpl(); + NearbyConnectionManagerImpl( + BleScanner* ble_scanner, + SecureChannelDisconnector* secure_channel_disconnector); // NearbyConnectionManager: void PerformAttemptNearbyInitiatorConnection( const DeviceIdPair& device_id_pair) override; void PerformCancelNearbyInitiatorConnectionAttempt( const DeviceIdPair& device_id_pair) override; + + // BleScanner::Observer: + void OnReceivedAdvertisement(multidevice::RemoteDeviceRef remote_device, + device::BluetoothDevice* bluetooth_device, + ConnectionMedium connection_medium, + ConnectionRole connection_role) override; + + // SecureChannel::Observer: + void OnSecureChannelStatusChanged( + SecureChannel* secure_channel, + const SecureChannel::Status& old_status, + const SecureChannel::Status& new_status) override; + + // Returns whether a channel exists connecting to |remote_device_id|, + // regardless of the local device ID used to create the connection. + bool DoesAuthenticatingChannelExist(const std::string& remote_device_id); + + // Adds |secure_channel| to |remote_device_id_to_secure_channel_map_| and + // pauses any ongoing attempts to |remote_device_id|, since a connection has + // already been established to that device. + void SetAuthenticatingChannel(const std::string& remote_device_id, + std::unique_ptr<SecureChannel> secure_channel); + + // Pauses pending connection attempts (i.e., BLE scanning) for + // |remote_device_id|. + void PauseConnectionAttemptsToDevice(const std::string& remote_device_id); + + // Restarts connections which were paused as part of + // PauseConnectionAttemptsToDevice(); + void RestartPausedAttemptsToDevice(const std::string& remote_device_id); + + // Checks to see if there is a leftover channel authenticating with + // |remote_device_id| even though there are no pending requests for a + // connection to that device. This situation arises when an active request is + // canceled after a connection has been established but before that connection + // has been fully authenticated. This function disconnects the channel in the + // case that it finds one. + void ProcessPotentialLingeringChannel(const std::string& remote_device_id); + + std::string GetRemoteDeviceIdForSecureChannel(SecureChannel* secure_channel); + void HandleSecureChannelDisconnection(const std::string& remote_device_id, + bool was_authenticating); + void HandleChannelAuthenticated(const std::string& remote_device_id); + + // Chooses the connection attempt which will receive the success callback. + // It is possible that there is more than one possible recipient in the case + // that two attempts are made with the same remote device ID but different + // local device IDs. In the case of multiple possible recipients, we + // arbitrarily choose the one which was registered first. + DeviceIdPair ChooseChannelRecipient(const std::string& remote_device_id); + + BleScanner* ble_scanner_; + SecureChannelDisconnector* secure_channel_disconnector_; + + base::flat_map<std::string, std::unique_ptr<SecureChannel>> + remote_device_id_to_secure_channel_map_; + base::Optional<std::string> notifying_remote_device_id_; }; } // namespace secure_channel
diff --git a/chromeos/services/secure_channel/nearby_connection_manager_impl_unittest.cc b/chromeos/services/secure_channel/nearby_connection_manager_impl_unittest.cc index 9f9b4cd..75e8bb5 100644 --- a/chromeos/services/secure_channel/nearby_connection_manager_impl_unittest.cc +++ b/chromeos/services/secure_channel/nearby_connection_manager_impl_unittest.cc
@@ -6,15 +6,118 @@ #include <memory> +#include "base/test/task_environment.h" +#include "chromeos/components/multidevice/remote_device_test_util.h" +#include "chromeos/services/secure_channel/authenticated_channel_impl.h" +#include "chromeos/services/secure_channel/fake_authenticated_channel.h" +#include "chromeos/services/secure_channel/fake_ble_scanner.h" +#include "chromeos/services/secure_channel/fake_connection.h" +#include "chromeos/services/secure_channel/fake_secure_channel_connection.h" +#include "chromeos/services/secure_channel/fake_secure_channel_disconnector.h" +#include "chromeos/services/secure_channel/nearby_connection.h" +#include "chromeos/services/secure_channel/secure_channel.h" #include "testing/gtest/include/gtest/gtest.h" namespace chromeos { namespace secure_channel { +namespace { + +const size_t kNumTestDevices = 3; + +class FakeNearbyConnectionFactory : public NearbyConnection::Factory { + public: + FakeNearbyConnectionFactory() = default; + FakeNearbyConnectionFactory(const FakeNearbyConnectionFactory&) = delete; + FakeNearbyConnectionFactory& operator=(const FakeNearbyConnectionFactory&) = + delete; + ~FakeNearbyConnectionFactory() override = default; + + FakeConnection* last_created_instance() { return last_created_instance_; } + + private: + // cryptauth::NearbyConnection::Factory: + std::unique_ptr<Connection> CreateInstance( + multidevice::RemoteDeviceRef remote_device) override { + auto instance = std::make_unique<FakeConnection>(remote_device); + last_created_instance_ = instance.get(); + return instance; + } + + FakeConnection* last_created_instance_ = nullptr; +}; + +class FakeSecureChannelFactory : public SecureChannel::Factory { + public: + FakeSecureChannelFactory() = default; + FakeSecureChannelFactory(const FakeSecureChannelFactory&) = delete; + FakeSecureChannelFactory& operator=(const FakeSecureChannelFactory&) = delete; + virtual ~FakeSecureChannelFactory() = default; + + FakeSecureChannelConnection* last_created_instance() { + return last_created_instance_; + } + + private: + // SecureChannel::Factory: + std::unique_ptr<SecureChannel> CreateInstance( + std::unique_ptr<Connection> connection) override { + auto instance = + std::make_unique<FakeSecureChannelConnection>(std::move(connection)); + last_created_instance_ = instance.get(); + return instance; + } + + FakeSecureChannelConnection* last_created_instance_ = nullptr; +}; + +class FakeAuthenticatedChannelFactory + : public AuthenticatedChannelImpl::Factory { + public: + FakeAuthenticatedChannelFactory() = default; + FakeAuthenticatedChannelFactory(const FakeAuthenticatedChannelFactory&) = + delete; + FakeAuthenticatedChannelFactory& operator=( + const FakeAuthenticatedChannelFactory&) = delete; + ~FakeAuthenticatedChannelFactory() override = default; + + void SetExpectationsForNextCall( + FakeSecureChannelConnection* expected_fake_secure_channel) { + expected_fake_secure_channel_ = expected_fake_secure_channel; + } + + FakeAuthenticatedChannel* last_created_instance() { + return last_created_instance_; + } + + private: + // AuthenticatedChannelImpl::Factory: + std::unique_ptr<AuthenticatedChannel> CreateInstance( + const std::vector<mojom::ConnectionCreationDetail>& + connection_creation_details, + std::unique_ptr<SecureChannel> secure_channel) override { + EXPECT_EQ(expected_fake_secure_channel_, secure_channel.get()); + + auto instance = std::make_unique<FakeAuthenticatedChannel>(); + last_created_instance_ = instance.get(); + return instance; + } + + FakeSecureChannelConnection* expected_fake_secure_channel_ = nullptr; + FakeAuthenticatedChannel* last_created_instance_ = nullptr; +}; + +} // namespace + class SecureChannelNearbyConnectionManagerImplTest : public testing::Test { protected: - SecureChannelNearbyConnectionManagerImplTest() = default; + SecureChannelNearbyConnectionManagerImplTest() + : task_environment_( + base::test::TaskEnvironment::MainThreadType::DEFAULT, + base::test::TaskEnvironment::ThreadPoolExecutionMode::QUEUED), + test_devices_( + multidevice::CreateRemoteDeviceRefListForTest(kNumTestDevices)) {} SecureChannelNearbyConnectionManagerImplTest( const SecureChannelNearbyConnectionManagerImplTest&) = delete; SecureChannelNearbyConnectionManagerImplTest& operator=( @@ -23,15 +126,341 @@ // testing::Test: void SetUp() override { - manager_ = NearbyConnectionManagerImpl::Factory::Create(); + fake_nearby_connection_factory_ = + std::make_unique<FakeNearbyConnectionFactory>(); + NearbyConnection::Factory::SetFactoryForTesting( + fake_nearby_connection_factory_.get()); + + fake_secure_channel_factory_ = std::make_unique<FakeSecureChannelFactory>(); + SecureChannel::Factory::SetFactoryForTesting( + fake_secure_channel_factory_.get()); + + fake_authenticated_channel_factory_ = + std::make_unique<FakeAuthenticatedChannelFactory>(); + AuthenticatedChannelImpl::Factory::SetFactoryForTesting( + fake_authenticated_channel_factory_.get()); + + fake_ble_scanner_ = std::make_unique<FakeBleScanner>(); + fake_secure_channel_disconnector_ = + std::make_unique<FakeSecureChannelDisconnector>(); + + manager_ = NearbyConnectionManagerImpl::Factory::Create( + fake_ble_scanner_.get(), fake_secure_channel_disconnector_.get()); } + void TearDown() override { + NearbyConnection::Factory::SetFactoryForTesting(nullptr); + SecureChannel::Factory::SetFactoryForTesting(nullptr); + AuthenticatedChannelImpl::Factory::SetFactoryForTesting(nullptr); + } + + void AttemptNearbyInitiatorConnection(const DeviceIdPair& device_id_pair, + bool expected_to_add_request, + bool should_cancel_attempt_on_failure) { + SetInRemoteDeviceIdToMetadataMap(device_id_pair); + + manager_->AttemptNearbyInitiatorConnection( + device_id_pair, + base::BindOnce( + &SecureChannelNearbyConnectionManagerImplTest::OnConnectionSuccess, + base::Unretained(this), device_id_pair), + base::BindRepeating(&SecureChannelNearbyConnectionManagerImplTest:: + OnNearbyInitiatorFailure, + base::Unretained(this), device_id_pair, + should_cancel_attempt_on_failure)); + + bool has_request = + fake_ble_scanner_->HasScanRequest(ConnectionAttemptDetails( + device_id_pair, ConnectionMedium::kNearbyConnections, + ConnectionRole::kInitiatorRole)); + EXPECT_EQ(expected_to_add_request, has_request); + } + + void CancelNearbyInitiatorConnectionAttempt( + const DeviceIdPair& device_id_pair) { + RemoveFromRemoteDeviceIdToMetadataMap(device_id_pair); + manager_->CancelNearbyInitiatorConnectionAttempt(device_id_pair); + EXPECT_FALSE(fake_ble_scanner_->HasScanRequest(ConnectionAttemptDetails( + device_id_pair, ConnectionMedium::kNearbyConnections, + ConnectionRole::kInitiatorRole))); + } + + // Returns the SecureChannel created by this call. + FakeSecureChannelConnection* SimulateConnectionEstablished( + multidevice::RemoteDeviceRef remote_device) { + fake_ble_scanner_->NotifyReceivedAdvertisementFromDevice( + remote_device, /*bluetooth_device=*/nullptr, + ConnectionMedium::kNearbyConnections, ConnectionRole::kInitiatorRole); + + // As a result of the connection, all ongoing connection attmepts should + // have been canceled, since a connection is in progress. + EXPECT_TRUE( + fake_ble_scanner_ + ->GetAllScanRequestsForRemoteDevice(remote_device.GetDeviceId()) + .empty()); + + FakeSecureChannelConnection* last_created_secure_channel = + fake_secure_channel_factory_->last_created_instance(); + EXPECT_TRUE(last_created_secure_channel->was_initialized()); + return last_created_secure_channel; + } + + void SimulateSecureChannelDisconnection( + const std::string& remote_device_id, + bool fail_during_authentication, + FakeSecureChannelConnection* fake_secure_channel, + size_t num_initiator_attempts_canceled_from_disconnection = 0u) { + size_t num_nearby_initiator_failures_before_call = + nearby_initiator_failures_.size(); + + // Connect, then disconnect. If needed, start authenticating before + // disconnecting. + fake_secure_channel->ChangeStatus(SecureChannel::Status::CONNECTED); + if (fail_during_authentication) { + fake_secure_channel->ChangeStatus(SecureChannel::Status::AUTHENTICATING); + } + fake_secure_channel->ChangeStatus(SecureChannel::Status::DISCONNECTED); + + // Iterate through all pending requests to |remote_device_id|, ensuring that + // all expected failures have been communicated back to the client. + size_t initiator_failures_index = + num_nearby_initiator_failures_before_call + + num_initiator_attempts_canceled_from_disconnection; + for (const auto& pair : + remote_device_id_to_id_pairs_map_[remote_device_id]) { + EXPECT_EQ(pair, + nearby_initiator_failures_[initiator_failures_index].first); + EXPECT_EQ(fail_during_authentication + ? NearbyInitiatorFailureType::kAuthenticationError + : NearbyInitiatorFailureType::kConnectivityError, + nearby_initiator_failures_[initiator_failures_index].second); + ++initiator_failures_index; + } + EXPECT_EQ(initiator_failures_index, nearby_initiator_failures_.size()); + + // All requests which were paused during the connection should have started + // back up again, since the connection became disconnected. + for (const auto& pair : + remote_device_id_to_id_pairs_map_[remote_device_id]) { + EXPECT_TRUE(fake_ble_scanner_->HasScanRequest( + ConnectionAttemptDetails(pair, ConnectionMedium::kNearbyConnections, + ConnectionRole::kInitiatorRole))); + } + } + + void SimulateSecureChannelAuthentication( + const std::string& remote_device_id, + FakeSecureChannelConnection* fake_secure_channel) { + fake_authenticated_channel_factory_->SetExpectationsForNextCall( + fake_secure_channel); + + size_t num_success_callbacks_before_call = successful_connections_.size(); + + fake_secure_channel->ChangeStatus(SecureChannel::Status::CONNECTED); + fake_secure_channel->ChangeStatus(SecureChannel::Status::AUTHENTICATING); + fake_secure_channel->ChangeStatus(SecureChannel::Status::AUTHENTICATED); + + // Verify that the callback was made. Verification that the provided + // DeviceIdPair was correct occurs in OnConnectionSuccess(). + EXPECT_EQ(num_success_callbacks_before_call + 1u, + successful_connections_.size()); + + // For all remaining requests, verify that they were added back. + for (const auto& pair : + remote_device_id_to_id_pairs_map_[remote_device_id]) { + EXPECT_TRUE(fake_ble_scanner_->HasScanRequest( + ConnectionAttemptDetails(pair, ConnectionMedium::kNearbyConnections, + ConnectionRole::kInitiatorRole))); + } + } + + bool WasChannelHandledByDisconnector( + FakeSecureChannelConnection* fake_secure_channel) { + return fake_secure_channel_disconnector_->WasChannelHandled( + fake_secure_channel); + } + + base::test::TaskEnvironment task_environment_; + const multidevice::RemoteDeviceRefList& test_devices() { + return test_devices_; + } + + private: + void OnConnectionSuccess( + const DeviceIdPair& device_id_pair, + std::unique_ptr<AuthenticatedChannel> authenticated_channel) { + successful_connections_.push_back( + std::make_pair(device_id_pair, std::move(authenticated_channel))); + + // The request which received the success callback is automatically removed + // by NearbyConnectionManager, so it no longer needs to be tracked. + remote_device_id_to_id_pairs_map_[device_id_pair.remote_device_id()].erase( + device_id_pair); + + // Make a copy of the entries which should be canceled. This is required + // because the Cancel*() calls above end up removing entries from + // |remote_device_id_to_id_pairs_map_|, which can cause access to deleted + // memory. + base::flat_set<DeviceIdPair> to_cancel = + remote_device_id_to_id_pairs_map_[device_id_pair.remote_device_id()]; + + for (const auto& pair : to_cancel) + CancelNearbyInitiatorConnectionAttempt(pair); + } + + void OnNearbyInitiatorFailure(const DeviceIdPair& device_id_pair, + bool should_cancel_attempt_on_failure, + NearbyInitiatorFailureType failure_type) { + nearby_initiator_failures_.push_back( + std::make_pair(device_id_pair, failure_type)); + if (!should_cancel_attempt_on_failure) + return; + + // Make a copy of the pair before canceling the attempt, since the reference + // points to memory owned by |manager_| which will be deleted. + DeviceIdPair device_id_pair_copy = device_id_pair; + CancelNearbyInitiatorConnectionAttempt(device_id_pair_copy); + } + + void SetInRemoteDeviceIdToMetadataMap(const DeviceIdPair& device_id_pair) { + remote_device_id_to_id_pairs_map_[device_id_pair.remote_device_id()].insert( + device_id_pair); + } + + void RemoveFromRemoteDeviceIdToMetadataMap( + const DeviceIdPair& device_id_pair) { + base::flat_set<DeviceIdPair>& set_for_remote_device = + remote_device_id_to_id_pairs_map_[device_id_pair.remote_device_id()]; + + for (auto it = set_for_remote_device.begin(); + it != set_for_remote_device.end(); ++it) { + if (*it == device_id_pair) { + set_for_remote_device.erase(it); + return; + } + } + + NOTREACHED(); + } + + const multidevice::RemoteDeviceRefList test_devices_; + + base::flat_map<std::string, base::flat_set<DeviceIdPair>> + remote_device_id_to_id_pairs_map_; + + std::vector<std::pair<DeviceIdPair, std::unique_ptr<AuthenticatedChannel>>> + successful_connections_; + std::vector<std::pair<DeviceIdPair, NearbyInitiatorFailureType>> + nearby_initiator_failures_; + + std::unique_ptr<FakeNearbyConnectionFactory> fake_nearby_connection_factory_; + std::unique_ptr<FakeSecureChannelFactory> fake_secure_channel_factory_; + std::unique_ptr<FakeAuthenticatedChannelFactory> + fake_authenticated_channel_factory_; + + std::unique_ptr<FakeBleScanner> fake_ble_scanner_; + std::unique_ptr<FakeSecureChannelDisconnector> + fake_secure_channel_disconnector_; + std::unique_ptr<NearbyConnectionManager> manager_; }; -// TODO(https://crbug.com/1106937): Delete when a real test is added. -TEST_F(SecureChannelNearbyConnectionManagerImplTest, Create) { - EXPECT_TRUE(manager_); +TEST_F(SecureChannelNearbyConnectionManagerImplTest, + AttemptAndCancelWithoutConnection) { + DeviceIdPair pair(test_devices()[1].GetDeviceId(), + test_devices()[0].GetDeviceId()); + + AttemptNearbyInitiatorConnection(pair, + /*expected_to_add_request=*/true, + /*should_cancel_attempt_on_failure=*/false); + CancelNearbyInitiatorConnectionAttempt(pair); +} + +TEST_F(SecureChannelNearbyConnectionManagerImplTest, + StartConnectionThenDisconnect_CancelAfter) { + DeviceIdPair pair(test_devices()[1].GetDeviceId(), + test_devices()[0].GetDeviceId()); + + AttemptNearbyInitiatorConnection(pair, + /*expected_to_add_request=*/true, + /*should_cancel_attempt_on_failure=*/false); + + FakeSecureChannelConnection* fake_secure_channel = + SimulateConnectionEstablished(test_devices()[1]); + SimulateSecureChannelDisconnection(pair.remote_device_id(), + /*fail_during_authentication=*/true, + fake_secure_channel); + + CancelNearbyInitiatorConnectionAttempt(pair); +} + +TEST_F(SecureChannelNearbyConnectionManagerImplTest, + StartConnectionThenDisconnect_CancelInCallback) { + DeviceIdPair pair(test_devices()[1].GetDeviceId(), + test_devices()[0].GetDeviceId()); + + AttemptNearbyInitiatorConnection(pair, + /*expected_to_add_request=*/true, + /*should_cancel_attempt_on_failure=*/true); + + FakeSecureChannelConnection* fake_secure_channel = + SimulateConnectionEstablished(test_devices()[1]); + SimulateSecureChannelDisconnection( + pair.remote_device_id(), + /*fail_during_authentication=*/true, fake_secure_channel, + /*num_initiator_attempts_canceled_from_disconnection=*/1u); +} + +TEST_F(SecureChannelNearbyConnectionManagerImplTest, SuccessfulConnection) { + DeviceIdPair pair(test_devices()[1].GetDeviceId(), + test_devices()[0].GetDeviceId()); + + AttemptNearbyInitiatorConnection(pair, + /*expected_to_add_request=*/true, + /*should_cancel_attempt_on_failure=*/true); + + FakeSecureChannelConnection* fake_secure_channel = + SimulateConnectionEstablished(test_devices()[1]); + SimulateSecureChannelAuthentication(pair.remote_device_id(), + fake_secure_channel); +} + +TEST_F(SecureChannelNearbyConnectionManagerImplTest, TwoSimultaneousAttempts) { + DeviceIdPair pair_1(test_devices()[1].GetDeviceId(), + test_devices()[0].GetDeviceId()); + DeviceIdPair pair_2(test_devices()[2].GetDeviceId(), + test_devices()[0].GetDeviceId()); + + AttemptNearbyInitiatorConnection(pair_1, + /*expected_to_add_request=*/true, + /*should_cancel_attempt_on_failure=*/true); + AttemptNearbyInitiatorConnection(pair_2, + /*expected_to_add_request=*/true, + /*should_cancel_attempt_on_failure=*/true); + + FakeSecureChannelConnection* fake_secure_channel_1 = + SimulateConnectionEstablished(test_devices()[1]); + SimulateSecureChannelAuthentication(pair_1.remote_device_id(), + fake_secure_channel_1); + FakeSecureChannelConnection* fake_secure_channel_2 = + SimulateConnectionEstablished(test_devices()[2]); + SimulateSecureChannelAuthentication(pair_2.remote_device_id(), + fake_secure_channel_2); +} + +TEST_F(SecureChannelNearbyConnectionManagerImplTest, + CancelWhileAuthenticating) { + DeviceIdPair pair(test_devices()[1].GetDeviceId(), + test_devices()[0].GetDeviceId()); + + AttemptNearbyInitiatorConnection(pair, + /*expected_to_add_request=*/true, + /*should_cancel_attempt_on_failure=*/true); + + FakeSecureChannelConnection* fake_secure_channel = + SimulateConnectionEstablished(test_devices()[1]); + CancelNearbyInitiatorConnectionAttempt(pair); + EXPECT_TRUE(WasChannelHandledByDisconnector(fake_secure_channel)); } } // namespace secure_channel
diff --git a/chromeos/services/secure_channel/secure_channel_impl.cc b/chromeos/services/secure_channel/secure_channel_impl.cc index 864bc6aa..bf65f28 100644 --- a/chromeos/services/secure_channel/secure_channel_impl.cc +++ b/chromeos/services/secure_channel/secure_channel_impl.cc
@@ -85,8 +85,9 @@ ble_scanner_.get(), secure_channel_disconnector_.get(), timer_factory_.get())), - nearby_connection_manager_( - NearbyConnectionManagerImpl::Factory::Create()), + nearby_connection_manager_(NearbyConnectionManagerImpl::Factory::Create( + ble_scanner_.get(), + secure_channel_disconnector_.get())), pending_connection_manager_(PendingConnectionManagerImpl::Factory::Create( this /* delegate */, ble_connection_manager_.get(),
diff --git a/chromeos/services/secure_channel/secure_channel_service_unittest.cc b/chromeos/services/secure_channel/secure_channel_service_unittest.cc index 8a19be9..d6de35a 100644 --- a/chromeos/services/secure_channel/secure_channel_service_unittest.cc +++ b/chromeos/services/secure_channel/secure_channel_service_unittest.cc
@@ -273,20 +273,37 @@ class FakeNearbyConnectionManagerFactory : public NearbyConnectionManagerImpl::Factory { public: - FakeNearbyConnectionManagerFactory() = default; + FakeNearbyConnectionManagerFactory( + FakeBleScannerFactory* fake_ble_scanner_factory, + FakeSecureChannelDisconnectorFactory* + fake_secure_channel_disconnector_factory) + : fake_ble_scanner_factory_(fake_ble_scanner_factory), + fake_secure_channel_disconnector_factory_( + fake_secure_channel_disconnector_factory) {} + ~FakeNearbyConnectionManagerFactory() override = default; FakeNearbyConnectionManager* instance() { return instance_; } private: // NearbyConnectionManagerImpl::Factory: - std::unique_ptr<NearbyConnectionManager> CreateInstance() override { + std::unique_ptr<NearbyConnectionManager> CreateInstance( + BleScanner* ble_scanner, + SecureChannelDisconnector* secure_channel_disconnector) override { + EXPECT_EQ(fake_ble_scanner_factory_->instance(), ble_scanner); + EXPECT_EQ(fake_secure_channel_disconnector_factory_->instance(), + secure_channel_disconnector); + EXPECT_FALSE(instance_); auto instance = std::make_unique<FakeNearbyConnectionManager>(); instance_ = instance.get(); return instance; } + FakeBleScannerFactory* fake_ble_scanner_factory_; + FakeSecureChannelDisconnectorFactory* + fake_secure_channel_disconnector_factory_; + FakeNearbyConnectionManager* instance_ = nullptr; DISALLOW_COPY_AND_ASSIGN(FakeNearbyConnectionManagerFactory); @@ -519,7 +536,9 @@ fake_ble_connection_manager_factory_.get()); fake_nearby_connection_manager_factory_ = - std::make_unique<FakeNearbyConnectionManagerFactory>(); + std::make_unique<FakeNearbyConnectionManagerFactory>( + fake_ble_scanner_factory_.get(), + fake_secure_channel_disconnector_factory_.get()); NearbyConnectionManagerImpl::Factory::SetFactoryForTesting( fake_nearby_connection_manager_factory_.get());
diff --git a/components/BUILD.gn b/components/BUILD.gn index 546312b..48ce9be 100644 --- a/components/BUILD.gn +++ b/components/BUILD.gn
@@ -775,6 +775,7 @@ "//components/embedder_support/android:components_embedder_support_junit_tests", "//components/gcm_driver/android:components_gcm_driver_junit_tests", "//components/media_router/browser/android:junit", + "//components/messages/android/internal:junit", "//components/permissions/android:components_permissions_junit_tests", "//components/policy/android:components_policy_junit_tests", "//components/prefs/android:junit",
diff --git a/components/README.md b/components/README.md index ea3b0eb9..9d8f29a 100644 --- a/components/README.md +++ b/components/README.md
@@ -48,6 +48,7 @@ * `//gpu` * `//mojo` * `//net` + * `//printing` * `//ui` Components **can** depend on each other. This must be made explicit in the
diff --git a/components/arc/mojom/metrics.mojom b/components/arc/mojom/metrics.mojom index b076bb6..5de9ef7 100644 --- a/components/arc/mojom/metrics.mojom +++ b/components/arc/mojom/metrics.mojom
@@ -1,7 +1,7 @@ // Copyright 2016 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -// Next MinVersion: 5 +// Next MinVersion: 6 module arc.mojom; @@ -39,6 +39,17 @@ int64 uptimeMillis; }; +// Describes a GFX metrics. +struct GfxMetrics { + // Total frames rendered, it includes janky frames below. + uint64 framesTotal; + // Janky frames. + uint64 framesJanky; + // Maximum frame time in milliseconds of 95% of frames sorted from the + // shortest to longest. + uint32 frameTimePercentile95; +}; + [Extensible] enum NativeBridgeType { // Native bridge is not used. @@ -105,11 +116,15 @@ [MinVersion=4] ReportCompanionLibApiUsage@2(CompanionLibApiId api_id); }; -// Next method ID: 2 +// Next method ID: 3 interface MetricsInstance { // DEPRECATED: Please use Init@1 instead. InitDeprecated@0(pending_remote<MetricsHost> host_remote); // Establishes full-duplex communication with the host. [MinVersion=2] Init@1(pending_remote<MetricsHost> host_remote) => (); + + // Requests GFX metrics for the specified package. In case of error, null is + // returned. + [MinVersion=5] GetGfxMetrics@2(string packageName) => (GfxMetrics? metrics); };
diff --git a/components/autofill/content/renderer/BUILD.gn b/components/autofill/content/renderer/BUILD.gn index 6e95790..84f03d8 100644 --- a/components/autofill/content/renderer/BUILD.gn +++ b/components/autofill/content/renderer/BUILD.gn
@@ -85,7 +85,6 @@ source_set("unit_tests") { testonly = true sources = [ - "form_cache_unittest.cc", "prefilled_values_detector_unittest.cc", "renderer_save_password_progress_logger_unittest.cc", ]
diff --git a/components/autofill/content/renderer/form_cache.cc b/components/autofill/content/renderer/form_cache.cc index d59103e..a64c24a 100644 --- a/components/autofill/content/renderer/form_cache.cc +++ b/components/autofill/content/renderer/form_cache.cc
@@ -55,38 +55,6 @@ namespace { -static const char* kSupportedAutocompleteTypes[] = {"given-name", - "additional-name", - "family-name", - "name", - "honorific-suffix", - "email", - "tel-local", - "tel-area-code", - "tel-country-code", - "tel-national", - "tel", - "tel-extension", - "street-address", - "address-line1", - "address-line2", - "address-line3", - "address-level1", - "address-level2", - "address-level3", - "postal-code", - "country-name", - "cc-name", - "cc-given-name", - "cc-family-name", - "cc-number", - "cc-exp-month", - "cc-exp-year", - "cc-exp", - "cc-type", - "cc-csc", - "organization"}; - blink::FormElementPiiType MapTypePredictionToFormElementPiiType( base::StringPiece type) { if (type == "NO_SERVER_DATA" || type == "UNKNOWN_TYPE" || @@ -101,77 +69,6 @@ return blink::FormElementPiiType::kOthers; } -// For a given |type| (a string representation of enum values), return the -// appropriate autocomplete value that should be suggested to the website -// developer. -const char* MapTypePredictionToAutocomplete(base::StringPiece type) { - if (type == "NAME_FIRST") - return kSupportedAutocompleteTypes[0]; - if (type == "NAME_MIDDLE") - return kSupportedAutocompleteTypes[1]; - if (type == "NAME_LAST") - return kSupportedAutocompleteTypes[2]; - if (type == "NAME_FULL") - return kSupportedAutocompleteTypes[3]; - if (type == "NAME_SUFFIX") - return kSupportedAutocompleteTypes[4]; - if (type == "EMAIL_ADDRESS") - return kSupportedAutocompleteTypes[5]; - if (type == "PHONE_HOME_NUMBER") - return kSupportedAutocompleteTypes[6]; - if (type == "PHONE_HOME_CITY_CODE") - return kSupportedAutocompleteTypes[7]; - if (type == "PHONE_HOME_COUNTRY_CODE") - return kSupportedAutocompleteTypes[8]; - if (type == "PHONE_HOME_CITY_AND_NUMBER") - return kSupportedAutocompleteTypes[9]; - if (type == "PHONE_HOME_WHOLE_NUMBER") - return kSupportedAutocompleteTypes[10]; - if (type == "PHONE_HOME_EXTENSION") - return kSupportedAutocompleteTypes[11]; - if (type == "ADDRESS_HOME_STREET_ADDRESS") - return kSupportedAutocompleteTypes[12]; - if (type == "ADDRESS_HOME_LINE1") - return kSupportedAutocompleteTypes[13]; - if (type == "ADDRESS_HOME_LINE2") - return kSupportedAutocompleteTypes[14]; - if (type == "ADDRESS_HOME_LINE3") - return kSupportedAutocompleteTypes[15]; - if (type == "ADDRESS_HOME_STATE") - return kSupportedAutocompleteTypes[16]; - if (type == "ADDRESS_HOME_CITY") - return kSupportedAutocompleteTypes[17]; - if (type == "ADDRESS_HOME_DEPENDENT_LOCALITY") - return kSupportedAutocompleteTypes[18]; - if (type == "ADDRESS_HOME_ZIP") - return kSupportedAutocompleteTypes[19]; - if (type == "ADDRESS_HOME_COUNTRY") - return kSupportedAutocompleteTypes[20]; - if (type == "CREDIT_CARD_NAME_FULL") - return kSupportedAutocompleteTypes[21]; - if (type == "CREDIT_CARD_NAME_FIRST") - return kSupportedAutocompleteTypes[22]; - if (type == "CREDIT_CARD_NAME_LAST") - return kSupportedAutocompleteTypes[23]; - if (type == "CREDIT_CARD_NUMBER") - return kSupportedAutocompleteTypes[24]; - if (type == "CREDIT_CARD_EXP_MONTH") - return kSupportedAutocompleteTypes[25]; - if (type == "CREDIT_CARD_EXP_2_DIGIT_YEAR" || - type == "CREDIT_CARD_EXP_4_DIGIT_YEAR") - return kSupportedAutocompleteTypes[26]; - if (type == "CREDIT_CARD_EXP_DATE_2_DIGIT_YEAR" || - type == "CREDIT_CARD_EXP_DATE_4_DIGIT_YEAR") - return kSupportedAutocompleteTypes[27]; - if (type == "CREDIT_CARD_TYPE") - return kSupportedAutocompleteTypes[28]; - if (type == "CREDIT_CARD_VERIFICATION_CODE") - return kSupportedAutocompleteTypes[29]; - if (type == "COMPANY_NAME") - return kSupportedAutocompleteTypes[30]; - return ""; -} - void LogDeprecationMessages(const WebFormControlElement& element) { std::string autocomplete_attribute = element.GetAttribute("autocomplete").Utf8(); @@ -468,21 +365,6 @@ continue; const FormFieldDataPredictions& field = form.fields[i]; - // Possibly add a console warning for this field regarding the usage of - // autocomplete attributes. - const std::string predicted_autocomplete_attribute = - MapTypePredictionToAutocomplete(field.overall_type); - if (ShouldShowAutocompleteConsoleWarnings( - predicted_autocomplete_attribute, - element.GetAttribute("autocomplete").Utf8())) { - logger.Send( - base::StringPrintf("Input elements should have autocomplete " - "attributes (suggested: autocomplete='%s', " - "confirm at https://goo.gl/6KgkJg)", - predicted_autocomplete_attribute.c_str()), - PageFormAnalyserLogger::kVerbose, element); - } - element.SetFormElementPiiType( MapTypePredictionToFormElementPiiType(field.overall_type)); @@ -569,38 +451,6 @@ } } -bool FormCache::ShouldShowAutocompleteConsoleWarnings( - const std::string& predicted_autocomplete, - const std::string& actual_autocomplete) { - if (!base::FeatureList::IsEnabled( - features::kAutofillShowAutocompleteConsoleWarnings)) { - return false; - } - - // If we have no better prediction, do not show. - if (predicted_autocomplete.empty()) - return false; - - // We should show a warning if the actual autocomplete attribute is empty, - // or we recognize the autocomplete attribute, but we think it's the wrong - // one. - if (actual_autocomplete.empty()) - return true; - - // An autocomplete attribute can be multiple strings (e.g. "shipping name"). - // Look at all the tokens. - for (base::StringPiece actual : base::SplitStringPiece( - actual_autocomplete, " ", base::WhitespaceHandling::TRIM_WHITESPACE, - base::SplitResult::SPLIT_WANT_NONEMPTY)) { - // If we recognize the value but it's not correct, show a warning. - if (base::Contains(kSupportedAutocompleteTypes, actual) && - actual != predicted_autocomplete) { - return true; - } - } - return false; -} - void FormCache::PruneInitialValueCaches( const std::set<FieldRendererId>& ids_to_retain) { auto should_not_retain = [&ids_to_retain](const auto& p) {
diff --git a/components/autofill/content/renderer/form_cache_unittest.cc b/components/autofill/content/renderer/form_cache_unittest.cc deleted file mode 100644 index 1cf98ed..0000000 --- a/components/autofill/content/renderer/form_cache_unittest.cc +++ /dev/null
@@ -1,82 +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. - -#include "components/autofill/content/renderer/form_cache.h" - -#include "base/macros.h" -#include "base/test/scoped_feature_list.h" -#include "components/autofill/core/common/autofill_features.h" -#include "testing/gtest/include/gtest/gtest.h" - -namespace autofill { - -class FormCacheTest : public testing::Test { - public: - FormCacheTest() {} - - protected: - base::test::ScopedFeatureList scoped_feature_list_; - - DISALLOW_COPY_AND_ASSIGN(FormCacheTest); -}; - -TEST_F(FormCacheTest, ShouldShowAutocompleteConsoleWarnings_Enabled) { - scoped_feature_list_.InitAndEnableFeature( - features::kAutofillShowAutocompleteConsoleWarnings); - FormCache form_cache(nullptr); - - // If we have a prediction and the actual attribute is empty. - EXPECT_TRUE( - form_cache.ShouldShowAutocompleteConsoleWarnings("given-name", "")); - // There is a predicted type, and there is an recognized type that is not the - // same. - EXPECT_TRUE( - form_cache.ShouldShowAutocompleteConsoleWarnings("given-name", "name")); - // Multi-values: there is a predicted type, and there is an recognized type - // that is not the same. - EXPECT_TRUE(form_cache.ShouldShowAutocompleteConsoleWarnings( - "given-name", "shipping name")); - // Multi-values: there is a predicted type, and there is an recognized type - // that is not the same along with an unrecognized type. - EXPECT_TRUE(form_cache.ShouldShowAutocompleteConsoleWarnings("given-name", - "fake name")); - - // No predicted type, no actual attribute. - EXPECT_FALSE(form_cache.ShouldShowAutocompleteConsoleWarnings("", "")); - // No predicted type, and there is a recognized type. - EXPECT_FALSE( - form_cache.ShouldShowAutocompleteConsoleWarnings("", "given-name")); - // No predicted type, and there is an unrecognized type. - EXPECT_FALSE(form_cache.ShouldShowAutocompleteConsoleWarnings("", "fake")); - // There is a predicted type, and there is an unrecognized type. - EXPECT_FALSE( - form_cache.ShouldShowAutocompleteConsoleWarnings("given-name", "fake")); - // Multi-values: there is a predicted type, and there is an recognized type - // that is the same. - EXPECT_FALSE(form_cache.ShouldShowAutocompleteConsoleWarnings( - "given-name", "shipping given-name")); - // Multi-values: there is a predicted type, and there is an unrecognized type. - EXPECT_FALSE(form_cache.ShouldShowAutocompleteConsoleWarnings( - "given-name", "shipping fake")); -} - -TEST_F(FormCacheTest, ShouldShowAutocompleteConsoleWarnings_Disabled) { - scoped_feature_list_.InitAndDisableFeature( - features::kAutofillShowAutocompleteConsoleWarnings); - FormCache form_cache(nullptr); - - // If we have a prediction and the actual attribute is empty. - EXPECT_FALSE( - form_cache.ShouldShowAutocompleteConsoleWarnings("given-name", "")); - // There is a predicted type, and there is an recognized type that is not the - // same. - EXPECT_FALSE( - form_cache.ShouldShowAutocompleteConsoleWarnings("given-name", "name")); - // Multi-values: there is a predicted type, and there is an recognized type - // that is not the same. - EXPECT_FALSE(form_cache.ShouldShowAutocompleteConsoleWarnings( - "given-name", "shipping name")); -} - -} // namespace autofill
diff --git a/components/autofill/core/browser/autofill_manager_unittest.cc b/components/autofill/core/browser/autofill_manager_unittest.cc index d387969..bfb7d482 100644 --- a/components/autofill/core/browser/autofill_manager_unittest.cc +++ b/components/autofill/core/browser/autofill_manager_unittest.cc
@@ -804,34 +804,21 @@ parts, l10n_util::GetStringUTF8(IDS_AUTOFILL_ADDRESS_SUMMARY_SEPARATOR)); } -// Credit card suggestion tests related with keyboard accessary and nickname. -class CreditCardSuggestionTest - : public AutofillManagerTest, - public testing::WithParamInterface<std::tuple<bool, bool>> { +// Credit card suggestion tests related with keyboard accessory. +class CreditCardSuggestionTest : public AutofillManagerTest, + public testing::WithParamInterface<bool> { protected: - CreditCardSuggestionTest() - : is_keyboard_accessory_enabled_(std::get<0>(GetParam())), - is_surfacing_server_card_nickname_enabled_(std::get<1>(GetParam())) {} + CreditCardSuggestionTest() : is_keyboard_accessory_enabled_(GetParam()) {} void SetUp() override { AutofillManagerTest::SetUp(); - std::vector<base::Feature> enabled; - std::vector<base::Feature> disabled; - (is_keyboard_accessory_enabled_ ? enabled : disabled) - .push_back(features::kAutofillKeyboardAccessory); - (is_surfacing_server_card_nickname_enabled_ ? enabled : disabled) - .push_back(features::kAutofillEnableSurfacingServerCardNickname); - features_.InitWithFeatures(enabled, disabled); - } - - bool IsSurfacingServerCardNicknameEnabled() { - return is_surfacing_server_card_nickname_enabled_; + features_.InitWithFeatureState(features::kAutofillKeyboardAccessory, + is_keyboard_accessory_enabled_); } private: base::test::ScopedFeatureList features_; const bool is_keyboard_accessory_enabled_; - const bool is_surfacing_server_card_nickname_enabled_; }; // Test that calling OnFormsSeen with an empty set of forms (such as when @@ -1646,11 +1633,9 @@ const std::string visa_value = std::string("Visa ") + test::ObfuscatedCardDigitsAsUTF8("3456"); // Mastercard has a valid nickname. Display nickname + last four in the - // suggestion title when feature enabled. + // suggestion title. const std::string master_card_value = - (IsSurfacingServerCardNicknameEnabled() ? kArbitraryNickname + " " - : std::string("Mastercard ")) + - test::ObfuscatedCardDigitsAsUTF8("8765"); + kArbitraryNickname + " " + test::ObfuscatedCardDigitsAsUTF8("8765"); #if defined(OS_ANDROID) || defined(OS_IOS) const std::string visa_label = std::string("04/99"); @@ -1700,11 +1685,9 @@ : std::string("Visa ") + obfuscated_last_four_digits1; // Mastercard has a valid nickname. const std::string master_card_label = - IsKeyboardAccessoryEnabled() ? obfuscated_last_four_digits2 - : (IsSurfacingServerCardNicknameEnabled() - ? kArbitraryNickname + " " - : std::string("Mastercard ")) + - obfuscated_last_four_digits2; + IsKeyboardAccessoryEnabled() + ? obfuscated_last_four_digits2 + : kArbitraryNickname + " " + obfuscated_last_four_digits2; #elif defined(OS_IOS) const std::string visa_label = obfuscated_last_four_digits1; @@ -1714,13 +1697,11 @@ // If no nickname available, we will show network. const std::string visa_label = base::JoinString( {"Visa ", obfuscated_last_four_digits1, ", expires on 04/99"}, ""); - // When nickname is available, if nickname experiment is enabled, show - // nickname. Otherwise, show network. - const std::string master_card_label = base::JoinString( - {IsSurfacingServerCardNicknameEnabled() ? kArbitraryNickname + " " - : "Mastercard ", - obfuscated_last_four_digits2, ", expires on 10/98"}, - ""); + // When nickname is available, show nickname. Otherwise, show network. + const std::string master_card_label = + base::JoinString({kArbitraryNickname + " ", obfuscated_last_four_digits2, + ", expires on 10/98"}, + ""); #endif // Test that we sent the right values to the external delegate. @@ -6999,14 +6980,12 @@ #if defined(OS_ANDROID) // When keyboard accessary is enabled, always show "7777". - // When keyboard accessary is disabled, if nickname feature is enabled and - // nickname is valid, show "Nickname ****7777", otherwise, show "Visa - // ****7777". + // When keyboard accessary is disabled, if nickname is valid, show "Nickname + // ****7777", otherwise, show "Visa ****7777". const std::string visa_label = IsKeyboardAccessoryEnabled() ? test::ObfuscatedCardDigitsAsUTF8("7777") - : (IsSurfacingServerCardNicknameEnabled() ? kArbitraryNickname + " " - : std::string("Visa ")) + + : kArbitraryNickname + " " + test::ObfuscatedCardDigitsAsUTF8("7777"); #elif defined(OS_IOS) @@ -7014,9 +6993,8 @@ #else const std::string visa_label = base::JoinString( - {IsSurfacingServerCardNicknameEnabled() ? kArbitraryNickname + " " - : "Visa ", - test::ObfuscatedCardDigitsAsUTF8("7777"), ", expires on 01/30"}, + {kArbitraryNickname + " ", test::ObfuscatedCardDigitsAsUTF8("7777"), + ", expires on 01/30"}, ""); #endif @@ -9163,11 +9141,8 @@ std::make_tuple(1, ""))); #endif // defined(OS_IOS) || defined(OS_ANDROID) -// First bool is to indicate whether AutofillKeyboardAccessory is enabled. -// Second bool is to indicate whether AutofillEnableSurfacingServerCardNickname -// is enabled. -INSTANTIATE_TEST_SUITE_P(All, - CreditCardSuggestionTest, - testing::Combine(testing::Bool(), testing::Bool())); +// The parameter indicates whether the AutofillKeyboardAccessory feature is +// enabled or disabled. +INSTANTIATE_TEST_SUITE_P(All, CreditCardSuggestionTest, testing::Bool()); } // namespace autofill
diff --git a/components/autofill/core/browser/autofill_metrics_unittest.cc b/components/autofill/core/browser/autofill_metrics_unittest.cc index b8e0fd1..95602fd5 100644 --- a/components/autofill/core/browser/autofill_metrics_unittest.cc +++ b/components/autofill/core/browser/autofill_metrics_unittest.cc
@@ -620,35 +620,6 @@ AutofillMetricsCompanyTest, testing::Bool()); -// Test parameter indicates if surfacing server nickname is enabled. The -// nickname-related metrics are always being logged when a server nickname is -// available. Note that depending on the experimental setup, the user may not be -// shown the nickname. -class AutofillMetricsServerNicknameTest - : public AutofillMetricsTest, - public testing::WithParamInterface<bool> { - public: - AutofillMetricsServerNicknameTest() - : is_surfacing_server_card_nickname_enabled_(GetParam()) {} - - void SetUp() override { - scoped_feature_list_.InitWithFeatureState( - features::kAutofillEnableSurfacingServerCardNickname, - is_surfacing_server_card_nickname_enabled_); - AutofillMetricsTest::SetUp(); - } - - protected: - const bool is_surfacing_server_card_nickname_enabled_; - - private: - base::test::ScopedFeatureList scoped_feature_list_; -}; - -INSTANTIATE_TEST_SUITE_P(AutofillMetricsTest, - AutofillMetricsServerNicknameTest, - testing::Bool()); - // Test that we log quality metrics appropriately. TEST_F(AutofillMetricsTest, QualityMetrics) { // Set up our form data. @@ -6650,11 +6621,9 @@ } } -// Test that we log form events for masked server card nickname. When -// surfacing-server-nickname flag is off (we won't display the nickname), we -// still log when user has a masked server card with nickname in order to -// compare the selection rate on the same group of user. -TEST_P(AutofillMetricsServerNicknameTest, LogServerNicknameFormEvents) { +// Test that we log form events for masked server card nickname. +// TODO(crbug.com/1059087): Remove histogram logging for server nickname. +TEST_F(AutofillMetricsTest, LogServerNicknameFormEvents) { // Set up our form data. FormData form; form.name = ASCIIToUTF16("TestForm"); @@ -6799,11 +6768,9 @@ } // Test that we log suggestion selection duration for masked server card -// nickname. When surfacing-server-nickname flag is off (we won't display the -// nickname), we still log when user has a masked server card with nickname in -// order to compare the selection duration on the same group of user when server -// nickname is displayed or not. -TEST_P(AutofillMetricsServerNicknameTest, LogServerNicknameSelectionDuration) { +// nickname. +// TODO(crbug.com/1059087): Remove histogram logging for server nickname. +TEST_F(AutofillMetricsTest, LogServerNicknameSelectionDuration) { base::TimeTicks now = AutofillTickClock::NowTicks(); TestAutofillTickClock test_clock; test_clock.SetNowTicks(now);
diff --git a/components/autofill/core/browser/data_model/credit_card.cc b/components/autofill/core/browser/data_model/credit_card.cc index b8ad297..0224642 100644 --- a/components/autofill/core/browser/data_model/credit_card.cc +++ b/components/autofill/core/browser/data_model/credit_card.cc
@@ -862,9 +862,7 @@ base::string16 CreditCard::CardIdentifierStringForAutofillDisplay( base::string16 customized_nickname) const { - if (base::FeatureList::IsEnabled( - features::kAutofillEnableSurfacingServerCardNickname) && - (HasNonEmptyValidNickname() || !customized_nickname.empty())) { + if (HasNonEmptyValidNickname() || !customized_nickname.empty()) { return NicknameAndLastFourDigits(customized_nickname); } // Return a Google-specific string for Google-issued cards.
diff --git a/components/autofill/core/browser/data_model/credit_card_unittest.cc b/components/autofill/core/browser/data_model/credit_card_unittest.cc index 1a19769..2990a9a4 100644 --- a/components/autofill/core/browser/data_model/credit_card_unittest.cc +++ b/components/autofill/core/browser/data_model/credit_card_unittest.cc
@@ -102,11 +102,9 @@ TEST(CreditCardTest, PreviewSummaryAndNetworkAndLastFourDigitsStrings) { base::test::ScopedFeatureList scoped_feature_list; base::string16 valid_nickname = ASCIIToUTF16("My Visa Card"); - // Enable the flags. - scoped_feature_list.InitWithFeatures( - /*enable_features=*/{features::kAutofillEnableSurfacingServerCardNickname, - features::kAutofillEnableCardNicknameManagement}, - /*disable_features=*/{}); + // Enable the flag. + scoped_feature_list.InitAndEnableFeature( + features::kAutofillEnableCardNicknameManagement); // Case 0: empty credit card. CreditCard credit_card0(base::GenerateGUID(), "https://www.example.com/"); @@ -208,32 +206,19 @@ test::ObfuscatedCardDigitsAsUTF8("5100") + ", 01/2010"), summary6); - // Case 7: Have everything including nickname but flag is off. + // Case 7: No credit card number, has valid nickname, but flag is off. // Reset and disable the nickname feature flags. scoped_feature_list.Reset(); - scoped_feature_list.InitWithFeatures( - /*enable_features=*/{}, /*disable_features=*/{ - features::kAutofillEnableSurfacingServerCardNickname, - features::kAutofillEnableCardNicknameManagement}); + scoped_feature_list.InitAndDisableFeature( + features::kAutofillEnableCardNicknameManagement); CreditCard credit_card7(base::GenerateGUID(), "https://www.example.com/"); - test::SetCreditCardInfo(&credit_card7, "John Dillinger", - "5105 1051 0510 5100" /* Mastercard */, "01", "2010", + test::SetCreditCardInfo(&credit_card7, "John Dillinger", "", "01", "2010", "1"); credit_card7.SetNickname(valid_nickname); - base::string16 summary7 = credit_card7.Label(); - EXPECT_EQ(UTF8ToUTF16(std::string("Mastercard ") + - test::ObfuscatedCardDigitsAsUTF8("5100") + ", 01/2010"), - summary7); - - // Case 8: No credit card number, has valid nickname, but flag is off. - CreditCard credit_card8(base::GenerateGUID(), "https://www.example.com/"); - test::SetCreditCardInfo(&credit_card8, "John Dillinger", "", "01", "2010", - "1"); - credit_card8.SetNickname(valid_nickname); - base::string16 summary8 = credit_card11.Label(); - EXPECT_EQ(base::string16(ASCIIToUTF16("John Dillinger")), summary8); - base::string16 obfuscated8 = credit_card8.NetworkAndLastFourDigits(); - EXPECT_EQ(ASCIIToUTF16(std::string("Card")), obfuscated8); + base::string16 summary7 = credit_card11.Label(); + EXPECT_EQ(base::string16(ASCIIToUTF16("John Dillinger")), summary7); + base::string16 obfuscated7 = credit_card7.NetworkAndLastFourDigits(); + EXPECT_EQ(ASCIIToUTF16(std::string("Card")), obfuscated7); } TEST(CreditCardTest, NicknameAndLastFourDigitsStrings) { @@ -262,9 +247,6 @@ base::string16 valid_nickname = ASCIIToUTF16("My Visa Card"); base::string16 invalid_nickname = ASCIIToUTF16("Nickname length exceeds 25 characters"); - // Enable the flag. - scoped_feature_list.InitAndEnableFeature( - features::kAutofillEnableSurfacingServerCardNickname); // Case 1: Nickname name is invalid -> show network name. CreditCard credit_card1(base::GenerateGUID(), "https://www.example.com/"); @@ -288,31 +270,13 @@ valid_nickname + UTF8ToUTF16(std::string(" ") + test::ObfuscatedCardDigitsAsUTF8("5100")), credit_card2.CardIdentifierStringForAutofillDisplay()); - - // Case 3: Experiment off -> show network name. - // Reset and disable the feature flag. - scoped_feature_list.Reset(); - scoped_feature_list.InitAndDisableFeature( - features::kAutofillEnableSurfacingServerCardNickname); - CreditCard credit_card3(base::GenerateGUID(), "https://www.example.com/"); - test::SetCreditCardInfo(&credit_card3, "John Dillinger", - "5105 1051 0510 5100" /* Mastercard */, "01", "2020", - "1"); - credit_card3.SetNickname(valid_nickname); - EXPECT_TRUE(credit_card3.HasNonEmptyValidNickname()); - EXPECT_EQ(UTF8ToUTF16(std::string("Mastercard ") + - test::ObfuscatedCardDigitsAsUTF8("5100")), - credit_card3.CardIdentifierStringForAutofillDisplay()); } TEST(CreditCardTest, CardIdentifierStringForIssuedCard) { base::test::ScopedFeatureList scoped_feature_list; // Enable the flag. - scoped_feature_list.InitWithFeatures( - /*enable_features=*/{features::kAutofillEnableGoogleIssuedCard, - features:: - kAutofillEnableSurfacingServerCardNickname}, - /*disable_features=*/{}); + scoped_feature_list.InitAndEnableFeature( + features::kAutofillEnableGoogleIssuedCard); // Case 1: Card Issuer set to GOOGLE with no nickname. CreditCard credit_card1(base::GenerateGUID(), "https://www.example.com/"); credit_card1.set_card_issuer(CreditCard::Issuer::GOOGLE); @@ -344,10 +308,8 @@ TEST(CreditCardTest, CardIdentifierStringForIssuedCardExpOff) { base::test::ScopedFeatureList scoped_feature_list; // Disable the flag. - scoped_feature_list.InitWithFeatures( - /*enable_features=*/{features:: - kAutofillEnableSurfacingServerCardNickname}, - /*disable_features=*/{features::kAutofillEnableGoogleIssuedCard}); + scoped_feature_list.InitAndDisableFeature( + features::kAutofillEnableGoogleIssuedCard); // Case 1: Card Issuer set to GOOGLE with no nickname. CreditCard credit_card1(base::GenerateGUID(), "https://www.example.com/"); credit_card1.set_card_issuer(CreditCard::Issuer::GOOGLE);
diff --git a/components/autofill/core/browser/form_data_importer.cc b/components/autofill/core/browser/form_data_importer.cc index 0f59c88..203fbe5 100644 --- a/components/autofill/core/browser/form_data_importer.cc +++ b/components/autofill/core/browser/form_data_importer.cc
@@ -754,10 +754,7 @@ // If the card is a local card and it has a nickname stored in the local // database, copy the nickname to the |candidate_credit_card| so that the // nickname also shows in the Upstream bubble. - if (base::FeatureList::IsEnabled( - features::kAutofillEnableSurfacingServerCardNickname)) { - candidate_credit_card.SetNickname(card_copy.nickname()); - } + candidate_credit_card.SetNickname(card_copy.nickname()); // If we should not return the local card, return that we merged it, // without setting |imported_credit_card|.
diff --git a/components/autofill/core/browser/personal_data_manager_unittest.cc b/components/autofill/core/browser/personal_data_manager_unittest.cc index ad229f23..4b5b41c7 100644 --- a/components/autofill/core/browser/personal_data_manager_unittest.cc +++ b/components/autofill/core/browser/personal_data_manager_unittest.cc
@@ -3627,8 +3627,6 @@ TEST_F(PersonalDataManagerTest, GetCreditCardSuggestions_NumberMissing_QueryNonNumberField) { base::test::ScopedFeatureList scoped_feature_list; - scoped_feature_list.InitAndEnableFeature( - features::kAutofillEnableSurfacingServerCardNickname); ASSERT_EQ(0U, personal_data_->GetCreditCards().size()); CreditCard credit_card("1141084B-72D7-4B73-90CF-3D6AC154673B", @@ -7919,11 +7917,8 @@ protected: void SetUp() override { PersonalDataManagerTest::SetUp(); - scoped_feature_list_.InitWithFeatures( - /*enabled_features=*/{features:: - kAutofillEnableSurfacingServerCardNickname, - features::kAutofillEnableCardNicknameManagement}, - /*disabled_features=*/{}); + scoped_feature_list_.InitAndEnableFeature( + features::kAutofillEnableCardNicknameManagement); } private:
diff --git a/components/autofill/core/browser/ui/payments/card_expiration_date_fix_flow_controller_impl_unittest.cc b/components/autofill/core/browser/ui/payments/card_expiration_date_fix_flow_controller_impl_unittest.cc index b4fdd611..03455605 100644 --- a/components/autofill/core/browser/ui/payments/card_expiration_date_fix_flow_controller_impl_unittest.cc +++ b/components/autofill/core/browser/ui/payments/card_expiration_date_fix_flow_controller_impl_unittest.cc
@@ -108,41 +108,13 @@ 1); } -// Tests to ensure the card nickname is shown correctly in the expiration fix -// flow prompt. The param indicates whether the nickname experiment is enabled. -class CardExpirationDateFixFlowControllerImplTestForNickname - : public CardExpirationDateFixFlowControllerImplTest, - public ::testing::WithParamInterface<bool> { - public: - CardExpirationDateFixFlowControllerImpl* GetController() { - return controller_.get(); - } - - protected: - CardExpirationDateFixFlowControllerImplTestForNickname() { - scoped_feature_list_.InitWithFeatureState( - features::kAutofillEnableSurfacingServerCardNickname, GetParam()); - } - - ~CardExpirationDateFixFlowControllerImplTestForNickname() override = default; - - private: - base::test::ScopedFeatureList scoped_feature_list_; -}; - -INSTANTIATE_TEST_SUITE_P(, - CardExpirationDateFixFlowControllerImplTestForNickname, - testing::Bool()); - -TEST_P(CardExpirationDateFixFlowControllerImplTestForNickname, - CardIdentifierString) { +TEST_F(CardExpirationDateFixFlowControllerImplTest, CardIdentifierString) { CreditCard card = test::GetCreditCard(); card.SetNickname(base::ASCIIToUTF16("nickname")); ShowPrompt(card); - EXPECT_EQ(GetController()->GetCardLabel(), - GetParam() ? card.NicknameAndLastFourDigitsForTesting() - : card.NetworkAndLastFourDigits()); + EXPECT_EQ(controller_->GetCardLabel(), + card.NicknameAndLastFourDigitsForTesting()); } } // namespace autofill
diff --git a/components/autofill/core/browser/ui/payments/card_unmask_prompt_controller_impl_unittest.cc b/components/autofill/core/browser/ui/payments/card_unmask_prompt_controller_impl_unittest.cc index 27ee299..cf32d1e 100644 --- a/components/autofill/core/browser/ui/payments/card_unmask_prompt_controller_impl_unittest.cc +++ b/components/autofill/core/browser/ui/payments/card_unmask_prompt_controller_impl_unittest.cc
@@ -256,33 +256,8 @@ } // Ensures to fallback to network name in the instruction message on iOS and in -// the title on other platforms when the experiment is disabled, even though the -// nickname is valid. -TEST_F(CardUnmaskPromptControllerImplTest, Nickname_ExpOffNicknameValid) { - scoped_feature_list_.InitAndDisableFeature( - features::kAutofillEnableSurfacingServerCardNickname); - SetCreditCardForTesting(test::GetMaskedServerCardWithNickname()); - ShowPrompt(); -#if defined(OS_IOS) - EXPECT_TRUE( - base::UTF16ToUTF8(controller_->GetInstructionsMessage()).find("Visa") != - std::string::npos); - EXPECT_FALSE(base::UTF16ToUTF8(controller_->GetInstructionsMessage()) - .find("Test nickname") != std::string::npos); -#else - EXPECT_TRUE(base::UTF16ToUTF8(controller_->GetWindowTitle()).find("Visa") != - std::string::npos); - EXPECT_FALSE( - base::UTF16ToUTF8(controller_->GetWindowTitle()).find("Test nickname") != - std::string::npos); -#endif -} - -// Ensures to fallback to network name in the instruction message on iOS and in // the title on other platforms when the nickname is invalid. -TEST_F(CardUnmaskPromptControllerImplTest, Nickname_ExpOnNicknameInvalid) { - scoped_feature_list_.InitAndEnableFeature( - features::kAutofillEnableSurfacingServerCardNickname); +TEST_F(CardUnmaskPromptControllerImplTest, Nickname_NicknameInvalid) { SetCreditCardForTesting(test::GetMaskedServerCardWithInvalidNickname()); ShowPrompt(); #if defined(OS_IOS) @@ -302,11 +277,9 @@ } // Ensures the nickname is displayed (instead of network) in the instruction -// message on iOS and in the title on other platforms when experiment is enabled -// and the nickname is valid. -TEST_F(CardUnmaskPromptControllerImplTest, Nickname_ExpOnNicknameValid) { - scoped_feature_list_.InitAndEnableFeature( - features::kAutofillEnableSurfacingServerCardNickname); +// message on iOS and in the title on other platforms when the nickname is +// valid. +TEST_F(CardUnmaskPromptControllerImplTest, Nickname_NicknameValid) { SetCreditCardForTesting(test::GetMaskedServerCardWithNickname()); ShowPrompt(); #if defined(OS_IOS)
diff --git a/components/autofill/core/common/autofill_features.cc b/components/autofill/core/common/autofill_features.cc index 31fa908..d2dc2757 100644 --- a/components/autofill/core/common/autofill_features.cc +++ b/components/autofill/core/common/autofill_features.cc
@@ -247,12 +247,6 @@ const base::Feature kAutofillServerCommunication{ "AutofillServerCommunication", base::FEATURE_ENABLED_BY_DEFAULT}; -// Controls whether we show warnings in the Dev console for misused autocomplete -// types. -const base::Feature kAutofillShowAutocompleteConsoleWarnings{ - "AutofillShowAutocompleteConsoleWarnings", - base::FEATURE_DISABLED_BY_DEFAULT}; - // Controls attaching the autofill type predictions to their respective // element in the DOM. const base::Feature kAutofillShowTypePredictions{
diff --git a/components/autofill/core/common/autofill_features.h b/components/autofill/core/common/autofill_features.h index 1f01ea0..cb3e744f 100644 --- a/components/autofill/core/common/autofill_features.h +++ b/components/autofill/core/common/autofill_features.h
@@ -64,7 +64,6 @@ extern const base::Feature kAutofillSaveAndFillVPA; extern const base::Feature kAutofillSectionUponRedundantNameInfo; extern const base::Feature kAutofillServerCommunication; -extern const base::Feature kAutofillShowAutocompleteConsoleWarnings; extern const base::Feature kAutofillShowTypePredictions; extern const base::Feature kAutofillSkipComparingInferredLabels; extern const base::Feature kAutofillSkipFillingFieldsWithChangedValues;
diff --git a/components/autofill/core/common/autofill_payments_features.cc b/components/autofill/core/common/autofill_payments_features.cc index 970f8dc5..5d89d6e7 100644 --- a/components/autofill/core/common/autofill_payments_features.cc +++ b/components/autofill/core/common/autofill_payments_features.cc
@@ -89,12 +89,6 @@ const base::Feature kAutofillEnableStickyPaymentsBubble{ "AutofillEnableStickyPaymentsBubble", base::FEATURE_DISABLED_BY_DEFAULT}; -// When enabled, if Google Payments cards were given nicknames in a Google Pay -// app, Autofill will surface these nicknames in suggestions. -const base::Feature kAutofillEnableSurfacingServerCardNickname{ - "AutofillEnableSurfacingServerCardNickname", - base::FEATURE_ENABLED_BY_DEFAULT}; - // When enabled, Autofill data related icons will be shown in the status // chip in toolbar along with the avatar toolbar button. const base::Feature kAutofillEnableToolbarStatusChip{
diff --git a/components/autofill/core/common/autofill_payments_features.h b/components/autofill/core/common/autofill_payments_features.h index 5af71f6..29ab241 100644 --- a/components/autofill/core/common/autofill_payments_features.h +++ b/components/autofill/core/common/autofill_payments_features.h
@@ -31,7 +31,6 @@ extern const base::Feature kAutofillEnableGoogleIssuedCard; extern const base::Feature kAutofillEnableOffersInDownstream; extern const base::Feature kAutofillEnableStickyPaymentsBubble; -extern const base::Feature kAutofillEnableSurfacingServerCardNickname; extern const base::Feature kAutofillEnableToolbarStatusChip; extern const base::Feature kAutofillEnableVirtualCard; extern const base::Feature kAutofillSaveCardDismissOnNavigation;
diff --git a/components/autofill_assistant/browser/BUILD.gn b/components/autofill_assistant/browser/BUILD.gn index e6f992c..827a161 100644 --- a/components/autofill_assistant/browser/BUILD.gn +++ b/components/autofill_assistant/browser/BUILD.gn
@@ -206,6 +206,7 @@ "//components/autofill/core/common", "//components/autofill_assistant/browser/devtools", "//components/google/core/common:common", + "//components/password_manager/content/browser:browser", "//components/password_manager/core/browser:browser", "//components/password_manager/core/browser/form_parsing:form_parsing", "//components/signin/public/identity_manager",
diff --git a/components/autofill_assistant/browser/DEPS b/components/autofill_assistant/browser/DEPS index 3308423..ff90e40 100644 --- a/components/autofill_assistant/browser/DEPS +++ b/components/autofill_assistant/browser/DEPS
@@ -2,6 +2,7 @@ "+chrome/android/features/autofill_assistant/test_support_jni_headers", "+components/autofill", "+components/google/core/common", + "+components/password_manager/content/browser", "+components/password_manager/core/browser", "+components/password_manager/core/common", "+components/version_info",
diff --git a/components/autofill_assistant/browser/website_login_manager_impl.cc b/components/autofill_assistant/browser/website_login_manager_impl.cc index 6e21c380c..d3d1ff8 100644 --- a/components/autofill_assistant/browser/website_login_manager_impl.cc +++ b/components/autofill_assistant/browser/website_login_manager_impl.cc
@@ -6,12 +6,13 @@ #include "base/stl_util.h" #include "base/strings/utf_string_conversions.h" +#include "components/password_manager/content/browser/content_password_manager_driver.h" +#include "components/password_manager/content/browser/content_password_manager_driver_factory.h" #include "components/password_manager/core/browser/form_fetcher_impl.h" #include "components/password_manager/core/browser/form_parsing/form_parser.h" #include "components/password_manager/core/browser/password_form_metrics_recorder.h" #include "components/password_manager/core/browser/password_generation_frame_helper.h" #include "components/password_manager/core/browser/password_manager_client.h" -#include "components/password_manager/core/browser/password_manager_driver.h" #include "components/password_manager/core/browser/password_save_manager_impl.h" #include "components/password_manager/core/browser/votes_uploader.h" #include "content/public/browser/browser_task_traits.h" @@ -231,8 +232,8 @@ WebsiteLoginManagerImpl::WebsiteLoginManagerImpl( password_manager::PasswordManagerClient* client, - password_manager::PasswordManagerDriver* driver) - : client_(client), driver_(driver), weak_ptr_factory_(this) {} + content::WebContents* web_contents) + : client_(client), web_contents_(web_contents), weak_ptr_factory_(this) {} WebsiteLoginManagerImpl::~WebsiteLoginManagerImpl() = default; @@ -266,9 +267,19 @@ autofill::FormSignature form_signature, autofill::FieldSignature field_signature, uint64_t max_length) { + auto* factory = + password_manager::ContentPasswordManagerDriverFactory::FromWebContents( + web_contents_); + DCHECK(factory); + // TODO(crbug.com/1043132): Add support for non-main frames. If another + // frame has a different origin than the main frame, passwords-related + // features may not work. + auto* driver = factory->GetDriverForFrame(web_contents_->GetMainFrame()); + DCHECK(driver); + return base::UTF16ToUTF8( - driver_->GetPasswordGenerationHelper()->GeneratePassword( - driver_->GetLastCommittedURL(), form_signature, field_signature, + driver->GetPasswordGenerationHelper()->GeneratePassword( + driver->GetLastCommittedURL(), form_signature, field_signature, max_length)); }
diff --git a/components/autofill_assistant/browser/website_login_manager_impl.h b/components/autofill_assistant/browser/website_login_manager_impl.h index d0012bb..a365d98 100644 --- a/components/autofill_assistant/browser/website_login_manager_impl.h +++ b/components/autofill_assistant/browser/website_login_manager_impl.h
@@ -9,10 +9,10 @@ #include "base/memory/weak_ptr.h" #include "components/autofill/core/common/password_form.h" #include "components/autofill_assistant/browser/website_login_manager.h" +#include "content/public/browser/web_contents.h" namespace password_manager { class PasswordManagerClient; -class PasswordManagerDriver; } // namespace password_manager namespace autofill_assistant { @@ -22,7 +22,7 @@ class WebsiteLoginManagerImpl : public WebsiteLoginManager { public: WebsiteLoginManagerImpl(password_manager::PasswordManagerClient* client, - password_manager::PasswordManagerDriver* driver); + content::WebContents* web_contents); ~WebsiteLoginManagerImpl() override; // From WebsiteLoginManager: @@ -55,7 +55,7 @@ password_manager::PasswordManagerClient* const client_; - password_manager::PasswordManagerDriver* const driver_; + content::WebContents* const web_contents_; // Update password request will be created in PresaveGeneratedPassword and // released in CommitGeneratedPassword after committing presaved password to @@ -74,4 +74,4 @@ } // namespace autofill_assistant -#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_website_login_manager_IMPL_H_ +#endif // COMPONENTS_AUTOFILL_ASSISTANT_BROWSER_WEBSITE_LOGIN_MANAGER_IMPL_H_
diff --git a/components/autofill_assistant/browser/website_login_manager_impl_unittest.cc b/components/autofill_assistant/browser/website_login_manager_impl_unittest.cc index 5b44d5d..c6438d9 100644 --- a/components/autofill_assistant/browser/website_login_manager_impl_unittest.cc +++ b/components/autofill_assistant/browser/website_login_manager_impl_unittest.cc
@@ -11,9 +11,10 @@ #include "components/password_manager/core/browser/mock_password_store.h" #include "components/password_manager/core/browser/password_store_consumer.h" #include "components/password_manager/core/browser/stub_password_manager_client.h" -#include "components/password_manager/core/browser/stub_password_manager_driver.h" #include "components/password_manager/core/common/password_manager_features.h" +#include "content/public/browser/web_contents.h" #include "content/public/test/browser_task_environment.h" +#include "content/public/test/test_renderer_host.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" @@ -50,15 +51,6 @@ password_manager::PasswordStore*()); }; -class MockPasswordManagerDriver - : public password_manager::StubPasswordManagerDriver { - public: - MockPasswordManagerDriver() = default; - - MOCK_CONST_METHOD0(GetId, int()); - MOCK_CONST_METHOD0(IsMainFrame, bool()); -}; - FormData MakeFormDataWithPasswordField() { FormData form_data; form_data.url = GURL(kFakeUrl); @@ -101,9 +93,12 @@ } // namespace -class WebsiteLoginManagerImplTest : public testing::Test { +class WebsiteLoginManagerImplTest : public content::RenderViewHostTestHarness { public: - WebsiteLoginManagerImplTest() = default; + WebsiteLoginManagerImplTest() + : RenderViewHostTestHarness( + base::test::TaskEnvironment::MainThreadType::UI, + base::test::TaskEnvironment::TimeSource::MOCK_TIME) {} ~WebsiteLoginManagerImplTest() override = default; protected: @@ -125,10 +120,8 @@ .WillByDefault(Return(account_store_.get())); } - ON_CALL(driver_, GetId()).WillByDefault(Return(0)); - ON_CALL(driver_, IsMainFrame()).WillByDefault(Return(true)); - - manager_ = std::make_unique<WebsiteLoginManagerImpl>(&client_, &driver_); + manager_ = + std::make_unique<WebsiteLoginManagerImpl>(&client_, web_contents()); } void TearDown() override { @@ -141,17 +134,13 @@ WebsiteLoginManagerImpl* manager() { return manager_.get(); } password_manager::MockPasswordStore* store() { return profile_store_.get(); } - void WaitForPasswordStore() { task_environment_.RunUntilIdle(); } + void WaitForPasswordStore() { task_environment()->RunUntilIdle(); } private: testing::NiceMock<MockPasswordManagerClient> client_; - MockPasswordManagerDriver driver_; std::unique_ptr<WebsiteLoginManagerImpl> manager_; scoped_refptr<password_manager::MockPasswordStore> profile_store_; scoped_refptr<password_manager::MockPasswordStore> account_store_; - content::BrowserTaskEnvironment task_environment_{ - base::test::TaskEnvironment::TimeSource::MOCK_TIME, - content::BrowserTaskEnvironment::IO_MAINLOOP}; }; // Checks if PasswordForm matches other PasswordForm.
diff --git a/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareHelper.java b/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareHelper.java index 26144ae..b4bcb3c3d 100644 --- a/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareHelper.java +++ b/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareHelper.java
@@ -338,10 +338,10 @@ intent.addCategory(Intent.CATEGORY_DEFAULT); intent.setType("multipart/related"); } else { - if (!TextUtils.equals(params.getText(), params.getTitle())) { + if (!TextUtils.equals(params.getTextAndUrl(), params.getTitle())) { intent.putExtra(Intent.EXTRA_SUBJECT, params.getTitle()); } - intent.putExtra(Intent.EXTRA_TEXT, params.getText()); + intent.putExtra(Intent.EXTRA_TEXT, params.getTextAndUrl()); if (isFileShare) { intent.setType(params.getFileContentType());
diff --git a/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareParams.java b/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareParams.java index f26655eb..10425a1 100644 --- a/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareParams.java +++ b/components/browser_ui/share/android/java/src/org/chromium/components/browser_ui/share/ShareParams.java
@@ -26,10 +26,7 @@ /** The title of the page to be shared. */ private final String mTitle; - /** - * The text to be shared. If both |text| and |url| are supplied, they are concatenated with a - * space. - */ + /** The text to be shared. */ private final String mText; /** The URL of the page to be shared. */ @@ -83,6 +80,20 @@ } /** + * @return The text concatenated with the url. + */ + public String getTextAndUrl() { + if (TextUtils.isEmpty(mUrl)) { + return mText; + } + if (TextUtils.isEmpty(mText)) { + return mUrl; + } + // Concatenate text and URL with a space. + return mText + " " + mUrl; + } + + /** * @return The text to be shared. */ public String getText() { @@ -213,12 +224,6 @@ public ShareParams build() { if (!TextUtils.isEmpty(mUrl)) { mUrl = DomDistillerUrlUtils.getOriginalUrlFromDistillerUrl(mUrl); - if (!TextUtils.isEmpty(mText)) { - // Concatenate text and URL with a space. - mText = mText + " " + mUrl; - } else { - mText = mUrl; - } } return new ShareParams(mWindow, mTitle, mText, mUrl, mFileContentType, mFileUris, mOfflineUri, mScreenshotUri, mCallback);
diff --git a/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc b/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc index d072578..03b849d 100644 --- a/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc +++ b/components/certificate_transparency/chrome_ct_policy_enforcer_unittest.cc
@@ -16,7 +16,6 @@ #include "crypto/rsa_private_key.h" #include "crypto/sha2.h" #include "net/cert/ct_policy_status.h" -#include "net/cert/ct_verify_result.h" #include "net/cert/x509_certificate.h" #include "net/cert/x509_util.h" #include "net/log/net_log_with_source.h"
diff --git a/components/content_settings/renderer/content_settings_agent_impl.cc b/components/content_settings/renderer/content_settings_agent_impl.cc index 5bdb837..20ae512 100644 --- a/components/content_settings/renderer/content_settings_agent_impl.cc +++ b/components/content_settings/renderer/content_settings_agent_impl.cc
@@ -95,13 +95,6 @@ return base::nullopt; } -base::Optional<bool> -ContentSettingsAgentImpl::Delegate::AllowRunningInsecureContent( - bool allowed_per_settings, - const blink::WebURL& resource_url) { - return base::nullopt; -} - void ContentSettingsAgentImpl::Delegate::PassiveInsecureContentFound( const blink::WebURL&) {} @@ -422,16 +415,18 @@ bool ContentSettingsAgentImpl::AllowRunningInsecureContent( bool allowed_per_settings, const blink::WebURL& resource_url) { - base::Optional<bool> result = delegate_->AllowRunningInsecureContent( - allowed_per_settings, resource_url); - if (result.has_value()) - return result.value(); + if (allowed_per_settings || allow_running_insecure_content_) + return true; - bool allow = allowed_per_settings || allow_running_insecure_content_; - if (!allow) { - DidBlockContentType(ContentSettingsType::MIXEDSCRIPT); + if (content_setting_rules_) { + blink::WebLocalFrame* frame = render_frame()->GetWebFrame(); + ContentSetting setting = GetContentSettingFromRules( + content_setting_rules_->mixed_content_rules, frame, GURL()); + if (setting == CONTENT_SETTING_ALLOW) + return true; } - return allow; + + return false; } bool ContentSettingsAgentImpl::AllowPopupsAndRedirects(bool default_value) {
diff --git a/components/content_settings/renderer/content_settings_agent_impl.h b/components/content_settings/renderer/content_settings_agent_impl.h index 1d9075a..41dcaac2 100644 --- a/components/content_settings/renderer/content_settings_agent_impl.h +++ b/components/content_settings/renderer/content_settings_agent_impl.h
@@ -56,9 +56,6 @@ virtual base::Optional<bool> AllowReadFromClipboard(); virtual base::Optional<bool> AllowWriteToClipboard(); virtual base::Optional<bool> AllowMutationEvents(); - virtual base::Optional<bool> AllowRunningInsecureContent( - bool allowed_per_settings, - const blink::WebURL& resource_url); virtual void PassiveInsecureContentFound(const blink::WebURL& resource_url); };
diff --git a/components/device_event_log/device_event_log.cc b/components/device_event_log/device_event_log.cc index f1311e7..386ab8d 100644 --- a/components/device_event_log/device_event_log.cc +++ b/components/device_event_log/device_event_log.cc
@@ -17,7 +17,9 @@ const size_t kDefaultMaxEntries = 4000; const int kSlowMethodThresholdMs = 10; -const int kVerySlowMethodThresholdMs = 50; +// Loaded builders may perform badly, set this to a fairly high value to catch +// extreme cases. +const int kVerySlowMethodThresholdMs = 250; DeviceEventLogImpl* g_device_event_log = nullptr;
diff --git a/components/messages/android/BUILD.gn b/components/messages/android/BUILD.gn index 1473718..da349bd 100644 --- a/components/messages/android/BUILD.gn +++ b/components/messages/android/BUILD.gn
@@ -3,6 +3,7 @@ # found in the LICENSE file. import("//build/config/android/rules.gni") +import("//chrome/android/features/android_library_factory_tmpl.gni") android_library("java") { sources = [ @@ -10,6 +11,7 @@ "java/src/org/chromium/components/messages/MessageBannerView.java", "java/src/org/chromium/components/messages/MessageBannerViewBinder.java", "java/src/org/chromium/components/messages/MessageContainer.java", + "java/src/org/chromium/components/messages/MessageQueueManager.java", "java/src/org/chromium/components/messages/MessageStateHandler.java", "java/src/org/chromium/components/messages/SingleActionMessage.java", ] @@ -69,3 +71,14 @@ "//ui/android:ui_java_test_support", ] } + +android_library_factory("factory_java") { + sources = [ + "internal/java/src/org/chromium/components/messages/MessagesFactory.java", + ] + + deps = [ + ":java", + "//ui/android:ui_full_java", + ] +}
diff --git a/components/messages/android/internal/BUILD.gn b/components/messages/android/internal/BUILD.gn new file mode 100644 index 0000000..19775a8b --- /dev/null +++ b/components/messages/android/internal/BUILD.gn
@@ -0,0 +1,30 @@ +# Copyright 2020 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("//build/config/android/rules.gni") + +android_library("java") { + sources = [ + "java/src/org/chromium/components/messages/MessageQueueManagerImpl.java", + "java/src/org/chromium/components/messages/MessagesFactory.java", + ] + + deps = [ + "..:java", + "//base:base_java", + "//ui/android:ui_full_java", + ] +} + +java_library("junit") { + # Skip platform checks since Robolectric depends on requires_android targets. + bypass_platform_checks = true + testonly = true + sources = [ "java/src/org/chromium/components/messages/MessageQueueManagerImplTest.java" ] + deps = [ + ":java", + "//base:base_junit_test_support", + "//third_party/junit", + ] +}
diff --git a/components/messages/android/internal/java/src/org/chromium/components/messages/MessageQueueManagerImpl.java b/components/messages/android/internal/java/src/org/chromium/components/messages/MessageQueueManagerImpl.java new file mode 100644 index 0000000..6bc6fc5 --- /dev/null +++ b/components/messages/android/internal/java/src/org/chromium/components/messages/MessageQueueManagerImpl.java
@@ -0,0 +1,46 @@ +// Copyright 2020 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.components.messages; + +import org.chromium.base.UnownedUserData; +import org.chromium.base.UnownedUserDataKey; +import org.chromium.ui.base.WindowAndroid; + +/** + * A class managing the queue of messages. Its primary role is to decide when to show/hide current + * message and which message to show next. + */ +class MessageQueueManagerImpl implements MessageQueueManager, UnownedUserData { + private static final UnownedUserDataKey<MessageQueueManagerImpl> KEY = + new UnownedUserDataKey<>(MessageQueueManagerImpl.class); + + /** + * Get the activity's MessageQueueManager from the provided WindowAndroid. + * @param window The window to get the manager from. + * @return The activity's MessageQueueManager. + */ + public static MessageQueueManagerImpl from(WindowAndroid window) { + return KEY.retrieveDataFromHost(window.getUnownedUserDataHost()); + } + + public MessageQueueManagerImpl() {} + + /** + * Attaches MessageQueueManager to a given window. This window will be used later to retrieve + * activity's MessageQueueManager. + * @param window The window to attach to. + */ + public void attachToWindowAndroid(WindowAndroid window) { + KEY.attachToHost(window.getUnownedUserDataHost(), this); + } + + /** + * Destroys MessageQueueManager, detaching it from the WindowAndroid it was attached to. + */ + @Override + public void destroy() { + KEY.detachFromAllHosts(this); + } +}
diff --git a/components/messages/android/internal/java/src/org/chromium/components/messages/MessageQueueManagerImplTest.java b/components/messages/android/internal/java/src/org/chromium/components/messages/MessageQueueManagerImplTest.java new file mode 100644 index 0000000..abfda8e --- /dev/null +++ b/components/messages/android/internal/java/src/org/chromium/components/messages/MessageQueueManagerImplTest.java
@@ -0,0 +1,21 @@ +// Copyright 2020 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.components.messages; + +import org.junit.Test; +import org.junit.runner.RunWith; + +import org.chromium.base.test.BaseRobolectricTestRunner; + +/** + * Unit tests for MessageQueueManagerImpl. + */ +@RunWith(BaseRobolectricTestRunner.class) +public class MessageQueueManagerImplTest { + @Test + public void testCreateMessageQueueManager() { + MessageQueueManagerImpl queueManager = new MessageQueueManagerImpl(); + } +}
diff --git a/components/messages/android/internal/java/src/org/chromium/components/messages/MessagesFactory.java b/components/messages/android/internal/java/src/org/chromium/components/messages/MessagesFactory.java new file mode 100644 index 0000000..176cdc00 --- /dev/null +++ b/components/messages/android/internal/java/src/org/chromium/components/messages/MessagesFactory.java
@@ -0,0 +1,21 @@ +// Copyright 2020 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.components.messages; + +import org.chromium.ui.base.WindowAndroid; + +/** A factory for constructing different Messages related objects. */ +public class MessagesFactory { + /** + * Creates an instance of MessageQueueManager and attaches it to WindowAndroid. + * @param windowAndroid The WindowAndroid to attach MessageQueueManager to. + * @return The constructed MessageQueueManager. + */ + public static MessageQueueManager createMessageQueueManager(WindowAndroid windowAndroid) { + MessageQueueManagerImpl messageQueueManager = new MessageQueueManagerImpl(); + messageQueueManager.attachToWindowAndroid(windowAndroid); + return messageQueueManager; + } +} \ No newline at end of file
diff --git a/components/messages/android/java/src/org/chromium/components/messages/MessageQueueManager.java b/components/messages/android/java/src/org/chromium/components/messages/MessageQueueManager.java new file mode 100644 index 0000000..799d9d1 --- /dev/null +++ b/components/messages/android/java/src/org/chromium/components/messages/MessageQueueManager.java
@@ -0,0 +1,16 @@ +// Copyright 2020 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.components.messages; + +/** + * The public interface for managing the queue of messages. The embedder should retain reference to + * MessageQueueManager and destroy it when the Activity gets destroyed. + */ +public interface MessageQueueManager { + /** + * Destroys MessageQueueManager, detaching it from the WindowAndroid it was attached to. + */ + void destroy(); +}
diff --git a/components/omnibox/browser/autocomplete_match.cc b/components/omnibox/browser/autocomplete_match.cc index c0c95dd..6bc2b1a 100644 --- a/components/omnibox/browser/autocomplete_match.cc +++ b/components/omnibox/browser/autocomplete_match.cc
@@ -183,7 +183,8 @@ : nullptr), additional_info(match.additional_info), duplicate_matches(match.duplicate_matches), - query_tiles(match.query_tiles) {} + query_tiles(match.query_tiles), + navsuggest_tiles(match.navsuggest_tiles) {} AutocompleteMatch::AutocompleteMatch(AutocompleteMatch&& match) noexcept = default; @@ -243,6 +244,7 @@ additional_info = match.additional_info; duplicate_matches = match.duplicate_matches; query_tiles = match.query_tiles; + navsuggest_tiles = match.navsuggest_tiles; return *this; } @@ -264,6 +266,7 @@ case Type::PHYSICAL_WEB_DEPRECATED: case Type::PHYSICAL_WEB_OVERFLOW_DEPRECATED: case Type::TAB_SEARCH_DEPRECATED: + case Type::TILE_NAVSUGGEST: return omnibox::kPageIcon; case Type::SEARCH_SUGGEST: { @@ -414,8 +417,9 @@ case Type::PHYSICAL_WEB_DEPRECATED: case Type::PHYSICAL_WEB_OVERFLOW_DEPRECATED: case Type::TAB_SEARCH_DEPRECATED: - case Type::NUM_TYPES: case Type::TILE_SUGGESTION: + case Type::TILE_NAVSUGGEST: + case Type::NUM_TYPES: NOTREACHED(); return base::string16(); } @@ -975,6 +979,8 @@ return OmniboxEventProto::Suggestion::CLIPBOARD_IMAGE; case AutocompleteMatchType::TILE_SUGGESTION: return OmniboxEventProto::Suggestion::TILE_SUGGESTION; + case AutocompleteMatchType::TILE_NAVSUGGEST: + return OmniboxEventProto::Suggestion::NAVSUGGEST; case AutocompleteMatchType::VOICE_SUGGEST: // VOICE_SUGGEST matches are only used in Java and are not logged, // so we should never reach this case.
diff --git a/components/omnibox/browser/autocomplete_match.h b/components/omnibox/browser/autocomplete_match.h index 68e7b7b..1d4b9b6 100644 --- a/components/omnibox/browser/autocomplete_match.h +++ b/components/omnibox/browser/autocomplete_match.h
@@ -106,6 +106,15 @@ int style; }; + // NavsuggestTiles are used specifically with TILE_NAVSUGGEST matches. + // This structure should describe only the specific details for individual + // tiles; all other properties are considered as shared and should be + // extracted from the encompassing AutocompleteMatch object. + struct NavsuggestTile { + GURL url; + base::string16 title; + }; + typedef std::vector<ACMatchClassification> ACMatchClassifications; // Type used by providers to attach additional, optional information to @@ -642,6 +651,10 @@ // A list of query tiles to be shown as part of this match. std::vector<query_tiles::Tile> query_tiles; + // A list of navsuggest tiles to be shown as part of this match. + // This object is only populated for TILE_NAVSUGGEST AutocompleteMatches. + std::vector<NavsuggestTile> navsuggest_tiles; + // So users of AutocompleteMatch can use the same ellipsis that it uses. static const char kEllipsis[];
diff --git a/components/omnibox/browser/autocomplete_match_type.cc b/components/omnibox/browser/autocomplete_match_type.cc index 025c48d9..b83a9c81 100644 --- a/components/omnibox/browser/autocomplete_match_type.cc +++ b/components/omnibox/browser/autocomplete_match_type.cc
@@ -49,6 +49,7 @@ "text-from-clipboard", "image-from-clipboard", "query-tiles", + "navsuggest-tiles", }; // clang-format on static_assert(base::size(strings) == AutocompleteMatchType::NUM_TYPES, @@ -128,6 +129,7 @@ IDS_ACC_AUTOCOMPLETE_CLIPBOARD_TEXT, // CLIPBOARD_TEXT IDS_ACC_AUTOCOMPLETE_CLIPBOARD_IMAGE, // CLIPBOARD_IMAGE 0, // TILE_SUGGESTION + 0, // TILE_NAVSUGGEST }; static_assert(base::size(message_ids) == AutocompleteMatchType::NUM_TYPES, "message_ids must have NUM_TYPES elements");
diff --git a/components/omnibox/browser/autocomplete_match_type.h b/components/omnibox/browser/autocomplete_match_type.h index 62bed8f..e7a2dfb 100644 --- a/components/omnibox/browser/autocomplete_match_type.h +++ b/components/omnibox/browser/autocomplete_match_type.h
@@ -73,6 +73,7 @@ CLIPBOARD_TEXT = 26, // Text based on the clipboard. CLIPBOARD_IMAGE = 27, // An image based on the clipboard. TILE_SUGGESTION = 28, // A suggestion containing query tiles. + TILE_NAVSUGGEST = 29, // A suggestion with navigation tiles. NUM_TYPES, }; // clang-format on
diff --git a/components/omnibox/browser/zero_suggest_provider.cc b/components/omnibox/browser/zero_suggest_provider.cc index 730d77d..4e689bc1 100644 --- a/components/omnibox/browser/zero_suggest_provider.cc +++ b/components/omnibox/browser/zero_suggest_provider.cc
@@ -91,6 +91,9 @@ // Relevance value to use if it was not set explicitly by the server. const int kDefaultZeroSuggestRelevance = 100; +// The relevance score for navsuggest tiles. +// Navsuggest tiles should be positioned below the Query Tiles object. +const int kMostVisitedTilesRelevance = 1500; // Used for testing whether zero suggest is ever available. constexpr char kArbitraryInsecureUrlString[] = "http://www.google.com/"; @@ -477,16 +480,34 @@ return; } matches_.push_back(current_text_match_); - int relevance = 600; - const base::string16 current_query_string16( - base::ASCIIToUTF16(current_query_)); - for (const auto& url : most_visited_urls_) { - SearchSuggestionParser::NavigationResult nav( - client()->GetSchemeClassifier(), url.url, - AutocompleteMatchType::NAVSUGGEST, {}, url.title, std::string(), - false, relevance, true, current_query_string16); - matches_.push_back(NavigationToMatch(nav)); - --relevance; + + // Short-circuit in case we have no MOST_VISITED urls to show. + if (most_visited_urls_.empty()) + return; + + if (base::FeatureList::IsEnabled(omnibox::kMostVisitedTiles)) { + AutocompleteMatch match = + NavigationToMatch(SearchSuggestionParser::NavigationResult( + client()->GetSchemeClassifier(), GURL::EmptyGURL(), + AutocompleteMatchType::TILE_NAVSUGGEST, {}, base::string16(), + std::string(), false, kMostVisitedTilesRelevance, true, + base::ASCIIToUTF16(current_query_))); + match.navsuggest_tiles.reserve(most_visited_urls_.size()); + + for (const auto& url : most_visited_urls_) { + match.navsuggest_tiles.push_back({url.url, url.title}); + } + matches_.push_back(std::move(match)); + } else { + int relevance = 600; + for (const auto& url : most_visited_urls_) { + SearchSuggestionParser::NavigationResult nav( + client()->GetSchemeClassifier(), url.url, + AutocompleteMatchType::NAVSUGGEST, {}, url.title, std::string(), + false, relevance, true, base::ASCIIToUTF16(current_query_)); + matches_.push_back(NavigationToMatch(nav)); + --relevance; + } } return; }
diff --git a/components/password_manager/core/browser/fake_form_fetcher.cc b/components/password_manager/core/browser/fake_form_fetcher.cc index e1e65bb..2eba1ab 100644 --- a/components/password_manager/core/browser/fake_form_fetcher.cc +++ b/components/password_manager/core/browser/fake_form_fetcher.cc
@@ -6,12 +6,10 @@ #include <memory> -#include "components/autofill/core/common/password_form.h" +#include "components/password_manager/core/browser/password_form.h" #include "components/password_manager/core/browser/password_manager_util.h" #include "components/password_manager/core/browser/statistics_table.h" -using autofill::PasswordForm; - namespace password_manager { FakeFormFetcher::FakeFormFetcher() = default;
diff --git a/components/password_manager/core/browser/fake_form_fetcher.h b/components/password_manager/core/browser/fake_form_fetcher.h index 3b73c18..543ef369 100644 --- a/components/password_manager/core/browser/fake_form_fetcher.h +++ b/components/password_manager/core/browser/fake_form_fetcher.h
@@ -9,14 +9,10 @@ #include "base/macros.h" #include "base/observer_list.h" -#include "components/autofill/core/common/password_form.h" #include "components/password_manager/core/browser/form_fetcher.h" +#include "components/password_manager/core/browser/password_form.h" #include "components/password_manager/core/browser/statistics_table.h" -namespace autofill { -struct PasswordForm; -} - namespace password_manager { struct InteractionsStats; @@ -46,18 +42,15 @@ const std::vector<InteractionsStats>& GetInteractionsStats() const override; base::span<const CompromisedCredentials> GetCompromisedCredentials() const override; - std::vector<const autofill::PasswordForm*> GetNonFederatedMatches() - const override; - std::vector<const autofill::PasswordForm*> GetFederatedMatches() - const override; + std::vector<const PasswordForm*> GetNonFederatedMatches() const override; + std::vector<const PasswordForm*> GetFederatedMatches() const override; bool IsBlacklisted() const override; bool IsMovingBlocked(const autofill::GaiaIdHash& destination, const base::string16& username) const override; - const std::vector<const autofill::PasswordForm*>& GetAllRelevantMatches() + const std::vector<const PasswordForm*>& GetAllRelevantMatches() const override; - const std::vector<const autofill::PasswordForm*>& GetBestMatches() - const override; - const autofill::PasswordForm* GetPreferredMatch() const override; + const std::vector<const PasswordForm*>& GetBestMatches() const override; + const PasswordForm* GetPreferredMatch() const override; // Returns a new FakeFormFetcher. std::unique_ptr<FormFetcher> Clone() override; @@ -66,10 +59,9 @@ stats_ = stats; } - void set_scheme(autofill::PasswordForm::Scheme scheme) { scheme_ = scheme; } + void set_scheme(PasswordForm::Scheme scheme) { scheme_ = scheme; } - void set_federated( - const std::vector<const autofill::PasswordForm*>& federated) { + void set_federated(const std::vector<const PasswordForm*>& federated) { state_ = State::NOT_WAITING; federated_ = federated; } @@ -78,8 +70,7 @@ compromised_ = compromised; } - void SetNonFederated( - const std::vector<const autofill::PasswordForm*>& non_federated); + void SetNonFederated(const std::vector<const PasswordForm*>& non_federated); void SetBlacklisted(bool is_blacklisted); @@ -88,15 +79,14 @@ private: base::ObserverList<Consumer> consumers_; State state_ = State::NOT_WAITING; - autofill::PasswordForm::Scheme scheme_ = - autofill::PasswordForm::Scheme::kHtml; + PasswordForm::Scheme scheme_ = PasswordForm::Scheme::kHtml; std::vector<InteractionsStats> stats_; - std::vector<const autofill::PasswordForm*> non_federated_; - std::vector<const autofill::PasswordForm*> federated_; - std::vector<const autofill::PasswordForm*> non_federated_same_scheme_; - std::vector<const autofill::PasswordForm*> best_matches_; + std::vector<const PasswordForm*> non_federated_; + std::vector<const PasswordForm*> federated_; + std::vector<const PasswordForm*> non_federated_same_scheme_; + std::vector<const PasswordForm*> best_matches_; std::vector<CompromisedCredentials> compromised_; - const autofill::PasswordForm* preferred_match_ = nullptr; + const PasswordForm* preferred_match_ = nullptr; bool is_blacklisted_ = false; DISALLOW_COPY_AND_ASSIGN(FakeFormFetcher);
diff --git a/components/password_manager/core/browser/field_info_manager.cc b/components/password_manager/core/browser/field_info_manager.cc index 4d06292..5fd3852 100644 --- a/components/password_manager/core/browser/field_info_manager.cc +++ b/components/password_manager/core/browser/field_info_manager.cc
@@ -41,7 +41,7 @@ } void FieldInfoManagerImpl::OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results) { + std::vector<std::unique_ptr<PasswordForm>> results) { NOTREACHED(); }
diff --git a/components/password_manager/core/browser/field_info_manager.h b/components/password_manager/core/browser/field_info_manager.h index 1b2a362..409d91ab 100644 --- a/components/password_manager/core/browser/field_info_manager.h +++ b/components/password_manager/core/browser/field_info_manager.h
@@ -10,6 +10,7 @@ #include "components/autofill/core/browser/field_types.h" #include "components/autofill/core/common/signatures.h" #include "components/keyed_service/core/keyed_service.h" +#include "components/password_manager/core/browser/password_form_forward.h" #include "components/password_manager/core/browser/password_store_consumer.h" namespace password_manager { @@ -50,7 +51,7 @@ private: // PasswordStoreConsumer: void OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results) override; + std::vector<std::unique_ptr<PasswordForm>> results) override; void OnGetAllFieldInfo(std::vector<FieldInfo>) override; std::map<std::pair<autofill::FormSignature, autofill::FieldSignature>,
diff --git a/components/password_manager/core/browser/form_fetcher.h b/components/password_manager/core/browser/form_fetcher.h index 3af1fc27..82fa9297 100644 --- a/components/password_manager/core/browser/form_fetcher.h +++ b/components/password_manager/core/browser/form_fetcher.h
@@ -13,10 +13,7 @@ #include "base/observer_list_types.h" #include "base/strings/string16.h" #include "components/autofill/core/common/gaia_id_hash.h" - -namespace autofill { -struct PasswordForm; -} +#include "components/password_manager/core/browser/password_form_forward.h" namespace password_manager { @@ -74,13 +71,11 @@ // Non-federated matches obtained from the backend. Valid only if GetState() // returns NOT_WAITING. - virtual std::vector<const autofill::PasswordForm*> GetNonFederatedMatches() - const = 0; + virtual std::vector<const PasswordForm*> GetNonFederatedMatches() const = 0; // Federated matches obtained from the backend. Valid only if GetState() // returns NOT_WAITING. - virtual std::vector<const autofill::PasswordForm*> GetFederatedMatches() - const = 0; + virtual std::vector<const PasswordForm*> GetFederatedMatches() const = 0; // Whether there are blacklisted matches in the backend. Valid only if // GetState() returns NOT_WAITING. @@ -95,15 +90,14 @@ // Non-federated matches obtained from the backend that have the same scheme // of this form. - virtual const std::vector<const autofill::PasswordForm*>& - GetAllRelevantMatches() const = 0; - - // Nonblacklisted matches obtained from the backend. - virtual const std::vector<const autofill::PasswordForm*>& GetBestMatches() + virtual const std::vector<const PasswordForm*>& GetAllRelevantMatches() const = 0; + // Nonblacklisted matches obtained from the backend. + virtual const std::vector<const PasswordForm*>& GetBestMatches() const = 0; + // Pointer to a preferred entry in the vector returned by GetBestMatches(). - virtual const autofill::PasswordForm* GetPreferredMatch() const = 0; + virtual const PasswordForm* GetPreferredMatch() const = 0; // Creates a copy of |*this| with contains the same credentials without the // need for calling Fetch().
diff --git a/components/password_manager/core/browser/form_fetcher_impl.cc b/components/password_manager/core/browser/form_fetcher_impl.cc index e9d04a7..b9f66c5 100644 --- a/components/password_manager/core/browser/form_fetcher_impl.cc +++ b/components/password_manager/core/browser/form_fetcher_impl.cc
@@ -10,10 +10,10 @@ #include <utility> #include "build/build_config.h" -#include "components/autofill/core/common/password_form.h" #include "components/password_manager/core/browser/browser_save_password_progress_logger.h" #include "components/password_manager/core/browser/credentials_filter.h" #include "components/password_manager/core/browser/multi_store_form_fetcher.h" +#include "components/password_manager/core/browser/password_form.h" #include "components/password_manager/core/browser/password_manager_client.h" #include "components/password_manager/core/browser/password_manager_util.h" #include "components/password_manager/core/browser/password_store.h" @@ -21,8 +21,6 @@ #include "components/password_manager/core/browser/statistics_table.h" #include "components/password_manager/core/common/password_manager_features.h" -using autofill::PasswordForm; - using Logger = autofill::SavePasswordProgressLogger; namespace password_manager { @@ -73,9 +71,9 @@ bool should_migrate_http_passwords) : form_digest_(std::move(form_digest)), client_(client), - should_migrate_http_passwords_( - should_migrate_http_passwords && - form_digest_.scheme == autofill::PasswordForm::Scheme::kHtml) {} + should_migrate_http_passwords_(should_migrate_http_passwords && + form_digest_.scheme == + PasswordForm::Scheme::kHtml) {} FormFetcherImpl::~FormFetcherImpl() = default;
diff --git a/components/password_manager/core/browser/form_fetcher_impl.h b/components/password_manager/core/browser/form_fetcher_impl.h index 35e2ffa9..e18b9b9 100644 --- a/components/password_manager/core/browser/form_fetcher_impl.h +++ b/components/password_manager/core/browser/form_fetcher_impl.h
@@ -53,29 +53,25 @@ const std::vector<InteractionsStats>& GetInteractionsStats() const override; base::span<const CompromisedCredentials> GetCompromisedCredentials() const override; - std::vector<const autofill::PasswordForm*> GetNonFederatedMatches() - const override; - std::vector<const autofill::PasswordForm*> GetFederatedMatches() - const override; + std::vector<const PasswordForm*> GetNonFederatedMatches() const override; + std::vector<const PasswordForm*> GetFederatedMatches() const override; bool IsBlacklisted() const override; bool IsMovingBlocked(const autofill::GaiaIdHash& destination, const base::string16& username) const override; - const std::vector<const autofill::PasswordForm*>& GetAllRelevantMatches() + const std::vector<const PasswordForm*>& GetAllRelevantMatches() const override; - const std::vector<const autofill::PasswordForm*>& GetBestMatches() - const override; - const autofill::PasswordForm* GetPreferredMatch() const override; + const std::vector<const PasswordForm*>& GetBestMatches() const override; + const PasswordForm* GetPreferredMatch() const override; std::unique_ptr<FormFetcher> Clone() override; protected: // Processes password form results and forwards them to the |consumers_|. void ProcessPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results); + std::vector<std::unique_ptr<PasswordForm>> results); // Splits |results| into |federated_|, |non_federated_| and |is_blacklisted_|. - virtual void SplitResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results); + virtual void SplitResults(std::vector<std::unique_ptr<PasswordForm>> results); // PasswordStore results will be fetched for this description. const PasswordStore::FormDigest form_digest_; @@ -91,12 +87,12 @@ bool need_to_refetch_ = false; // Results obtained from PasswordStore: - std::vector<std::unique_ptr<autofill::PasswordForm>> non_federated_; + std::vector<std::unique_ptr<PasswordForm>> non_federated_; // Federated credentials relevant to the observed form. They are neither // filled not saved by PasswordFormManager, so they are kept separately from // non-federated matches. - std::vector<std::unique_ptr<autofill::PasswordForm>> federated_; + std::vector<std::unique_ptr<PasswordForm>> federated_; // List of compromised credentials for the current domain. std::vector<CompromisedCredentials> compromised_credentials_; @@ -108,12 +104,12 @@ private: // PasswordStoreConsumer: void OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results) override; + std::vector<std::unique_ptr<PasswordForm>> results) override; void OnGetSiteStatistics(std::vector<InteractionsStats> stats) override; // HttpPasswordStoreMigrator::Consumer: void ProcessMigratedForms( - std::vector<std::unique_ptr<autofill::PasswordForm>> forms) override; + std::vector<std::unique_ptr<PasswordForm>> forms) override; // CompromisedCredentialsConsumer: void OnGetCompromisedCredentials( @@ -123,17 +119,17 @@ std::unique_ptr<HttpPasswordStoreMigrator> http_migrator_; // Non-federated credentials of the same scheme as the observed form. - std::vector<const autofill::PasswordForm*> non_federated_same_scheme_; + std::vector<const PasswordForm*> non_federated_same_scheme_; // Set of nonblacklisted PasswordForms from the password store that best match // the form being managed by |this|. - std::vector<const autofill::PasswordForm*> best_matches_; + std::vector<const PasswordForm*> best_matches_; // Convenience pointer to entry in |best_matches_| that is marked as // preferred. This is only allowed to be null if there are no best matches at // all, since there will always be one preferred login when there are multiple // matches (when first saved, a login is marked preferred). - const autofill::PasswordForm* preferred_match_ = nullptr; + const PasswordForm* preferred_match_ = nullptr; // Whether there were any blacklisted credentials obtained from the password // store.
diff --git a/components/password_manager/core/browser/form_fetcher_impl_unittest.cc b/components/password_manager/core/browser/form_fetcher_impl_unittest.cc index 8c8761f..3c0deb49 100644 --- a/components/password_manager/core/browser/form_fetcher_impl_unittest.cc +++ b/components/password_manager/core/browser/form_fetcher_impl_unittest.cc
@@ -17,9 +17,9 @@ #include "base/test/scoped_feature_list.h" #include "base/test/task_environment.h" #include "build/build_config.h" -#include "components/autofill/core/common/password_form.h" #include "components/password_manager/core/browser/mock_password_store.h" #include "components/password_manager/core/browser/multi_store_form_fetcher.h" +#include "components/password_manager/core/browser/password_form.h" #include "components/password_manager/core/browser/password_manager_test_utils.h" #include "components/password_manager/core/browser/password_store.h" #include "components/password_manager/core/browser/statistics_table.h" @@ -33,7 +33,6 @@ #include "url/origin.h" #include "url/url_constants.h" -using autofill::PasswordForm; using base::ASCIIToUTF16; using base::StringPiece; using testing::_;
diff --git a/components/password_manager/core/browser/form_saver.h b/components/password_manager/core/browser/form_saver.h index 494abaf..2215604 100644 --- a/components/password_manager/core/browser/form_saver.h +++ b/components/password_manager/core/browser/form_saver.h
@@ -12,7 +12,7 @@ #include "base/macros.h" #include "base/optional.h" #include "base/strings/string16.h" -#include "components/autofill/core/common/password_form.h" +#include "components/password_manager/core/browser/password_form_forward.h" #include "components/password_manager/core/browser/password_store.h" namespace password_manager { @@ -27,7 +27,7 @@ // Blacklist the origin described by |digest|. Returns the PasswordForm pushed // to the store. - virtual autofill::PasswordForm PermanentlyBlacklist( + virtual PasswordForm PermanentlyBlacklist( PasswordStore::FormDigest digest) = 0; // Unblacklist the origin described by |digest| by deleting all corresponding @@ -41,16 +41,16 @@ // - empty-username credentials with the same password are removed. // - if |old_password| is provided, the old credentials with the same username // and the old password are updated to the new password. - virtual void Save(autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + virtual void Save(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password) = 0; // Updates the saved credential in the password store sharing the same key as // the |pending| form. // The algorithm for handling |matches| and |old_password| is the same as // above. - virtual void Update(autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + virtual void Update(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password) = 0; // If any of the unique key fields (signon_realm, origin, username_element, @@ -59,14 +59,13 @@ // old values for the unique key fields (the rest of the fields are ignored). // The algorithm for handling |matches| and |old_password| is the same as // above. - virtual void UpdateReplace( - autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, - const base::string16& old_password, - const autofill::PasswordForm& old_unique_key) = 0; + virtual void UpdateReplace(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, + const base::string16& old_password, + const PasswordForm& old_unique_key) = 0; // Removes |form| from the password store. - virtual void Remove(const autofill::PasswordForm& form) = 0; + virtual void Remove(const PasswordForm& form) = 0; // Creates a new FormSaver with the same state as |*this|. virtual std::unique_ptr<FormSaver> Clone() = 0;
diff --git a/components/password_manager/core/browser/form_saver_impl.cc b/components/password_manager/core/browser/form_saver_impl.cc index 3b73ffd..031c2ba9 100644 --- a/components/password_manager/core/browser/form_saver_impl.cc +++ b/components/password_manager/core/browser/form_saver_impl.cc
@@ -19,7 +19,6 @@ using autofill::FormData; using autofill::FormFieldData; -using autofill::PasswordForm; namespace password_manager { @@ -106,10 +105,9 @@ PostProcessMatches(pending, matches, old_password, store_); } -void FormSaverImpl::Update( - autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, - const base::string16& old_password) { +void FormSaverImpl::Update(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, + const base::string16& old_password) { SanitizeFormData(&pending.form_data); store_->UpdateLogin(pending); // Update existing matches in the password store. @@ -117,10 +115,10 @@ } void FormSaverImpl::UpdateReplace( - autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password, - const autofill::PasswordForm& old_unique_key) { + const PasswordForm& old_unique_key) { SanitizeFormData(&pending.form_data); store_->UpdateLoginWithPrimaryKey(pending, old_unique_key); // Update existing matches in the password store.
diff --git a/components/password_manager/core/browser/form_saver_impl.h b/components/password_manager/core/browser/form_saver_impl.h index 7e10e46..dddcee7 100644 --- a/components/password_manager/core/browser/form_saver_impl.h +++ b/components/password_manager/core/browser/form_saver_impl.h
@@ -24,20 +24,19 @@ ~FormSaverImpl() override; // FormSaver: - autofill::PasswordForm PermanentlyBlacklist( - PasswordStore::FormDigest digest) override; + PasswordForm PermanentlyBlacklist(PasswordStore::FormDigest digest) override; void Unblacklist(const PasswordStore::FormDigest& digest) override; - void Save(autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + void Save(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password) override; - void Update(autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + void Update(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password) override; - void UpdateReplace(autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + void UpdateReplace(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password, - const autofill::PasswordForm& old_unique_key) override; - void Remove(const autofill::PasswordForm& form) override; + const PasswordForm& old_unique_key) override; + void Remove(const PasswordForm& form) override; std::unique_ptr<FormSaver> Clone() override; private:
diff --git a/components/password_manager/core/browser/form_saver_impl_unittest.cc b/components/password_manager/core/browser/form_saver_impl_unittest.cc index c5fdc02..ef1a51bb 100644 --- a/components/password_manager/core/browser/form_saver_impl_unittest.cc +++ b/components/password_manager/core/browser/form_saver_impl_unittest.cc
@@ -14,15 +14,14 @@ #include "base/strings/string_piece.h" #include "base/strings/utf_string_conversions.h" #include "base/test/task_environment.h" -#include "components/autofill/core/common/password_form.h" #include "components/password_manager/core/browser/mock_password_store.h" +#include "components/password_manager/core/browser/password_form.h" #include "components/password_manager/core/browser/password_manager_util.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" #include "url/gurl.h" using autofill::FormFieldData; -using autofill::PasswordForm; using base::ASCIIToUTF16; using base::StringPiece; using testing::_; @@ -89,14 +88,14 @@ public ::testing::WithParamInterface<SaveOperation> { protected: // Either saves, updates or replaces |pending| according to the test param. - void SaveCredential(autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + void SaveCredential(PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password); }; void FormSaverImplSaveTest::SaveCredential( - autofill::PasswordForm pending, - const std::vector<const autofill::PasswordForm*>& matches, + PasswordForm pending, + const std::vector<const PasswordForm*>& matches, const base::string16& old_password) { switch (GetParam()) { case SaveOperation::kSave:
diff --git a/components/password_manager/core/browser/http_auth_manager.h b/components/password_manager/core/browser/http_auth_manager.h index ab886a9a..50455af 100644 --- a/components/password_manager/core/browser/http_auth_manager.h +++ b/components/password_manager/core/browser/http_auth_manager.h
@@ -5,8 +5,8 @@ #ifndef COMPONENTS_PASSWORD_MANAGER_CORE_BROWSER_HTTP_AUTH_MANAGER_H_ #define COMPONENTS_PASSWORD_MANAGER_CORE_BROWSER_HTTP_AUTH_MANAGER_H_ -#include "components/autofill/core/common/password_form.h" #include "components/password_manager/core/browser/browser_save_password_progress_logger.h" +#include "components/password_manager/core/browser/password_form_forward.h" namespace password_manager { @@ -26,7 +26,7 @@ // Set the observer which is notified in case a form can be auto-filled. virtual void SetObserverAndDeliverCredentials( HttpAuthObserver* observer, - const autofill::PasswordForm& observed_form) = 0; + const PasswordForm& observed_form) = 0; // Detach |observer| as the observer if it is the current observer. // Called by the observer when destructed to unregister itself. @@ -34,8 +34,7 @@ // Handles submitted http-auth credentials event. // Called by the LoginHandler instance. - virtual void OnPasswordFormSubmitted( - const autofill::PasswordForm& password_form) = 0; + virtual void OnPasswordFormSubmitted(const PasswordForm& password_form) = 0; // Called by the LoginHandler instance when the password form is dismissed. virtual void OnPasswordFormDismissed() = 0;
diff --git a/components/password_manager/core/browser/http_auth_manager_impl.cc b/components/password_manager/core/browser/http_auth_manager_impl.cc index e4cdc054..079eee9 100644 --- a/components/password_manager/core/browser/http_auth_manager_impl.cc +++ b/components/password_manager/core/browser/http_auth_manager_impl.cc
@@ -6,16 +6,14 @@ #include <utility> -#include "components/autofill/core/common/password_form.h" #include "components/autofill/core/common/save_password_progress_logger.h" +#include "components/password_manager/core/browser/password_form.h" #include "components/password_manager/core/browser/password_form_manager.h" #include "components/password_manager/core/browser/password_form_manager_for_ui.h" #include "components/password_manager/core/browser/password_manager_client.h" #include "components/password_manager/core/browser/password_manager_util.h" #include "components/password_manager/core/browser/password_save_manager_impl.h" -using autofill::PasswordForm; - namespace password_manager { namespace {
diff --git a/components/password_manager/core/browser/http_auth_manager_impl.h b/components/password_manager/core/browser/http_auth_manager_impl.h index bd54cf4..6086a372 100644 --- a/components/password_manager/core/browser/http_auth_manager_impl.h +++ b/components/password_manager/core/browser/http_auth_manager_impl.h
@@ -10,10 +10,10 @@ #include <string> #include <vector> -#include "components/autofill/core/common/password_form.h" #include "components/password_manager/core/browser/browser_save_password_progress_logger.h" #include "components/password_manager/core/browser/http_auth_manager.h" #include "components/password_manager/core/browser/http_auth_observer.h" +#include "components/password_manager/core/browser/password_form_forward.h" namespace password_manager { @@ -28,24 +28,23 @@ HttpAuthManagerImpl(PasswordManagerClient* client, HttpAuthObserver* observer, - const autofill::PasswordForm& observed_form); + const PasswordForm& observed_form); ~HttpAuthManagerImpl() override; // HttpAuthManager: void SetObserverAndDeliverCredentials( HttpAuthObserver* observer, - const autofill::PasswordForm& observed_form) override; + const PasswordForm& observed_form) override; void DetachObserver(HttpAuthObserver* observer) override; - void OnPasswordFormSubmitted( - const autofill::PasswordForm& password_form) override; + void OnPasswordFormSubmitted(const PasswordForm& password_form) override; void OnPasswordFormDismissed() override; // Called by a PasswordManagerClient when it decides that a HTTP auth dialog // can be auto-filled. It notifies the observer about new credentials given // that the form manged by |form_manager| equals the one observed by the // observer that is managed by |form_manager|. - void Autofill(const autofill::PasswordForm& preferred_match, + void Autofill(const PasswordForm& preferred_match, const PasswordFormManagerForUI* form_manager) const; // Handles successful navigation to the main frame. @@ -57,7 +56,7 @@ // Passes |form| to PasswordFormManager that manages it for using it after // detecting submission success for saving. - void ProvisionallySaveForm(const autofill::PasswordForm& password_form); + void ProvisionallySaveForm(const PasswordForm& password_form); // Initiates the saving of the password. void OnLoginSuccesfull();
diff --git a/components/password_manager/core/browser/http_auth_manager_unittest.cc b/components/password_manager/core/browser/http_auth_manager_unittest.cc index 42743cb2..ba24cef 100644 --- a/components/password_manager/core/browser/http_auth_manager_unittest.cc +++ b/components/password_manager/core/browser/http_auth_manager_unittest.cc
@@ -31,8 +31,6 @@ #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" -using autofill::PasswordForm; - using base::ASCIIToUTF16; using base::TestMockTimeTaskRunner; using testing::_; @@ -53,8 +51,7 @@ MOCK_CONST_METHOD1(IsSavingAndFillingEnabled, bool(const GURL&)); MOCK_CONST_METHOD1(IsFillingEnabled, bool(const GURL&)); MOCK_METHOD2(AutofillHttpAuth, - void(const autofill::PasswordForm&, - const PasswordFormManagerForUI*)); + void(const PasswordForm&, const PasswordFormManagerForUI*)); MOCK_CONST_METHOD0(GetProfilePasswordStore, PasswordStore*()); MOCK_CONST_METHOD0(GetAccountPasswordStore, PasswordStore*()); MOCK_METHOD0(PromptUserToSaveOrUpdatePasswordPtr, void());
diff --git a/components/password_manager/core/browser/http_auth_observer.h b/components/password_manager/core/browser/http_auth_observer.h index 06e45d7..539949d 100644 --- a/components/password_manager/core/browser/http_auth_observer.h +++ b/components/password_manager/core/browser/http_auth_observer.h
@@ -9,7 +9,6 @@ #include "base/macros.h" #include "base/strings/string16.h" -#include "components/autofill/core/common/password_form.h" namespace password_manager {
diff --git a/components/password_manager/core/browser/http_credentials_cleaner.cc b/components/password_manager/core/browser/http_credentials_cleaner.cc index 60e380f..1853b7d 100644 --- a/components/password_manager/core/browser/http_credentials_cleaner.cc +++ b/components/password_manager/core/browser/http_credentials_cleaner.cc
@@ -39,7 +39,7 @@ } void HttpCredentialCleaner::OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results) { + std::vector<std::unique_ptr<PasswordForm>> results) { // Non HTTP or HTTPS credentials are ignored, in particular Android or // federated credentials. for (auto& form : RemoveNonHTTPOrHTTPSForms(std::move(results))) { @@ -64,7 +64,7 @@ } void HttpCredentialCleaner::OnHSTSQueryResult( - std::unique_ptr<autofill::PasswordForm> form, + std::unique_ptr<PasswordForm> form, FormKey key, HSTSResult hsts_result) { ++processed_results_;
diff --git a/components/password_manager/core/browser/http_credentials_cleaner.h b/components/password_manager/core/browser/http_credentials_cleaner.h index 9a11290..d044be9 100644 --- a/components/password_manager/core/browser/http_credentials_cleaner.h +++ b/components/password_manager/core/browser/http_credentials_cleaner.h
@@ -14,9 +14,9 @@ #include "base/containers/flat_set.h" #include "base/memory/ref_counted.h" -#include "components/autofill/core/common/password_form.h" #include "components/password_manager/core/browser/credentials_cleaner.h" #include "components/password_manager/core/browser/hsts_query.h" +#include "components/password_manager/core/browser/password_form.h" #include "components/password_manager/core/browser/password_store_consumer.h" namespace network { @@ -77,19 +77,18 @@ // signon-realm excluding the protocol, the second argument is // the PasswordForm::scheme (i.e. HTML, BASIC, etc.) and the third argument is // the username of the form. - using FormKey = - std::tuple<std::string, autofill::PasswordForm::Scheme, base::string16>; + using FormKey = std::tuple<std::string, PasswordForm::Scheme, base::string16>; // PasswordStoreConsumer: void OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results) override; + std::vector<std::unique_ptr<PasswordForm>> results) override; // This function will inform us using |hsts_result| parameter if the |form|'s // host has HSTS enabled. |key| is |form|'s encoding which is used for // matching |form| with an HTTPS credential with the same FormKey. // Inside the function the metric counters are updated and, if needed, the // |form| is removed or migrated to HTTPS. - void OnHSTSQueryResult(std::unique_ptr<autofill::PasswordForm> form, + void OnHSTSQueryResult(std::unique_ptr<PasswordForm> form, FormKey key, HSTSResult hsts_result);
diff --git a/components/password_manager/core/browser/http_credentials_cleaner_unittest.cc b/components/password_manager/core/browser/http_credentials_cleaner_unittest.cc index 9f1a174..0dd8a3b8 100644 --- a/components/password_manager/core/browser/http_credentials_cleaner_unittest.cc +++ b/components/password_manager/core/browser/http_credentials_cleaner_unittest.cc
@@ -35,7 +35,7 @@ struct TestCase { bool is_hsts_enabled; - autofill::PasswordForm::Scheme http_form_scheme; + PasswordForm::Scheme http_form_scheme; bool same_signon_realm; bool same_scheme; bool same_username; @@ -54,48 +54,48 @@ constexpr static TestCase kCases[] = { - {true, autofill::PasswordForm::Scheme::kHtml, false, true, true, true, + {true, PasswordForm::Scheme::kHtml, false, true, true, true, HttpCredentialType::kNoMatching}, - {true, autofill::PasswordForm::Scheme::kHtml, true, false, true, true, + {true, PasswordForm::Scheme::kHtml, true, false, true, true, HttpCredentialType::kNoMatching}, - {true, autofill::PasswordForm::Scheme::kHtml, true, true, false, true, + {true, PasswordForm::Scheme::kHtml, true, true, false, true, HttpCredentialType::kNoMatching}, - {true, autofill::PasswordForm::Scheme::kHtml, true, true, true, false, + {true, PasswordForm::Scheme::kHtml, true, true, true, false, HttpCredentialType::kConflicting}, - {true, autofill::PasswordForm::Scheme::kHtml, true, true, true, true, + {true, PasswordForm::Scheme::kHtml, true, true, true, true, HttpCredentialType::kEquivalent}, - {false, autofill::PasswordForm::Scheme::kHtml, false, true, true, true, + {false, PasswordForm::Scheme::kHtml, false, true, true, true, HttpCredentialType::kNoMatching}, - {false, autofill::PasswordForm::Scheme::kHtml, true, false, true, true, + {false, PasswordForm::Scheme::kHtml, true, false, true, true, HttpCredentialType::kNoMatching}, - {false, autofill::PasswordForm::Scheme::kHtml, true, true, false, true, + {false, PasswordForm::Scheme::kHtml, true, true, false, true, HttpCredentialType::kNoMatching}, - {false, autofill::PasswordForm::Scheme::kHtml, true, true, true, false, + {false, PasswordForm::Scheme::kHtml, true, true, true, false, HttpCredentialType::kConflicting}, - {false, autofill::PasswordForm::Scheme::kHtml, true, true, true, true, + {false, PasswordForm::Scheme::kHtml, true, true, true, true, HttpCredentialType::kEquivalent}, - {true, autofill::PasswordForm::Scheme::kBasic, false, true, true, true, + {true, PasswordForm::Scheme::kBasic, false, true, true, true, HttpCredentialType::kNoMatching}, - {true, autofill::PasswordForm::Scheme::kBasic, true, false, true, true, + {true, PasswordForm::Scheme::kBasic, true, false, true, true, HttpCredentialType::kNoMatching}, - {true, autofill::PasswordForm::Scheme::kBasic, true, true, false, true, + {true, PasswordForm::Scheme::kBasic, true, true, false, true, HttpCredentialType::kNoMatching}, - {true, autofill::PasswordForm::Scheme::kBasic, true, true, true, false, + {true, PasswordForm::Scheme::kBasic, true, true, true, false, HttpCredentialType::kConflicting}, - {true, autofill::PasswordForm::Scheme::kBasic, true, true, true, true, + {true, PasswordForm::Scheme::kBasic, true, true, true, true, HttpCredentialType::kEquivalent}, - {false, autofill::PasswordForm::Scheme::kBasic, false, true, true, true, + {false, PasswordForm::Scheme::kBasic, false, true, true, true, HttpCredentialType::kNoMatching}, - {false, autofill::PasswordForm::Scheme::kBasic, true, false, true, true, + {false, PasswordForm::Scheme::kBasic, true, false, true, true, HttpCredentialType::kNoMatching}, - {false, autofill::PasswordForm::Scheme::kBasic, true, true, false, true, + {false, PasswordForm::Scheme::kBasic, true, true, false, true, HttpCredentialType::kNoMatching}, - {false, autofill::PasswordForm::Scheme::kBasic, true, true, true, false, + {false, PasswordForm::Scheme::kBasic, true, true, true, false, HttpCredentialType::kConflicting}, - {false, autofill::PasswordForm::Scheme::kBasic, true, true, true, true, + {false, PasswordForm::Scheme::kBasic, true, true, true, true, HttpCredentialType::kEquivalent}}; } // namespace @@ -151,7 +151,7 @@ << ", same_username=" << test.same_username << ", same_password=" << test.same_password); - autofill::PasswordForm http_form; + PasswordForm http_form; http_form.url = GURL("http://example.org/"); http_form.signon_realm = "http://example.org/"; http_form.scheme = test.http_form_scheme; @@ -159,17 +159,16 @@ http_form.password_value = password[1]; store_->AddLogin(http_form); - autofill::PasswordForm https_form; + PasswordForm https_form; https_form.url = GURL("https://example.org/"); https_form.signon_realm = signon_realm[test.same_signon_realm]; https_form.username_value = username[test.same_username]; https_form.password_value = password[test.same_password]; https_form.scheme = test.http_form_scheme; if (!test.same_scheme) { - https_form.scheme = - (http_form.scheme == autofill::PasswordForm::Scheme::kBasic - ? autofill::PasswordForm::Scheme::kHtml - : autofill::PasswordForm::Scheme::kBasic); + https_form.scheme = (http_form.scheme == PasswordForm::Scheme::kBasic + ? PasswordForm::Scheme::kHtml + : PasswordForm::Scheme::kBasic); } store_->AddLogin(https_form);
diff --git a/components/password_manager/core/browser/http_password_store_migrator.cc b/components/password_manager/core/browser/http_password_store_migrator.cc index 722bf49..3eef1f9 100644 --- a/components/password_manager/core/browser/http_password_store_migrator.cc +++ b/components/password_manager/core/browser/http_password_store_migrator.cc
@@ -48,7 +48,7 @@ GURL::Replacements rep; rep.SetSchemeStr(url::kHttpScheme); GURL http_origin = https_origin.GetURL().ReplaceComponents(rep); - PasswordStore::FormDigest form(autofill::PasswordForm::Scheme::kHtml, + PasswordStore::FormDigest form(PasswordForm::Scheme::kHtml, http_origin.GetOrigin().spec(), http_origin); http_origin_domain_ = url::Origin::Create(http_origin); store_->GetLogins(form, this); @@ -60,11 +60,11 @@ HttpPasswordStoreMigrator::~HttpPasswordStoreMigrator() = default; -autofill::PasswordForm HttpPasswordStoreMigrator::MigrateHttpFormToHttps( - const autofill::PasswordForm& http_form) { +PasswordForm HttpPasswordStoreMigrator::MigrateHttpFormToHttps( + const PasswordForm& http_form) { DCHECK(http_form.url.SchemeIs(url::kHttpScheme)); - autofill::PasswordForm https_form = http_form; + PasswordForm https_form = http_form; GURL::Replacements rep; rep.SetSchemeStr(url::kHttpsScheme); https_form.url = http_form.url.ReplaceComponents(rep); @@ -83,13 +83,13 @@ https_form.action = https_form.url; https_form.form_data = autofill::FormData(); https_form.generation_upload_status = - autofill::PasswordForm::GenerationUploadStatus::kNoSignalSent; + PasswordForm::GenerationUploadStatus::kNoSignalSent; https_form.skip_zero_click = false; return https_form; } void HttpPasswordStoreMigrator::OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results) { + std::vector<std::unique_ptr<PasswordForm>> results) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); results_ = std::move(results); got_password_store_results_ = true; @@ -113,15 +113,14 @@ void HttpPasswordStoreMigrator::ProcessPasswordStoreResults() { // Android and PSL matches are ignored. - base::EraseIf( - results_, [](const std::unique_ptr<autofill::PasswordForm>& form) { - return form->is_affiliation_based_match || form->is_public_suffix_match; - }); + base::EraseIf(results_, [](const std::unique_ptr<PasswordForm>& form) { + return form->is_affiliation_based_match || form->is_public_suffix_match; + }); // Add the new credentials to the password store. The HTTP forms are // removed iff |mode_| == MigrationMode::MOVE. for (const auto& form : results_) { - autofill::PasswordForm new_form = + PasswordForm new_form = HttpPasswordStoreMigrator::MigrateHttpFormToHttps(*form); store_->AddLogin(new_form);
diff --git a/components/password_manager/core/browser/http_password_store_migrator.h b/components/password_manager/core/browser/http_password_store_migrator.h index d6dd716e..755d24d 100644 --- a/components/password_manager/core/browser/http_password_store_migrator.h +++ b/components/password_manager/core/browser/http_password_store_migrator.h
@@ -11,13 +11,10 @@ #include "base/macros.h" #include "base/sequence_checker.h" #include "components/password_manager/core/browser/hsts_query.h" +#include "components/password_manager/core/browser/password_form_forward.h" #include "components/password_manager/core/browser/password_store_consumer.h" #include "url/origin.h" -namespace autofill { -struct PasswordForm; -} - namespace password_manager { // These values are persisted to logs. Entries should not be renumbered and @@ -51,7 +48,7 @@ // Notify the embedder that |forms| were migrated to HTTPS. |forms| contain // the updated HTTPS scheme. virtual void ProcessMigratedForms( - std::vector<std::unique_ptr<autofill::PasswordForm>> forms) = 0; + std::vector<std::unique_ptr<PasswordForm>> forms) = 0; }; // |https_origin| should specify a valid HTTPS URL. @@ -62,12 +59,11 @@ ~HttpPasswordStoreMigrator() override; // Creates HTTPS version of |http_form|. - static autofill::PasswordForm MigrateHttpFormToHttps( - const autofill::PasswordForm& http_form); + static PasswordForm MigrateHttpFormToHttps(const PasswordForm& http_form); // PasswordStoreConsumer: void OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>> results) override; + std::vector<std::unique_ptr<PasswordForm>> results) override; // Callback for PostHSTSQueryForHostAndNetworkContext. void OnHSTSQueryResult(HSTSResult is_hsts); @@ -85,7 +81,7 @@ bool got_hsts_query_result_ = false; bool got_password_store_results_ = false; HttpPasswordMigrationMode mode_ = HttpPasswordMigrationMode::kMove; - std::vector<std::unique_ptr<autofill::PasswordForm>> results_; + std::vector<std::unique_ptr<PasswordForm>> results_; url::Origin http_origin_domain_; SEQUENCE_CHECKER(sequence_checker_);
diff --git a/components/password_manager/core/browser/http_password_store_migrator_unittest.cc b/components/password_manager/core/browser/http_password_store_migrator_unittest.cc index b79bbf8b..20e5f928 100644 --- a/components/password_manager/core/browser/http_password_store_migrator_unittest.cc +++ b/components/password_manager/core/browser/http_password_store_migrator_unittest.cc
@@ -16,7 +16,6 @@ namespace password_manager { namespace { -using autofill::PasswordForm; using testing::_; using testing::ElementsAre; using testing::Invoke; @@ -78,16 +77,14 @@ class MockConsumer : public HttpPasswordStoreMigrator::Consumer { public: - MOCK_METHOD1(ProcessForms, - void(const std::vector<autofill::PasswordForm*>& forms)); + MOCK_METHOD1(ProcessForms, void(const std::vector<PasswordForm*>& forms)); void ProcessMigratedForms( - std::vector<std::unique_ptr<autofill::PasswordForm>> forms) override { - std::vector<autofill::PasswordForm*> raw_forms(forms.size()); - std::transform(forms.begin(), forms.end(), raw_forms.begin(), - [](const std::unique_ptr<autofill::PasswordForm>& form) { - return form.get(); - }); + std::vector<std::unique_ptr<PasswordForm>> forms) override { + std::vector<PasswordForm*> raw_forms(forms.size()); + std::transform( + forms.begin(), forms.end(), raw_forms.begin(), + [](const std::unique_ptr<PasswordForm>& form) { return form.get(); }); ProcessForms(raw_forms); } }; @@ -153,9 +150,9 @@ .Times(is_hsts); WaitForPasswordStore(); - EXPECT_CALL(consumer(), ProcessForms(std::vector<autofill::PasswordForm*>())); + EXPECT_CALL(consumer(), ProcessForms(std::vector<PasswordForm*>())); migrator.OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>>()); + std::vector<std::unique_ptr<PasswordForm>>()); } void HttpPasswordStoreMigratorTest::TestFullStore(bool is_hsts) { @@ -195,7 +192,7 @@ EXPECT_CALL(consumer(), ProcessForms(ElementsAre(Pointee(expected_form), Pointee(expected_federated_form)))); - std::vector<std::unique_ptr<autofill::PasswordForm>> results; + std::vector<std::unique_ptr<PasswordForm>> results; results.push_back(std::make_unique<PasswordForm>(psl_form)); results.push_back(std::make_unique<PasswordForm>(form)); results.push_back(std::make_unique<PasswordForm>(android_form)); @@ -226,7 +223,7 @@ })); migrator->OnGetPasswordStoreResults( - std::vector<std::unique_ptr<autofill::PasswordForm>>()); + std::vector<std::unique_ptr<PasswordForm>>()); // We expect a potential call to |RemoveSiteStatsImpl| which is a async task // posted from |PasswordStore::RemoveSiteStats|. Hence the following lines are
diff --git a/components/payments/content/android_payment_app_factory.cc b/components/payments/content/android_payment_app_factory.cc index 41ea8caf..6b6ef32 100644 --- a/components/payments/content/android_payment_app_factory.cc +++ b/components/payments/content/android_payment_app_factory.cc
@@ -58,6 +58,7 @@ DCHECK_EQ(0U, number_of_pending_is_ready_to_pay_queries_); DCHECK_EQ(nullptr, communication_.get()); DCHECK_NE(nullptr, communication.get()); + DCHECK(delegate->GetSpec()); DCHECK(delegate->GetSpec()->details().id.has_value()); delegate_ = delegate; @@ -87,7 +88,7 @@ std::vector<std::unique_ptr<AndroidAppDescription>> app_descriptions) { DCHECK_CURRENTLY_ON(content::BrowserThread::UI); // The browser could be shutting down. - if (!communication_ || !delegate_) + if (!communication_ || !delegate_ || !delegate_->GetSpec()) return; if (error_message.has_value()) { @@ -178,7 +179,7 @@ DCHECK_LT(0U, number_of_pending_is_ready_to_pay_queries_); // The browser could be shutting down. - if (!communication_ || !delegate_) { + if (!communication_ || !delegate_ || !delegate_->GetSpec()) { OnDoneCreatingPaymentApps(); return; }
diff --git a/components/payments/content/autofill_payment_app_factory.cc b/components/payments/content/autofill_payment_app_factory.cc index b6eadc5..dafa6381 100644 --- a/components/payments/content/autofill_payment_app_factory.cc +++ b/components/payments/content/autofill_payment_app_factory.cc
@@ -21,6 +21,9 @@ AutofillPaymentAppFactory::ConvertCardToPaymentAppIfSupportedNetwork( const autofill::CreditCard& card, base::WeakPtr<Delegate> delegate) { + DCHECK(delegate); + DCHECK(delegate->GetSpec()); + std::string basic_card_network = autofill::data_util::GetPaymentRequestData(card.network()) .basic_card_issuer_network; @@ -46,6 +49,11 @@ AutofillPaymentAppFactory::~AutofillPaymentAppFactory() = default; void AutofillPaymentAppFactory::Create(base::WeakPtr<Delegate> delegate) { + DCHECK(delegate); + + if (!delegate->GetSpec()) + return; + // No need to create autofill payment apps if native app creation is skipped // because autofill payment apps are created completely by the Java factory. if (delegate->SkipCreatingNativePaymentApps()) {
diff --git a/components/payments/content/payment_app_factory.h b/components/payments/content/payment_app_factory.h index d31696a..0708bd1 100644 --- a/components/payments/content/payment_app_factory.h +++ b/components/payments/content/payment_app_factory.h
@@ -58,6 +58,9 @@ GetPaymentManifestWebDataService() const = 0; virtual bool MayCrawlForInstallablePaymentApps() = 0; virtual bool IsOffTheRecord() const = 0; + + // Returns the merchant provided information, or null if the payment is + // being aborted. virtual PaymentRequestSpec* GetSpec() const = 0; // Returns the Android package name of the Trusted Web Activity that invoked
diff --git a/components/payments/content/payment_request_spec.cc b/components/payments/content/payment_request_spec.cc index 38ee88f0..9846567 100644 --- a/components/payments/content/payment_request_spec.cc +++ b/components/payments/content/payment_request_spec.cc
@@ -366,6 +366,10 @@ methods::kSecurePaymentConfirmation; } +base::WeakPtr<PaymentRequestSpec> PaymentRequestSpec::GetWeakPtr() { + return weak_ptr_factory_.GetWeakPtr(); +} + const mojom::PaymentDetailsModifierPtr* PaymentRequestSpec::GetApplicableModifier(PaymentApp* selected_app) const { if (!selected_app ||
diff --git a/components/payments/content/payment_request_spec.h b/components/payments/content/payment_request_spec.h index 97215a6e..1aa3a47 100644 --- a/components/payments/content/payment_request_spec.h +++ b/components/payments/content/payment_request_spec.h
@@ -11,6 +11,7 @@ #include <vector> #include "base/macros.h" +#include "base/memory/weak_ptr.h" #include "base/observer_list.h" #include "base/strings/string16.h" #include "components/autofill/core/browser/data_model/credit_card.h" @@ -206,6 +207,8 @@ bool IsSecurePaymentConfirmationRequested() const; + base::WeakPtr<PaymentRequestSpec> GetWeakPtr(); + private: // Returns the first applicable modifier in the Payment Request for the // |selected_app|. @@ -286,6 +289,8 @@ base::string16 retry_error_message_; mojom::PayerErrorsPtr payer_errors_; + base::WeakPtrFactory<PaymentRequestSpec> weak_ptr_factory_{this}; + DISALLOW_COPY_AND_ASSIGN(PaymentRequestSpec); };
diff --git a/components/payments/content/payment_request_state.cc b/components/payments/content/payment_request_state.cc index 3ab500e..6c1f5545 100644 --- a/components/payments/content/payment_request_state.cc +++ b/components/payments/content/payment_request_state.cc
@@ -73,7 +73,7 @@ frame_origin_(frame_origin), frame_security_origin_(frame_security_origin), app_locale_(app_locale), - spec_(spec), + spec_(spec->GetWeakPtr()), delegate_(delegate), personal_data_manager_(personal_data_manager), journey_logger_(journey_logger), @@ -108,7 +108,7 @@ } PaymentRequestSpec* PaymentRequestState::GetSpec() const { - return spec_; + return spec_.get(); } std::string PaymentRequestState::GetTwaPackageName() const { @@ -134,6 +134,7 @@ const std::vector<mojom::PaymentMethodDataPtr>& PaymentRequestState::GetMethodData() const { + DCHECK(GetSpec()); return GetSpec()->method_data(); } @@ -159,7 +160,7 @@ bool PaymentRequestState::MayCrawlForInstallablePaymentApps() { return PaymentsExperimentalFeatures::IsEnabled( features::kAlwaysAllowJustInTimePaymentApp) || - !spec_->supports_basic_card(); + !spec_ || !spec_->supports_basic_card(); } bool PaymentRequestState::IsOffTheRecord() const { @@ -260,6 +261,9 @@ } void PaymentRequestState::OnSpecUpdated() { + if (!spec_) + return; + autofill::AutofillProfile* selected_shipping_profile = selected_shipping_profile_; autofill::AutofillProfile* selected_contact_profile = @@ -336,6 +340,9 @@ MethodsSupportedCallback callback) { DCHECK(get_all_apps_finished_); + if (!spec_) + return; + // Don't modify the value of |are_requested_methods_supported_|, because it's // used for canMakePayment(). bool supported = are_requested_methods_supported_; @@ -375,9 +382,12 @@ void PaymentRequestState::GeneratePaymentResponse() { DCHECK(is_ready_to_pay()); + if (!spec_) + return; + // Once the response is ready, will call back into OnPaymentResponseReady. response_helper_ = std::make_unique<PaymentResponseHelper>( - app_locale_, spec_, selected_app_, payment_request_delegate_, + app_locale_, spec_.get(), selected_app_, payment_request_delegate_, selected_shipping_profile_, selected_contact_profile_, this); } @@ -467,6 +477,9 @@ void PaymentRequestState::SetSelectedShippingOption( const std::string& shipping_option_id) { + if (!spec_) + return; + spec_->StartWaitingForUpdateWith( PaymentRequestSpec::UpdateReason::SHIPPING_OPTION); if (delegate_) { @@ -479,6 +492,9 @@ void PaymentRequestState::SetSelectedShippingProfile( autofill::AutofillProfile* profile, SectionSelectionStatus selection_status) { + if (!spec_) + return; + spec_->StartWaitingForUpdateWith( PaymentRequestSpec::UpdateReason::SHIPPING_ADDRESS); selected_shipping_profile_ = profile; @@ -574,7 +590,8 @@ // Only pre-select an address if the merchant provided at least one selected // shipping option, and the top profile is complete. Assumes that profiles // have already been sorted for completeness and frecency. - if (!shipping_profiles().empty() && spec_->selected_shipping_option() && + if (!shipping_profiles().empty() && spec_ && + spec_->selected_shipping_option() && profile_comparator()->IsShippingComplete(shipping_profiles_[0])) { selected_shipping_profile_ = shipping_profiles()[0]; } @@ -586,13 +603,16 @@ } bool PaymentRequestState::ShouldShowShippingSection() const { - if (!spec_->request_shipping()) + if (!spec_ || !spec_->request_shipping()) return false; return selected_app_ ? !selected_app_->HandlesShippingAddress() : true; } bool PaymentRequestState::ShouldShowContactSection() const { + if (!spec_) + return false; + if (spec_->request_payer_name() && (!selected_app_ || !selected_app_->HandlesPayerName())) { return true; @@ -682,7 +702,7 @@ // Record the missing required payment fields when no complete payment // info exists. if (available_apps_.empty()) { - if (spec_->supports_basic_card()) { + if (spec_ && spec_->supports_basic_card()) { // All fields are missing when basic-card is requested but no card exits. base::UmaHistogramSparse("PaymentRequest.MissingPaymentFields", CREDIT_CARD_EXPIRED | CREDIT_CARD_NO_CARDHOLDER | @@ -726,7 +746,7 @@ } bool PaymentRequestState::ArePaymentOptionsSatisfied() { - if (is_waiting_for_merchant_validation_) + if (is_waiting_for_merchant_validation_ || !spec_) return false; if (ShouldShowShippingSection() &&
diff --git a/components/payments/content/payment_request_state.h b/components/payments/content/payment_request_state.h index 762b864..b813157 100644 --- a/components/payments/content/payment_request_state.h +++ b/components/payments/content/payment_request_state.h
@@ -114,6 +114,7 @@ base::OnceCallback<void(bool methods_supported, const std::string& error_message)>; + // The `spec` parameter should not be null. PaymentRequestState(content::WebContents* web_contents, content::RenderFrameHost* initiator_render_frame_host, const GURL& top_level_origin, @@ -390,9 +391,10 @@ const std::string app_locale_; - // Not owned. Never null. Will outlive this object. - PaymentRequestSpec* spec_; + base::WeakPtr<PaymentRequestSpec> spec_; base::WeakPtr<Delegate> delegate_; + + // Not owned. Never null. Will outlive this object. autofill::PersonalDataManager* personal_data_manager_; JourneyLogger* journey_logger_;
diff --git a/components/payments/content/payment_response_helper.cc b/components/payments/content/payment_response_helper.cc index 9f3c676..09e19de9 100644 --- a/components/payments/content/payment_response_helper.cc +++ b/components/payments/content/payment_response_helper.cc
@@ -33,12 +33,11 @@ : app_locale_(app_locale), is_waiting_for_shipping_address_normalization_(false), is_waiting_for_instrument_details_(false), - spec_(spec), + spec_(spec->GetWeakPtr()), delegate_(delegate), selected_app_(selected_app), payment_request_delegate_(payment_request_delegate), selected_contact_profile_(selected_contact_profile) { - DCHECK(spec_); DCHECK(selected_app_); DCHECK(delegate_); @@ -113,6 +112,9 @@ const autofill::AutofillProfile* selected_contact_profile) const { mojom::PayerDetailPtr payer = mojom::PayerDetail::New(); + if (!spec_) + return payer; + if (spec_->request_payer_name()) { if (selected_app_->HandlesPayerName()) { payer->name = payer_data_from_app_.payer_name; @@ -159,6 +161,9 @@ DCHECK(!is_waiting_for_instrument_details_); DCHECK(!is_waiting_for_shipping_address_normalization_); + if (!spec_) + return; + mojom::PaymentResponsePtr payment_response = mojom::PaymentResponse::New(); // Make sure that we return the method name that the merchant specified for
diff --git a/components/payments/content/payment_response_helper.h b/components/payments/content/payment_response_helper.h index e326866..a761d65 100644 --- a/components/payments/content/payment_response_helper.h +++ b/components/payments/content/payment_response_helper.h
@@ -65,8 +65,9 @@ bool is_waiting_for_shipping_address_normalization_; bool is_waiting_for_instrument_details_; + base::WeakPtr<PaymentRequestSpec> spec_; + // Not owned, cannot be null. - PaymentRequestSpec* spec_; Delegate* delegate_; PaymentApp* selected_app_; PaymentRequestDelegate* payment_request_delegate_;
diff --git a/components/payments/content/secure_payment_confirmation_app_factory.cc b/components/payments/content/secure_payment_confirmation_app_factory.cc index 56da6c1..4ca45390 100644 --- a/components/payments/content/secure_payment_confirmation_app_factory.cc +++ b/components/payments/content/secure_payment_confirmation_app_factory.cc
@@ -109,9 +109,11 @@ void SecurePaymentConfirmationAppFactory::Create( base::WeakPtr<Delegate> delegate) { + DCHECK(delegate); + PaymentRequestSpec* spec = delegate->GetSpec(); - if (!base::Contains(spec->payment_method_identifiers_set(), - methods::kSecurePaymentConfirmation)) { + if (!spec || !base::Contains(spec->payment_method_identifiers_set(), + methods::kSecurePaymentConfirmation)) { delegate->OnDoneCreatingPaymentApps(); return; } @@ -210,11 +212,11 @@ std::unique_ptr<SecurePaymentConfirmationInstrument> instrument, std::unique_ptr<Request> request, const SkBitmap& decoded_icon) { - if (!request->delegate || !request->web_contents()) - return; - - if (request->authenticator->GetRenderFrameHost() != - request->web_contents()->GetMainFrame()) { + DCHECK(request); + if (!request->delegate || !request->web_contents() || + !request->delegate->GetSpec() || + request->authenticator->GetRenderFrameHost() != + request->web_contents()->GetMainFrame()) { request->delegate->OnDoneCreatingPaymentApps(); return; }
diff --git a/components/payments/content/secure_payment_confirmation_controller.cc b/components/payments/content/secure_payment_confirmation_controller.cc index 401cdcd..217cca6 100644 --- a/components/payments/content/secure_payment_confirmation_controller.cc +++ b/components/payments/content/secure_payment_confirmation_controller.cc
@@ -34,7 +34,7 @@ NOTREACHED(); #endif // OS_ANDROID - if (!request_) + if (!request_ || request_->spec()) return; if (!request_->state()->IsInitialized()) { @@ -57,7 +57,7 @@ // If no apps are available then don't show any UI. The payment_request.cc // code will reject the PaymentRequest.show() call with appropriate error // message on its own. - if (!request_ || !request_->state() || + if (!request_ || !request_->state() || !request_->spec() || request_->state()->available_apps().empty()) { return; }
diff --git a/components/payments/content/service_worker_payment_app.cc b/components/payments/content/service_worker_payment_app.cc index 897b35f..612ddb2 100644 --- a/components/payments/content/service_worker_payment_app.cc +++ b/components/payments/content/service_worker_payment_app.cc
@@ -33,7 +33,7 @@ content::WebContents* web_contents, const GURL& top_origin, const GURL& frame_origin, - const PaymentRequestSpec* spec, + PaymentRequestSpec* spec, std::unique_ptr<content::StoredPaymentApp> stored_payment_app_info, bool is_incognito, const base::RepeatingClosure& show_processing_spinner) @@ -41,7 +41,7 @@ content::WebContentsObserver(web_contents), top_origin_(top_origin), frame_origin_(frame_origin), - spec_(spec), + spec_(spec->GetWeakPtr()), stored_payment_app_info_(std::move(stored_payment_app_info)), delegate_(nullptr), is_incognito_(is_incognito), @@ -52,7 +52,6 @@ DCHECK(web_contents); DCHECK(top_origin_.is_valid()); DCHECK(frame_origin_.is_valid()); - DCHECK(spec_); app_method_names_.insert(stored_payment_app_info_->enabled_methods.begin(), stored_payment_app_info_->enabled_methods.end()); @@ -64,7 +63,7 @@ content::WebContents* web_contents, const GURL& top_origin, const GURL& frame_origin, - const PaymentRequestSpec* spec, + PaymentRequestSpec* spec, std::unique_ptr<WebAppInstallationInfo> installable_payment_app_info, const std::string& enabled_method, bool is_incognito, @@ -73,7 +72,7 @@ content::WebContentsObserver(web_contents), top_origin_(top_origin), frame_origin_(frame_origin), - spec_(spec), + spec_(spec->GetWeakPtr()), delegate_(nullptr), is_incognito_(is_incognito), show_processing_spinner_(show_processing_spinner), @@ -85,7 +84,6 @@ DCHECK(web_contents); DCHECK(top_origin_.is_valid()); DCHECK(frame_origin_.is_valid()); - DCHECK(spec_); app_method_names_.insert(installable_enabled_method_); } @@ -101,6 +99,9 @@ void ServiceWorkerPaymentApp::ValidateCanMakePayment( ValidateCanMakePaymentCallback callback) { + if (!spec_) + return; + // Returns true for payment app that needs installation. if (needs_installation_) { OnCanMakePaymentEventSkipped(std::move(callback)); @@ -145,6 +146,9 @@ mojom::CanMakePaymentEventDataPtr ServiceWorkerPaymentApp::CreateCanMakePaymentEventData() { + if (!spec_) + return nullptr; + std::set<std::string> requested_url_methods; for (const auto& method : spec_->payment_method_identifiers_set()) { GURL url_method(method); @@ -259,6 +263,9 @@ mojom::PaymentRequestEventDataPtr event_data = mojom::PaymentRequestEventData::New(); + if (!spec_) + return event_data; + event_data->top_origin = top_origin_; event_data->payment_request_origin = frame_origin_; @@ -518,7 +525,7 @@ } bool ServiceWorkerPaymentApp::HandlesShippingAddress() const { - if (!spec_->request_shipping()) + if (!spec_ || !spec_->request_shipping()) return false; return needs_installation_ @@ -527,7 +534,7 @@ } bool ServiceWorkerPaymentApp::HandlesPayerName() const { - if (!spec_->request_payer_name()) + if (!spec_ || !spec_->request_payer_name()) return false; return needs_installation_ @@ -536,7 +543,7 @@ } bool ServiceWorkerPaymentApp::HandlesPayerEmail() const { - if (!spec_->request_payer_email()) + if (!spec_ || !spec_->request_payer_email()) return false; return needs_installation_ @@ -545,7 +552,7 @@ } bool ServiceWorkerPaymentApp::HandlesPayerPhone() const { - if (!spec_->request_payer_phone()) + if (!spec_ || !spec_->request_payer_phone()) return false; return needs_installation_ @@ -602,7 +609,7 @@ void ServiceWorkerPaymentApp::AbortPaymentApp( base::OnceCallback<void(bool)> abort_callback) { auto* payment_app_provider = GetPaymentAppProvider(); - if (!payment_app_provider) + if (!spec_ || !payment_app_provider) return; payment_app_provider->AbortPayment(
diff --git a/components/payments/content/service_worker_payment_app.h b/components/payments/content/service_worker_payment_app.h index 97f55e6..69490bb 100644 --- a/components/payments/content/service_worker_payment_app.h +++ b/components/payments/content/service_worker_payment_app.h
@@ -37,23 +37,24 @@ public content::WebContentsObserver { public: // This constructor is used for a payment app that has been installed in - // Chrome. + // Chrome. The `spec` parameter should not be null. ServiceWorkerPaymentApp( content::WebContents* web_contents, const GURL& top_origin, const GURL& frame_origin, - const PaymentRequestSpec* spec, + PaymentRequestSpec* spec, std::unique_ptr<content::StoredPaymentApp> stored_payment_app_info, bool is_incognito, const base::RepeatingClosure& show_processing_spinner); // This constructor is used for a payment app that has not been installed in - // Chrome but can be installed when paying with it. + // Chrome but can be installed when paying with it. The `spec` parameter + // should not be null. ServiceWorkerPaymentApp( content::WebContents* web_contents, const GURL& top_origin, const GURL& frame_origin, - const PaymentRequestSpec* spec, + PaymentRequestSpec* spec, std::unique_ptr<WebAppInstallationInfo> installable_payment_app_info, const std::string& enabled_method, bool is_incognito, @@ -134,7 +135,7 @@ GURL top_origin_; GURL frame_origin_; - const PaymentRequestSpec* spec_; + base::WeakPtr<PaymentRequestSpec> spec_; std::unique_ptr<content::StoredPaymentApp> stored_payment_app_info_; // Weak pointer is fine here since the owner of this object is
diff --git a/components/payments/content/service_worker_payment_app_factory.cc b/components/payments/content/service_worker_payment_app_factory.cc index 4663c9fe..963a064 100644 --- a/components/payments/content/service_worker_payment_app_factory.cc +++ b/components/payments/content/service_worker_payment_app_factory.cc
@@ -48,7 +48,7 @@ content::InstalledPaymentAppsFinder::PaymentApps apps, ServiceWorkerPaymentAppFinder::InstallablePaymentApps installable_apps, const std::string& error_message) { - if (!delegate_) { + if (!delegate_ || !delegate_->GetSpec()) { FinishAndCleanup(); return; } @@ -127,6 +127,8 @@ const content::SupportedDelegations& supported_delegations, const base::WeakPtr<PaymentAppFactory::Delegate>& delegate, bool has_app_store_billing_method) const { + DCHECK(delegate); + DCHECK(delegate->GetSpec()); return (base::FeatureList::IsEnabled(features::kEnforceFullDelegation) || has_app_store_billing_method) && !supported_delegations.ProvidesAll(
diff --git a/components/policy/proto/record_constants.proto b/components/policy/proto/record_constants.proto index 6972ac4..480eb316 100644 --- a/components/policy/proto/record_constants.proto +++ b/components/policy/proto/record_constants.proto
@@ -18,6 +18,10 @@ // |APP_INSTALL_EVENT| for sending events to the DmServer for the // APP_INSTALL_EVENT pipeline. APP_INSTALL_EVENT = 2; + + // |MEET_DEVICE_TELEMETRY| handler is for telemetry data sent by Meet + // Devices. For more information, see go/reliable-meet-device-telemetry. + MEET_DEVICE_TELEMETRY = 3; } // |Priority| is used to determine when items from the queue should be rate
diff --git a/components/policy/resources/policy_templates.json b/components/policy/resources/policy_templates.json index c5e4b556..e6cf270 100644 --- a/components/policy/resources/policy_templates.json +++ b/components/policy/resources/policy_templates.json
@@ -1768,7 +1768,7 @@ }, { 'name': 'RemoteAccessClientFirewallTraversal', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:14-16', 'chrome_os:14-16'], @@ -1790,7 +1790,7 @@ }, { 'name': 'RemoteAccessHostClientDomain', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:22-', 'chrome_os:41-'], @@ -1807,7 +1807,7 @@ }, { 'name': 'RemoteAccessHostClientDomainList', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'list', 'schema': { 'type': 'array', @@ -1834,7 +1834,7 @@ }, { 'name': 'RemoteAccessHostFirewallTraversal', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:14-', 'chrome_os:41-'], @@ -1856,7 +1856,7 @@ }, { 'name': 'RemoteAccessHostDomain', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:22-', 'chrome_os:41-'], @@ -1873,7 +1873,7 @@ }, { 'name': 'RemoteAccessHostDomainList', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'list', 'schema': { 'type': 'array', @@ -1900,7 +1900,7 @@ }, { 'name': 'RemoteAccessHostRequireTwoFactor', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:22-22'], @@ -1922,7 +1922,7 @@ }, { 'name': 'RemoteAccessHostTalkGadgetPrefix', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:22-75', 'chrome_os:41-75'], @@ -1947,7 +1947,7 @@ }, { 'name': 'RemoteAccessHostRequireCurtain', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:23-'], @@ -1967,7 +1967,7 @@ }, { 'name': 'RemoteAccessHostAllowClientPairing', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:30-'], @@ -1985,7 +1985,7 @@ }, { 'name': 'RemoteAccessHostAllowGnubbyAuth', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:35-'], @@ -2003,7 +2003,7 @@ }, { 'name': 'RemoteAccessHostAllowRelayedConnection', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:36-', 'chrome_os:86-'], @@ -2025,7 +2025,7 @@ }, { 'name': 'RemoteAccessHostUdpPortRange', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:36-', 'chrome_os:41-'], @@ -2043,7 +2043,7 @@ }, { 'name': 'RemoteAccessHostMatchUsername', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.linux:25-', 'chrome.mac:25-'], @@ -2061,7 +2061,7 @@ }, { 'name': 'RemoteAccessHostTokenUrl', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:28-'], @@ -2079,7 +2079,7 @@ }, { 'name': 'RemoteAccessHostTokenValidationUrl', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:28-'], @@ -2097,7 +2097,7 @@ }, { 'name': 'RemoteAccessHostTokenValidationCertificateIssuer', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:28-'], @@ -2115,7 +2115,7 @@ }, { 'name': 'RemoteAccessHostDebugOverridePolicies', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'string', 'schema': { 'type': 'string' }, 'supported_on': ['chrome.*:25-47','chrome_os:42-47'], @@ -2134,7 +2134,7 @@ }, { 'name': 'RemoteAccessHostAllowUiAccessForRemoteAssistance', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.win:55-'], @@ -2152,7 +2152,7 @@ }, { 'name': 'RemoteAccessHostAllowFileTransfer', - 'owners': ['jamiewalch@chromium.org', 'rkjnsn@chromium.org'], + 'owners': ['file://remoting/OWNERS'], 'type': 'main', 'schema': { 'type': 'boolean' }, 'supported_on': ['chrome.*:74-'],
diff --git a/components/printing/renderer/BUILD.gn b/components/printing/renderer/BUILD.gn index 22d16476..3db4aab 100644 --- a/components/printing/renderer/BUILD.gn +++ b/components/printing/renderer/BUILD.gn
@@ -2,6 +2,13 @@ # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + static_library("renderer") { sources = [ "print_render_frame_helper.cc",
diff --git a/components/spellcheck/renderer/BUILD.gn b/components/spellcheck/renderer/BUILD.gn index 3dc1613..6055fd44 100644 --- a/components/spellcheck/renderer/BUILD.gn +++ b/components/spellcheck/renderer/BUILD.gn
@@ -4,6 +4,13 @@ import("//components/spellcheck/spellcheck_build_features.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + source_set("renderer") { sources = [ "custom_dictionary_engine.cc",
diff --git a/components/sync/driver/profile_sync_service.cc b/components/sync/driver/profile_sync_service.cc index 0232946..ef6757f5 100644 --- a/components/sync/driver/profile_sync_service.cc +++ b/components/sync/driver/profile_sync_service.cc
@@ -1155,7 +1155,7 @@ return; } - RecordMemoryUsageHistograms(); + RecordMemoryUsageAndCountsHistograms(); StartSyncingWithServer(); } @@ -2008,7 +2008,7 @@ } } -void ProfileSyncService::RecordMemoryUsageHistograms() { +void ProfileSyncService::RecordMemoryUsageAndCountsHistograms() { ModelTypeSet active_types = GetActiveDataTypes(); for (ModelType type : active_types) { auto dtc_it = data_type_controllers_.find(type);
diff --git a/components/sync/driver/profile_sync_service.h b/components/sync/driver/profile_sync_service.h index 475bd2f..b809a57 100644 --- a/components/sync/driver/profile_sync_service.h +++ b/components/sync/driver/profile_sync_service.h
@@ -356,8 +356,9 @@ // Tell the sync server that this client has disabled sync. void RemoveClientFromServer() const; - // Estimates and records memory usage histograms per type. - void RecordMemoryUsageHistograms(); + // Records per type histograms for estimated memory usage and number of + // entities. + void RecordMemoryUsageAndCountsHistograms(); // True if setup has been completed at least once and is not in progress. bool CanConfigureDataTypes(bool bypass_setup_in_progress_check) const;
diff --git a/components/viz/common/display/renderer_settings.h b/components/viz/common/display/renderer_settings.h index 733d83e..2e32385 100644 --- a/components/viz/common/display/renderer_settings.h +++ b/components/viz/common/display/renderer_settings.h
@@ -35,7 +35,6 @@ int highp_threshold_min = 0; bool auto_resize_output_surface = true; bool requires_alpha_channel = false; - bool record_sk_picture = false; int slow_down_compositing_scale_factor = 1;
diff --git a/components/viz/common/features.cc b/components/viz/common/features.cc index 4a39a0f..956b3b48c 100644 --- a/components/viz/common/features.cc +++ b/components/viz/common/features.cc
@@ -30,10 +30,6 @@ base::FEATURE_DISABLED_BY_DEFAULT}; #endif -// Use the SkiaRenderer to record SkPicture. -const base::Feature kRecordSkPicture{"RecordSkPicture", - base::FEATURE_DISABLED_BY_DEFAULT}; - // Kill-switch to disable de-jelly, even if flags/properties indicate it should // be enabled. const base::Feature kDisableDeJelly{"DisableDeJelly", @@ -123,11 +119,6 @@ base::FeatureList::IsEnabled(kVulkan); } -bool IsRecordingSkPicture() { - return IsUsingSkiaRenderer() && - base::FeatureList::IsEnabled(kRecordSkPicture); -} - #if defined(OS_ANDROID) bool IsDynamicColorGamutEnabled() { if (viz::AlwaysUseWideColorGamut())
diff --git a/components/viz/common/features.h b/components/viz/common/features.h index 10edc3b..72491fe 100644 --- a/components/viz/common/features.h +++ b/components/viz/common/features.h
@@ -35,7 +35,6 @@ VIZ_COMMON_EXPORT bool IsForcePreferredIntervalForVideoEnabled(); VIZ_COMMON_EXPORT bool IsVizHitTestingDebugEnabled(); VIZ_COMMON_EXPORT bool IsUsingSkiaRenderer(); -VIZ_COMMON_EXPORT bool IsRecordingSkPicture(); #if defined(OS_ANDROID) VIZ_COMMON_EXPORT bool IsDynamicColorGamutEnabled(); #endif
diff --git a/components/viz/host/host_frame_sink_manager.h b/components/viz/host/host_frame_sink_manager.h index 52ac3aa0..0cff58b2 100644 --- a/components/viz/host/host_frame_sink_manager.h +++ b/components/viz/host/host_frame_sink_manager.h
@@ -173,10 +173,9 @@ // Starts throttling the frame sinks specified by |frame_sink_ids| and all // their descendant sinks to send BeginFrames at an interval of |interval|. - // |interval| should be greater than zero. Calling this function before - // calling EndThrottling() to end a previous throttling operation will - // automatically end the previous operation before applying the current - // throttling operation. + // |interval| should be greater than zero. Previous throttling operation + // on any frame sinks must be ended by EndThrottling() before applying the + // current throttling operation. void StartThrottling(const std::vector<FrameSinkId>& frame_sink_ids, base::TimeDelta interval);
diff --git a/components/viz/host/renderer_settings_creation.cc b/components/viz/host/renderer_settings_creation.cc index b06ea5f9..5575c90 100644 --- a/components/viz/host/renderer_settings_creation.cc +++ b/components/viz/host/renderer_settings_creation.cc
@@ -70,7 +70,6 @@ !base::CommandLine::ForCurrentProcess()->HasSwitch( switches::kDisableMacOverlays); #endif - renderer_settings.record_sk_picture = features::IsRecordingSkPicture(); if (command_line->HasSwitch(switches::kSlowDownCompositingScaleFactor)) { const int kMinSlowDownScaleFactor = 1;
diff --git a/components/viz/service/display/display.cc b/components/viz/service/display/display.cc index 5eacfb3..fd94313 100644 --- a/components/viz/service/display/display.cc +++ b/components/viz/service/display/display.cc
@@ -519,23 +519,10 @@ mode, output_surface_->context_provider(), bitmap_manager_, enable_shared_images); if (settings_.use_skia_renderer && mode == DisplayResourceProvider::kGpu) { - // Default to use DDL if skia_output_surface is not null. - if (skia_output_surface_) { - renderer_ = std::make_unique<SkiaRenderer>( - &settings_, debug_settings_, output_surface_.get(), - resource_provider_.get(), overlay_processor_.get(), - skia_output_surface_, SkiaRenderer::DrawMode::DDL); - } else { - // GPU compositing with GL to an SKP. - DCHECK(output_surface_); - DCHECK(output_surface_->context_provider()); - DCHECK(settings_.record_sk_picture); - DCHECK(!overlay_processor_->IsOverlaySupported()); - renderer_ = std::make_unique<SkiaRenderer>( - &settings_, debug_settings_, output_surface_.get(), - resource_provider_.get(), overlay_processor_.get(), - nullptr /* skia_output_surface */, SkiaRenderer::DrawMode::SKPRECORD); - } + renderer_ = std::make_unique<SkiaRenderer>( + &settings_, debug_settings_, output_surface_.get(), + resource_provider_.get(), overlay_processor_.get(), + skia_output_surface_); } else if (output_surface_->context_provider()) { renderer_ = std::make_unique<GLRenderer>( &settings_, debug_settings_, output_surface_.get(),
diff --git a/components/viz/service/display/skia_renderer.cc b/components/viz/service/display/skia_renderer.cc index 3fe6509..73620ae3 100644 --- a/components/viz/service/display/skia_renderer.cc +++ b/components/viz/service/display/skia_renderer.cc
@@ -46,10 +46,8 @@ #include "third_party/skia/include/core/SkCanvas.h" #include "third_party/skia/include/core/SkColor.h" #include "third_party/skia/include/core/SkColorFilter.h" -#include "third_party/skia/include/core/SkData.h" #include "third_party/skia/include/core/SkDeferredDisplayList.h" #include "third_party/skia/include/core/SkMatrix.h" -#include "third_party/skia/include/core/SkOverdrawCanvas.h" #include "third_party/skia/include/core/SkPath.h" #include "third_party/skia/include/core/SkPixelRef.h" #include "third_party/skia/include/core/SkShader.h" @@ -558,7 +556,6 @@ const SkImage* sk_image() const { return sk_image_; } private: - base::Optional<DisplayResourceProvider::ScopedReadLockSkImage> lock_; const SkImage* sk_image_ = nullptr; DISALLOW_COPY_AND_ASSIGN(ScopedSkImageBuilder); @@ -574,27 +571,21 @@ return; auto* resource_provider = skia_renderer->resource_provider_; DCHECK(IsTextureResource(resource_provider, resource_id)); - if (!skia_renderer->is_using_ddl()) { - // TODO(penghuang): remove this code when DDL is used everywhere. - lock_.emplace(resource_provider, resource_id, alpha_type, origin); - sk_image_ = lock_->sk_image(); - } else { - auto* image_context = - skia_renderer->lock_set_for_external_use_->LockResource( - resource_id, use_skia_color_conversion); - // |ImageContext::image| provides thread safety: (a) this ImageContext is - // only accessed by GPU thread after |image| is set and (b) the fields of - // ImageContext that are accessed by both compositor and GPU thread are no - // longer modified after |image| is set. - if (!image_context->has_image()) { - image_context->set_alpha_type(alpha_type); - image_context->set_origin(origin); - } - skia_renderer->skia_output_surface_->MakePromiseSkImage(image_context); - LOG_IF(ERROR, !image_context->has_image()) - << "Failed to create the promise sk image."; - sk_image_ = image_context->image().get(); + + auto* image_context = skia_renderer->lock_set_for_external_use_->LockResource( + resource_id, use_skia_color_conversion); + // |ImageContext::image| provides thread safety: (a) this ImageContext is + // only accessed by GPU thread after |image| is set and (b) the fields of + // ImageContext that are accessed by both compositor and GPU thread are no + // longer modified after |image| is set. + if (!image_context->has_image()) { + image_context->set_alpha_type(alpha_type); + image_context->set_origin(origin); } + skia_renderer->skia_output_surface_->MakePromiseSkImage(image_context); + LOG_IF(ERROR, !image_context->has_image()) + << "Failed to create the promise sk image."; + sk_image_ = image_context->image().get(); } class SkiaRenderer::ScopedYUVSkImageBuilder { @@ -602,7 +593,6 @@ ScopedYUVSkImageBuilder(SkiaRenderer* skia_renderer, const YUVVideoDrawQuad* quad, sk_sp<SkColorSpace> dst_color_space) { - DCHECK(skia_renderer->is_using_ddl()); DCHECK(IsTextureResource(skia_renderer->resource_provider_, quad->y_plane_resource_id())); DCHECK(IsTextureResource(skia_renderer->resource_provider_, @@ -661,33 +651,15 @@ OutputSurface* output_surface, DisplayResourceProvider* resource_provider, OverlayProcessorInterface* overlay_processor, - SkiaOutputSurface* skia_output_surface, - DrawMode mode) + SkiaOutputSurface* skia_output_surface) : DirectRenderer(settings, debug_settings, output_surface, resource_provider, overlay_processor), - draw_mode_(mode), skia_output_surface_(skia_output_surface) { - switch (draw_mode_) { - case DrawMode::DDL: { - DCHECK(skia_output_surface_); - lock_set_for_external_use_.emplace(resource_provider, - skia_output_surface_); - break; - } - case DrawMode::SKPRECORD: { - DCHECK(output_surface_); - context_provider_ = output_surface_->context_provider(); - const auto& context_caps = context_provider_->ContextCapabilities(); - use_swap_with_bounds_ = context_caps.swap_buffers_with_bounds; - if (context_caps.sync_query) { - sync_queries_ = - base::Optional<SyncQueryCollection>(context_provider_->ContextGL()); - } - } - } + DCHECK(skia_output_surface_); + lock_set_for_external_use_.emplace(resource_provider, skia_output_surface_); } SkiaRenderer::~SkiaRenderer() = default; @@ -715,17 +687,7 @@ }; bool SkiaRenderer::CanPartialSwap() { - if (draw_mode_ == DrawMode::DDL) return output_surface_->capabilities().supports_post_sub_buffer; - - if (draw_mode_ != DrawMode::SKPRECORD) - return false; - - DCHECK(context_provider_); - if (use_swap_with_bounds_) - return false; - - return context_provider_->ContextCapabilities().post_sub_buffer; } void SkiaRenderer::BeginDrawingFrame() { @@ -733,16 +695,8 @@ DCHECK(!current_frame_resource_fence_); - // Copied from GLRenderer. - scoped_refptr<ResourceFence> read_lock_fence; - if (sync_queries_) { - read_lock_fence = sync_queries_->StartNewFrame(); - current_frame_resource_fence_ = nullptr; - } else { - current_frame_resource_fence_ = base::MakeRefCounted<FrameResourceFence>(); - read_lock_fence = current_frame_resource_fence_; - } - resource_provider_->SetReadLockFence(read_lock_fence.get()); + current_frame_resource_fence_ = base::MakeRefCounted<FrameResourceFence>(); + resource_provider_->SetReadLockFence(current_frame_resource_fence_.get()); #if defined(OS_ANDROID) for (const auto& pass : *current_frame()->render_passes_in_draw_order) { @@ -752,26 +706,10 @@ } } #endif - - if (draw_mode_ != DrawMode::SKPRECORD) - return; - - // Insert WaitSyncTokenCHROMIUM on quad resources prior to drawing the - // frame, so that drawing can proceed without GL context switching - // interruptions. - for (const auto& pass : *current_frame()->render_passes_in_draw_order) { - for (auto* quad : pass->quad_list) { - for (ResourceId resource_id : quad->resources) - resource_provider_->WaitSyncToken(resource_id); - } - } } void SkiaRenderer::FinishDrawingFrame() { TRACE_EVENT0("viz", "SkiaRenderer::FinishDrawingFrame"); - if (sync_queries_) { - sync_queries_->EndCurrentFrame(); - } current_frame_resource_fence_ = nullptr; current_canvas_ = nullptr; current_surface_ = nullptr; @@ -806,25 +744,7 @@ output_frame.sub_buffer_rect = swap_buffer_rect_; } - switch (draw_mode_) { - case DrawMode::DDL: { - skia_output_surface_->SwapBuffers(std::move(output_frame)); - break; - } - case DrawMode::SKPRECORD: { - // write to skp files - std::string file_name = "composited-frame.skp"; - SkFILEWStream file(file_name.c_str()); - DCHECK(file.isValid()); - - auto data = root_picture_->serialize(); - file.write(data->data(), data->size()); - file.fsync(); - root_picture_ = nullptr; - root_recorder_.reset(); - } - } - + skia_output_surface_->SwapBuffers(std::move(output_frame)); swap_buffer_rect_ = gfx::Rect(); } @@ -881,39 +801,9 @@ void SkiaRenderer::BindFramebufferToOutputSurface() { DCHECK(!output_surface_->HasExternalStencilTest()); - switch (draw_mode_) { - case DrawMode::DDL: { - root_canvas_ = skia_output_surface_->BeginPaintCurrentFrame(); - break; - } - case DrawMode::SKPRECORD: { - root_recorder_ = std::make_unique<SkPictureRecorder>(); - - current_recorder_ = root_recorder_.get(); - current_picture_ = &root_picture_; - root_canvas_ = root_recorder_->beginRecording( - SkRect::MakeWH(current_frame()->device_viewport_size.width(), - current_frame()->device_viewport_size.height())); - break; - } - } - + root_canvas_ = skia_output_surface_->BeginPaintCurrentFrame(); current_canvas_ = root_canvas_; current_surface_ = root_surface_.get(); - - // For DDL mode, if overdraw feedback is enabled, the root canvas is the nway - // canvas. - if (debug_settings_->show_overdraw_feedback && draw_mode_ != DrawMode::DDL) { - const auto& size = current_frame()->device_viewport_size; - overdraw_surface_ = root_canvas_->makeSurface( - SkImageInfo::MakeA8(size.width(), size.height())); - nway_canvas_ = std::make_unique<SkNWayCanvas>(size.width(), size.height()); - overdraw_canvas_ = - std::make_unique<SkOverdrawCanvas>(overdraw_surface_->getCanvas()); - nway_canvas_->addCanvas(overdraw_canvas_.get()); - nway_canvas_->addCanvas(root_canvas_); - current_canvas_ = nway_canvas_.get(); - } } void SkiaRenderer::BindFramebufferToTexture( @@ -923,20 +813,9 @@ // This function is called after AllocateRenderPassResourceIfNeeded, so there // should be backing ready. RenderPassBacking& backing = iter->second; - switch (draw_mode_) { - case DrawMode::DDL: { - current_canvas_ = skia_output_surface_->BeginPaintRenderPass( - render_pass_id, backing.size, backing.format, backing.generate_mipmap, - backing.color_space.ToSkColorSpace()); - break; - } - case DrawMode::SKPRECORD: { - current_recorder_ = backing.recorder.get(); - current_picture_ = &backing.picture; - current_canvas_ = current_recorder_->beginRecording( - SkRect::MakeWH(backing.size.width(), backing.size.height())); - } - } + current_canvas_ = skia_output_surface_->BeginPaintRenderPass( + render_pass_id, backing.size, backing.format, backing.generate_mipmap, + backing.color_space.ToSkColorSpace()); } void SkiaRenderer::SetScissorTestRect(const gfx::Rect& scissor_rect) { @@ -2109,10 +1988,6 @@ // that precludes batching. If this changes, we could add YUV quads that don't // require a filter to the batch instead of drawing one at a time. DCHECK(batched_quads_.empty()); - if (draw_mode_ != DrawMode::DDL) { - NOTIMPLEMENTED(); - return; - } gfx::ColorSpace src_color_space = quad->video_color_space; // Invalid or unspecified color spaces should be treated as REC709. @@ -2555,23 +2430,12 @@ // there should be backing ready. RenderPassBacking& backing = iter->second; - sk_sp<SkImage> content_image; - switch (draw_mode_) { - case DrawMode::DDL: - content_image = skia_output_surface_->MakePromiseSkImageFromRenderPass( + sk_sp<SkImage> content_image = + skia_output_surface_->MakePromiseSkImageFromRenderPass( quad->render_pass_id, backing.size, backing.format, backing.generate_mipmap, backing.color_space.ToSkColorSpace()); - DLOG_IF(ERROR, !content_image) - << "MakePromiseSkImageFromRenderPass() failed for render pass"; - break; - case DrawMode::SKPRECORD: - content_image = SkImage::MakeFromPicture( - backing.picture, - SkISize::Make(backing.size.width(), backing.size.height()), nullptr, - nullptr, SkImage::BitDepth::kU8, - backing.color_space.ToSkColorSpace()); - break; - } + DLOG_IF(ERROR, !content_image) + << "MakePromiseSkImageFromRenderPass() failed for render pass"; if (!content_image) return; @@ -2612,24 +2476,15 @@ // TODO(weiliangc): Make copy request work. (crbug.com/644851) TRACE_EVENT0("viz", "SkiaRenderer::CopyDrawnRenderPass"); - switch (draw_mode_) { - case DrawMode::DDL: { - // Root framebuffer uses id 0 in SkiaOutputSurface. - AggregatedRenderPassId render_pass_id; - const auto* const render_pass = current_frame()->current_render_pass; - if (render_pass != current_frame()->root_render_pass) { - render_pass_id = render_pass->id; - } - skia_output_surface_->CopyOutput(render_pass_id, geometry, - CurrentRenderPassColorSpace(), - std::move(request)); - break; - } - case DrawMode::SKPRECORD: { - NOTIMPLEMENTED(); - break; - } + // Root framebuffer uses id 0 in SkiaOutputSurface. + AggregatedRenderPassId render_pass_id; + const auto* const render_pass = current_frame()->current_render_pass; + if (render_pass != current_frame()->root_render_pass) { + render_pass_id = render_pass->id; } + skia_output_surface_->CopyOutput(render_pass_id, geometry, + CurrentRenderPassColorSpace(), + std::move(request)); } void SkiaRenderer::DidChangeVisibility() { @@ -2642,32 +2497,21 @@ void SkiaRenderer::FinishDrawingQuadList() { if (!batched_quads_.empty()) FlushBatchedQuads(); - switch (draw_mode_) { - case DrawMode::DDL: { - base::OnceClosure on_finished_callback; - // Signal |current_frame_resource_fence_| when the root render pass is - // finished. - if (current_frame_resource_fence_ && - current_frame_resource_fence_->WasSet() && - current_frame()->current_render_pass == - current_frame()->root_render_pass) { - on_finished_callback = - base::BindOnce(&FrameResourceFence::Signal, - std::move(current_frame_resource_fence_)); - } - gpu::SyncToken sync_token = - skia_output_surface_->SubmitPaint(std::move(on_finished_callback)); - - lock_set_for_external_use_->UnlockResources(sync_token); - break; - } - case DrawMode::SKPRECORD: { - current_canvas_->flush(); - sk_sp<SkPicture> picture = current_recorder_->finishRecordingAsPicture(); - *current_picture_ = picture; - } + base::OnceClosure on_finished_callback; + // Signal |current_frame_resource_fence_| when the root render pass is + // finished. + if (current_frame_resource_fence_ && + current_frame_resource_fence_->WasSet() && + current_frame()->current_render_pass == + current_frame()->root_render_pass) { + on_finished_callback = base::BindOnce( + &FrameResourceFence::Signal, std::move(current_frame_resource_fence_)); } + gpu::SyncToken sync_token = + skia_output_surface_->SubmitPaint(std::move(on_finished_callback)); + + lock_set_for_external_use_->UnlockResources(sync_token); } void SkiaRenderer::GenerateMipmap() { @@ -2675,15 +2519,6 @@ // CompositorRenderPassDrawQuad is what actually generates generate_mipmap. } -GrDirectContext* SkiaRenderer::GetGrContext() { - switch (draw_mode_) { - case DrawMode::DDL: - return nullptr; - case DrawMode::SKPRECORD: - return nullptr; - } -} - void SkiaRenderer::UpdateRenderPassTextures( const AggregatedRenderPassList& render_passes_in_draw_order, const base::flat_map<AggregatedRenderPassId, RenderPassRequirements>& @@ -2713,7 +2548,7 @@ render_pass_backings_.erase(it); } - if (is_using_ddl() && !passes_to_delete.empty()) { + if (!passes_to_delete.empty()) { skia_output_surface_->RemoveRenderPassResource(std::move(passes_to_delete)); } } @@ -2727,31 +2562,22 @@ return; } + auto color_space = CurrentRenderPassColorSpace(); // TODO(penghuang): check supported format correctly. gpu::Capabilities caps; caps.texture_format_bgra8888 = true; - GrDirectContext* gr_context = GetGrContext(); - switch (draw_mode_) { - case DrawMode::DDL: - break; - case DrawMode::SKPRECORD: { - render_pass_backings_.emplace( - render_pass_id, - RenderPassBacking(requirements.size, requirements.generate_mipmap, - CurrentRenderPassColorSpace())); - return; - } - } + auto format = color_space.IsHDR() + ? RGBA_F16 + : PlatformColor::BestSupportedTextureFormat(caps); render_pass_backings_.emplace( - render_pass_id, RenderPassBacking(gr_context, caps, requirements.size, - requirements.generate_mipmap, - CurrentRenderPassColorSpace())); + render_pass_id, + RenderPassBacking({requirements.size, requirements.generate_mipmap, + color_space, format})); } #if defined(OS_APPLE) void SkiaRenderer::PrepareRenderPassOverlay(CALayerOverlay* overlay) { DCHECK(!current_canvas_); - DCHECK_EQ(draw_mode_, DrawMode::DDL); DCHECK(batched_quads_.empty()); DCHECK(overlay->rpdq); @@ -2882,75 +2708,6 @@ } #endif -SkiaRenderer::RenderPassBacking::RenderPassBacking( - GrDirectContext* gr_context, - const gpu::Capabilities& caps, - const gfx::Size& size, - bool generate_mipmap, - const gfx::ColorSpace& color_space) - : size(size), generate_mipmap(generate_mipmap), color_space(color_space) { - if (color_space.IsHDR()) { - // If a platform does not support half-float renderbuffers then it should - // not should request HDR rendering. - // DCHECK(caps.texture_half_float_linear); - // DCHECK(caps.color_buffer_half_float_rgba); - format = RGBA_F16; - } else { - format = PlatformColor::BestSupportedTextureFormat(caps); - } - - // For DDL, we don't need create teh render_pass_surface here, and we will - // create the SkSurface by SkiaOutputSurface on Gpu thread. - if (!gr_context) - return; - - constexpr uint32_t flags = 0; - // LegacyFontHost will get LCD text and skia figures out what type to use. - SkSurfaceProps surface_props(flags, SkSurfaceProps::kLegacyFontHost_InitType); - int msaa_sample_count = 0; - SkColorType color_type = - ResourceFormatToClosestSkColorType(true /* gpu_compositing*/, format); - SkImageInfo image_info = - SkImageInfo::Make(size.width(), size.height(), color_type, - kPremul_SkAlphaType, color_space.ToSkColorSpace()); - render_pass_surface = SkSurface::MakeRenderTarget( - gr_context, SkBudgeted::kNo, image_info, msaa_sample_count, - kTopLeft_GrSurfaceOrigin, &surface_props, generate_mipmap); -} - -SkiaRenderer::RenderPassBacking::RenderPassBacking( - const gfx::Size& size, - bool generate_mipmap, - const gfx::ColorSpace& color_space) - : size(size), generate_mipmap(generate_mipmap), color_space(color_space) { - recorder = std::make_unique<SkPictureRecorder>(); -} - -SkiaRenderer::RenderPassBacking::~RenderPassBacking() {} - -SkiaRenderer::RenderPassBacking::RenderPassBacking( - SkiaRenderer::RenderPassBacking&& other) - : size(other.size), - generate_mipmap(other.generate_mipmap), - color_space(other.color_space), - format(other.format) { - render_pass_surface = other.render_pass_surface; - other.render_pass_surface = nullptr; - recorder = std::move(other.recorder); -} - -SkiaRenderer::RenderPassBacking& SkiaRenderer::RenderPassBacking::operator=( - SkiaRenderer::RenderPassBacking&& other) { - size = other.size; - generate_mipmap = other.generate_mipmap; - color_space = other.color_space; - format = other.format; - render_pass_surface = other.render_pass_surface; - other.render_pass_surface = nullptr; - recorder = std::move(other.recorder); - return *this; -} - bool SkiaRenderer::IsRenderPassResourceAllocated( const AggregatedRenderPassId& render_pass_id) const { auto it = render_pass_backings_.find(render_pass_id);
diff --git a/components/viz/service/display/skia_renderer.h b/components/viz/service/display/skia_renderer.h index 067ddbd..ad22656 100644 --- a/components/viz/service/display/skia_renderer.h +++ b/components/viz/service/display/skia_renderer.h
@@ -17,18 +17,11 @@ #include "components/viz/service/display/direct_renderer.h" #include "components/viz/service/display/sync_query_collection.h" #include "components/viz/service/viz_service_export.h" -#include "third_party/skia/include/core/SkPictureRecorder.h" #include "ui/latency/latency_info.h" class SkColorFilter; -class SkNWayCanvas; -class SkPictureRecorder; class SkRuntimeEffect; -namespace gpu { -struct Capabilities; -} - namespace viz { class AggregatedRenderPassDrawQuad; class DebugBorderDrawQuad; @@ -44,17 +37,13 @@ // SkColorSpace. class VIZ_SERVICE_EXPORT SkiaRenderer : public DirectRenderer { public: - // Different draw modes that are supported by SkiaRenderer right now. - enum DrawMode { DDL, SKPRECORD }; - // TODO(penghuang): Remove skia_output_surface when DDL is used everywhere. SkiaRenderer(const RendererSettings* settings, const DebugRendererSettings* debug_settings, OutputSurface* output_surface, DisplayResourceProvider* resource_provider, OverlayProcessorInterface* overlay_processor, - SkiaOutputSurface* skia_output_surface, - DrawMode mode); + SkiaOutputSurface* skia_output_surface); ~SkiaRenderer() override; void SwapBuffers(SwapFrameData swap_frame_data) override; @@ -232,12 +221,6 @@ const DrawQuad* CanPassBeDrawnDirectly( const AggregatedRenderPass* pass) override; - // Get corresponding GrContext. Returns nullptr when there is no GrContext. - // TODO(weiliangc): This currently only returns nullptr. If SKPRecord isn't - // going to use this later, it should be removed. - GrDirectContext* GetGrContext(); - bool is_using_ddl() const { return draw_mode_ == DrawMode::DDL; } - // Get a color filter that converts from |src| color space to |dst| color // space using a shader constructed from gfx::ColorTransform. The color // filters are cached in |color_filter_cache_|. Resource offset and @@ -257,33 +240,14 @@ // A map from RenderPass id to the texture used to draw the RenderPass from. struct RenderPassBacking { - sk_sp<SkSurface> render_pass_surface; gfx::Size size; bool generate_mipmap; gfx::ColorSpace color_space; ResourceFormat format; - - // Specific for SkPictureRecorder. - std::unique_ptr<SkPictureRecorder> recorder; - sk_sp<SkPicture> picture; - - RenderPassBacking(GrDirectContext* gr_context, - const gpu::Capabilities& caps, - const gfx::Size& size, - bool generate_mipmap, - const gfx::ColorSpace& color_space); - RenderPassBacking(const gfx::Size& size, - bool generate_mipmap, - const gfx::ColorSpace& color_space); - ~RenderPassBacking(); - RenderPassBacking(RenderPassBacking&&); - RenderPassBacking& operator=(RenderPassBacking&&); }; base::flat_map<AggregatedRenderPassId, RenderPassBacking> render_pass_backings_; - const DrawMode draw_mode_; - // Interface used for drawing. Common among different draw modes. sk_sp<SkSurface> root_surface_; SkCanvas* root_canvas_ = nullptr; @@ -296,11 +260,6 @@ bool is_scissor_enabled_ = false; gfx::Rect scissor_rect_; - // Specific for overdraw. - sk_sp<SkSurface> overdraw_surface_; - std::unique_ptr<SkCanvas> overdraw_canvas_; - std::unique_ptr<SkNWayCanvas> nway_canvas_; - // TODO(crbug.com/920344): Use partial swap for SkDDL. bool use_swap_with_bounds_ = false; gfx::Rect swap_buffer_rect_; @@ -368,14 +327,6 @@ awaiting_release_overlay_locks_; #endif // defined(OS_APPLE) - // Specific for SkPRecord. - std::unique_ptr<SkPictureRecorder> root_recorder_; - sk_sp<SkPicture> root_picture_; - sk_sp<SkPicture>* current_picture_; - SkPictureRecorder* current_recorder_; - ContextProvider* context_provider_ = nullptr; - base::Optional<SyncQueryCollection> sync_queries_; - base::flat_map<gfx::ColorSpace, base::flat_map<gfx::ColorSpace, sk_sp<SkRuntimeEffect>>> color_filter_cache_;
diff --git a/components/viz/service/frame_sinks/frame_sink_manager_impl.cc b/components/viz/service/frame_sinks/frame_sink_manager_impl.cc index 62fee9f..14d8887 100644 --- a/components/viz/service/frame_sinks/frame_sink_manager_impl.cc +++ b/components/viz/service/frame_sinks/frame_sink_manager_impl.cc
@@ -642,10 +642,9 @@ const std::vector<FrameSinkId>& frame_sink_ids, base::TimeDelta interval) { DCHECK_GT(interval, base::TimeDelta()); - if (frame_sinks_throttled) - EndThrottling(); + DCHECK(!frame_sinks_throttled_); - frame_sinks_throttled = true; + frame_sinks_throttled_ = true; for (auto& frame_sink_id : frame_sink_ids) { UpdateThrottlingRecursively(frame_sink_id, interval); } @@ -655,6 +654,6 @@ for (auto& support_map_item : support_map_) { support_map_item.second->ThrottleBeginFrame(base::TimeDelta()); } - frame_sinks_throttled = false; + frame_sinks_throttled_ = false; } } // namespace viz
diff --git a/components/viz/service/frame_sinks/frame_sink_manager_impl.h b/components/viz/service/frame_sinks/frame_sink_manager_impl.h index 9b5c6ae..cde77aa 100644 --- a/components/viz/service/frame_sinks/frame_sink_manager_impl.h +++ b/components/viz/service/frame_sinks/frame_sink_manager_impl.h
@@ -341,7 +341,7 @@ base::flat_map<uint32_t, base::ScopedClosureRunner> cached_back_buffers_; // This tells if any frame sinks are currently throttled. - bool frame_sinks_throttled = false; + bool frame_sinks_throttled_ = false; THREAD_CHECKER(thread_checker_);
diff --git a/content/browser/accessibility/browser_accessibility_manager_mac.mm b/content/browser/accessibility/browser_accessibility_manager_mac.mm index f77433f..8c1c60ee 100644 --- a/content/browser/accessibility/browser_accessibility_manager_mac.mm +++ b/content/browser/accessibility/browser_accessibility_manager_mac.mm
@@ -222,6 +222,13 @@ } break; case ui::AXEventGenerator::Event::LOAD_COMPLETE: + // On MacOS 10.15, firing AXLoadComplete causes focus to move to the + // webpage and read content, despite the "Automatically speak the webpage" + // checkbox in Voiceover utility being unchecked. The checkbox is + // unchecked by default in 10.15 so we don't fire AXLoadComplete events to + // support the default behavior. + if (base::mac::IsOS10_15()) + return; // |NSAccessibilityLoadCompleteNotification| should only be fired on the // top document and when the document is not Chrome's new tab page. if (IsRootTree() && !IsChromeNewTabPage()) {
diff --git a/content/browser/media/media_web_contents_observer.cc b/content/browser/media/media_web_contents_observer.cc index 5c2162d..309ca1f 100644 --- a/content/browser/media/media_web_contents_observer.cc +++ b/content/browser/media/media_web_contents_observer.cc
@@ -147,6 +147,7 @@ MediaWebContentsObserver::~MediaWebContentsObserver() = default; void MediaWebContentsObserver::WebContentsDestroyed() { + use_after_free_checker_.check(); AudioStreamMonitor* audio_stream_monitor = web_contents_impl()->audio_stream_monitor(); @@ -160,6 +161,7 @@ void MediaWebContentsObserver::RenderFrameDeleted( RenderFrameHost* render_frame_host) { + use_after_free_checker_.check(); base::EraseIf( player_info_map_, [render_frame_host](const PlayerInfoMap::value_type& id_and_player_info) { @@ -175,6 +177,7 @@ } // Cancel any pending callbacks for players from this frame. + use_after_free_checker_.check(); per_frame_factory_.erase(render_frame_host); } @@ -506,6 +509,7 @@ void MediaWebContentsObserver::OnExperimentStateChanged(MediaPlayerId id, bool is_starting) { + use_after_free_checker_.check(); id.render_frame_host->Send( new MediaPlayerDelegateMsg_NotifyPowerExperimentState( id.render_frame_host->GetRoutingID(), id.delegate_id, is_starting));
diff --git a/content/browser/media/media_web_contents_observer.h b/content/browser/media/media_web_contents_observer.h index 876927a..6365fe7 100644 --- a/content/browser/media/media_web_contents_observer.h +++ b/content/browser/media/media_web_contents_observer.h
@@ -20,6 +20,7 @@ #include "content/common/content_export.h" #include "content/public/browser/media_player_id.h" #include "content/public/browser/web_contents_observer.h" +#include "media/base/use_after_free_checker.h" #include "mojo/public/cpp/bindings/remote.h" #include "services/device/public/mojom/wake_lock.mojom.h" @@ -197,6 +198,8 @@ std::unique_ptr<base::WeakPtrFactory<MediaWebContentsObserver>>> per_frame_factory_; + media::UseAfterFreeChecker use_after_free_checker_; + base::WeakPtrFactory<MediaWebContentsObserver> weak_ptr_factory_{this}; DISALLOW_COPY_AND_ASSIGN(MediaWebContentsObserver); };
diff --git a/content/browser/site_per_process_browsertest.cc b/content/browser/site_per_process_browsertest.cc index 1db9644..4748084f 100644 --- a/content/browser/site_per_process_browsertest.cc +++ b/content/browser/site_per_process_browsertest.cc
@@ -542,12 +542,13 @@ // (Equivalent to the declared policy "feature *") blink::ParsedFeaturePolicyDeclaration CreateParsedFeaturePolicyDeclaration( blink::mojom::FeaturePolicyFeature feature, - const std::vector<GURL>& origins) { + const std::vector<GURL>& origins, + bool match_all_origins = false) { blink::ParsedFeaturePolicyDeclaration declaration; declaration.feature = feature; - declaration.matches_all_origins = origins.empty(); - declaration.matches_opaque_src = declaration.matches_all_origins; + declaration.matches_all_origins = match_all_origins; + declaration.matches_opaque_src = match_all_origins; for (const auto& origin : origins) declaration.allowed_origins.push_back(url::Origin::Create(origin)); @@ -560,16 +561,23 @@ blink::ParsedFeaturePolicy CreateParsedFeaturePolicy( const std::vector<blink::mojom::FeaturePolicyFeature>& features, - const std::vector<GURL>& origins) { + const std::vector<GURL>& origins, + bool match_all_origins = false) { blink::ParsedFeaturePolicy result; result.reserve(features.size()); for (const auto& feature : features) - result.push_back(CreateParsedFeaturePolicyDeclaration(feature, origins)); + result.push_back(CreateParsedFeaturePolicyDeclaration(feature, origins, + match_all_origins)); return result; } blink::ParsedFeaturePolicy CreateParsedFeaturePolicyMatchesAll( const std::vector<blink::mojom::FeaturePolicyFeature>& features) { + return CreateParsedFeaturePolicy(features, {}, true); +} + +blink::ParsedFeaturePolicy CreateParsedFeaturePolicyMatchesNone( + const std::vector<blink::mojom::FeaturePolicyFeature>& features) { return CreateParsedFeaturePolicy(features, {}); } @@ -8995,7 +9003,7 @@ // exists.) NavigateFrameToURL(root->child_at(1), first_nav_url); EXPECT_EQ( - CreateParsedFeaturePolicyMatchesAll( + CreateParsedFeaturePolicyMatchesNone( {blink::mojom::FeaturePolicyFeature::kGeolocation, blink::mojom::FeaturePolicyFeature::kPayment}), root->child_at(1)->current_replication_state().feature_policy_header); @@ -9004,15 +9012,16 @@ // Ask the deepest iframe to report the enabled state of the geolocation // feature. If its parent frame's policy was replicated correctly to the - // proxy, then this will be enabled. Otherwise, it will be disabled, as - // geolocation is disabled by default in cross-origin frames. - EXPECT_EQ(true, + // proxy, then this will be disabled. Otherwise, it will be enabled by the + // "allow" attribute on the parent frame. + EXPECT_EQ(false, EvalJs(root->child_at(1)->child_at(0), "document.featurePolicy.allowsFeature('geolocation')")); - // TODO(loonybear): Add JS test for parameterized features. - // Now navigate the iframe to a page with no policy, and the same nested - // cross-site iframe. The policy should be cleared in the proxy. + // Now navigate the iframe to a page with no header policy, and the same + // nested cross-site iframe. The header policy should be cleared in the proxy. + // In this case, the frame policy from the parent will allow geolocation to be + // delegated. NavigateFrameToURL(root->child_at(1), second_nav_url); EXPECT_TRUE(root->child_at(1) ->current_replication_state() @@ -9021,8 +9030,8 @@ // Ask the deepest iframe to report the enabled state of the geolocation // feature. If its parent frame's policy was replicated correctly to the - // proxy, then this will now be disabled. - EXPECT_EQ(false, + // proxy, then this will now be allowed. + EXPECT_EQ(true, EvalJs(root->child_at(1)->child_at(0), "document.featurePolicy.allowsFeature('geolocation')")); }
diff --git a/content/browser/web_package/signed_exchange_handler.cc b/content/browser/web_package/signed_exchange_handler.cc index debde4c..66ab29d 100644 --- a/content/browser/web_package/signed_exchange_handler.cc +++ b/content/browser/web_package/signed_exchange_handler.cc
@@ -80,9 +80,8 @@ return version == SignedExchangeVersion::kB3; } -using VerifyCallback = base::OnceCallback<void(int32_t, - const net::CertVerifyResult&, - const net::ct::CTVerifyResult&)>; +using VerifyCallback = + base::OnceCallback<void(int32_t, const net::CertVerifyResult&)>; void VerifyCert(const scoped_refptr<net::X509Certificate>& certificate, const GURL& url, @@ -91,8 +90,7 @@ int frame_tree_node_id, VerifyCallback callback) { VerifyCallback wrapped_callback = mojo::WrapCallbackWithDefaultInvokeIfNotRun( - std::move(callback), net::ERR_FAILED, net::CertVerifyResult(), - net::ct::CTVerifyResult()); + std::move(callback), net::ERR_FAILED, net::CertVerifyResult()); network::mojom::NetworkContext* network_context = g_network_context_for_testing; @@ -597,14 +595,13 @@ void SignedExchangeHandler::OnVerifyCert( int32_t error_code, - const net::CertVerifyResult& cv_result, - const net::ct::CTVerifyResult& ct_result) { + const net::CertVerifyResult& cv_result) { TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("loading"), "SignedExchangeHandler::OnCertVerifyComplete"); // net::Error codes are negative, so we put - in front of it. base::UmaHistogramSparse(kHistogramCertVerificationResult, -error_code); UMA_HISTOGRAM_ENUMERATION(kHistogramCTVerificationResult, - ct_result.policy_compliance, + cv_result.policy_compliance, net::ct::CTPolicyCompliance::CT_POLICY_COUNT); if (error_code != net::OK) { @@ -614,7 +611,7 @@ error_message = base::StringPrintf( "CT verification failed. result: %s, policy compliance: %d", net::ErrorToShortString(error_code).c_str(), - ct_result.policy_compliance); + cv_result.policy_compliance); result = SignedExchangeLoadResult::kCTVerificationError; } else { error_message = @@ -690,7 +687,8 @@ ssl_info.public_key_hashes = cv_result.public_key_hashes; ssl_info.ocsp_result = cv_result.ocsp_result; ssl_info.is_fatal_cert_error = net::IsCertStatusError(ssl_info.cert_status); - ssl_info.UpdateCertificateTransparencyInfo(ct_result); + ssl_info.signed_certificate_timestamps = cv_result.scts; + ssl_info.ct_policy_compliance = cv_result.policy_compliance; if (devtools_proxy_) { devtools_proxy_->OnSignedExchangeReceived(
diff --git a/content/browser/web_package/signed_exchange_handler.h b/content/browser/web_package/signed_exchange_handler.h index d0fd6571..89d9340 100644 --- a/content/browser/web_package/signed_exchange_handler.h +++ b/content/browser/web_package/signed_exchange_handler.h
@@ -143,9 +143,7 @@ const net::X509Certificate* verified_cert); bool CheckOCSPStatus(const net::OCSPVerifyResult& ocsp_result); - void OnVerifyCert(int32_t error_code, - const net::CertVerifyResult& cv_result, - const net::ct::CTVerifyResult& ct_result); + void OnVerifyCert(int32_t error_code, const net::CertVerifyResult& cv_result); std::unique_ptr<net::SourceStream> CreateResponseBodyStream(); const bool is_secure_transport_;
diff --git a/content/browser/web_package/signed_exchange_handler_unittest.cc b/content/browser/web_package/signed_exchange_handler_unittest.cc index 4082c0c..36b72d9a 100644 --- a/content/browser/web_package/signed_exchange_handler_unittest.cc +++ b/content/browser/web_package/signed_exchange_handler_unittest.cc
@@ -931,7 +931,6 @@ net::CERT_STATUS_IS_EV); EXPECT_FALSE(resource_response().ssl_info->cert_status & net::CERT_STATUS_CT_COMPLIANCE_FAILED); - EXPECT_TRUE(resource_response().ssl_info->ct_policy_compliance_required); EXPECT_EQ(net::ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS, resource_response().ssl_info->ct_policy_compliance); ExpectHistogramValues( @@ -973,7 +972,6 @@ net::CERT_STATUS_IS_EV); EXPECT_TRUE(resource_response().ssl_info->cert_status & net::CERT_STATUS_CT_COMPLIANCE_FAILED); - EXPECT_FALSE(resource_response().ssl_info->ct_policy_compliance_required); EXPECT_EQ(net::ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS, resource_response().ssl_info->ct_policy_compliance); ExpectHistogramValues(
diff --git a/content/browser/webauth/authenticator_impl_unittest.cc b/content/browser/webauth/authenticator_impl_unittest.cc index a6a6f83..29d19f0a 100644 --- a/content/browser/webauth/authenticator_impl_unittest.cc +++ b/content/browser/webauth/authenticator_impl_unittest.cc
@@ -3855,6 +3855,18 @@ *test_client_.failure_reason); } +TEST_F(PINAuthenticatorImplTest, MakeCredentialWrongPINFirst) { + virtual_device_factory_->mutable_state()->pin = kTestPIN; + virtual_device_factory_->mutable_state()->pin_retries = + device::kMaxPinRetries; + + // Test that we can successfully get a PIN token after a failure. + test_client_.expected = {{8, "wrong"}, {7, kTestPIN}}; + EXPECT_EQ(AuthenticatorMakeCredential().status, AuthenticatorStatus::SUCCESS); + EXPECT_EQ(static_cast<int>(device::kMaxPinRetries), + virtual_device_factory_->mutable_state()->pin_retries); +} + TEST_F(PINAuthenticatorImplTest, GetAssertion) { typedef int Expectations[3][3]; // kExpectedWithUISupport enumerates the expected behaviour when the embedder
diff --git a/content/browser/xr/service/xr_runtime_manager_impl.cc b/content/browser/xr/service/xr_runtime_manager_impl.cc index 34dd88be..9182c46f 100644 --- a/content/browser/xr/service/xr_runtime_manager_impl.cc +++ b/content/browser/xr/service/xr_runtime_manager_impl.cc
@@ -311,6 +311,9 @@ void XRRuntimeManagerImpl::MakeXrCompatible() { auto* runtime = GetImmersiveVrRuntime(); + if (!runtime) + runtime = GetImmersiveArRuntime(); + if (!runtime) { for (VRServiceImpl* service : services_) service->OnMakeXrCompatibleComplete(
diff --git a/content/child/runtime_features.cc b/content/child/runtime_features.cc index 5857415..a8d9a08 100644 --- a/content/child/runtime_features.cc +++ b/content/child/runtime_features.cc
@@ -377,6 +377,7 @@ {"UserAgentClientHint", features::kUserAgentClientHint}, {"WebAppManifestDisplayOverride", features::kWebAppManifestDisplayOverride}, + {"WebXRMultiGpu", blink::features::kWebXrMultiGpu}, }; for (const auto& mapping : runtimeFeatureNameToChromiumFeatureMapping) { SetRuntimeFeatureFromChromiumFeature(
diff --git a/content/public/common/frame_navigate_params.h b/content/public/common/frame_navigate_params.h index ec72335..1c3778c 100644 --- a/content/public/common/frame_navigate_params.h +++ b/content/public/common/frame_navigate_params.h
@@ -74,9 +74,6 @@ // Contents MIME type of main frame. std::string contents_mime_type; - - // Remote address of the socket which fetched this resource. - net::HostPortPair socket_address; }; } // namespace content
diff --git a/content/renderer/pepper/video_decoder_shim.cc b/content/renderer/pepper/video_decoder_shim.cc index 7b43c76b..3c3126d 100644 --- a/content/renderer/pepper/video_decoder_shim.cc +++ b/content/renderer/pepper/video_decoder_shim.cc
@@ -120,7 +120,7 @@ private: void OnInitDone(media::Status status); void DoDecode(); - void OnDecodeComplete(media::DecodeStatus status); + void OnDecodeComplete(media::Status status); void OnOutputComplete(scoped_refptr<media::VideoFrame> frame); void OnResetComplete(); @@ -252,18 +252,17 @@ pending_decodes_.pop(); } -void VideoDecoderShim::DecoderImpl::OnDecodeComplete( - media::DecodeStatus status) { +void VideoDecoderShim::DecoderImpl::OnDecodeComplete(media::Status status) { DCHECK(awaiting_decoder_); awaiting_decoder_ = false; int32_t result; - switch (status) { - case media::DecodeStatus::OK: - case media::DecodeStatus::ABORTED: + switch (status.code()) { + case media::StatusCode::kOk: + case media::StatusCode::kAborted: result = PP_OK; break; - case media::DecodeStatus::DECODE_ERROR: + default: result = PP_ERROR_RESOURCE_FAILED; break; }
diff --git a/content/test/data/feature-policy3.html b/content/test/data/feature-policy3.html index e73e4d0..b0d44ed 100644 --- a/content/test/data/feature-policy3.html +++ b/content/test/data/feature-policy3.html
@@ -1,6 +1,9 @@ <html> <head></head> <body>This page has a different feature policy header. -<iframe src="/cross-site/b.com/title2.html"></iframe> +<p> +Note that we can't use use allow="geolocation" here, as this will redirect to a +different origin, and we don't know the port which will be used. +<iframe src="/cross-site/b.com/title2.html" allow="geolocation *"></iframe> </body> </html>
diff --git a/content/test/data/feature-policy3.html.mock-http-headers b/content/test/data/feature-policy3.html.mock-http-headers index 4c50dd1c..091a181 100644 --- a/content/test/data/feature-policy3.html.mock-http-headers +++ b/content/test/data/feature-policy3.html.mock-http-headers
@@ -1,2 +1,2 @@ HTTP/1.1 200 OK -Feature-Policy: geolocation *; payment *; +Feature-Policy: geolocation 'none'; payment 'none';
diff --git a/content/test/data/feature-policy4.html b/content/test/data/feature-policy4.html index e73e4d0..b0d44ed 100644 --- a/content/test/data/feature-policy4.html +++ b/content/test/data/feature-policy4.html
@@ -1,6 +1,9 @@ <html> <head></head> <body>This page has a different feature policy header. -<iframe src="/cross-site/b.com/title2.html"></iframe> +<p> +Note that we can't use use allow="geolocation" here, as this will redirect to a +different origin, and we don't know the port which will be used. +<iframe src="/cross-site/b.com/title2.html" allow="geolocation *"></iframe> </body> </html>
diff --git a/content/test/test_render_frame_host.cc b/content/test/test_render_frame_host.cc index 53e9ba7..4cc055a 100644 --- a/content/test/test_render_frame_host.cc +++ b/content/test/test_render_frame_host.cc
@@ -207,8 +207,6 @@ params.contents_mime_type = "text/html"; params.method = "GET"; params.http_status_code = 200; - params.socket_address.set_host("2001:db8::1"); - params.socket_address.set_port(80); params.history_list_was_cleared = simulate_history_list_was_cleared_; params.original_request_url = url; @@ -593,8 +591,6 @@ params->contents_mime_type = "text/html"; params->method = "GET"; params->http_status_code = response_code; - params->socket_address.set_host("2001:db8::1"); - params->socket_address.set_port(80); params->history_list_was_cleared = simulate_history_list_was_cleared_; params->original_request_url = url;
diff --git a/content/test/test_web_contents.cc b/content/test/test_web_contents.cc index 5309898..f05d9ac6 100644 --- a/content/test/test_web_contents.cc +++ b/content/test/test_web_contents.cc
@@ -167,7 +167,6 @@ params.redirects = std::vector<GURL>(); params.should_update_history = true; params.contents_mime_type = std::string("text/html"); - params.socket_address = net::HostPortPair(); params.intended_as_new_entry = did_create_new_entry; params.did_create_new_entry = did_create_new_entry; params.should_replace_current_entry = false;
diff --git a/device/fido/virtual_ctap2_device.cc b/device/fido/virtual_ctap2_device.cc index ec4c0c8..ca36525 100644 --- a/device/fido/virtual_ctap2_device.cc +++ b/device/fido/virtual_ctap2_device.cc
@@ -449,12 +449,16 @@ VirtualCtap2Device::Config::~Config() = default; VirtualCtap2Device::VirtualCtap2Device() { + RegenerateKeyAgreementKey(); Init({ProtocolVersion::kCtap2}); } VirtualCtap2Device::VirtualCtap2Device(scoped_refptr<State> state, const Config& config) : VirtualFidoDevice(std::move(state)), config_(config) { + RegenerateKeyAgreementKey(); + + Init({ProtocolVersion::kCtap2}); std::vector<ProtocolVersion> versions = {ProtocolVersion::kCtap2}; if (config.u2f_support) { versions.emplace_back(ProtocolVersion::kU2f); @@ -1528,19 +1532,16 @@ break; case static_cast<int>(device::pin::Subcommand::kGetKeyAgreement): { - bssl::UniquePtr<EC_KEY> key( - EC_KEY_new_by_curve_name(NID_X9_62_prime256v1)); - CHECK(EC_KEY_generate_key(key.get())); std::array<uint8_t, kP256X962Length> x962; CHECK_EQ(x962.size(), - EC_POINT_point2oct(EC_KEY_get0_group(key.get()), - EC_KEY_get0_public_key(key.get()), - POINT_CONVERSION_UNCOMPRESSED, x962.data(), - x962.size(), nullptr /* BN_CTX */)); + EC_POINT_point2oct( + EC_KEY_get0_group(mutable_state()->ecdh_key.get()), + EC_KEY_get0_public_key(mutable_state()->ecdh_key.get()), + POINT_CONVERSION_UNCOMPRESSED, x962.data(), x962.size(), + nullptr /* BN_CTX */)); response_map.emplace(static_cast<int>(pin::ResponseKey::kKeyAgreement), pin::EncodeCOSEPublicKey(x962)); - mutable_state()->ecdh_key = std::move(key); break; } @@ -1602,17 +1603,13 @@ } uint8_t shared_key[SHA256_DIGEST_LENGTH]; - if (!mutable_state()->ecdh_key) { - // kGetKeyAgreement should have been called first. - NOTREACHED(); - return CtapDeviceResponseCode::kCtap2ErrPinTokenExpired; - } pin::CalculateSharedKey(mutable_state()->ecdh_key.get(), peer_key->get(), shared_key); CtapDeviceResponseCode err = ConfirmPresentedPIN(mutable_state(), shared_key, *encrypted_pin_hash); if (err != CtapDeviceResponseCode::kSuccess) { + RegenerateKeyAgreementKey(); return err; } @@ -1680,6 +1677,7 @@ CtapDeviceResponseCode err = ConfirmPresentedPIN(mutable_state(), shared_key, *encrypted_pin_hash); if (err != CtapDeviceResponseCode::kSuccess) { + RegenerateKeyAgreementKey(); return err; } @@ -2381,6 +2379,12 @@ } } +void VirtualCtap2Device::RegenerateKeyAgreementKey() { + bssl::UniquePtr<EC_KEY> key(EC_KEY_new_by_curve_name(NID_X9_62_prime256v1)); + CHECK(EC_KEY_generate_key(key.get())); + mutable_state()->ecdh_key = std::move(key); +} + void VirtualCtap2Device::GetNextRP(cbor::Value::MapValue* response_map) { DCHECK(!mutable_state()->pending_rps.empty()); response_map->emplace(
diff --git a/device/fido/virtual_ctap2_device.h b/device/fido/virtual_ctap2_device.h index 93bd1c4b..6753add 100644 --- a/device/fido/virtual_ctap2_device.h +++ b/device/fido/virtual_ctap2_device.h
@@ -235,6 +235,7 @@ void InitPendingRPs(); void GetNextRP(cbor::Value::MapValue* response_map); void InitPendingRegistrations(base::span<const uint8_t> rp_id_hash); + void RegenerateKeyAgreementKey(); AttestedCredentialData ConstructAttestedCredentialData( base::span<const uint8_t> key_handle,
diff --git a/device/fido/virtual_fido_device.cc b/device/fido/virtual_fido_device.cc index d1182762e..97ddd61 100644 --- a/device/fido/virtual_fido_device.cc +++ b/device/fido/virtual_fido_device.cc
@@ -431,7 +431,6 @@ VirtualFidoDevice::VirtualFidoDevice() = default; - VirtualFidoDevice::VirtualFidoDevice(scoped_refptr<State> state) : state_(std::move(state)) {}
diff --git a/docs/security/sheriff.md b/docs/security/sheriff.md index 522f802f..ed005d88 100644 --- a/docs/security/sheriff.md +++ b/docs/security/sheriff.md
@@ -86,6 +86,12 @@ * When triaging an email to be handled off of the list, make sure to bcc: the list that it arrived on, so that other people including future marshals can see that it has been handled. + * Some of these emails are requests for inclusion of third party code. + By the time you hand over to the next Marshal, please + ensure these are either completed or have been acknowledged by some other + owner. If not, you may need to do them yourself. Please see + [How to do Chrome Third-Party Security Reviews](https://goto.google.com/how-to-do-chrome-third-party-security-reviews) + for hints. * Change bugs status to **Fixed** for those that the developer forgets to close. Make sure to read bug comments where developer might point out that it needs more CLs, et c. Wait 24 hours before closing ClusterFuzz bugs, to give
diff --git a/fuchsia/engine/test/test_data.cc b/fuchsia/engine/test/test_data.cc index 1ca9e32..f37640f 100644 --- a/fuchsia/engine/test/test_data.cc +++ b/fuchsia/engine/test/test_data.cc
@@ -8,6 +8,6 @@ namespace cr_fuchsia { -const char kTestServerRoot[] = FILE_PATH_LITERAL("fuchsia/engine/test/data"); +const char kTestServerRoot[] = "fuchsia/engine/test/data"; } // namespace cr_fuchsia \ No newline at end of file
diff --git a/fuchsia/engine/web_engine_debug_integration_test.cc b/fuchsia/engine/web_engine_debug_integration_test.cc index 185ac67..cda82e7 100644 --- a/fuchsia/engine/web_engine_debug_integration_test.cc +++ b/fuchsia/engine/web_engine_debug_integration_test.cc
@@ -25,7 +25,7 @@ namespace { -const char kTestServerRoot[] = FILE_PATH_LITERAL("fuchsia/engine/test/data"); +const char kTestServerRoot[] = "fuchsia/engine/test/data"; } // namespace
diff --git a/fuchsia/engine/web_engine_main_delegate.cc b/fuchsia/engine/web_engine_main_delegate.cc index 6600fb0..f3eccc76 100644 --- a/fuchsia/engine/web_engine_main_delegate.cc +++ b/fuchsia/engine/web_engine_main_delegate.cc
@@ -28,7 +28,7 @@ base::FilePath pak_file; bool result = base::PathService::Get(base::DIR_ASSETS, &pak_file); DCHECK(result); - pak_file = pak_file.Append(FILE_PATH_LITERAL("web_engine.pak")); + pak_file = pak_file.Append("web_engine.pak"); ui::ResourceBundle::InitSharedInstanceWithPakPath(pak_file); }
diff --git a/fuchsia/http/http_service_unittest.cc b/fuchsia/http/http_service_unittest.cc index a7e5189a..020538a 100644 --- a/fuchsia/http/http_service_unittest.cc +++ b/fuchsia/http/http_service_unittest.cc
@@ -19,8 +19,7 @@ namespace { -const base::FilePath::CharType kTestFilePath[] = - FILE_PATH_LITERAL("fuchsia/http/testdata"); +const base::FilePath::CharType kTestFilePath[] = "fuchsia/http/testdata"; // Capacity, in bytes, for buffers used to read data off the URLResponse. const size_t kBufferCapacity = 1024; @@ -33,8 +32,7 @@ : task_environment_(base::test::TaskEnvironment::MainThreadType::IO), binding_(&http_service_server_) { // Initialize the test server. - test_server_.AddDefaultHandlers( - base::FilePath(FILE_PATH_LITERAL(kTestFilePath))); + test_server_.AddDefaultHandlers(base::FilePath(kTestFilePath)); net::test_server::RegisterDefaultHandlers(&test_server_); }
diff --git a/fuchsia/runners/cast/cast_runner_integration_test.cc b/fuchsia/runners/cast/cast_runner_integration_test.cc index a934c0b7c..73ebd91 100644 --- a/fuchsia/runners/cast/cast_runner_integration_test.cc +++ b/fuchsia/runners/cast/cast_runner_integration_test.cc
@@ -56,8 +56,7 @@ constexpr char kBlankAppUrl[] = "/defaultresponse"; constexpr char kEchoHeaderPath[] = "/echoheader?Test"; -constexpr char kTestServerRoot[] = - FILE_PATH_LITERAL("fuchsia/runners/cast/testdata"); +constexpr char kTestServerRoot[] = "fuchsia/runners/cast/testdata"; constexpr char kDummyAgentUrl[] = "fuchsia-pkg://fuchsia.com/dummy_agent#meta/dummy_agent.cmx";
diff --git a/gpu/config/gpu_test_config.cc b/gpu/config/gpu_test_config.cc index e07e734..49219e45 100644 --- a/gpu/config/gpu_test_config.cc +++ b/gpu/config/gpu_test_config.cc
@@ -239,8 +239,12 @@ } if (gpu_vendor().size() != 1 || gpu_vendor()[0] == 0) return false; - if (gpu_device_id() == 0) - return false; + if (!(os() & gpu::GPUTestConfig::kOsMac)) { + // ARM-based Mac GPUs do not have valid PCI device IDs. + // https://crbug.com/1110421 + if (gpu_device_id() == 0) + return false; + } switch (build_type()) { case kBuildTypeRelease: case kBuildTypeDebug:
diff --git a/gpu/config/gpu_test_config_unittest.cc b/gpu/config/gpu_test_config_unittest.cc index bafd5ec..c29abf4c 100644 --- a/gpu/config/gpu_test_config_unittest.cc +++ b/gpu/config/gpu_test_config_unittest.cc
@@ -66,8 +66,13 @@ config.AddGPUVendor(0x10de); EXPECT_TRUE(config.IsValid()); + // Device ID of 0 is valid only on macOS. config.set_gpu_device_id(0); + config.set_os(GPUTestConfig::kOsMacBigSur); + EXPECT_TRUE(config.IsValid()); + config.set_os(GPUTestConfig::kOsWin7); EXPECT_FALSE(config.IsValid()); + config.set_gpu_device_id(0x0640); EXPECT_TRUE(config.IsValid());
diff --git a/gpu/vulkan/BUILD.gn b/gpu/vulkan/BUILD.gn index 921229d3..28ee623 100644 --- a/gpu/vulkan/BUILD.gn +++ b/gpu/vulkan/BUILD.gn
@@ -9,6 +9,13 @@ import("//ui/ozone/ozone.gni") import("features.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + # Generate a buildflag header for compile-time checking of Vulkan support. buildflag_header("buildflags") { header = "buildflags.h" @@ -26,8 +33,8 @@ source_set("vulkan_function_pointers") { visibility = [ - ":vulkan", ":vma_wrapper", + ":vulkan", ] sources = [
diff --git a/gpu/vulkan/demo/vulkan_demo.cc b/gpu/vulkan/demo/vulkan_demo.cc index b9b089b..c2fe838 100644 --- a/gpu/vulkan/demo/vulkan_demo.cc +++ b/gpu/vulkan/demo/vulkan_demo.cc
@@ -122,7 +122,7 @@ vk_image_info.fFormat = VK_FORMAT_B8G8R8A8_UNORM; vk_image_info.fLevelCount = 1; const auto& size = vulkan_surface_->image_size(); - GrBackendRenderTarget render_target(size.width(), size.height(), 0, 0, + GrBackendRenderTarget render_target(size.width(), size.height(), 0, vk_image_info); sk_surface = SkSurface::MakeFromBackendRenderTarget( vulkan_context_provider_->GetGrContext(), render_target,
diff --git a/headless/app/headless_shell.cc b/headless/app/headless_shell.cc index 2e2a397..17e23c3 100644 --- a/headless/app/headless_shell.cc +++ b/headless/app/headless_shell.cc
@@ -715,7 +715,7 @@ address = command_line.GetSwitchValueASCII(switches::kRemoteDebuggingAddress); net::IPAddress parsed_address; - if (!net::ParseURLHostnameToAddress(address, &parsed_address)) { + if (!parsed_address.AssignFromIPLiteral(address)) { LOG(ERROR) << "Invalid devtools server address"; return EXIT_FAILURE; }
diff --git a/ios/chrome/app/strings/ios_strings.grd b/ios/chrome/app/strings/ios_strings.grd index 3bbb124..eb370ba 100644 --- a/ios/chrome/app/strings/ios_strings.grd +++ b/ios/chrome/app/strings/ios_strings.grd
@@ -1015,6 +1015,12 @@ <message name="IDS_IOS_KEYBOARD_REOPEN_CLOSED_TAB" desc="Title of the keyboard shortcut to reopen a recently closed tab. [Length: 20 em] [iOS only]"> Reopen Closed Tab </message> + <message name="IDS_IOS_KEYBOARD_NEXT_TAB" desc="Title of the keyboard shortcut to switch to the next tab in the tab strip. [Length: 20 em] [iOS only]"> + Next Tab + </message> + <message name="IDS_IOS_KEYBOARD_PREVIOUS_TAB" desc="Title of the keyboard shortcut to switch to the previous tab in the tab strip. [Length: 20 em] [iOS only]"> + Previous Tab + </message> <message name="IDS_IOS_LONG_PRESS_TOOLBAR_IPH_PROMOTION_TEXT" desc="Text for the LongPress Toolbar Tip in-product help promotion, explaining that the user can long press on the toolbar's button to display more options. [iOS only]"> Touch & hold for more tab options </message>
diff --git a/ios/chrome/app/strings/ios_strings_grd/IDS_IOS_KEYBOARD_NEXT_TAB.png.sha1 b/ios/chrome/app/strings/ios_strings_grd/IDS_IOS_KEYBOARD_NEXT_TAB.png.sha1 new file mode 100644 index 0000000..2dbe1e91 --- /dev/null +++ b/ios/chrome/app/strings/ios_strings_grd/IDS_IOS_KEYBOARD_NEXT_TAB.png.sha1
@@ -0,0 +1 @@ +ce0e6afda38f6e05303f521b39b9cc4128133723 \ No newline at end of file
diff --git a/ios/chrome/app/strings/ios_strings_grd/IDS_IOS_KEYBOARD_PREVIOUS_TAB.png.sha1 b/ios/chrome/app/strings/ios_strings_grd/IDS_IOS_KEYBOARD_PREVIOUS_TAB.png.sha1 new file mode 100644 index 0000000..2dbe1e91 --- /dev/null +++ b/ios/chrome/app/strings/ios_strings_grd/IDS_IOS_KEYBOARD_PREVIOUS_TAB.png.sha1
@@ -0,0 +1 @@ +ce0e6afda38f6e05303f521b39b9cc4128133723 \ No newline at end of file
diff --git a/ios/chrome/browser/flags/about_flags.mm b/ios/chrome/browser/flags/about_flags.mm index 602f080f..3ba69e3 100644 --- a/ios/chrome/browser/flags/about_flags.mm +++ b/ios/chrome/browser/flags/about_flags.mm
@@ -544,12 +544,6 @@ flag_descriptions::kSafeBrowsingRealTimeLookupDescription, flags_ui::kOsIos, FEATURE_VALUE_TYPE(safe_browsing::kRealTimeUrlLookupEnabled)}, - {"autofill-enable-surfacing-server-card-nickname", - flag_descriptions::kAutofillEnableSurfacingServerCardNicknameName, - flag_descriptions::kAutofillEnableSurfacingServerCardNicknameDescription, - flags_ui::kOsIos, - FEATURE_VALUE_TYPE( - autofill::features::kAutofillEnableSurfacingServerCardNickname)}, {"managed-bookmarks-ios", flag_descriptions::kManagedBookmarksIOSName, flag_descriptions::kManagedBookmarksIOSDescription, flags_ui::kOsIos, FEATURE_VALUE_TYPE(kManagedBookmarksIOS)},
diff --git a/ios/chrome/browser/flags/ios_chrome_flag_descriptions.cc b/ios/chrome/browser/flags/ios_chrome_flag_descriptions.cc index 3616ae7f..93ac56e 100644 --- a/ios/chrome/browser/flags/ios_chrome_flag_descriptions.cc +++ b/ios/chrome/browser/flags/ios_chrome_flag_descriptions.cc
@@ -58,12 +58,6 @@ "When enabled, offer data will be retrieved during downstream and shown in " "the dropdown list."; -const char kAutofillEnableSurfacingServerCardNicknameName[] = - "Enable surfacing masked server card nicknames"; -const char kAutofillEnableSurfacingServerCardNicknameDescription[] = - "When enabled, if Google Payments cards were given nicknames in a Google " - "Pay app, Autofill will surface these nicknames in suggestions."; - const char kAutofillEnforceMinRequiredFieldsForHeuristicsName[] = "Autofill Enforce Min Required Fields For Heuristics"; const char kAutofillEnforceMinRequiredFieldsForHeuristicsDescription[] =
diff --git a/ios/chrome/browser/flags/ios_chrome_flag_descriptions.h b/ios/chrome/browser/flags/ios_chrome_flag_descriptions.h index 5248564..4d209cf 100644 --- a/ios/chrome/browser/flags/ios_chrome_flag_descriptions.h +++ b/ios/chrome/browser/flags/ios_chrome_flag_descriptions.h
@@ -45,10 +45,6 @@ extern const char kAutofillEnableOffersInDownstreamName[]; extern const char kAutofillEnableOffersInDownstreamDescription[]; -// Title and description for the flag to control surfacing server card nickname. -extern const char kAutofillEnableSurfacingServerCardNicknameName[]; -extern const char kAutofillEnableSurfacingServerCardNicknameDescription[]; - // Enforcing restrictions to enable/disable autofill small form support. extern const char kAutofillEnforceMinRequiredFieldsForHeuristicsName[]; extern const char kAutofillEnforceMinRequiredFieldsForHeuristicsDescription[];
diff --git a/ios/chrome/browser/ui/browser_view/key_commands_provider.mm b/ios/chrome/browser/ui/browser_view/key_commands_provider.mm index bee1589..d9bb1b60 100644 --- a/ios/chrome/browser/ui/browser_view/key_commands_provider.mm +++ b/ios/chrome/browser/ui/browser_view/key_commands_provider.mm
@@ -66,6 +66,25 @@ }; } + // Blocks for next/previous tab. + void (^focusTabLeft)(); + void (^focusTabRight)(); + if (useRTLLayout) { + focusTabLeft = ^{ + [weakConsumer focusNextTab]; + }; + focusTabRight = ^{ + [weakConsumer focusPreviousTab]; + }; + } else { + focusTabLeft = ^{ + [weakConsumer focusPreviousTab]; + }; + focusTabRight = ^{ + [weakConsumer focusNextTab]; + }; + } + // New tab blocks. void (^newTab)() = ^{ OpenNewTabCommand* newTabCommand = [OpenNewTabCommand command]; @@ -169,6 +188,44 @@ [weakDispatcher closeCurrentTab]; } }], + ]]; + + // Deal with the multiple next/previous tab commands we have, only one pair + // of which appears in the HUD. Take RTL into account for the direction. + const int tabLeftDescriptionID = useRTLLayout + ? IDS_IOS_KEYBOARD_NEXT_TAB + : IDS_IOS_KEYBOARD_PREVIOUS_TAB; + const int tabRightDescriptionID = useRTLLayout + ? IDS_IOS_KEYBOARD_PREVIOUS_TAB + : IDS_IOS_KEYBOARD_NEXT_TAB; + NSString* tabLeftTitle = l10n_util::GetNSStringWithFixup( + tabLeftDescriptionID); + NSString* tabRightTitle = l10n_util::GetNSStringWithFixup( + tabRightDescriptionID); + [keyCommands addObjectsFromArray:@[ + [UIKeyCommand + cr_keyCommandWithInput:UIKeyInputLeftArrow + modifierFlags:UIKeyModifierCommand | UIKeyModifierAlternate + title:tabLeftTitle + action:focusTabLeft], + [UIKeyCommand + cr_keyCommandWithInput:UIKeyInputRightArrow + modifierFlags:UIKeyModifierCommand | UIKeyModifierAlternate + title:tabRightTitle + action:focusTabRight], + [UIKeyCommand + cr_keyCommandWithInput:@"{" + modifierFlags:UIKeyModifierCommand + title:nil + action:focusTabLeft], + [UIKeyCommand + cr_keyCommandWithInput:@"}" + modifierFlags:UIKeyModifierCommand + title:nil + action:focusTabRight], + ]]; + + [keyCommands addObjectsFromArray:@[ [UIKeyCommand cr_keyCommandWithInput:@"d" modifierFlags:UIKeyModifierCommand @@ -340,20 +397,6 @@ focusTab([weakConsumer tabsCount] - 1); }], [UIKeyCommand - cr_keyCommandWithInput:UIKeyInputLeftArrow - modifierFlags:UIKeyModifierCommand | UIKeyModifierAlternate - title:nil - action:^{ - [weakConsumer focusPreviousTab]; - }], - [UIKeyCommand - cr_keyCommandWithInput:UIKeyInputRightArrow - modifierFlags:UIKeyModifierCommand | UIKeyModifierAlternate - title:nil - action:^{ - [weakConsumer focusNextTab]; - }], - [UIKeyCommand cr_keyCommandWithInput:@"\t" modifierFlags:UIKeyModifierControl | UIKeyModifierShift title:nil
diff --git a/ios/chrome/browser/ui/omnibox/omnibox_util.mm b/ios/chrome/browser/ui/omnibox/omnibox_util.mm index ab9e03fc..49537571c 100644 --- a/ios/chrome/browser/ui/omnibox/omnibox_util.mm +++ b/ios/chrome/browser/ui/omnibox/omnibox_util.mm
@@ -59,6 +59,7 @@ return CALCULATOR; case AutocompleteMatchType::EXTENSION_APP_DEPRECATED: case AutocompleteMatchType::TILE_SUGGESTION: + case AutocompleteMatchType::TILE_NAVSUGGEST: case AutocompleteMatchType::NUM_TYPES: NOTREACHED(); return DEFAULT_FAVICON;
diff --git a/ios/chrome/browser/ui/omnibox/popup/omnibox_icon_formatter.mm b/ios/chrome/browser/ui/omnibox/popup/omnibox_icon_formatter.mm index 46f59ec6..0dd9889 100644 --- a/ios/chrome/browser/ui/omnibox/popup/omnibox_icon_formatter.mm +++ b/ios/chrome/browser/ui/omnibox/popup/omnibox_icon_formatter.mm
@@ -82,6 +82,7 @@ return CALCULATOR; case AutocompleteMatchType::EXTENSION_APP_DEPRECATED: case AutocompleteMatchType::TILE_SUGGESTION: + case AutocompleteMatchType::TILE_NAVSUGGEST: case AutocompleteMatchType::NUM_TYPES: NOTREACHED(); return DEFAULT_FAVICON;
diff --git a/ios/web_view/internal/translate/cwv_translation_language.mm b/ios/web_view/internal/translate/cwv_translation_language.mm index 13062c70..bff46f90 100644 --- a/ios/web_view/internal/translate/cwv_translation_language.mm +++ b/ios/web_view/internal/translate/cwv_translation_language.mm
@@ -29,6 +29,22 @@ return self; } +- (BOOL)isEqual:(id)object { + if (self == object) { + return YES; + } + if (![object isKindOfClass:[CWVTranslationLanguage class]]) { + return NO; + } + + CWVTranslationLanguage* otherLanguage = (CWVTranslationLanguage*)object; + return [_languageCode isEqualToString:otherLanguage.languageCode]; +} + +- (NSUInteger)hash { + return [_languageCode hash]; +} + - (NSString*)description { return [NSString stringWithFormat:@"%@ name:%@(%@) code:%@", [super description],
diff --git a/ios/web_view/internal/translate/cwv_translation_language_unittest.mm b/ios/web_view/internal/translate/cwv_translation_language_unittest.mm index 29247050..d2dbb34 100644 --- a/ios/web_view/internal/translate/cwv_translation_language_unittest.mm +++ b/ios/web_view/internal/translate/cwv_translation_language_unittest.mm
@@ -34,4 +34,21 @@ EXPECT_NSEQ(native_name, language.nativeName); } +TEST_F(CWVTranslationLanguageTest, Equality) { + // Two languages with the same langauge code but different localized/native + // names. + CWVTranslationLanguage* language_a = [[CWVTranslationLanguage alloc] + initWithLanguageCode:"ja" + localizedName:base::SysNSStringToUTF16(@"JapaneseA") + nativeName:base::SysNSStringToUTF16(@"日本語A")]; + CWVTranslationLanguage* language_b = [[CWVTranslationLanguage alloc] + initWithLanguageCode:"ja" + localizedName:base::SysNSStringToUTF16(@"JapaneseB") + nativeName:base::SysNSStringToUTF16(@"日本語B")]; + + // Equality should only be based on the language code. + EXPECT_NSEQ(language_a, language_b); + EXPECT_EQ(language_a.hash, language_b.hash); +} + } // namespace ios_web_view
diff --git a/media/base/BUILD.gn b/media/base/BUILD.gn index 20b75e8..fc8480d 100644 --- a/media/base/BUILD.gn +++ b/media/base/BUILD.gn
@@ -297,6 +297,7 @@ "tuneable.h", "unaligned_shared_memory.cc", "unaligned_shared_memory.h", + "use_after_free_checker.h", "user_input_monitor.cc", "user_input_monitor.h", "video_bitrate_allocation.cc",
diff --git a/media/base/audio_decoder.h b/media/base/audio_decoder.h index d9a458db4..7361e251 100644 --- a/media/base/audio_decoder.h +++ b/media/base/audio_decoder.h
@@ -27,16 +27,20 @@ class MEDIA_EXPORT AudioDecoder : public Decoder { public: - // Callback for AudioDecoder initialization. + // Callback for Decoder initialization. using InitCB = base::OnceCallback<void(Status)>; // Callback for AudioDecoder to return a decoded frame whenever it becomes // available. Only non-EOS frames should be returned via this callback. using OutputCB = base::RepeatingCallback<void(scoped_refptr<AudioBuffer>)>; - // Callback for Decode(). Called after the decoder has accepted corresponding - // DecoderBuffer, indicating that the pipeline can send next buffer to decode. - using DecodeCB = base::OnceCallback<void(DecodeStatus)>; + // Callback type for Decode(). Called after the decoder has completed decoding + // corresponding DecoderBuffer, indicating that it's ready to accept another + // buffer to decode. |kOk| implies success, |kAborted| implies that the + // decode was aborted, which does not necessarily indicate an error. For + // example, a Reset() can trigger this. Any other status code indicates that + // the decoder encountered an error, and must be reset. + using DecodeCB = base::OnceCallback<void(Status)>; AudioDecoder();
diff --git a/media/base/decode_status.cc b/media/base/decode_status.cc index de30ca7..af52c1b8d 100644 --- a/media/base/decode_status.cc +++ b/media/base/decode_status.cc
@@ -7,6 +7,7 @@ #include <ostream> #include "base/trace_event/trace_event.h" +#include "media/base/status.h" namespace media { @@ -18,17 +19,16 @@ return "DecodeStatus::ABORTED"; case DecodeStatus::DECODE_ERROR: return "DecodeStatus::DECODE_ERROR"; + default: + // TODO(liberato): Temporary while converting to media::Status. This + // fn should go away. + return "DecodeStatus::UNKNOWN_ERROR"; } NOTREACHED(); return ""; } -std::ostream& operator<<(std::ostream& os, const DecodeStatus& status) { - os << GetDecodeStatusString(status); - return os; -} - // static bool ScopedDecodeTrace::IsEnabled() { bool enable_decode_traces = false; @@ -59,11 +59,11 @@ EndTrace(DecodeStatus::ABORTED); } -void ScopedDecodeTrace::EndTrace(DecodeStatus status) { +void ScopedDecodeTrace::EndTrace(const Status& status) { DCHECK(!closed_); closed_ = true; TRACE_EVENT_ASYNC_END1("media", trace_name_, this, "status", - GetDecodeStatusString(status)); + GetDecodeStatusString(status.code())); } } // namespace media
diff --git a/media/base/decode_status.h b/media/base/decode_status.h index 0271668..d17d8573 100644 --- a/media/base/decode_status.h +++ b/media/base/decode_status.h
@@ -9,23 +9,18 @@ #include "media/base/decoder_buffer.h" #include "media/base/media_export.h" +#include "media/base/status_codes.h" namespace media { -enum class DecodeStatus { - OK = 0, // Everything went as planned. - ABORTED, // Read aborted due to Reset() during pending read. - DECODE_ERROR, // Decoder returned decode error. Note: Prefixed by DECODE_ - // since ERROR is a reserved name (special macro) on Windows. - DECODE_STATUS_MAX = DECODE_ERROR -}; +class Status; + +// TODO(crbug.com/1129662): This is temporary, to allow DecodeStatus::OK to +// work, while we replace DecodeStatus with actual status codes. +using DecodeStatus = StatusCode; MEDIA_EXPORT const char* GetDecodeStatusString(DecodeStatus status); -// Helper function so that DecodeStatus can be printed easily. -MEDIA_EXPORT std::ostream& operator<<(std::ostream& os, - const DecodeStatus& status); - // Helper class for ensuring that Decode() traces are properly unique and closed // if the Decode is aborted via a WeakPtr invalidation. We use the |this| // pointer of the ScopedDecodeTrace object itself as the id. Since the callback @@ -45,7 +40,7 @@ ~ScopedDecodeTrace(); // Completes the Decode() trace with the given status. - void EndTrace(DecodeStatus status); + void EndTrace(const Status& status); private: const char* trace_name_;
diff --git a/media/base/decoder.h b/media/base/decoder.h index 3c0d6c3..8ebec52 100644 --- a/media/base/decoder.h +++ b/media/base/decoder.h
@@ -7,8 +7,10 @@ #include <string> +#include "base/callback.h" #include "base/macros.h" #include "media/base/media_export.h" +#include "media/base/status.h" namespace media {
diff --git a/media/base/ipc/media_param_traits_macros.h b/media/base/ipc/media_param_traits_macros.h index b81de0e..93799338 100644 --- a/media/base/ipc/media_param_traits_macros.h +++ b/media/base/ipc/media_param_traits_macros.h
@@ -75,9 +75,6 @@ IPC_ENUM_TRAITS_MAX_VALUE(media::ChannelLayout, media::CHANNEL_LAYOUT_MAX) -IPC_ENUM_TRAITS_MAX_VALUE(media::DecodeStatus, - media::DecodeStatus::DECODE_STATUS_MAX) - IPC_ENUM_TRAITS_MAX_VALUE(media::Decryptor::Status, media::Decryptor::Status::kStatusMax)
diff --git a/media/base/status_codes.h b/media/base/status_codes.h index 24fc929..5c2b7fe 100644 --- a/media/base/status_codes.h +++ b/media/base/status_codes.h
@@ -27,6 +27,9 @@ enum class StatusCode : StatusCodeType { kOk = 0, + // General errors: 0x00 + kAborted = 0x00000001, + // Decoder Errors: 0x01 kDecoderInitializeNeverCompleted = 0x00000101, kDecoderFailedDecode = 0x00000102, @@ -44,6 +47,9 @@ kInitializationUnspecifiedFailure = 0x0000010C, kDecoderVideoFrameConstructionFailed = 0x0000010D, kMakeContextCurrentFailed = 0x0000010E, + // This is a temporary error for use only by existing code during the + // DecodeStatus => Status conversion. + kDecodeErrorDoNotUse = 0x0000010F, // Windows Errors: 0x02 kWindowsWrappedHresult = 0x00000201, @@ -120,6 +126,19 @@ kH264ParsingError = 0x00000801, kH264BufferTooSmall = 0x00000802, + // DecodeStatus temporary codes. These names were chosen to match the + // DecodeStatus enum, so that un-converted code can DecodeStatus::OK/etc. + // Note that OK must result in Status::is_ok(), since converted code will + // check for it. These will be removed when the conversion is complete. + // + // DO NOT ADD NEW USES OF OK/ABORTED/DECODE_ERROR. + OK = kOk, // Everything went as planned. + // Read aborted due to Reset() during pending read. + ABORTED = kAborted, // Read aborted due to Reset() during pending read. + // Decoder returned decode error. Note: Prefixed by DECODE_ + // since ERROR is a reserved name (special macro) on Windows. + DECODE_ERROR = kDecodeErrorDoNotUse, + // Special codes kGenericErrorPleaseRemove = 0x79999999, kCodeOnlyForTesting = std::numeric_limits<StatusCodeType>::max(),
diff --git a/media/base/test_helpers.h b/media/base/test_helpers.h index cdb6352..3a0df8e 100644 --- a/media/base/test_helpers.h +++ b/media/base/test_helpers.h
@@ -224,7 +224,7 @@ return arg.code() == status.code(); } -// Compares two an |arg| Status to a StatusCode provided +// Compares an `arg` Status.code() to a test-supplied StatusCode. MATCHER_P(HasStatusCode, status_code, "") { return arg.code() == status_code; } @@ -233,6 +233,12 @@ return arg.is_ok(); } +// True if and only if the Status would be interpreted as an error from a decode +// callback (not okay, not aborted). +MATCHER(IsDecodeErrorStatus, "") { + return !arg.is_ok() && arg.code() != StatusCode::kAborted; +} + // Compares two {Audio|Video}DecoderConfigs MATCHER_P(DecoderConfigEq, config, "") { return arg.Matches(config);
diff --git a/media/base/use_after_free_checker.h b/media/base/use_after_free_checker.h new file mode 100644 index 0000000..aefcaae2 --- /dev/null +++ b/media/base/use_after_free_checker.h
@@ -0,0 +1,60 @@ +// Copyright 2020 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 MEDIA_BASE_USE_AFTER_FREE_CHECKER_H_ +#define MEDIA_BASE_USE_AFTER_FREE_CHECKER_H_ + +#include "base/debug/dump_without_crashing.h" +#include "base/location.h" +#include "media/base/media_export.h" + +namespace { + +static base::debug::CrashKeyString* crash_key_string() { + static base::debug::CrashKeyString* string = nullptr; + if (!string) { + string = base::debug::AllocateCrashKeyString( + "use_after_free_checker", base::debug::CrashKeySize::Size32); + } + + return string; +} + +} // namespace + +namespace media { + +// Maintains a guard value from ctor => dtor, and causes a crash if it's ever +// found to be in an incorrect state. Includes a crash key that identifies +// whether itse use-after-free or corruption. +class MEDIA_EXPORT UseAfterFreeChecker { + public: + inline ~UseAfterFreeChecker() { + check(); + state_ = State::kDestructed; + } + + void check() { + if (state_ != State::kConstructed) { + base::debug::ScopedCrashKeyString scoped( + crash_key_string(), + state_ == State::kDestructed ? "destructed" : "corrupt"); + CHECK(false); + } + } + + private: + enum State : uint64_t { + kConstructed = 0x80C0FFEE, + kDestructed = 0xDEADC0DE, + }; + + // Declare this as an int rather than State, to avoid undefinedness if it gets + // overwritten with an arbitrary value. + uint64_t state_ = State::kConstructed; +}; + +} // namespace media + +#endif // MEDIA_BASE_USE_AFTER_FREE_CHECKER_H_
diff --git a/media/base/video_decoder.h b/media/base/video_decoder.h index 145ee96d..b66186c62 100644 --- a/media/base/video_decoder.h +++ b/media/base/video_decoder.h
@@ -7,14 +7,12 @@ #include <string> -#include "base/callback.h" #include "base/macros.h" #include "base/memory/ref_counted.h" #include "media/base/decode_status.h" #include "media/base/decoder.h" #include "media/base/media_export.h" #include "media/base/pipeline_status.h" -#include "media/base/status.h" #include "media/base/waiting.h" #include "ui/gfx/geometry/size.h" @@ -27,8 +25,8 @@ class MEDIA_EXPORT VideoDecoder : public Decoder { public: - // Callback for VideoDecoder initialization. - using InitCB = base::OnceCallback<void(Status status)>; + // Callback for Decoder initialization. + using InitCB = base::OnceCallback<void(Status)>; // Callback for VideoDecoder to return a decoded frame whenever it becomes // available. Only non-EOS frames should be returned via this callback. @@ -36,8 +34,11 @@ // Callback type for Decode(). Called after the decoder has completed decoding // corresponding DecoderBuffer, indicating that it's ready to accept another - // buffer to decode. - using DecodeCB = base::OnceCallback<void(DecodeStatus)>; + // buffer to decode. |kOk| implies success, |kAborted| implies that the + // decode was aborted, which does not necessarily indicate an error. For + // example, a Reset() can trigger this. Any other status code indicates that + // the decoder encountered an error, and must be reset. + using DecodeCB = base::OnceCallback<void(Status)>; VideoDecoder(); ~VideoDecoder() override;
diff --git a/media/base/video_thumbnail_decoder.cc b/media/base/video_thumbnail_decoder.cc index 130813a..e1ba856 100644 --- a/media/base/video_thumbnail_decoder.cc +++ b/media/base/video_thumbnail_decoder.cc
@@ -50,8 +50,8 @@ weak_factory_.GetWeakPtr())); } -void VideoThumbnailDecoder::OnVideoBufferDecoded(DecodeStatus status) { - if (status != DecodeStatus::OK) { +void VideoThumbnailDecoder::OnVideoBufferDecoded(Status status) { + if (!status.is_ok()) { NotifyComplete(nullptr); return; } @@ -62,8 +62,8 @@ weak_factory_.GetWeakPtr())); } -void VideoThumbnailDecoder::OnEosBufferDecoded(DecodeStatus status) { - if (status != DecodeStatus::OK) +void VideoThumbnailDecoder::OnEosBufferDecoded(Status status) { + if (!status.is_ok()) NotifyComplete(nullptr); }
diff --git a/media/base/video_thumbnail_decoder.h b/media/base/video_thumbnail_decoder.h index 69f0c4f..409ec23 100644 --- a/media/base/video_thumbnail_decoder.h +++ b/media/base/video_thumbnail_decoder.h
@@ -39,8 +39,8 @@ private: void OnVideoDecoderInitialized(Status status); - void OnVideoBufferDecoded(DecodeStatus status); - void OnEosBufferDecoded(DecodeStatus status); + void OnVideoBufferDecoded(Status status); + void OnEosBufferDecoded(Status status); // Called when the output frame is generated. void OnVideoFrameDecoded(scoped_refptr<VideoFrame> frame);
diff --git a/media/capture/video/video_capture_device_unittest.cc b/media/capture/video/video_capture_device_unittest.cc index a878a553..ab064ef 100644 --- a/media/capture/video/video_capture_device_unittest.cc +++ b/media/capture/video/video_capture_device_unittest.cc
@@ -466,7 +466,8 @@ // Causes a flaky crash on Chrome OS. https://crbug.com/1069608 // Cause hangs on Windows Debug. http://crbug.com/417824 -#if defined(OS_CHROMEOS) || (defined(OS_WIN) && !defined(NDEBUG)) +#if defined(OS_CHROMEOS) || (defined(OS_WIN) && !defined(NDEBUG)) || \ + defined(OS_MAC) #define MAYBE_OpenInvalidDevice DISABLED_OpenInvalidDevice #else #define MAYBE_OpenInvalidDevice OpenInvalidDevice
diff --git a/media/cast/sender/h264_vt_encoder_unittest.cc b/media/cast/sender/h264_vt_encoder_unittest.cc index 769d8ba..e91ef8f3 100644 --- a/media/cast/sender/h264_vt_encoder_unittest.cc +++ b/media/cast/sender/h264_vt_encoder_unittest.cc
@@ -157,7 +157,7 @@ ++count_frames_checked_; } - void DecodeDone(DecodeStatus status) { EXPECT_EQ(DecodeStatus::OK, status); } + void DecodeDone(Status status) { EXPECT_TRUE(status.is_ok()); } int count_frames_checked() const { return count_frames_checked_; }
diff --git a/media/cdm/library_cdm/clear_key_cdm/cdm_video_decoder.cc b/media/cdm/library_cdm/clear_key_cdm/cdm_video_decoder.cc index c52f6c4..fd52b40 100644 --- a/media/cdm/library_cdm/clear_key_cdm/cdm_video_decoder.cc +++ b/media/cdm/library_cdm/clear_key_cdm/cdm_video_decoder.cc
@@ -233,11 +233,12 @@ auto decode_status = last_decode_status_.value(); last_decode_status_.reset(); - if (decode_status == DecodeStatus::DECODE_ERROR) - return cdm::kDecodeError; + // "kAborted" shouldn't happen during a sync decode, so treat it as an + // error. + DCHECK_NE(decode_status.code(), StatusCode::kAborted); - // "ABORTED" shouldn't happen during a sync decode, so treat it as an error. - DCHECK_EQ(decode_status, DecodeStatus::OK); + if (!decode_status.is_ok()) + return cdm::kDecodeError; if (decoded_video_frames_.empty()) return cdm::kNeedMoreData; @@ -272,9 +273,9 @@ std::move(quit_closure).Run(); } - void OnDecoded(base::OnceClosure quit_closure, DecodeStatus decode_status) { + void OnDecoded(base::OnceClosure quit_closure, Status decode_status) { DCHECK(!last_decode_status_.has_value()); - last_decode_status_ = decode_status; + last_decode_status_ = std::move(decode_status); std::move(quit_closure).Run(); } @@ -284,7 +285,7 @@ // Results of |video_decoder_| operations. Set iff the callback of the // operation has been called. base::Optional<Status> last_init_result_; - base::Optional<DecodeStatus> last_decode_status_; + base::Optional<Status> last_decode_status_; // Queue of decoded video frames. using VideoFrameQueue = base::queue<scoped_refptr<VideoFrame>>;
diff --git a/media/filters/audio_decoder_unittest.cc b/media/filters/audio_decoder_unittest.cc index d46d4c6..72f5e2a 100644 --- a/media/filters/audio_decoder_unittest.cc +++ b/media/filters/audio_decoder_unittest.cc
@@ -301,11 +301,11 @@ decoded_audio_.push_back(std::move(buffer)); } - void DecodeFinished(const base::Closure& quit_closure, DecodeStatus status) { + void DecodeFinished(const base::Closure& quit_closure, Status status) { EXPECT_TRUE(pending_decode_); EXPECT_FALSE(pending_reset_); pending_decode_ = false; - last_decode_status_ = status; + last_decode_status_ = std::move(status); quit_closure.Run(); } @@ -389,7 +389,7 @@ const scoped_refptr<AudioBuffer>& decoded_audio(size_t i) { return decoded_audio_[i]; } - DecodeStatus last_decode_status() const { return last_decode_status_; } + const Status& last_decode_status() const { return last_decode_status_; } private: const AudioDecoderType decoder_type_; @@ -409,7 +409,7 @@ std::unique_ptr<AudioDecoder> decoder_; bool pending_decode_; bool pending_reset_; - DecodeStatus last_decode_status_; + Status last_decode_status_; base::circular_deque<scoped_refptr<AudioBuffer>> decoded_audio_; base::TimeDelta start_timestamp_; @@ -599,7 +599,7 @@ // (i.e. decoding EOS). do { ASSERT_NO_FATAL_FAILURE(Decode()); - ASSERT_EQ(last_decode_status(), DecodeStatus::OK); + ASSERT_TRUE(last_decode_status().is_ok()); } while (decoded_audio_size() < kDecodeRuns); // With MediaCodecAudioDecoder the output buffers might appear after @@ -631,7 +631,7 @@ SKIP_TEST_IF_NOT_SUPPORTED(); ASSERT_NO_FATAL_FAILURE(Initialize()); Decode(); - EXPECT_EQ(DecodeStatus::OK, last_decode_status()); + EXPECT_TRUE(last_decode_status().is_ok()); } TEST_P(AudioDecoderTest, Reset) { @@ -646,7 +646,7 @@ scoped_refptr<DecoderBuffer> buffer(new DecoderBuffer(0)); buffer->set_timestamp(kNoTimestamp); DecodeBuffer(std::move(buffer)); - EXPECT_EQ(DecodeStatus::DECODE_ERROR, last_decode_status()); + EXPECT_THAT(last_decode_status(), IsDecodeErrorStatus()); } INSTANTIATE_TEST_SUITE_P(FFmpeg,
diff --git a/media/filters/dav1d_video_decoder_unittest.cc b/media/filters/dav1d_video_decoder_unittest.cc index 69640df..93b53b7 100644 --- a/media/filters/dav1d_video_decoder_unittest.cc +++ b/media/filters/dav1d_video_decoder_unittest.cc
@@ -85,15 +85,14 @@ // Sets up expectations and actions to put Dav1dVideoDecoder in an active // decoding state. void ExpectDecodingState() { - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); } // Sets up expectations and actions to put Dav1dVideoDecoder in an end // of stream state. void ExpectEndOfStreamState() { - EXPECT_EQ(DecodeStatus::OK, - DecodeSingleFrame(DecoderBuffer::CreateEOSBuffer())); + EXPECT_TRUE(DecodeSingleFrame(DecoderBuffer::CreateEOSBuffer()).is_ok()); ASSERT_FALSE(output_frames_.empty()); } @@ -103,26 +102,26 @@ // Decodes all buffers in |input_buffers| and push all successfully decoded // output frames into |output_frames|. Returns the last decode status returned // by the decoder. - DecodeStatus DecodeMultipleFrames(const InputBuffers& input_buffers) { + Status DecodeMultipleFrames(const InputBuffers& input_buffers) { for (auto iter = input_buffers.begin(); iter != input_buffers.end(); ++iter) { - DecodeStatus status = Decode(*iter); - switch (status) { - case DecodeStatus::OK: + Status status = Decode(*iter); + switch (status.code()) { + case StatusCode::kOk: break; - case DecodeStatus::ABORTED: + case StatusCode::kAborted: NOTREACHED(); FALLTHROUGH; - case DecodeStatus::DECODE_ERROR: + default: DCHECK(output_frames_.empty()); return status; } } - return DecodeStatus::OK; + return StatusCode::kOk; } // Decodes the single compressed frame in |buffer|. - DecodeStatus DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { + Status DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { InputBuffers input_buffers; input_buffers.push_back(std::move(buffer)); return DecodeMultipleFrames(input_buffers); @@ -141,9 +140,9 @@ input_buffers.push_back(buffer); input_buffers.push_back(DecoderBuffer::CreateEOSBuffer()); - DecodeStatus status = DecodeMultipleFrames(input_buffers); + Status status = DecodeMultipleFrames(input_buffers); - EXPECT_EQ(DecodeStatus::OK, status); + EXPECT_TRUE(status.is_ok()); ASSERT_EQ(2U, output_frames_.size()); gfx::Size original_size = TestVideoConfig::NormalCodedSize(); @@ -157,8 +156,8 @@ output_frames_[1]->visible_rect().size().height()); } - DecodeStatus Decode(scoped_refptr<DecoderBuffer> buffer) { - DecodeStatus status; + Status Decode(scoped_refptr<DecoderBuffer> buffer) { + Status status; EXPECT_CALL(*this, DecodeDone(_)).WillOnce(testing::SaveArg<0>(&status)); decoder_->Decode(std::move(buffer), @@ -183,7 +182,7 @@ return base::MD5DigestToBase16(digest); } - MOCK_METHOD1(DecodeDone, void(DecodeStatus)); + MOCK_METHOD1(DecodeDone, void(Status)); testing::StrictMock<MockMediaLog> media_log_; @@ -223,7 +222,7 @@ Initialize(); // Simulate decoding a single frame. - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front(); @@ -233,8 +232,9 @@ TEST_F(Dav1dVideoDecoderTest, DecodeFrame_8bitMono) { Initialize(); - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(ReadTestDataFile( - "av1-monochrome-I-frame-320x240-8bpp"))); + EXPECT_TRUE( + DecodeSingleFrame(ReadTestDataFile("av1-monochrome-I-frame-320x240-8bpp")) + .is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front(); @@ -245,8 +245,9 @@ TEST_F(Dav1dVideoDecoderTest, DecodeFrame_10bitMono) { Initialize(); - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(ReadTestDataFile( - "av1-monochrome-I-frame-320x240-10bpp"))); + EXPECT_TRUE(DecodeSingleFrame( + ReadTestDataFile("av1-monochrome-I-frame-320x240-10bpp")) + .is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front(); @@ -257,8 +258,9 @@ TEST_F(Dav1dVideoDecoderTest, DecodeFrame_12bitMono) { Initialize(); - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(ReadTestDataFile( - "av1-monochrome-I-frame-320x240-12bpp"))); + EXPECT_TRUE(DecodeSingleFrame( + ReadTestDataFile("av1-monochrome-I-frame-320x240-12bpp")) + .is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front();
diff --git a/media/filters/decoder_stream.cc b/media/filters/decoder_stream.cc index 0c3e5cf..f1f45c9 100644 --- a/media/filters/decoder_stream.cc +++ b/media/filters/decoder_stream.cc
@@ -520,8 +520,8 @@ int buffer_size, bool end_of_stream, std::unique_ptr<ScopedDecodeTrace> trace_event, - DecodeStatus status) { - FUNCTION_DVLOG(3) << ": " << status; + Status status) { + FUNCTION_DVLOG(status.is_ok() ? 3 : 1) << ": " << status.code(); DCHECK(state_ == STATE_NORMAL || state_ == STATE_FLUSHING_DECODER || state_ == STATE_ERROR) << state_; @@ -534,7 +534,7 @@ if (end_of_stream) { DCHECK(!pending_decode_requests_); decoding_eos_ = false; - if (status == DecodeStatus::OK) { + if (status.is_ok()) { // Even if no frames were decoded, completing a flush counts as // successfully selecting a decoder. This allows back-to-back config // changes to select from all decoders. @@ -552,8 +552,37 @@ if (reset_cb_) return; - switch (status) { - case DecodeStatus::DECODE_ERROR: + switch (status.code()) { + case StatusCode::kAborted: + // Decoder can return kAborted during Reset() or during + // destruction. + return; + + case StatusCode::kOk: + // Any successful decode counts! + if (buffer_size > 0) + traits_->ReportStatistics(statistics_cb_, buffer_size); + + if (state_ == STATE_NORMAL) { + if (end_of_stream) { + state_ = STATE_END_OF_STREAM; + if (ready_outputs_.empty() && unprepared_outputs_.empty() && read_cb_) + SatisfyRead(OK, StreamTraits::CreateEOSOutput()); + return; + } + + if (CanDecodeMore()) + ReadFromDemuxerStream(); + return; + } + + if (state_ == STATE_FLUSHING_DECODER && !pending_decode_requests_) + ReinitializeDecoder(); + return; + + default: + // TODO(liberato): Use |status| better, since it might not be a generic + // error anymore. if (!decoder_produced_a_frame_ && base::FeatureList::IsEnabled(kFallbackAfterDecodeError)) { pending_decode_requests_ = 0; @@ -579,33 +608,6 @@ SatisfyRead(DECODE_ERROR, nullptr); } return; - - case DecodeStatus::ABORTED: - // Decoder can return DecodeStatus::ABORTED during Reset() or during - // destruction. - return; - - case DecodeStatus::OK: - // Any successful decode counts! - if (buffer_size > 0) - traits_->ReportStatistics(statistics_cb_, buffer_size); - - if (state_ == STATE_NORMAL) { - if (end_of_stream) { - state_ = STATE_END_OF_STREAM; - if (ready_outputs_.empty() && unprepared_outputs_.empty() && read_cb_) - SatisfyRead(OK, StreamTraits::CreateEOSOutput()); - return; - } - - if (CanDecodeMore()) - ReadFromDemuxerStream(); - return; - } - - if (state_ == STATE_FLUSHING_DECODER && !pending_decode_requests_) - ReinitializeDecoder(); - return; } }
diff --git a/media/filters/decoder_stream.h b/media/filters/decoder_stream.h index b130828..cbea02b 100644 --- a/media/filters/decoder_stream.h +++ b/media/filters/decoder_stream.h
@@ -203,7 +203,7 @@ void OnDecodeDone(int buffer_size, bool end_of_stream, std::unique_ptr<ScopedDecodeTrace> trace_event, - DecodeStatus status); + media::Status status); // Output callback passed to Decoder::Initialize(). void OnDecodeOutputReady(scoped_refptr<Output> output);
diff --git a/media/filters/decrypting_audio_decoder_unittest.cc b/media/filters/decrypting_audio_decoder_unittest.cc index 25717ca..7772462 100644 --- a/media/filters/decrypting_audio_decoder_unittest.cc +++ b/media/filters/decrypting_audio_decoder_unittest.cc
@@ -136,9 +136,8 @@ } // Decode |buffer| and expect DecodeDone to get called with |status|. - void DecodeAndExpect(scoped_refptr<DecoderBuffer> buffer, - DecodeStatus status) { - EXPECT_CALL(*this, DecodeDone(status)); + void DecodeAndExpect(scoped_refptr<DecoderBuffer> buffer, StatusCode status) { + EXPECT_CALL(*this, DecodeDone(HasStatusCode(status))); decoder_->Decode(buffer, base::Bind(&DecryptingAudioDecoderTest::DecodeDone, base::Unretained(this))); base::RunLoop().RunUntilIdle(); @@ -247,7 +246,7 @@ } MOCK_METHOD1(FrameReady, void(scoped_refptr<AudioBuffer>)); - MOCK_METHOD1(DecodeDone, void(DecodeStatus)); + MOCK_METHOD1(DecodeDone, void(Status)); MOCK_METHOD1(OnWaiting, void(WaitingReason)); @@ -414,7 +413,7 @@ EXPECT_CALL(*decryptor_, DecryptAndDecodeAudio(_, _)) .WillRepeatedly(RunCallback<1>(Decryptor::kSuccess, decoded_frame_list_)); EXPECT_CALL(*this, FrameReady(decoded_frame_)); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::OK)); + EXPECT_CALL(*this, DecodeDone(IsOkStatus())); event_cb_.Run(CdmContext::Event::kHasAdditionalUsableKey); base::RunLoop().RunUntilIdle(); } @@ -428,7 +427,7 @@ EXPECT_CALL(*decryptor_, DecryptAndDecodeAudio(_, _)) .WillRepeatedly(RunCallback<1>(Decryptor::kSuccess, decoded_frame_list_)); EXPECT_CALL(*this, FrameReady(decoded_frame_)); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::OK)); + EXPECT_CALL(*this, DecodeDone(IsOkStatus())); // The audio decode callback is returned after the correct decryption key is // added. event_cb_.Run(CdmContext::Event::kHasAdditionalUsableKey); @@ -457,7 +456,7 @@ Initialize(); EnterPendingDecodeState(); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)); + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))); Reset(); } @@ -467,7 +466,7 @@ Initialize(); EnterWaitingForKeyState(); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)); + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))); Reset(); }
diff --git a/media/filters/decrypting_video_decoder_unittest.cc b/media/filters/decrypting_video_decoder_unittest.cc index 47c9f3d..caa4221 100644 --- a/media/filters/decrypting_video_decoder_unittest.cc +++ b/media/filters/decrypting_video_decoder_unittest.cc
@@ -114,9 +114,17 @@ } // Decode |buffer| and expect DecodeDone to get called with |status|. - void DecodeAndExpect(scoped_refptr<DecoderBuffer> buffer, - DecodeStatus status) { - EXPECT_CALL(*this, DecodeDone(status)); + void DecodeAndExpect(scoped_refptr<DecoderBuffer> buffer, StatusCode status) { + EXPECT_CALL(*this, DecodeDone(HasStatusCode(status))); + decoder_->Decode(buffer, + base::BindOnce(&DecryptingVideoDecoderTest::DecodeDone, + base::Unretained(this))); + base::RunLoop().RunUntilIdle(); + } + + // Decode |buffer| and expect DecodeDone to get called with an error. + void DecodeAndExpectError(scoped_refptr<DecoderBuffer> buffer) { + EXPECT_CALL(*this, DecodeDone(IsDecodeErrorStatus())); decoder_->Decode(buffer, base::BindOnce(&DecryptingVideoDecoderTest::DecodeDone, base::Unretained(this))); @@ -224,7 +232,7 @@ } MOCK_METHOD1(FrameReady, void(scoped_refptr<VideoFrame>)); - MOCK_METHOD1(DecodeDone, void(DecodeStatus)); + MOCK_METHOD1(DecodeDone, void(Status)); MOCK_METHOD1(OnWaiting, void(WaitingReason)); @@ -313,10 +321,10 @@ .WillRepeatedly(RunCallback<1>(Decryptor::kError, scoped_refptr<VideoFrame>(nullptr))); - DecodeAndExpect(encrypted_buffer_, DecodeStatus::DECODE_ERROR); + DecodeAndExpectError(encrypted_buffer_); // After a decode error occurred, all following decodes return DECODE_ERROR. - DecodeAndExpect(encrypted_buffer_, DecodeStatus::DECODE_ERROR); + DecodeAndExpectError(encrypted_buffer_); } // Test the case where the decryptor receives end-of-stream buffer. @@ -336,7 +344,7 @@ .WillRepeatedly( RunCallback<1>(Decryptor::kSuccess, decoded_video_frame_)); EXPECT_CALL(*this, FrameReady(decoded_video_frame_)); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::OK)); + EXPECT_CALL(*this, DecodeDone(IsOkStatus())); event_cb_.Run(CdmContext::Event::kHasAdditionalUsableKey); base::RunLoop().RunUntilIdle(); } @@ -351,7 +359,7 @@ .WillRepeatedly( RunCallback<1>(Decryptor::kSuccess, decoded_video_frame_)); EXPECT_CALL(*this, FrameReady(decoded_video_frame_)); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::OK)); + EXPECT_CALL(*this, DecodeDone(IsOkStatus())); // The video decode callback is returned after the correct decryption key is // added. event_cb_.Run(CdmContext::Event::kHasAdditionalUsableKey); @@ -379,7 +387,7 @@ Initialize(); EnterPendingDecodeState(); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)); + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))); Reset(); } @@ -389,7 +397,7 @@ Initialize(); EnterWaitingForKeyState(); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)); + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))); Reset(); } @@ -449,7 +457,7 @@ Initialize(); EnterPendingDecodeState(); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)); + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))); Destroy(); } @@ -459,7 +467,7 @@ Initialize(); EnterWaitingForKeyState(); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)); + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))); Destroy(); } @@ -481,7 +489,7 @@ EnterPendingDecodeState(); EXPECT_CALL(*decryptor_, ResetDecoder(Decryptor::kVideo)); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)); + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))); decoder_->Reset(NewExpectedClosure()); Destroy();
diff --git a/media/filters/fake_video_decoder.cc b/media/filters/fake_video_decoder.cc index 5ef6326..cfdd7ba4f 100644 --- a/media/filters/fake_video_decoder.cc +++ b/media/filters/fake_video_decoder.cc
@@ -233,15 +233,15 @@ void FakeVideoDecoder::OnFrameDecoded(int buffer_size, DecodeCB decode_cb, - DecodeStatus status) { + Status status) { DCHECK(thread_checker_.CalledOnValidThread()); - if (status == DecodeStatus::OK) { + if (status.is_ok()) { total_bytes_decoded_ += buffer_size; if (bytes_decoded_cb_) bytes_decoded_cb_.Run(buffer_size); } - std::move(decode_cb).Run(status); + std::move(decode_cb).Run(std::move(status)); } void FakeVideoDecoder::RunOrHoldDecode(DecodeCB decode_cb) {
diff --git a/media/filters/fake_video_decoder.h b/media/filters/fake_video_decoder.h index 2b134049..e846717 100644 --- a/media/filters/fake_video_decoder.h +++ b/media/filters/fake_video_decoder.h
@@ -95,7 +95,7 @@ virtual scoped_refptr<VideoFrame> MakeVideoFrame(const DecoderBuffer& buffer); // Callback for updating |total_bytes_decoded_|. - void OnFrameDecoded(int buffer_size, DecodeCB decode_cb, DecodeStatus status); + void OnFrameDecoded(int buffer_size, DecodeCB decode_cb, Status status); // Runs |decode_cb| or puts it to |held_decode_callbacks_| depending on // current value of |hold_decode_|.
diff --git a/media/filters/fake_video_decoder_unittest.cc b/media/filters/fake_video_decoder_unittest.cc index ec68971..1c7fa61 100644 --- a/media/filters/fake_video_decoder_unittest.cc +++ b/media/filters/fake_video_decoder_unittest.cc
@@ -81,10 +81,10 @@ } // Callback for VideoDecoder::Decode(). - void DecodeDone(DecodeStatus status) { + void DecodeDone(Status status) { DCHECK_GT(pending_decode_requests_, 0); --pending_decode_requests_; - last_decode_status_ = status; + last_decode_status_ = std::move(status); } void FrameReady(scoped_refptr<VideoFrame> frame) { @@ -111,17 +111,17 @@ break; case OK: EXPECT_EQ(0, pending_decode_requests_); - ASSERT_EQ(DecodeStatus::OK, last_decode_status_); + ASSERT_TRUE(last_decode_status_.is_ok()); ASSERT_TRUE(last_decoded_frame_.get()); break; case NOT_ENOUGH_DATA: EXPECT_EQ(0, pending_decode_requests_); - ASSERT_EQ(DecodeStatus::OK, last_decode_status_); + ASSERT_TRUE(last_decode_status_.is_ok()); ASSERT_FALSE(last_decoded_frame_.get()); break; case ABORTED: EXPECT_EQ(0, pending_decode_requests_); - ASSERT_EQ(DecodeStatus::ABORTED, last_decode_status_); + ASSERT_EQ(StatusCode::kAborted, last_decode_status_.code()); EXPECT_FALSE(last_decoded_frame_.get()); break; } @@ -237,7 +237,7 @@ int total_bytes_in_buffers_; // Callback result/status. - DecodeStatus last_decode_status_; + Status last_decode_status_; scoped_refptr<VideoFrame> last_decoded_frame_; int pending_decode_requests_; bool is_reset_pending_; @@ -263,7 +263,7 @@ decoder_->SimulateFailureToInit(); InitializeWithConfigAndExpectResult(TestVideoConfig::Normal(), false); Decode(); - EXPECT_EQ(last_decode_status_, DecodeStatus::DECODE_ERROR); + EXPECT_THAT(last_decode_status_, IsDecodeErrorStatus()); } TEST_P(FakeVideoDecoderTest, Read_AllFrames) { @@ -364,7 +364,7 @@ decoder_->SimulateFailureToInit(); InitializeWithConfigAndExpectResult(TestVideoConfig::Normal(), false); Decode(); - EXPECT_EQ(last_decode_status_, DecodeStatus::DECODE_ERROR); + EXPECT_THAT(last_decode_status_, IsDecodeErrorStatus()); } // Reinitializing the decoder during the middle of the decoding process can
diff --git a/media/filters/ffmpeg_video_decoder_unittest.cc b/media/filters/ffmpeg_video_decoder_unittest.cc index 7c705bd..2d9be601 100644 --- a/media/filters/ffmpeg_video_decoder_unittest.cc +++ b/media/filters/ffmpeg_video_decoder_unittest.cc
@@ -107,14 +107,14 @@ // Sets up expectations and actions to put FFmpegVideoDecoder in an active // decoding state. void EnterDecodingState() { - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); } // Sets up expectations and actions to put FFmpegVideoDecoder in an end // of stream state. void EnterEndOfStreamState() { - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(end_of_stream_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(end_of_stream_buffer_).is_ok()); ASSERT_FALSE(output_frames_.empty()); } @@ -124,29 +124,29 @@ // Decodes all buffers in |input_buffers| and push all successfully decoded // output frames into |output_frames|. // Returns the last decode status returned by the decoder. - DecodeStatus DecodeMultipleFrames(const InputBuffers& input_buffers) { + Status DecodeMultipleFrames(const InputBuffers& input_buffers) { for (auto iter = input_buffers.begin(); iter != input_buffers.end(); ++iter) { - DecodeStatus status = Decode(*iter); - switch (status) { - case DecodeStatus::OK: + Status status = Decode(*iter); + switch (status.code()) { + case StatusCode::kOk: break; - case DecodeStatus::ABORTED: + case StatusCode::kAborted: NOTREACHED(); FALLTHROUGH; - case DecodeStatus::DECODE_ERROR: + default: DCHECK(output_frames_.empty()); return status; } } - return DecodeStatus::OK; + return StatusCode::kOk; } // Decodes the single compressed frame in |buffer| and writes the // uncompressed output to |video_frame|. This method works with single // and multithreaded decoders. End of stream buffers are used to trigger // the frame to be returned in the multithreaded decoder case. - DecodeStatus DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { + Status DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { InputBuffers input_buffers; input_buffers.push_back(buffer); input_buffers.push_back(end_of_stream_buffer_); @@ -168,9 +168,9 @@ input_buffers.push_back(buffer); input_buffers.push_back(end_of_stream_buffer_); - DecodeStatus status = DecodeMultipleFrames(input_buffers); + Status status = DecodeMultipleFrames(input_buffers); - EXPECT_EQ(DecodeStatus::OK, status); + EXPECT_TRUE(status.is_ok()); ASSERT_EQ(2U, output_frames_.size()); gfx::Size original_size = kVisibleRect.size(); @@ -184,8 +184,8 @@ output_frames_[1]->visible_rect().size().height()); } - DecodeStatus Decode(scoped_refptr<DecoderBuffer> buffer) { - DecodeStatus status; + Status Decode(scoped_refptr<DecoderBuffer> buffer) { + Status status; EXPECT_CALL(*this, DecodeDone(_)).WillOnce(SaveArg<0>(&status)); decoder_->Decode(buffer, base::BindOnce(&FFmpegVideoDecoderTest::DecodeDone, @@ -201,7 +201,7 @@ output_frames_.push_back(std::move(frame)); } - MOCK_METHOD1(DecodeDone, void(DecodeStatus)); + MOCK_METHOD1(DecodeDone, void(Status)); StrictMock<MockMediaLog> media_log_; @@ -256,7 +256,7 @@ Initialize(); // Simulate decoding a single frame. - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); } @@ -268,14 +268,14 @@ // The error is only raised on the second decode attempt, so we expect at // least one successful decode but we don't expect valid frame to be decoded. // During the second decode attempt an error is raised. - EXPECT_EQ(DecodeStatus::OK, Decode(corrupt_i_frame_buffer_)); + EXPECT_TRUE(Decode(corrupt_i_frame_buffer_).is_ok()); EXPECT_TRUE(output_frames_.empty()); - EXPECT_EQ(DecodeStatus::DECODE_ERROR, Decode(i_frame_buffer_)); + EXPECT_THAT(Decode(i_frame_buffer_), IsDecodeErrorStatus()); EXPECT_TRUE(output_frames_.empty()); // After a decode error occurred, all following decodes will return // DecodeStatus::DECODE_ERROR. - EXPECT_EQ(DecodeStatus::DECODE_ERROR, Decode(i_frame_buffer_)); + EXPECT_THAT(Decode(i_frame_buffer_), IsDecodeErrorStatus()); EXPECT_TRUE(output_frames_.empty()); } @@ -285,8 +285,8 @@ EXPECT_MEDIA_LOG(ContainsFailedToSendLog()); - EXPECT_EQ(DecodeStatus::DECODE_ERROR, - DecodeSingleFrame(corrupt_i_frame_buffer_)); + EXPECT_THAT(DecodeSingleFrame(corrupt_i_frame_buffer_), + IsDecodeErrorStatus()); } // Decode |i_frame_buffer_| and then a frame with a larger width and verify
diff --git a/media/filters/fuchsia/fuchsia_video_decoder_unittest.cc b/media/filters/fuchsia/fuchsia_video_decoder_unittest.cc index 61144c2f..e50a856 100644 --- a/media/filters/fuchsia/fuchsia_video_decoder_unittest.cc +++ b/media/filters/fuchsia/fuchsia_video_decoder_unittest.cc
@@ -260,10 +260,10 @@ DecodeBuffer(ReadTestDataFile(name)); } - void OnFrameDecoded(size_t frame_pos, DecodeStatus status) { + void OnFrameDecoded(size_t frame_pos, Status status) { EXPECT_EQ(frame_pos, num_decoded_buffers_); num_decoded_buffers_ += 1; - last_decode_status_ = status; + last_decode_status_ = std::move(status); if (run_loop_) run_loop_->Quit(); } @@ -276,7 +276,7 @@ run_loop_ = &run_loop; run_loop.Run(); run_loop_ = nullptr; - ASSERT_EQ(last_decode_status_, DecodeStatus::OK); + ASSERT_TRUE(last_decode_status_.is_ok()); } } @@ -298,7 +298,7 @@ std::list<scoped_refptr<VideoFrame>> output_frames_; size_t num_output_frames_ = 0; - DecodeStatus last_decode_status_ = DecodeStatus::OK; + Status last_decode_status_; base::RunLoop* run_loop_ = nullptr; // Number of frames that OnVideoFrame() should keep in |output_frames_|.
diff --git a/media/filters/gav1_video_decoder_unittest.cc b/media/filters/gav1_video_decoder_unittest.cc index 5a4d2fd..c12a6be4 100644 --- a/media/filters/gav1_video_decoder_unittest.cc +++ b/media/filters/gav1_video_decoder_unittest.cc
@@ -110,15 +110,14 @@ // Sets up expectations and actions to put Gav1VideoDecoder in an active // decoding state. void ExpectDecodingState() { - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); } // Sets up expectations and actions to put Gav1VideoDecoder in an end // of stream state. void ExpectEndOfStreamState() { - EXPECT_EQ(DecodeStatus::OK, - DecodeSingleFrame(DecoderBuffer::CreateEOSBuffer())); + EXPECT_TRUE(DecodeSingleFrame(DecoderBuffer::CreateEOSBuffer()).is_ok()); ASSERT_FALSE(output_frames_.empty()); } @@ -128,26 +127,26 @@ // Decodes all buffers in |input_buffers| and push all successfully decoded // output frames into |output_frames|. Returns the last decode status returned // by the decoder. - DecodeStatus DecodeMultipleFrames(const InputBuffers& input_buffers) { + Status DecodeMultipleFrames(const InputBuffers& input_buffers) { for (auto iter = input_buffers.begin(); iter != input_buffers.end(); ++iter) { - DecodeStatus status = Decode(*iter); - switch (status) { - case DecodeStatus::OK: + Status status = Decode(*iter); + switch (status.code()) { + case StatusCode::kOk: break; - case DecodeStatus::ABORTED: + case StatusCode::kAborted: NOTREACHED(); FALLTHROUGH; - case DecodeStatus::DECODE_ERROR: + default: DCHECK(output_frames_.empty()); return status; } } - return DecodeStatus::OK; + return StatusCode::kOk; } // Decodes the single compressed frame in |buffer|. - DecodeStatus DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { + Status DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { InputBuffers input_buffers; input_buffers.push_back(std::move(buffer)); return DecodeMultipleFrames(input_buffers); @@ -166,9 +165,9 @@ input_buffers.push_back(buffer); input_buffers.push_back(DecoderBuffer::CreateEOSBuffer()); - DecodeStatus status = DecodeMultipleFrames(input_buffers); + Status status = DecodeMultipleFrames(input_buffers); - EXPECT_EQ(DecodeStatus::OK, status); + EXPECT_TRUE(status.is_ok()); ASSERT_EQ(2U, output_frames_.size()); gfx::Size original_size = TestVideoConfig::NormalCodedSize(); @@ -182,8 +181,8 @@ output_frames_[1]->visible_rect().size().height()); } - DecodeStatus Decode(scoped_refptr<DecoderBuffer> buffer) { - DecodeStatus status; + Status Decode(scoped_refptr<DecoderBuffer> buffer) { + Status status; EXPECT_CALL(*this, DecodeDone(_)).WillOnce(testing::SaveArg<0>(&status)); decoder_->Decode(std::move(buffer), @@ -208,7 +207,7 @@ return base::MD5DigestToBase16(digest); } - MOCK_METHOD1(DecodeDone, void(DecodeStatus)); + MOCK_METHOD1(DecodeDone, void(Status)); testing::StrictMock<MockMediaLog> media_log_; @@ -248,7 +247,7 @@ Initialize(); // Simulate decoding a single frame. - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front(); @@ -258,8 +257,9 @@ TEST_F(Gav1VideoDecoderTest, DecodeFrame_8bitMono) { Initialize(); - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(ReadTestDataFile( - "av1-monochrome-I-frame-320x240-8bpp"))); + EXPECT_TRUE( + DecodeSingleFrame(ReadTestDataFile("av1-monochrome-I-frame-320x240-8bpp")) + .is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front(); @@ -269,8 +269,9 @@ TEST_F(Gav1VideoDecoderTest, DecodeFrame_10bitMono) { Initialize(); - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(ReadTestDataFile( - "av1-monochrome-I-frame-320x240-10bpp"))); + EXPECT_TRUE(DecodeSingleFrame( + ReadTestDataFile("av1-monochrome-I-frame-320x240-10bpp")) + .is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front(); @@ -281,8 +282,9 @@ // libgav1 does not support bit depth 12. TEST_F(Gav1VideoDecoderTest, DISABLED_DecodeFrame_12bitMono) { Initialize(); - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(ReadTestDataFile( - "av1-monochrome-I-frame-320x240-12bpp"))); + EXPECT_TRUE(DecodeSingleFrame( + ReadTestDataFile("av1-monochrome-I-frame-320x240-12bpp")) + .is_ok()); ASSERT_EQ(1U, output_frames_.size()); const auto& frame = output_frames_.front();
diff --git a/media/filters/offloading_video_decoder_unittest.cc b/media/filters/offloading_video_decoder_unittest.cc index 925bd7c0..53b4354 100644 --- a/media/filters/offloading_video_decoder_unittest.cc +++ b/media/filters/offloading_video_decoder_unittest.cc
@@ -95,8 +95,8 @@ base::Unretained(this)); } - VideoDecoder::DecodeCB ExpectDecodeCB(DecodeStatus status) { - EXPECT_CALL(*this, DecodeDone(status)) + VideoDecoder::DecodeCB ExpectDecodeCB(StatusCode status) { + EXPECT_CALL(*this, DecodeDone(HasStatusCode(status))) .WillOnce(VerifyOn(task_env_.GetMainThreadTaskRunner())); return base::BindOnce(&OffloadingVideoDecoderTest::DecodeDone, base::Unretained(this)); @@ -190,7 +190,7 @@ MOCK_METHOD1(InitDone, void(bool)); MOCK_METHOD1(OutputDone, void(scoped_refptr<VideoFrame>)); - MOCK_METHOD1(DecodeDone, void(DecodeStatus)); + MOCK_METHOD1(DecodeDone, void(Status)); MOCK_METHOD0(ResetDone, void(void)); base::test::TaskEnvironment task_env_; @@ -297,7 +297,7 @@ .WillRepeatedly(DoAll(VerifyNotOn(task_env_.GetMainThreadTaskRunner()), RunClosure(base::BindRepeating(output_cb, nullptr)), RunOnceCallback<1>(DecodeStatus::OK))); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::OK)) + EXPECT_CALL(*this, DecodeDone(IsOkStatus())) .Times(2) .WillRepeatedly(VerifyOn(task_env_.GetMainThreadTaskRunner())); EXPECT_CALL(*this, OutputDone(_)) @@ -344,7 +344,7 @@ base::Unretained(this))); EXPECT_CALL(*decoder_, Decode_(_, _)).Times(0); - EXPECT_CALL(*this, DecodeDone(DecodeStatus::ABORTED)) + EXPECT_CALL(*this, DecodeDone(HasStatusCode(StatusCode::kAborted))) .Times(2) .WillRepeatedly(VerifyOn(task_env_.GetMainThreadTaskRunner())); offloading_decoder_->Reset(ExpectResetCB());
diff --git a/media/filters/vpx_video_decoder_fuzzertest.cc b/media/filters/vpx_video_decoder_fuzzertest.cc index c66304e..577fa38 100644 --- a/media/filters/vpx_video_decoder_fuzzertest.cc +++ b/media/filters/vpx_video_decoder_fuzzertest.cc
@@ -30,8 +30,7 @@ base::test::SingleThreadTaskEnvironment task_environment; }; -void OnDecodeComplete(const base::Closure& quit_closure, - media::DecodeStatus status) { +void OnDecodeComplete(const base::Closure& quit_closure, media::Status status) { quit_closure.Run(); }
diff --git a/media/filters/vpx_video_decoder_unittest.cc b/media/filters/vpx_video_decoder_unittest.cc index f889357..379f2f8 100644 --- a/media/filters/vpx_video_decoder_unittest.cc +++ b/media/filters/vpx_video_decoder_unittest.cc
@@ -71,15 +71,14 @@ // Sets up expectations and actions to put VpxVideoDecoder in an active // decoding state. void ExpectDecodingState() { - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); } // Sets up expectations and actions to put VpxVideoDecoder in an end // of stream state. void ExpectEndOfStreamState() { - EXPECT_EQ(DecodeStatus::OK, - DecodeSingleFrame(DecoderBuffer::CreateEOSBuffer())); + EXPECT_TRUE(DecodeSingleFrame(DecoderBuffer::CreateEOSBuffer()).is_ok()); ASSERT_FALSE(output_frames_.empty()); } @@ -89,29 +88,29 @@ // Decodes all buffers in |input_buffers| and push all successfully decoded // output frames into |output_frames|. // Returns the last decode status returned by the decoder. - DecodeStatus DecodeMultipleFrames(const InputBuffers& input_buffers) { + Status DecodeMultipleFrames(const InputBuffers& input_buffers) { for (auto iter = input_buffers.begin(); iter != input_buffers.end(); ++iter) { - DecodeStatus status = Decode(*iter); - switch (status) { - case DecodeStatus::OK: + Status status = Decode(*iter); + switch (status.code()) { + case StatusCode::kOk: break; - case DecodeStatus::ABORTED: + case StatusCode::kAborted: NOTREACHED(); FALLTHROUGH; - case DecodeStatus::DECODE_ERROR: + default: DCHECK(output_frames_.empty()); return status; } } - return DecodeStatus::OK; + return OkStatus(); } // Decodes the single compressed frame in |buffer| and writes the // uncompressed output to |video_frame|. This method works with single // and multithreaded decoders. End of stream buffers are used to trigger // the frame to be returned in the multithreaded decoder case. - DecodeStatus DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { + Status DecodeSingleFrame(scoped_refptr<DecoderBuffer> buffer) { InputBuffers input_buffers; input_buffers.push_back(std::move(buffer)); input_buffers.push_back(DecoderBuffer::CreateEOSBuffer()); @@ -132,9 +131,9 @@ input_buffers.push_back(buffer); input_buffers.push_back(DecoderBuffer::CreateEOSBuffer()); - DecodeStatus status = DecodeMultipleFrames(input_buffers); + Status status = DecodeMultipleFrames(input_buffers); - EXPECT_EQ(DecodeStatus::OK, status); + EXPECT_TRUE(status.is_ok()); ASSERT_EQ(2U, output_frames_.size()); gfx::Size original_size = TestVideoConfig::NormalCodedSize(); @@ -148,8 +147,8 @@ output_frames_[1]->visible_rect().size().height()); } - DecodeStatus Decode(scoped_refptr<DecoderBuffer> buffer) { - DecodeStatus status; + Status Decode(scoped_refptr<DecoderBuffer> buffer) { + Status status; EXPECT_CALL(*this, DecodeDone(_)).WillOnce(testing::SaveArg<0>(&status)); decoder_->Decode(std::move(buffer), @@ -165,7 +164,7 @@ output_frames_.push_back(std::move(frame)); } - MOCK_METHOD1(DecodeDone, void(DecodeStatus)); + MOCK_METHOD1(DecodeDone, void(Status)); base::test::TaskEnvironment task_env_; std::unique_ptr<VideoDecoder> decoder_; @@ -192,7 +191,7 @@ Initialize(); // Simulate decoding a single frame. - EXPECT_EQ(DecodeStatus::OK, DecodeSingleFrame(i_frame_buffer_)); + EXPECT_TRUE(DecodeSingleFrame(i_frame_buffer_).is_ok()); ASSERT_EQ(1U, output_frames_.size()); } @@ -318,10 +317,10 @@ AVPacket packet = {}; while (av_read_frame(glue.format_context(), &packet) >= 0) { - DecodeStatus decode_status = + Status decode_status = Decode(DecoderBuffer::CopyFrom(packet.data, packet.size)); av_packet_unref(&packet); - if (decode_status != DecodeStatus::OK) + if (!decode_status.is_ok()) break; }
diff --git a/media/gpu/android/media_codec_video_decoder_unittest.cc b/media/gpu/android/media_codec_video_decoder_unittest.cc index 21591dd26e..190ccee 100644 --- a/media/gpu/android/media_codec_video_decoder_unittest.cc +++ b/media/gpu/android/media_codec_video_decoder_unittest.cc
@@ -396,7 +396,7 @@ Initialize(TestVideoConfig::Large(codec_)); ON_CALL(*video_frame_factory_, Initialize(ExpectedOverlayMode(), _)) .WillByDefault(RunCallback<1>(nullptr)); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::DECODE_ERROR)).Times(1); + EXPECT_CALL(decode_cb_, Run(IsDecodeErrorStatus())).Times(1); EXPECT_CALL(*surface_chooser_, MockUpdateState()).Times(0); mcvd_->Decode(fake_decoder_buffer_, decode_cb_.Get()); } @@ -404,7 +404,7 @@ TEST_P(MediaCodecVideoDecoderTest, CodecCreationFailureIsAnError) { InitializeWithTextureOwner_OneDecodePending(TestVideoConfig::Large(codec_)); mcvd_->Decode(fake_decoder_buffer_, decode_cb_.Get()); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::DECODE_ERROR)).Times(2); + EXPECT_CALL(decode_cb_, Run(IsDecodeErrorStatus())).Times(2); // Failing to create a codec should put MCVD into an error state. codec_allocator_->ProvideNullCodecAsync(); } @@ -414,7 +414,7 @@ InitializeFully_OneDecodePending(TestVideoConfig::Large(codec_)); EXPECT_CALL(*codec, DequeueInputBuffer(_, _)) .WillOnce(Return(MEDIA_CODEC_ERROR)); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::DECODE_ERROR)); + EXPECT_CALL(decode_cb_, Run(IsDecodeErrorStatus())); PumpCodec(); } @@ -553,7 +553,7 @@ surface_chooser_->ProvideTextureOwner(); EXPECT_CALL(*codec, SetSurface(_)).WillOnce(Return(false)); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::DECODE_ERROR)).Times(2); + EXPECT_CALL(decode_cb_, Run(IsDecodeErrorStatus())).Times(2); EXPECT_CALL(*codec_allocator_, MockReleaseMediaCodec(codec)); mcvd_->Decode(fake_decoder_buffer_, decode_cb_.Get()); // Verify expectations before we delete the MCVD. @@ -599,7 +599,7 @@ TEST_P(MediaCodecVideoDecoderTest, ResetAbortsPendingDecodes) { InitializeWithTextureOwner_OneDecodePending(TestVideoConfig::Large(codec_)); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::ABORTED)); + EXPECT_CALL(decode_cb_, Run(HasStatusCode(StatusCode::kAborted))); DoReset(); testing::Mock::VerifyAndClearExpectations(&decode_cb_); } @@ -617,7 +617,7 @@ codec->AcceptOneInput(MockMediaCodecBridge::kEos); PumpCodec(); - EXPECT_CALL(eos_decode_cb, Run(DecodeStatus::ABORTED)); + EXPECT_CALL(eos_decode_cb, Run(HasStatusCode(StatusCode::kAborted))); DoReset(); // Should be run before |mcvd_| is destroyed. testing::Mock::VerifyAndClearExpectations(&eos_decode_cb); @@ -766,7 +766,7 @@ codec->ProduceOneOutput(MockMediaCodecBridge::kEos); PumpCodec(); - EXPECT_CALL(eos_decode_cb, Run(DecodeStatus::OK)); + EXPECT_CALL(eos_decode_cb, Run(IsOkStatus())); std::move(video_frame_factory_->last_closure_).Run(); }
diff --git a/media/gpu/chromeos/vd_video_decode_accelerator.cc b/media/gpu/chromeos/vd_video_decode_accelerator.cc index 2c1cb0b..fb085cba 100644 --- a/media/gpu/chromeos/vd_video_decode_accelerator.cc +++ b/media/gpu/chromeos/vd_video_decode_accelerator.cc
@@ -190,12 +190,12 @@ } void VdVideoDecodeAccelerator::OnDecodeDone(int32_t bitstream_buffer_id, - DecodeStatus status) { - DVLOGF(4) << "status: " << status; + Status status) { + DVLOGF(4) << "status: " << status.code(); DCHECK_CALLED_ON_VALID_SEQUENCE(client_sequence_checker_); DCHECK(client_); - if (status == DecodeStatus::DECODE_ERROR) { + if (!status.is_ok() && status.code() != StatusCode::kAborted) { OnError(FROM_HERE, PLATFORM_FAILURE); return; } @@ -241,19 +241,19 @@ base::BindOnce(&VdVideoDecodeAccelerator::OnFlushDone, weak_this_)); } -void VdVideoDecodeAccelerator::OnFlushDone(DecodeStatus status) { - DVLOGF(3) << "status: " << status; +void VdVideoDecodeAccelerator::OnFlushDone(Status status) { + DVLOGF(3) << "status: " << status.code(); DCHECK_CALLED_ON_VALID_SEQUENCE(client_sequence_checker_); DCHECK(client_); - switch (status) { - case DecodeStatus::OK: + switch (status.code()) { + case StatusCode::kOk: client_->NotifyFlushDone(); break; - case DecodeStatus::ABORTED: + case StatusCode::kAborted: // Do nothing. break; - case DecodeStatus::DECODE_ERROR: + default: OnError(FROM_HERE, PLATFORM_FAILURE); break; }
diff --git a/media/gpu/chromeos/vd_video_decode_accelerator.h b/media/gpu/chromeos/vd_video_decode_accelerator.h index ffdb43c..f4ea148 100644 --- a/media/gpu/chromeos/vd_video_decode_accelerator.h +++ b/media/gpu/chromeos/vd_video_decode_accelerator.h
@@ -94,9 +94,9 @@ // Callback methods of |vd_|. void OnInitializeDone(Status status); - void OnDecodeDone(int32_t bitstream_buffer_id, DecodeStatus status); + void OnDecodeDone(int32_t bitstream_buffer_id, Status status); void OnFrameReady(scoped_refptr<VideoFrame> frame); - void OnFlushDone(DecodeStatus status); + void OnFlushDone(Status status); void OnResetDone(); // Get Picture instance that represents the same buffer as |frame|. Return
diff --git a/media/gpu/chromeos/video_decoder_pipeline.cc b/media/gpu/chromeos/video_decoder_pipeline.cc index dd1544f..7c52f3c 100644 --- a/media/gpu/chromeos/video_decoder_pipeline.cc +++ b/media/gpu/chromeos/video_decoder_pipeline.cc
@@ -365,21 +365,21 @@ void VideoDecoderPipeline::OnDecodeDone(bool is_flush, DecodeCB decode_cb, - DecodeStatus status) { + Status status) { DCHECK_CALLED_ON_VALID_SEQUENCE(decoder_sequence_checker_); - DVLOGF(4) << "is_flush: " << is_flush << ", status: " << status; + DVLOGF(4) << "is_flush: " << is_flush << ", status: " << status.code(); if (has_error_) - status = DecodeStatus::DECODE_ERROR; + status = Status(DecodeStatus::DECODE_ERROR); - if (is_flush && status == DecodeStatus::OK) { + if (is_flush && status.is_ok()) { client_flush_cb_ = std::move(decode_cb); CallFlushCbIfNeeded(DecodeStatus::OK); return; } - client_task_runner_->PostTask(FROM_HERE, - base::BindOnce(std::move(decode_cb), status)); + client_task_runner_->PostTask( + FROM_HERE, base::BindOnce(std::move(decode_cb), std::move(status))); } void VideoDecoderPipeline::OnFrameDecoded(scoped_refptr<VideoFrame> frame) {
diff --git a/media/gpu/chromeos/video_decoder_pipeline.h b/media/gpu/chromeos/video_decoder_pipeline.h index 16287e243..c3af61a 100644 --- a/media/gpu/chromeos/video_decoder_pipeline.h +++ b/media/gpu/chromeos/video_decoder_pipeline.h
@@ -42,7 +42,7 @@ // TODO(crbug.com/998413): Replace VideoFrame to GpuMemoryBuffer-based // instance. using OutputCB = base::RepeatingCallback<void(scoped_refptr<VideoFrame>)>; - using DecodeCB = base::OnceCallback<void(DecodeStatus)>; + using DecodeCB = VideoDecoder::DecodeCB; // Client interface of DecoderInterface. class MEDIA_GPU_EXPORT Client { @@ -190,7 +190,7 @@ Status parent_error, Status status); - void OnDecodeDone(bool eos_buffer, DecodeCB decode_cb, DecodeStatus status); + void OnDecodeDone(bool eos_buffer, DecodeCB decode_cb, Status status); void OnResetDone(); void OnError(const std::string& msg);
diff --git a/media/gpu/command_buffer_helper.cc b/media/gpu/command_buffer_helper.cc index 61f000f..d4b91d05 100644 --- a/media/gpu/command_buffer_helper.cc +++ b/media/gpu/command_buffer_helper.cc
@@ -191,6 +191,14 @@ will_destroy_stub_cb_ = std::move(will_destroy_stub_cb); } + bool IsPassthrough() const override { + if (!stub_) + return false; + return stub_->decoder_context() + ->GetFeatureInfo() + ->is_passthrough_cmd_decoder(); + } + private: ~CommandBufferHelperImpl() override { DVLOG(1) << __func__;
diff --git a/media/gpu/command_buffer_helper.h b/media/gpu/command_buffer_helper.h index 57922b49..11fd1da 100644 --- a/media/gpu/command_buffer_helper.h +++ b/media/gpu/command_buffer_helper.h
@@ -134,6 +134,9 @@ // may not change the current context. virtual void SetWillDestroyStubCB(WillDestroyStubCB will_destroy_stub_cb) = 0; + // Is the backing command buffer passthrough (versus validating). + virtual bool IsPassthrough() const = 0; + protected: explicit CommandBufferHelper( scoped_refptr<base::SequencedTaskRunner> task_runner);
diff --git a/media/gpu/gpu_video_decode_accelerator_helpers.h b/media/gpu/gpu_video_decode_accelerator_helpers.h index 4ab6dd1..18cedb0 100644 --- a/media/gpu/gpu_video_decode_accelerator_helpers.h +++ b/media/gpu/gpu_video_decode_accelerator_helpers.h
@@ -109,6 +109,9 @@ // Callback to return a DecoderContext*. CreateAbstractTextureCallback create_abstract_texture; + + // Whether or not the command buffer is passthrough. + bool is_passthrough = false; }; // Convert vector of VDA::SupportedProfile to vector of
diff --git a/media/gpu/ipc/service/gpu_video_decode_accelerator.cc b/media/gpu/ipc/service/gpu_video_decode_accelerator.cc index abce10ca..76f22dcd 100644 --- a/media/gpu/ipc/service/gpu_video_decode_accelerator.cc +++ b/media/gpu/ipc/service/gpu_video_decode_accelerator.cc
@@ -189,6 +189,8 @@ base::BindRepeating(&GetContextGroup, stub_->AsWeakPtr()); gl_client_.create_abstract_texture = base::BindRepeating(&CreateAbstractTexture, stub_->AsWeakPtr()); + gl_client_.is_passthrough = + stub_->decoder_context()->GetFeatureInfo()->is_passthrough_cmd_decoder(); } GpuVideoDecodeAccelerator::~GpuVideoDecodeAccelerator() {
diff --git a/media/gpu/ipc/service/vda_video_decoder.cc b/media/gpu/ipc/service/vda_video_decoder.cc index a971e5bf..3d0e5be 100644 --- a/media/gpu/ipc/service/vda_video_decoder.cc +++ b/media/gpu/ipc/service/vda_video_decoder.cc
@@ -75,6 +75,7 @@ gl_client.make_context_current = base::BindRepeating( &CommandBufferHelper::MakeContextCurrent, command_buffer_helper); gl_client.bind_image = base::BindRepeating(&BindImage, command_buffer_helper); + gl_client.is_passthrough = command_buffer_helper->IsPassthrough(); std::unique_ptr<GpuVideoDecodeAcceleratorFactory> factory = GpuVideoDecodeAcceleratorFactory::Create(gl_client);
diff --git a/media/gpu/ipc/service/vda_video_decoder_unittest.cc b/media/gpu/ipc/service/vda_video_decoder_unittest.cc index 6bff33cd..1d887b20 100644 --- a/media/gpu/ipc/service/vda_video_decoder_unittest.cc +++ b/media/gpu/ipc/service/vda_video_decoder_unittest.cc
@@ -176,7 +176,7 @@ } void NotifyEndOfBitstreamBuffer(int32_t bitstream_id) { - EXPECT_CALL(decode_cb_, Run(DecodeStatus::OK)); + EXPECT_CALL(decode_cb_, Run(HasStatusCode(DecodeStatus::OK))); if (GetParam()) { // TODO(sandersd): The VDA could notify on either thread. Test both. client_->NotifyEndOfBitstreamBuffer(bitstream_id); @@ -375,7 +375,7 @@ vdavd_->Reset(reset_cb_.Get()); RunUntilIdle(); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::ABORTED)); + EXPECT_CALL(decode_cb_, Run(HasStatusCode(DecodeStatus::ABORTED))); EXPECT_CALL(reset_cb_, Run()); NotifyResetDone(); } @@ -384,7 +384,7 @@ Initialize(); Decode(base::TimeDelta()); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::DECODE_ERROR)); + EXPECT_CALL(decode_cb_, Run(IsDecodeErrorStatus())); NotifyError(VideoDecodeAccelerator::PLATFORM_FAILURE); } @@ -461,7 +461,7 @@ vdavd_->Decode(DecoderBuffer::CreateEOSBuffer(), decode_cb_.Get()); RunUntilIdle(); - EXPECT_CALL(decode_cb_, Run(DecodeStatus::OK)); + EXPECT_CALL(decode_cb_, Run(IsOkStatus())); NotifyFlushDone(); }
diff --git a/media/gpu/mac/vt_video_decode_accelerator_mac.cc b/media/gpu/mac/vt_video_decode_accelerator_mac.cc index 0959744..a688e9c6 100644 --- a/media/gpu/mac/vt_video_decode_accelerator_mac.cc +++ b/media/gpu/mac/vt_video_decode_accelerator_mac.cc
@@ -1540,13 +1540,10 @@ gl_params.is_cleared = true; gpu::SharedImageBackingGLCommon::UnpackStateAttribs gl_attribs; - // TODO(https://crbug.com/1108909): Plumb the correct value of - // |is_passthrough|, or deprecate the non-passthrough path. - const bool is_passthrough = true; auto shared_image = std::make_unique<gpu::SharedImageBackingGLImage>( gl_image, mailbox, viz_resource_format, frame.image_size, color_space, kTopLeft_GrSurfaceOrigin, kOpaque_SkAlphaType, shared_image_usage, - gl_params, gl_attribs, is_passthrough); + gl_params, gl_attribs, gl_client_.is_passthrough); const bool success = shared_image_stub->factory()->RegisterBacking( std::move(shared_image), /* legacy_mailbox */ true);
diff --git a/media/gpu/test/fake_command_buffer_helper.cc b/media/gpu/test/fake_command_buffer_helper.cc index 4890e0b..f31ec7c 100644 --- a/media/gpu/test/fake_command_buffer_helper.cc +++ b/media/gpu/test/fake_command_buffer_helper.cc
@@ -164,4 +164,8 @@ will_destroy_stub_cb_ = std::move(will_destroy_stub_cb); } +bool FakeCommandBufferHelper::IsPassthrough() const { + return false; +} + } // namespace media
diff --git a/media/gpu/test/fake_command_buffer_helper.h b/media/gpu/test/fake_command_buffer_helper.h index c32595ddb..4a61372 100644 --- a/media/gpu/test/fake_command_buffer_helper.h +++ b/media/gpu/test/fake_command_buffer_helper.h
@@ -61,6 +61,7 @@ void WaitForSyncToken(gpu::SyncToken sync_token, base::OnceClosure done_cb) override; void SetWillDestroyStubCB(WillDestroyStubCB will_destroy_stub_cb) override; + bool IsPassthrough() const override; private: ~FakeCommandBufferHelper() override;
diff --git a/media/gpu/test/video.cc b/media/gpu/test/video.cc index e2e76a0c..3f85ebe2 100644 --- a/media/gpu/test/video.cc +++ b/media/gpu/test/video.cc
@@ -487,8 +487,8 @@ num_decoded_frames < num_frames) { if (packet.stream_index == stream_index) { media::VideoDecoder::DecodeCB decode_cb = base::BindOnce( - [](bool* success, media::DecodeStatus status) { - *success = (status == media::DecodeStatus::OK); + [](bool* success, media::Status status) { + *success = (status.is_ok()); }, success); decoder.Decode(DecoderBuffer::CopyFrom(packet.data, packet.size),
diff --git a/media/gpu/test/video_encoder/bitstream_validator.cc b/media/gpu/test/video_encoder/bitstream_validator.cc index 33036172..7e62260 100644 --- a/media/gpu/test/video_encoder/bitstream_validator.cc +++ b/media/gpu/test/video_encoder/bitstream_validator.cc
@@ -151,14 +151,14 @@ } } -void BitstreamValidator::DecodeDone(int64_t timestamp, DecodeStatus status) { +void BitstreamValidator::DecodeDone(int64_t timestamp, Status status) { SEQUENCE_CHECKER(validator_thread_sequence_checker_); - if (status != DecodeStatus::OK) { + if (!status.is_ok()) { base::AutoLock lock(validator_lock_); if (!decode_error_) { decode_error_ = true; LOG(ERROR) << "DecodeStatus is not OK, status=" - << GetDecodeStatusString(status); + << GetDecodeStatusString(status.code()); } } if (timestamp == kEOSTimeStamp) {
diff --git a/media/gpu/test/video_encoder/bitstream_validator.h b/media/gpu/test/video_encoder/bitstream_validator.h index dcdb84d..10b3d45 100644 --- a/media/gpu/test/video_encoder/bitstream_validator.h +++ b/media/gpu/test/video_encoder/bitstream_validator.h
@@ -67,7 +67,7 @@ size_t frame_index); // Functions for media::VideoDecoder. - void DecodeDone(int64_t timestamp, DecodeStatus status); + void DecodeDone(int64_t timestamp, Status status); void VerifyOutputFrame(scoped_refptr<VideoFrame> frame); // Validator components touched by validator_thread_ only.
diff --git a/media/gpu/test/video_player/video_decoder_client.cc b/media/gpu/test/video_player/video_decoder_client.cc index 3c2978f..da475de 100644 --- a/media/gpu/test/video_player/video_decoder_client.cc +++ b/media/gpu/test/video_player/video_decoder_client.cc
@@ -316,7 +316,7 @@ VideoDecoder::DecodeCB decode_cb = base::BindOnce( CallbackThunk<decltype(&VideoDecoderClient::DecodeDoneTask), - media::DecodeStatus>, + media::Status>, weak_this_, decoder_client_thread_.task_runner(), &VideoDecoderClient::DecodeDoneTask); decoder_->Decode(std::move(bitstream_buffer), std::move(decode_cb)); @@ -337,7 +337,7 @@ VideoDecoder::DecodeCB flush_done_cb = base::BindOnce(CallbackThunk<decltype(&VideoDecoderClient::FlushDoneTask), - media::DecodeStatus>, + media::Status>, weak_this_, decoder_client_thread_.task_runner(), &VideoDecoderClient::FlushDoneTask); decoder_->Decode(DecoderBuffer::CreateEOSBuffer(), std::move(flush_done_cb)); @@ -371,10 +371,10 @@ FireEvent(VideoPlayerEvent::kInitialized); } -void VideoDecoderClient::DecodeDoneTask(media::DecodeStatus status) { +void VideoDecoderClient::DecodeDoneTask(media::Status status) { DCHECK_CALLED_ON_VALID_SEQUENCE(decoder_client_sequence_checker_); DCHECK_NE(VideoDecoderClientState::kIdle, decoder_client_state_); - ASSERT_TRUE(status != media::DecodeStatus::ABORTED || + ASSERT_TRUE(status.code() != media::StatusCode::kAborted || decoder_client_state_ == VideoDecoderClientState::kResetting); DVLOGF(4); @@ -403,7 +403,7 @@ current_frame_index_++; } -void VideoDecoderClient::FlushDoneTask(media::DecodeStatus status) { +void VideoDecoderClient::FlushDoneTask(media::Status status) { DCHECK_CALLED_ON_VALID_SEQUENCE(decoder_client_sequence_checker_); DCHECK_EQ(0u, num_outstanding_decode_requests_);
diff --git a/media/gpu/test/video_player/video_decoder_client.h b/media/gpu/test/video_player/video_decoder_client.h index 232205c8..87e81b43 100644 --- a/media/gpu/test/video_player/video_decoder_client.h +++ b/media/gpu/test/video_player/video_decoder_client.h
@@ -150,11 +150,11 @@ // Called by the decoder when initialization has completed. void DecoderInitializedTask(Status status); // Called by the decoder when a fragment has been decoded. - void DecodeDoneTask(media::DecodeStatus status); + void DecodeDoneTask(media::Status status); // Called by the decoder when a video frame is ready. void FrameReadyTask(scoped_refptr<VideoFrame> video_frame); // Called by the decoder when flushing has completed. - void FlushDoneTask(media::DecodeStatus status); + void FlushDoneTask(media::Status status); // Called by the decoder when resetting has completed. void ResetDoneTask();
diff --git a/media/gpu/video_encode_accelerator_unittest.cc b/media/gpu/video_encode_accelerator_unittest.cc index 23320bdc..da750bc6 100644 --- a/media/gpu/video_encode_accelerator_unittest.cc +++ b/media/gpu/video_encode_accelerator_unittest.cc
@@ -1087,8 +1087,8 @@ private: void InitializeCB(Status status); - void DecodeDone(DecodeStatus status); - void FlushDone(DecodeStatus status); + void DecodeDone(Status status); + void FlushDone(Status status); void VerifyOutputFrame(scoped_refptr<VideoFrame> output_frame); void Decode(); void WriteFrameStats(); @@ -1196,20 +1196,21 @@ original_frames_.push(frame); } -void VideoFrameQualityValidator::DecodeDone(DecodeStatus status) { +void VideoFrameQualityValidator::DecodeDone(Status status) { DCHECK(thread_checker_.CalledOnValidThread()); - if (status == DecodeStatus::OK) { + if (status.is_ok()) { decoder_state_ = INITIALIZED; Decode(); } else { decoder_state_ = DECODER_ERROR; decode_error_cb_.Run(); - FAIL() << "Unexpected decode status = " << status << ". Stop decoding."; + FAIL() << "Unexpected decode status = " << status.code() + << ". Stop decoding."; } } -void VideoFrameQualityValidator::FlushDone(DecodeStatus status) { +void VideoFrameQualityValidator::FlushDone(Status status) { DCHECK(thread_checker_.CalledOnValidThread()); WriteFrameStats();
diff --git a/media/midi/BUILD.gn b/media/midi/BUILD.gn index 8053cce..6c34560f 100644 --- a/media/midi/BUILD.gn +++ b/media/midi/BUILD.gn
@@ -15,6 +15,13 @@ import("//build/config/android/rules.gni") } +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + # Common configuration for targets in the media/midi directory. config("midi_config") { if (use_alsa && use_udev) {
diff --git a/media/mojo/clients/mojo_audio_decoder.cc b/media/mojo/clients/mojo_audio_decoder.cc index ddfe31c0..fad002c 100644 --- a/media/mojo/clients/mojo_audio_decoder.cc +++ b/media/mojo/clients/mojo_audio_decoder.cc
@@ -217,8 +217,8 @@ std::move(init_cb_).Run(std::move(status)); } -void MojoAudioDecoder::OnDecodeStatus(DecodeStatus status) { - DVLOG(1) << __func__ << ": status:" << status; +void MojoAudioDecoder::OnDecodeStatus(const Status& status) { + DVLOG(1) << __func__ << ": status:" << status.code(); DCHECK(task_runner_->BelongsToCurrentThread()); DCHECK(decode_cb_);
diff --git a/media/mojo/clients/mojo_audio_decoder.h b/media/mojo/clients/mojo_audio_decoder.h index a7db243..b3b17b5 100644 --- a/media/mojo/clients/mojo_audio_decoder.h +++ b/media/mojo/clients/mojo_audio_decoder.h
@@ -67,7 +67,7 @@ void OnInitialized(const Status& status, bool needs_bitstream_conversion); // Called when |remote_decoder_| accepted or rejected DecoderBuffer. - void OnDecodeStatus(DecodeStatus decode_status); + void OnDecodeStatus(const Status& decode_status); // called when |remote_decoder_| finished Reset() sequence. void OnResetDone();
diff --git a/media/mojo/clients/mojo_audio_decoder_unittest.cc b/media/mojo/clients/mojo_audio_decoder_unittest.cc index 17d5d19..f699b14 100644 --- a/media/mojo/clients/mojo_audio_decoder_unittest.cc +++ b/media/mojo/clients/mojo_audio_decoder_unittest.cc
@@ -83,7 +83,7 @@ MOCK_METHOD1(OnInitialized, void(Status)); MOCK_METHOD1(OnOutput, void(scoped_refptr<AudioBuffer>)); MOCK_METHOD1(OnWaiting, void(WaitingReason)); - MOCK_METHOD1(OnDecoded, void(DecodeStatus)); + MOCK_METHOD1(OnDecoded, void(Status)); MOCK_METHOD0(OnReset, void()); // Always create a new RunLoop (and destroy the old loop if it exists) before @@ -206,7 +206,7 @@ InSequence s; // Make sure OnOutput() and OnDecoded() are called in order. EXPECT_CALL(*this, OnOutput(_)).Times(kOutputPerDecode); - EXPECT_CALL(*this, OnDecoded(DecodeStatus::OK)) + EXPECT_CALL(*this, OnDecoded(IsOkStatus())) .WillOnce( InvokeWithoutArgs(this, &MojoAudioDecoderTest::KeepDecodingOrQuit)); Decode(); @@ -215,7 +215,7 @@ void DecodeAndReset() { InSequence s; // Make sure all callbacks are fired in order. EXPECT_CALL(*this, OnOutput(_)).Times(kOutputPerDecode); - EXPECT_CALL(*this, OnDecoded(DecodeStatus::OK)); + EXPECT_CALL(*this, OnDecoded(IsOkStatus())); EXPECT_CALL(*this, OnReset()) .WillOnce(InvokeWithoutArgs(this, &MojoAudioDecoderTest::QuitLoop)); Decode(); @@ -297,7 +297,7 @@ std::move(decode_cb).Run(DecodeStatus::OK); }); EXPECT_CALL(*this, OnWaiting(WaitingReason::kNoDecryptionKey)).Times(1); - EXPECT_CALL(*this, OnDecoded(DecodeStatus::OK)) + EXPECT_CALL(*this, OnDecoded(IsOkStatus())) .WillOnce(InvokeWithoutArgs(this, &MojoAudioDecoderTest::QuitLoop)); Decode(); RunLoop();
diff --git a/media/mojo/clients/mojo_video_decoder.cc b/media/mojo/clients/mojo_video_decoder.cc index fb9169b5..524f979 100644 --- a/media/mojo/clients/mojo_video_decoder.cc +++ b/media/mojo/clients/mojo_video_decoder.cc
@@ -294,7 +294,7 @@ } } -void MojoVideoDecoder::OnDecodeDone(uint64_t decode_id, DecodeStatus status) { +void MojoVideoDecoder::OnDecodeDone(uint64_t decode_id, const Status& status) { DVLOG(3) << __func__; DCHECK(task_runner_->BelongsToCurrentThread()); @@ -305,7 +305,7 @@ return; } - if (status == DecodeStatus::DECODE_ERROR) + if (!status.is_ok() && status.code() != StatusCode::kAborted) ReportInitialPlaybackErrorUMA(); DecodeCB decode_cb = std::move(it->second);
diff --git a/media/mojo/clients/mojo_video_decoder.h b/media/mojo/clients/mojo_video_decoder.h index 87f6989..6d7fc9b3 100644 --- a/media/mojo/clients/mojo_video_decoder.h +++ b/media/mojo/clients/mojo_video_decoder.h
@@ -91,7 +91,7 @@ void OnInitializeDone(const Status& status, bool needs_bitstream_conversion, int32_t max_decode_requests); - void OnDecodeDone(uint64_t decode_id, DecodeStatus status); + void OnDecodeDone(uint64_t decode_id, const Status& status); void OnResetDone(); void BindRemoteDecoder();
diff --git a/media/mojo/mojom/audio_decoder.mojom b/media/mojo/mojom/audio_decoder.mojom index 27222222..599834e8 100644 --- a/media/mojo/mojom/audio_decoder.mojom +++ b/media/mojo/mojom/audio_decoder.mojom
@@ -33,7 +33,7 @@ // pending buffers should be processed, the corresponding decoded buffers // should be returned to the proxy, and only then the service should return // DecoderStatus. - Decode(DecoderBuffer buffer) => (DecodeStatus status); + Decode(DecoderBuffer buffer) => (Status status); // Resets decoder state. Should be called only if Initialize() succeeds. // All pending Decode() requests will be finished or aborted, then the method
diff --git a/media/mojo/mojom/video_decoder.mojom b/media/mojo/mojom/video_decoder.mojom index 719c226..1ff471e 100644 --- a/media/mojo/mojom/video_decoder.mojom +++ b/media/mojo/mojom/video_decoder.mojom
@@ -142,7 +142,7 @@ // If |buffer| is an EOS buffer, implementations must execute all other // pending Decode() callbacks and output all pending frames before executing // the Decode(EOS) callback. (That is, they must flush.) - Decode(DecoderBuffer buffer) => (DecodeStatus status); + Decode(DecoderBuffer buffer) => (Status status); // Reset the decoder. All ongoing Decode() requests must be completed or // aborted before executing the callback. This must not be called while there
diff --git a/media/mojo/services/mojo_audio_decoder_service.cc b/media/mojo/services/mojo_audio_decoder_service.cc index 8edf30d..66157cd1 100644 --- a/media/mojo/services/mojo_audio_decoder_service.cc +++ b/media/mojo/services/mojo_audio_decoder_service.cc
@@ -140,9 +140,9 @@ } void MojoAudioDecoderService::OnDecodeStatus(DecodeCallback callback, - media::DecodeStatus status) { - DVLOG(3) << __func__ << " status:" << status; - std::move(callback).Run(status); + const Status status) { + DVLOG(3) << __func__ << " status:" << status.code(); + std::move(callback).Run(std::move(status)); } void MojoAudioDecoderService::OnResetDone(ResetCallback callback) {
diff --git a/media/mojo/services/mojo_audio_decoder_service.h b/media/mojo/services/mojo_audio_decoder_service.h index 6dcb2f4..d827174 100644 --- a/media/mojo/services/mojo_audio_decoder_service.h +++ b/media/mojo/services/mojo_audio_decoder_service.h
@@ -13,6 +13,7 @@ #include "base/memory/weak_ptr.h" #include "media/base/audio_decoder.h" #include "media/base/cdm_context.h" +#include "media/base/status.h" #include "media/mojo/mojom/audio_decoder.mojom.h" #include "media/mojo/services/media_mojo_export.h" #include "mojo/public/cpp/bindings/associated_remote.h" @@ -54,7 +55,7 @@ void OnReaderFlushDone(ResetCallback callback); // Called by |decoder_| when DecoderBuffer is accepted or rejected. - void OnDecodeStatus(DecodeCallback callback, media::DecodeStatus status); + void OnDecodeStatus(DecodeCallback callback, media::Status status); // Called by |decoder_| when reset sequence is finished. void OnResetDone(ResetCallback callback);
diff --git a/media/mojo/services/mojo_video_decoder_service.cc b/media/mojo/services/mojo_video_decoder_service.cc index 8ef9c584..c0d9729 100644 --- a/media/mojo/services/mojo_video_decoder_service.cc +++ b/media/mojo/services/mojo_video_decoder_service.cc
@@ -316,7 +316,7 @@ void MojoVideoDecoderService::OnDecoderDecoded( DecodeCallback callback, std::unique_ptr<ScopedDecodeTrace> trace_event, - DecodeStatus status) { + media::Status status) { DVLOG(3) << __func__; if (trace_event) { TRACE_EVENT_ASYNC_STEP_PAST0("media", kDecodeTraceName, trace_event.get(), @@ -324,7 +324,7 @@ trace_event->EndTrace(status); } - std::move(callback).Run(status); + std::move(callback).Run(std::move(status)); } void MojoVideoDecoderService::OnDecoderReset() {
diff --git a/media/mojo/services/mojo_video_decoder_service.h b/media/mojo/services/mojo_video_decoder_service.h index ee80356..da0ff47 100644 --- a/media/mojo/services/mojo_video_decoder_service.h +++ b/media/mojo/services/mojo_video_decoder_service.h
@@ -72,7 +72,7 @@ scoped_refptr<DecoderBuffer> buffer); void OnDecoderDecoded(DecodeCallback callback, std::unique_ptr<ScopedDecodeTrace> trace_event, - DecodeStatus status); + media::Status status); // Called by |mojo_decoder_buffer_reader_| when reset is finished. void OnReaderFlushed();
diff --git a/media/mojo/test/mojo_video_decoder_integration_test.cc b/media/mojo/test/mojo_video_decoder_integration_test.cc index 3b67d0f..90de9ab 100644 --- a/media/mojo/test/mojo_video_decoder_integration_test.cc +++ b/media/mojo/test/mojo_video_decoder_integration_test.cc
@@ -257,10 +257,10 @@ return result.is_ok(); } - DecodeStatus Decode(scoped_refptr<DecoderBuffer> buffer, - VideoFrame::ReleaseMailboxCB release_cb = - VideoFrame::ReleaseMailboxCB()) { - DecodeStatus result = DecodeStatus::DECODE_ERROR; + Status Decode(scoped_refptr<DecoderBuffer> buffer, + VideoFrame::ReleaseMailboxCB release_cb = + VideoFrame::ReleaseMailboxCB()) { + Status result(DecodeStatus::DECODE_ERROR); if (!buffer->end_of_stream()) { decoder_->release_mailbox_cb = std::move(release_cb); @@ -432,7 +432,7 @@ EXPECT_CALL(*decoder_, Decode_(_, _)); EXPECT_CALL(waiting_cb_, Run(WaitingReason::kNoDecryptionKey)); - EXPECT_CALL(decode_cb, Run(DecodeStatus::OK)); + EXPECT_CALL(decode_cb, Run(IsOkStatus())); client_->Decode(buffer, decode_cb.Get()); RunUntilIdle(); @@ -442,10 +442,10 @@ ASSERT_TRUE(Initialize()); EXPECT_CALL(output_cb_, Run(_)); - ASSERT_EQ(Decode(CreateKeyframe(0)), DecodeStatus::OK); + ASSERT_TRUE(Decode(CreateKeyframe(0)).is_ok()); Mock::VerifyAndClearExpectations(&output_cb_); - ASSERT_EQ(Decode(DecoderBuffer::CreateEOSBuffer()), DecodeStatus::OK); + ASSERT_TRUE(Decode(DecoderBuffer::CreateEOSBuffer()).is_ok()); } TEST_F(MojoVideoDecoderIntegrationTest, Release) { @@ -455,7 +455,7 @@ scoped_refptr<VideoFrame> frame; EXPECT_CALL(output_cb_, Run(_)).WillOnce(SaveArg<0>(&frame)); - ASSERT_EQ(Decode(CreateKeyframe(0), release_cb.Get()), DecodeStatus::OK); + ASSERT_TRUE(Decode(CreateKeyframe(0), release_cb.Get()).is_ok()); Mock::VerifyAndClearExpectations(&output_cb_); EXPECT_CALL(release_cb, Run(_)); @@ -470,7 +470,7 @@ scoped_refptr<VideoFrame> frame; EXPECT_CALL(output_cb_, Run(_)).WillOnce(SaveArg<0>(&frame)); - ASSERT_EQ(Decode(CreateKeyframe(0), release_cb.Get()), DecodeStatus::OK); + ASSERT_TRUE(Decode(CreateKeyframe(0), release_cb.Get()).is_ok()); Mock::VerifyAndClearExpectations(&output_cb_); client_.reset(); @@ -546,7 +546,7 @@ EXPECT_CALL(output_cb_, Run(_)).Times(frames_to_decode); EXPECT_CALL(*decoder_, Decode_(_, _)).Times(frames_to_decode); - EXPECT_CALL(decode_cb, Run(DecodeStatus::OK)).Times(frames_to_decode); + EXPECT_CALL(decode_cb, Run(IsOkStatus())).Times(frames_to_decode); for (int i = 0; i < frames_to_decode - 1; i++) client_->Decode(CreateKeyframe(i * 16), decode_cb.Get()); @@ -574,9 +574,9 @@ EXPECT_CALL(output_cb_, Run(_)).Times(frames_to_decode - 1); EXPECT_CALL(*decoder_, Decode_(_, _)).Times(frames_to_decode); - EXPECT_CALL(decode_cb, Run(DecodeStatus::OK)).Times(frames_to_decode - 1); + EXPECT_CALL(decode_cb, Run(IsOkStatus())).Times(frames_to_decode - 1); - EXPECT_CALL(decode_cb, Run(DecodeStatus::DECODE_ERROR)).Times(1); + EXPECT_CALL(decode_cb, Run(IsDecodeErrorStatus())).Times(1); for (int i = 0; i < frames_to_decode - 1; i++) client_->Decode(CreateKeyframe(i * 16), decode_cb.Get());
diff --git a/net/BUILD.gn b/net/BUILD.gn index c3ef470..0ad6289 100644 --- a/net/BUILD.gn +++ b/net/BUILD.gn
@@ -188,8 +188,6 @@ "cert/ct_policy_enforcer.h", "cert/ct_policy_status.h", "cert/ct_verifier.h", - "cert/ct_verify_result.cc", - "cert/ct_verify_result.h", "cert/do_nothing_ct_verifier.cc", "cert/do_nothing_ct_verifier.h", "cert/internal/cert_error_id.cc",
diff --git a/net/cert/cert_verify_result.cc b/net/cert/cert_verify_result.cc index 5d88b7fb..f3c8740 100644 --- a/net/cert/cert_verify_result.cc +++ b/net/cert/cert_verify_result.cc
@@ -8,6 +8,8 @@ #include "base/values.h" #include "net/base/net_errors.h" +#include "net/cert/ct_policy_status.h" +#include "net/cert/ct_signed_certificate_timestamp_log_param.h" #include "net/cert/x509_certificate.h" #include "net/cert/x509_certificate_net_log_param.h" @@ -38,6 +40,9 @@ public_key_hashes = other.public_key_hashes; ocsp_result = other.ocsp_result; + scts = other.scts; + policy_compliance = other.policy_compliance; + ClearAllUserData(); CloneDataFrom(other); @@ -58,6 +63,10 @@ public_key_hashes.clear(); ocsp_result = OCSPVerifyResult(); + scts.clear(); + policy_compliance = + ct::CTPolicyCompliance::CT_POLICY_COMPLIANCE_DETAILS_NOT_AVAILABLE; + ClearAllUserData(); } @@ -89,6 +98,8 @@ hashes.Append(public_key_hash.ToString()); results.SetKey("public_key_hashes", std::move(hashes)); + results.SetKey("scts", net::NetLogSignedCertificateTimestampParams(&scts)); + return std::move(results); }
diff --git a/net/cert/cert_verify_result.h b/net/cert/cert_verify_result.h index 5663b28..35dee119 100644 --- a/net/cert/cert_verify_result.h +++ b/net/cert/cert_verify_result.h
@@ -11,13 +11,19 @@ #include "base/supports_user_data.h" #include "net/base/net_export.h" #include "net/cert/cert_status_flags.h" +#include "net/cert/ct_policy_status.h" #include "net/cert/ocsp_verify_result.h" +#include "net/cert/signed_certificate_timestamp_and_status.h" #include "net/cert/x509_cert_types.h" namespace base { class Value; } +namespace ct { +enum class CTPolicyCompliance; +} // namespace ct + namespace net { class X509Certificate; @@ -97,6 +103,16 @@ // Verification of stapled OCSP response, if present. OCSPVerifyResult ocsp_result; + + // `scts` contains the result of verifying any provided or embedded SCTs for + // this certificate against the set of known logs. Consumers should not simply + // check this for the presence of a successfully verified SCT to determine CT + // compliance. Instead look at `policy_compliance`. + SignedCertificateTimestampAndStatusList scts; + + // The result of evaluating whether the certificate complies with the + // Certificate Transparency policy. + ct::CTPolicyCompliance policy_compliance; }; } // namespace net
diff --git a/net/cert/ct_verify_result.cc b/net/cert/ct_verify_result.cc deleted file mode 100644 index 9da8828d..0000000 --- a/net/cert/ct_verify_result.cc +++ /dev/null
@@ -1,35 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "net/cert/ct_verify_result.h" - -#include "net/cert/ct_policy_status.h" - -namespace net { - -namespace ct { - -CTVerifyResult::CTVerifyResult() - : policy_compliance( - ct::CTPolicyCompliance::CT_POLICY_COMPLIANCE_DETAILS_NOT_AVAILABLE), - policy_compliance_required(false) {} - -CTVerifyResult::CTVerifyResult(const CTVerifyResult& other) = default; - -CTVerifyResult::~CTVerifyResult() = default; - -SCTList SCTsMatchingStatus( - const SignedCertificateTimestampAndStatusList& sct_and_status_list, - SCTVerifyStatus match_status) { - SCTList result; - for (const auto& sct_and_status : sct_and_status_list) - if (sct_and_status.status == match_status) - result.push_back(sct_and_status.sct); - - return result; -} - -} // namespace ct - -} // namespace net
diff --git a/net/cert/ct_verify_result.h b/net/cert/ct_verify_result.h deleted file mode 100644 index 742ec65..0000000 --- a/net/cert/ct_verify_result.h +++ /dev/null
@@ -1,49 +0,0 @@ -// Copyright 2013 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef NET_CERT_CT_VERIFY_RESULT_H_ -#define NET_CERT_CT_VERIFY_RESULT_H_ - -#include <vector> - -#include "net/base/net_export.h" -#include "net/cert/signed_certificate_timestamp_and_status.h" - -namespace net { - -namespace ct { - -enum class CTPolicyCompliance; - -// Holds Signed Certificate Timestamps, depending on their verification -// results, and information about CT policies that were applied on the -// connection. -struct NET_EXPORT CTVerifyResult { - CTVerifyResult(); - CTVerifyResult(const CTVerifyResult& other); - ~CTVerifyResult(); - - // All SCTs and their statuses - SignedCertificateTimestampAndStatusList scts; - - // The result of evaluating whether the connection complies with the - // CT certificate policy. - CTPolicyCompliance policy_compliance; - // True if the connection was required to comply with the CT certificate - // policy. This value is not meaningful if |policy_compliance| is - // COMPLIANCE_DETAILS_NOT_AVAILABLE. - bool policy_compliance_required; -}; - -// Returns a list of SCTs from |sct_and_status_list| whose status matches -// |match_status|. -SCTList NET_EXPORT SCTsMatchingStatus( - const SignedCertificateTimestampAndStatusList& sct_and_status_list, - SCTVerifyStatus match_status); - -} // namespace ct - -} // namespace net - -#endif // NET_CERT_CT_VERIFY_RESULT_H_
diff --git a/net/dns/BUILD.gn b/net/dns/BUILD.gn index b8da0cde..ce93723f 100644 --- a/net/dns/BUILD.gn +++ b/net/dns/BUILD.gn
@@ -5,10 +5,6 @@ import("//net/features.gni") import("//testing/libfuzzer/fuzzer_test.gni") -if (is_android) { - import("//build/config/android/rules.gni") -} - # Reset sources_assignment_filter for the BUILD.gn file to prevent # regression during the migration of Chromium away from the feature. # See docs/no_sources_assignment_filter.md for more information. @@ -396,12 +392,6 @@ public_deps = [ "//net:net_public_deps" ] } -if (is_android) { - java_cpp_enum("secure_dns_mode_generated_enum") { - sources = [ "dns_config.h" ] - } -} - source_set("tests") { testonly = true sources = [
diff --git a/net/dns/README.md b/net/dns/README.md index 7bb8b07..4f88fea 100644 --- a/net/dns/README.md +++ b/net/dns/README.md
@@ -241,7 +241,7 @@ * Requests with the `HOST_RESOLVER_CANONNAME` flag * For hostnames ending in ".local" -* When the Secure DNS mode is `net::DnsConfig::SecureDnsMode::OFF` and +* When the Secure DNS mode is `net::SecureDnsMode::OFF` and `net::HostResolverSource::DNS` is not enabled via `net::HostResolverManager::SetInsecureDnsClientEnabled(true)` * When a system DNS configuration could not be determined @@ -282,7 +282,7 @@ * DnsClient is enabled for insecure requests enabled via `net::HostResolverManager::SetInsecureDnsClientEnabled(true)` or - the Secure DNS mode is not `net::DnsConfig::SecureDnsMode::OFF`. + the Secure DNS mode is not `net::SecureDnsMode::OFF`. * The system DNS configuration could be determined successfully * The request hostname does not end in ".local" * The request is not an address query with the `HOST_RESOLVER_CANONNAME` flag
diff --git a/net/dns/dns_client.cc b/net/dns/dns_client.cc index bc626a1..dfb6407 100644 --- a/net/dns/dns_client.cc +++ b/net/dns/dns_client.cc
@@ -15,6 +15,7 @@ #include "net/dns/dns_socket_allocator.h" #include "net/dns/dns_transaction.h" #include "net/dns/dns_util.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/dns/resolve_context.h" #include "net/log/net_log.h" #include "net/log/net_log_event_type.h" @@ -48,7 +49,7 @@ // when there are aspects of the system DNS config that are unhandled. if (!config->unhandled_options && config->allow_dns_over_https_upgrade && !has_doh_servers && - config->secure_dns_mode == DnsConfig::SecureDnsMode::AUTOMATIC) { + config->secure_dns_mode == SecureDnsMode::kAutomatic) { // If we're in strict mode on Android, only attempt to upgrade the // specified DoT hostname. if (!config->dns_over_tls_hostname.empty()) {
diff --git a/net/dns/dns_config.cc b/net/dns/dns_config.cc index 937c7a9..3265807 100644 --- a/net/dns/dns_config.cc +++ b/net/dns/dns_config.cc
@@ -30,7 +30,7 @@ doh_attempts(1), rotate(false), use_local_ipv6(false), - secure_dns_mode(SecureDnsMode::OFF), + secure_dns_mode(SecureDnsMode::kOff), allow_dns_over_https_upgrade(false) {} DnsConfig::~DnsConfig() = default;
diff --git a/net/dns/dns_config.h b/net/dns/dns_config.h index b165a655..96e8540 100644 --- a/net/dns/dns_config.h +++ b/net/dns/dns_config.h
@@ -14,6 +14,7 @@ #include "net/base/net_export.h" #include "net/dns/dns_hosts.h" #include "net/dns/public/dns_over_https_server_config.h" +#include "net/dns/public/secure_dns_mode.h" namespace base { class Value; @@ -51,20 +52,6 @@ return !nameservers.empty() || !dns_over_https_servers.empty(); } - // GENERATED_JAVA_ENUM_PACKAGE: org.chromium.net - // The SecureDnsMode specifies what types of lookups (secure/insecure) should - // be performed and in what order when resolving a specific query. The int - // values should not be changed as they are logged. - enum class SecureDnsMode : int { - // In OFF mode, no DoH lookups should be performed. - OFF = 0, - // In AUTOMATIC mode, DoH lookups should be performed first if DoH is - // available, and insecure DNS lookups should be performed as a fallback. - AUTOMATIC = 1, - // In SECURE mode, only DoH lookups should be performed. - SECURE = 2, - }; - // List of name server addresses. std::vector<IPEndPoint> nameservers;
diff --git a/net/dns/dns_config_overrides.cc b/net/dns/dns_config_overrides.cc index fa0437e..594e178e 100644 --- a/net/dns/dns_config_overrides.cc +++ b/net/dns/dns_config_overrides.cc
@@ -4,6 +4,8 @@ #include "net/dns/dns_config_overrides.h" +#include "net/dns/dns_config.h" + namespace net { DnsConfigOverrides::DnsConfigOverrides() = default;
diff --git a/net/dns/dns_config_overrides.h b/net/dns/dns_config_overrides.h index a87d0e5..b1fcdc1 100644 --- a/net/dns/dns_config_overrides.h +++ b/net/dns/dns_config_overrides.h
@@ -12,12 +12,14 @@ #include "base/time/time.h" #include "net/base/ip_endpoint.h" #include "net/base/net_export.h" -#include "net/dns/dns_config.h" #include "net/dns/dns_hosts.h" #include "net/dns/public/dns_over_https_server_config.h" +#include "net/dns/public/secure_dns_mode.h" namespace net { +struct DnsConfig; + // Overriding values to be applied over a DnsConfig struct. struct NET_EXPORT DnsConfigOverrides { DnsConfigOverrides(); @@ -57,7 +59,7 @@ base::Optional<bool> rotate; base::Optional<bool> use_local_ipv6; base::Optional<std::vector<DnsOverHttpsServerConfig>> dns_over_https_servers; - base::Optional<DnsConfig::SecureDnsMode> secure_dns_mode; + base::Optional<SecureDnsMode> secure_dns_mode; base::Optional<bool> allow_dns_over_https_upgrade; base::Optional<std::vector<std::string>> disabled_upgrade_providers;
diff --git a/net/dns/dns_server_iterator.cc b/net/dns/dns_server_iterator.cc index d04d28b..9d25870 100644 --- a/net/dns/dns_server_iterator.cc +++ b/net/dns/dns_server_iterator.cc
@@ -6,7 +6,6 @@ #include "base/optional.h" #include "base/time/time.h" -#include "net/dns/dns_config.h" #include "net/dns/dns_session.h" #include "net/dns/resolve_context.h" @@ -48,7 +47,7 @@ // If the DoH mode is "secure" then don't check GetDohServerAvailability() // because we try every server regardless of availability. bool secure_or_available_server = - secure_dns_mode_ == DnsConfig::SecureDnsMode::SECURE || + secure_dns_mode_ == SecureDnsMode::kSecure || resolve_context_->GetDohServerAvailability(curr_index, session_); // If we've tried this server |max_times_returned_| already, then we're done @@ -72,7 +71,6 @@ least_recently_failed_time = curr_index_failure_time; least_recently_failed_index = curr_index; } - } while (next_index_ != previous_index); // At this point the only available servers we haven't attempted @@ -92,7 +90,7 @@ // If the DoH mode is "secure" then don't check GetDohServerAvailability() // because we try every server regardless of availability. bool secure_or_available_server = - secure_dns_mode_ == DnsConfig::SecureDnsMode::SECURE || + secure_dns_mode_ == SecureDnsMode::kSecure || resolve_context_->GetDohServerAvailability(i, session_); if (times_returned_[i] < max_times_returned_ && secure_or_available_server) @@ -139,7 +137,6 @@ least_recently_failed_time = curr_index_failure_time; least_recently_failed_index = curr_index; } - } while (next_index_ != previous_index); // At this point the only servers we haven't attempted |max_times_returned_|
diff --git a/net/dns/dns_server_iterator.h b/net/dns/dns_server_iterator.h index 532297f3..97c42f7 100644 --- a/net/dns/dns_server_iterator.h +++ b/net/dns/dns_server_iterator.h
@@ -5,8 +5,10 @@ #ifndef NET_DNS_DNS_SERVER_ITERATOR_H_ #define NET_DNS_DNS_SERVER_ITERATOR_H_ +#include <vector> + #include "net/base/net_export.h" -#include "net/dns/dns_config.h" +#include "net/dns/public/secure_dns_mode.h" namespace net { @@ -81,7 +83,7 @@ size_t starting_index, int max_times_returned, int max_failures, - const DnsConfig::SecureDnsMode& secure_dns_mode, + const SecureDnsMode& secure_dns_mode, const ResolveContext* resolve_context, const DnsSession* session) : DnsServerIterator(nameservers_size, @@ -107,7 +109,7 @@ bool AttemptAvailable() override; private: - DnsConfig::SecureDnsMode secure_dns_mode_; + SecureDnsMode secure_dns_mode_; }; // Iterator used to get the next server to try for a classic DNS transaction.
diff --git a/net/dns/dns_test_util.cc b/net/dns/dns_test_util.cc index 0ced88c..6a39447c 100644 --- a/net/dns/dns_test_util.cc +++ b/net/dns/dns_test_util.cc
@@ -370,7 +370,7 @@ uint16_t qtype, bool secure, bool force_doh_server_available, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, ResolveContext* resolve_context, DnsTransactionFactory::CallbackType callback) : result_(MockDnsClientRule::FAIL), @@ -544,7 +544,7 @@ DnsTransactionFactory::CallbackType callback, const NetLogWithSource&, bool secure, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, ResolveContext* resolve_context) { std::unique_ptr<MockTransaction> transaction = std::make_unique<MockTransaction>( @@ -562,8 +562,8 @@ void MockDnsTransactionFactory::AddEDNSOption(const OptRecordRdata::Opt& opt) {} -DnsConfig::SecureDnsMode MockDnsTransactionFactory::GetSecureDnsModeForTest() { - return DnsConfig::SecureDnsMode::AUTOMATIC; +SecureDnsMode MockDnsTransactionFactory::GetSecureDnsModeForTest() { + return SecureDnsMode::kAutomatic; } void MockDnsTransactionFactory::CompleteDelayedTransactions() {
diff --git a/net/dns/dns_test_util.h b/net/dns/dns_test_util.h index 3944541..7d79a35 100644 --- a/net/dns/dns_test_util.h +++ b/net/dns/dns_test_util.h
@@ -24,6 +24,7 @@ #include "net/dns/dns_transaction.h" #include "net/dns/dns_util.h" #include "net/dns/public/dns_protocol.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/socket/socket_test_util.h" namespace net { @@ -286,7 +287,7 @@ DnsTransactionFactory::CallbackType callback, const NetLogWithSource&, bool secure, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, ResolveContext* resolve_context) override; std::unique_ptr<DnsProbeRunner> CreateDohProbeRunner( @@ -294,7 +295,7 @@ void AddEDNSOption(const OptRecordRdata::Opt& opt) override; - DnsConfig::SecureDnsMode GetSecureDnsModeForTest() override; + SecureDnsMode GetSecureDnsModeForTest() override; void CompleteDelayedTransactions(); // If there are any pending transactions of the given type,
diff --git a/net/dns/dns_transaction.cc b/net/dns/dns_transaction.cc index 52e4eaee..cb3e48b 100644 --- a/net/dns/dns_transaction.cc +++ b/net/dns/dns_transaction.cc
@@ -1044,7 +1044,7 @@ const NetLogWithSource& net_log, const OptRecordRdata* opt_rdata, bool secure, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, ResolveContext* resolve_context) : session_(session), hostname_(hostname), @@ -1530,7 +1530,7 @@ uint16_t qtype_; const OptRecordRdata* opt_rdata_; const bool secure_; - const DnsConfig::SecureDnsMode secure_dns_mode_; + const SecureDnsMode secure_dns_mode_; // Cleared in DoCallback. DnsTransactionFactory::CallbackType callback_; @@ -1578,7 +1578,7 @@ CallbackType callback, const NetLogWithSource& net_log, bool secure, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, ResolveContext* resolve_context) override { return std::make_unique<DnsTransactionImpl>( session_.get(), hostname, qtype, std::move(callback), net_log, @@ -1598,7 +1598,7 @@ opt_rdata_->AddOpt(opt); } - DnsConfig::SecureDnsMode GetSecureDnsModeForTest() override { + SecureDnsMode GetSecureDnsModeForTest() override { return session_->config().secure_dns_mode; }
diff --git a/net/dns/dns_transaction.h b/net/dns/dns_transaction.h index bc182ff..aa866b9 100644 --- a/net/dns/dns_transaction.h +++ b/net/dns/dns_transaction.h
@@ -14,7 +14,7 @@ #include "base/memory/weak_ptr.h" #include "base/time/time.h" #include "net/base/request_priority.h" -#include "net/dns/dns_config.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/dns/record_rdata.h" #include "url/gurl.h" @@ -109,7 +109,7 @@ CallbackType callback, const NetLogWithSource& net_log, bool secure, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, ResolveContext* resolve_context) WARN_UNUSED_RESULT = 0; // Creates a runner to run the DoH probe sequence for all configured DoH @@ -122,7 +122,7 @@ virtual void AddEDNSOption(const OptRecordRdata::Opt& opt) = 0; // Returns the default SecureDnsMode in the config. - virtual DnsConfig::SecureDnsMode GetSecureDnsModeForTest() = 0; + virtual SecureDnsMode GetSecureDnsModeForTest() = 0; // Creates a DnsTransactionFactory which creates DnsTransactionImpl using the // |session|.
diff --git a/net/dns/dns_transaction_unittest.cc b/net/dns/dns_transaction_unittest.cc index 3816b918..6154eb3 100644 --- a/net/dns/dns_transaction_unittest.cc +++ b/net/dns/dns_transaction_unittest.cc
@@ -1852,9 +1852,8 @@ resolve_context_->GetClassicDnsIterator(session_->config(), session_.get()); std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_TRUE(classic_itr->AttemptAvailable()); EXPECT_EQ(classic_itr->GetNextAttemptIndex(), 0u); ASSERT_TRUE(doh_itr->AttemptAvailable()); @@ -1880,9 +1879,8 @@ resolve_context_->GetClassicDnsIterator(session_->config(), session_.get()); std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_EQ(classic_itr->GetNextAttemptIndex(), 0u); ASSERT_TRUE(doh_itr->AttemptAvailable()); @@ -1947,9 +1945,8 @@ { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -1967,9 +1964,8 @@ CheckServerOrder(kOrder0, base::size(kOrder0)); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -1979,7 +1975,7 @@ // Fail first DoH server, then no fallbacks marked available in AUTOMATIC mode. TEST_F(DnsTransactionTest, HttpsFailureThenNotAvailable_Automatic) { - config_.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + config_.secure_dns_mode = SecureDnsMode::kAutomatic; ConfigureDohServers(true /* use_post */, 3 /* num_doh_servers */, false /* make_available */); @@ -1989,9 +1985,8 @@ { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2014,9 +2009,8 @@ { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2027,7 +2021,7 @@ // Test a secure transaction failure in SECURE mode when other DoH servers are // only available for fallback because of TEST_F(DnsTransactionTest, HttpsFailureThenNotAvailable_Secure) { - config_.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + config_.secure_dns_mode = SecureDnsMode::kSecure; ConfigureDohServers(true /* use_post */, 3 /* num_doh_servers */, false /* make_available */); @@ -2037,9 +2031,8 @@ { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::SECURE, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kSecure, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2076,9 +2069,8 @@ // Expect server 0 to be preferred due to least recent failure. { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::SECURE, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kSecure, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2090,9 +2082,8 @@ ConfigureDohServers(false /* use_post */); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2109,9 +2100,8 @@ EXPECT_TRUE(failure.RunUntilDone(transaction_factory_.get())); std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2128,9 +2118,8 @@ EXPECT_TRUE(success.RunUntilDone(transaction_factory_.get())); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2148,9 +2137,8 @@ EXPECT_TRUE(last_failure.RunUntilDone(transaction_factory_.get())); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2162,9 +2150,8 @@ ConfigureDohServers(false /* use_post */); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2180,9 +2167,8 @@ ERR_CONNECTION_REFUSED, resolve_context_.get()); EXPECT_TRUE(failure.RunUntilDone(transaction_factory_.get())); std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2200,9 +2186,8 @@ EXPECT_TRUE(last_failure.RunUntilDone(transaction_factory_.get())); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); } @@ -2214,9 +2199,8 @@ ConfigureDohServers(false /* use_post */); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -2846,7 +2830,7 @@ // The first probe happens without any delay. RunUntilIdle(); std::unique_ptr<DnsServerIterator> doh_itr = resolve_context_->GetDohIterator( - session_->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session_.get()); + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); @@ -2989,9 +2973,8 @@ RunUntilIdle(); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -3045,17 +3028,15 @@ RunUntilIdle(); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); } { std::unique_ptr<DnsServerIterator> doh_itr2 = context2.GetDohIterator( - session_->config(), DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_FALSE(doh_itr2->AttemptAvailable()); } @@ -3068,8 +3049,7 @@ FastForwardBy(runner2->GetDelayUntilNextProbeForTest(0)); { std::unique_ptr<DnsServerIterator> doh_itr2 = context2.GetDohIterator( - session_->config(), DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr2->AttemptAvailable()); EXPECT_EQ(doh_itr2->GetNextAttemptIndex(), 0u); @@ -3099,7 +3079,7 @@ // The first probe happens without any delay. RunUntilIdle(); std::unique_ptr<DnsServerIterator> doh_itr = resolve_context_->GetDohIterator( - session_->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session_.get()); + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); @@ -3148,7 +3128,7 @@ // The first two probes (one for each runner) happen without any delay. RunUntilIdle(); std::unique_ptr<DnsServerIterator> doh_itr = resolve_context_->GetDohIterator( - session_->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session_.get()); + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); EXPECT_GT(runner1->GetDelayUntilNextProbeForTest(0), base::TimeDelta()); @@ -3190,7 +3170,7 @@ // The first two probes (one for each runner) happen without any delay. RunUntilIdle(); std::unique_ptr<DnsServerIterator> doh_itr = resolve_context_->GetDohIterator( - session_->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session_.get()); + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); EXPECT_GT(runner1->GetDelayUntilNextProbeForTest(0), base::TimeDelta()); @@ -3224,9 +3204,8 @@ RunUntilIdle(); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -3238,9 +3217,8 @@ RunUntilIdle(); { std::unique_ptr<DnsServerIterator> doh_itr = - resolve_context_->GetDohIterator(session_->config(), - DnsConfig::SecureDnsMode::AUTOMATIC, - session_.get()); + resolve_context_->GetDohIterator( + session_->config(), SecureDnsMode::kAutomatic, session_.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -3263,7 +3241,7 @@ // The first probe happens without any delay. RunUntilIdle(); std::unique_ptr<DnsServerIterator> doh_itr = resolve_context_->GetDohIterator( - session_->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session_.get()); + session_->config(), SecureDnsMode::kAutomatic, session_.get()); EXPECT_FALSE(doh_itr->AttemptAvailable());
diff --git a/net/dns/dns_util.cc b/net/dns/dns_util.cc index 9ad7d536..2883a07 100644 --- a/net/dns/dns_util.cc +++ b/net/dns/dns_util.cc
@@ -365,14 +365,13 @@ return entries.empty() ? "Other" : entries[0]->provider; } -std::string SecureDnsModeToString( - const DnsConfig::SecureDnsMode secure_dns_mode) { +std::string SecureDnsModeToString(const SecureDnsMode secure_dns_mode) { switch (secure_dns_mode) { - case DnsConfig::SecureDnsMode::OFF: + case SecureDnsMode::kOff: return "Off"; - case DnsConfig::SecureDnsMode::AUTOMATIC: + case SecureDnsMode::kAutomatic: return "Automatic"; - case DnsConfig::SecureDnsMode::SECURE: + case SecureDnsMode::kSecure: return "Secure"; } }
diff --git a/net/dns/dns_util.h b/net/dns/dns_util.h index ae1620016..00b5ff59 100644 --- a/net/dns/dns_util.h +++ b/net/dns/dns_util.h
@@ -14,9 +14,9 @@ #include "net/base/ip_endpoint.h" #include "net/base/net_export.h" #include "net/base/network_change_notifier.h" -#include "net/dns/dns_config.h" #include "net/dns/public/dns_over_https_server_config.h" #include "net/dns/public/dns_query_type.h" +#include "net/dns/public/secure_dns_mode.h" namespace net { @@ -140,7 +140,7 @@ const IPEndPoint& nameserver); NET_EXPORT_PRIVATE std::string SecureDnsModeToString( - const DnsConfig::SecureDnsMode secure_dns_mode); + const SecureDnsMode secure_dns_mode); } // namespace net
diff --git a/net/dns/host_resolver.h b/net/dns/host_resolver.h index 9468c62..5abb6265 100644 --- a/net/dns/host_resolver.h +++ b/net/dns/host_resolver.h
@@ -19,12 +19,12 @@ #include "net/base/completion_once_callback.h" #include "net/base/host_port_pair.h" #include "net/base/request_priority.h" -#include "net/dns/dns_config.h" #include "net/dns/dns_config_overrides.h" #include "net/dns/host_cache.h" #include "net/dns/host_resolver_source.h" #include "net/dns/public/dns_query_type.h" #include "net/dns/public/resolve_error_info.h" +#include "net/dns/public/secure_dns_mode.h" namespace base { class Value; @@ -245,8 +245,7 @@ bool is_speculative = false; // Set to override the resolver's default secure dns mode for this request. - base::Optional<DnsConfig::SecureDnsMode> secure_dns_mode_override = - base::nullopt; + base::Optional<SecureDnsMode> secure_dns_mode_override = base::nullopt; }; // Handler for an ongoing MDNS listening operation. Created by
diff --git a/net/dns/host_resolver_manager.cc b/net/dns/host_resolver_manager.cc index ee1ec4d..9a78419 100644 --- a/net/dns/host_resolver_manager.cc +++ b/net/dns/host_resolver_manager.cc
@@ -1090,7 +1090,7 @@ DnsQueryType query_type, ResolveContext* resolve_context, bool secure, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, Delegate* delegate, const NetLogWithSource& job_net_log, const base::TickClock* tick_clock) @@ -1749,7 +1749,7 @@ // Whether lookups in this DnsTask should occur using DoH or plaintext. const bool secure_; - const DnsConfig::SecureDnsMode secure_dns_mode_; + const SecureDnsMode secure_dns_mode_; // The listener to the results of this DnsTask. Delegate* delegate_; @@ -1795,7 +1795,7 @@ DnsQueryType query_type; HostResolverFlags flags; HostResolverSource source; - DnsConfig::SecureDnsMode secure_dns_mode; + SecureDnsMode secure_dns_mode; // TODO(ericorth@chromium.org): Use base::UnownedPtr once available. ResolveContext* resolve_context; }; @@ -1814,7 +1814,7 @@ HostResolverFlags host_resolver_flags, HostResolverSource requested_source, ResolveHostParameters::CacheUsage cache_usage, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, ResolveContext* resolve_context, HostCache* host_cache, std::deque<TaskType> tasks, @@ -2319,12 +2319,11 @@ bool secure) { DCHECK_NE(OK, failure_results.error()); - if (secure_dns_mode_ == DnsConfig::SecureDnsMode::SECURE) { + if (secure_dns_mode_ == SecureDnsMode::kSecure) { DCHECK(secure); UMA_HISTOGRAM_LONG_TIMES_100( "Net.DNS.SecureDnsTask.DnsModeSecure.FailureTime", duration); - } else if (secure_dns_mode_ == DnsConfig::SecureDnsMode::AUTOMATIC && - secure) { + } else if (secure_dns_mode_ == SecureDnsMode::kAutomatic && secure) { UMA_HISTOGRAM_LONG_TIMES_100( "Net.DNS.SecureDnsTask.DnsModeAutomatic.FailureTime", duration); } else { @@ -2667,7 +2666,7 @@ const HostResolverFlags host_resolver_flags_; const HostResolverSource requested_source_; const ResolveHostParameters::CacheUsage cache_usage_; - const DnsConfig::SecureDnsMode secure_dns_mode_; + const SecureDnsMode secure_dns_mode_; // TODO(ericorth@chromium.org): Use base::UnownedPtr once available. ResolveContext* const resolve_context_; // TODO(crbug.com/969847): Consider allowing requests within a single Job to @@ -2993,7 +2992,7 @@ DnsQueryType effective_query_type; HostResolverFlags effective_host_resolver_flags; - DnsConfig::SecureDnsMode effective_secure_dns_mode; + SecureDnsMode effective_secure_dns_mode; std::deque<TaskType> tasks; base::Optional<HostCache::EntryStaleness> stale_info; HostCache::Entry results = ResolveLocally( @@ -3030,14 +3029,14 @@ DnsQueryType dns_query_type, HostResolverSource source, HostResolverFlags flags, - base::Optional<DnsConfig::SecureDnsMode> secure_dns_mode_override, + base::Optional<SecureDnsMode> secure_dns_mode_override, ResolveHostParameters::CacheUsage cache_usage, const NetLogWithSource& source_net_log, HostCache* cache, ResolveContext* resolve_context, DnsQueryType* out_effective_query_type, HostResolverFlags* out_effective_host_resolver_flags, - DnsConfig::SecureDnsMode* out_effective_secure_dns_mode, + SecureDnsMode* out_effective_secure_dns_mode, std::deque<TaskType>* out_tasks, base::Optional<HostCache::EntryStaleness>* out_stale_info) { DCHECK(out_stale_info); @@ -3144,7 +3143,7 @@ void HostResolverManager::CreateAndStartJob( DnsQueryType effective_query_type, HostResolverFlags effective_host_resolver_flags, - DnsConfig::SecureDnsMode effective_secure_dns_mode, + SecureDnsMode effective_secure_dns_mode, std::deque<TaskType> tasks, RequestImpl* request) { DCHECK(!tasks.empty()); @@ -3347,13 +3346,13 @@ return job; } -DnsConfig::SecureDnsMode HostResolverManager::GetEffectiveSecureDnsMode( +SecureDnsMode HostResolverManager::GetEffectiveSecureDnsMode( const std::string& hostname, - base::Optional<DnsConfig::SecureDnsMode> secure_dns_mode_override) { + base::Optional<SecureDnsMode> secure_dns_mode_override) { const DnsConfig* config = dns_client_ ? dns_client_->GetEffectiveConfig() : nullptr; - DnsConfig::SecureDnsMode secure_dns_mode = DnsConfig::SecureDnsMode::OFF; + SecureDnsMode secure_dns_mode = SecureDnsMode::kOff; if (secure_dns_mode_override) { secure_dns_mode = secure_dns_mode_override.value(); } else if (config) { @@ -3367,7 +3366,7 @@ } void HostResolverManager::PushDnsTasks(bool proc_task_allowed, - DnsConfig::SecureDnsMode secure_dns_mode, + SecureDnsMode secure_dns_mode, bool insecure_tasks_allowed, bool allow_cache, bool prioritize_local_lookups, @@ -3382,14 +3381,14 @@ bool dns_tasks_allowed = !HaveTestProcOverride(); // Upgrade the insecure DnsTask depending on the secure dns mode. switch (secure_dns_mode) { - case DnsConfig::SecureDnsMode::SECURE: + case SecureDnsMode::kSecure: DCHECK(!allow_cache || out_tasks->front() == TaskType::SECURE_CACHE_LOOKUP); DCHECK(dns_client_->CanUseSecureDnsTransactions()); if (dns_tasks_allowed) out_tasks->push_back(TaskType::SECURE_DNS); break; - case DnsConfig::SecureDnsMode::AUTOMATIC: + case SecureDnsMode::kAutomatic: DCHECK(!allow_cache || out_tasks->front() == TaskType::CACHE_LOOKUP); if (dns_client_->FallbackFromSecureTransactionPreferred( resolve_context)) { @@ -3420,7 +3419,7 @@ out_tasks->push_back(TaskType::DNS); } break; - case DnsConfig::SecureDnsMode::OFF: + case SecureDnsMode::kOff: DCHECK(!allow_cache || out_tasks->front() == TaskType::CACHE_LOOKUP); if (dns_tasks_allowed && insecure_tasks_allowed) out_tasks->push_back(TaskType::DNS); @@ -3448,10 +3447,10 @@ DnsQueryType dns_query_type, HostResolverSource source, HostResolverFlags flags, - base::Optional<DnsConfig::SecureDnsMode> secure_dns_mode_override, + base::Optional<SecureDnsMode> secure_dns_mode_override, ResolveHostParameters::CacheUsage cache_usage, ResolveContext* resolve_context, - DnsConfig::SecureDnsMode* out_effective_secure_dns_mode, + SecureDnsMode* out_effective_secure_dns_mode, std::deque<TaskType>* out_tasks) { DCHECK(out_tasks->empty()); *out_effective_secure_dns_mode = @@ -3462,7 +3461,7 @@ bool allow_cache = cache_usage != ResolveHostParameters::CacheUsage::DISALLOWED; if (allow_cache) { - if (*out_effective_secure_dns_mode == DnsConfig::SecureDnsMode::SECURE) { + if (*out_effective_secure_dns_mode == SecureDnsMode::kSecure) { out_tasks->push_front(TaskType::SECURE_CACHE_LOOKUP); } else { out_tasks->push_front(TaskType::CACHE_LOOKUP); @@ -3487,7 +3486,7 @@ } else if (!ResemblesMulticastDNSName(hostname)) { bool proc_task_allowed = IsAddressType(dns_query_type) && - *out_effective_secure_dns_mode != DnsConfig::SecureDnsMode::SECURE; + *out_effective_secure_dns_mode != SecureDnsMode::kSecure; if (dns_client_ && dns_client_->GetEffectiveConfig()) { bool insecure_allowed = dns_client_->CanUseInsecureDnsTransactions() && @@ -3532,14 +3531,14 @@ DnsQueryType dns_query_type, HostResolverSource source, HostResolverFlags flags, - base::Optional<DnsConfig::SecureDnsMode> secure_dns_mode_override, + base::Optional<SecureDnsMode> secure_dns_mode_override, ResolveHostParameters::CacheUsage cache_usage, const IPAddress* ip_address, const NetLogWithSource& net_log, ResolveContext* resolve_context, DnsQueryType* out_effective_type, HostResolverFlags* out_effective_flags, - DnsConfig::SecureDnsMode* out_effective_secure_dns_mode, + SecureDnsMode* out_effective_secure_dns_mode, std::deque<TaskType>* out_tasks) { *out_effective_flags = flags | additional_resolver_flags_; *out_effective_type = dns_query_type;
diff --git a/net/dns/host_resolver_manager.h b/net/dns/host_resolver_manager.h index dd64a18..7d86fcd2 100644 --- a/net/dns/host_resolver_manager.h +++ b/net/dns/host_resolver_manager.h
@@ -31,6 +31,7 @@ #include "net/dns/host_resolver.h" #include "net/dns/host_resolver_proc.h" #include "net/dns/public/dns_query_type.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/dns/resolve_context.h" #include "net/dns/system_dns_config_change_notifier.h" #include "url/gurl.h" @@ -93,7 +94,6 @@ public: using MdnsListener = HostResolver::MdnsListener; using ResolveHostParameters = HostResolver::ResolveHostParameters; - using SecureDnsMode = DnsConfig::SecureDnsMode; // A request that allows explicit cancellation before destruction. Enables // callers (e.g. ContextHostResolver) to implement cancellation of requests on @@ -295,7 +295,7 @@ ResolveContext* resolve_context, DnsQueryType* out_effective_query_type, HostResolverFlags* out_effective_host_resolver_flags, - DnsConfig::SecureDnsMode* out_effective_secure_dns_mode, + SecureDnsMode* out_effective_secure_dns_mode, std::deque<TaskType>* out_tasks, base::Optional<HostCache::EntryStaleness>* out_stale_info); @@ -303,7 +303,7 @@ // |request|. void CreateAndStartJob(DnsQueryType effective_query_type, HostResolverFlags effective_host_resolver_flags, - DnsConfig::SecureDnsMode effective_secure_dns_mode, + SecureDnsMode effective_secure_dns_mode, std::deque<TaskType> tasks, RequestImpl* request); @@ -373,7 +373,7 @@ base::Optional<SecureDnsMode> secure_dns_mode_override, ResolveHostParameters::CacheUsage cache_usage, ResolveContext* resolve_context, - DnsConfig::SecureDnsMode* out_effective_secure_dns_mode, + SecureDnsMode* out_effective_secure_dns_mode, std::deque<TaskType>* out_tasks); // Determines "effective" request parameters using manager properties and IPv6 @@ -390,7 +390,7 @@ ResolveContext* resolve_context, DnsQueryType* out_effective_type, HostResolverFlags* out_effective_flags, - DnsConfig::SecureDnsMode* out_effective_secure_dns_mode, + SecureDnsMode* out_effective_secure_dns_mode, std::deque<TaskType>* out_tasks); // Probes IPv6 support and returns true if IPv6 support is enabled.
diff --git a/net/dns/host_resolver_manager_unittest.cc b/net/dns/host_resolver_manager_unittest.cc index 21727a7..32feedf 100644 --- a/net/dns/host_resolver_manager_unittest.cc +++ b/net/dns/host_resolver_manager_unittest.cc
@@ -3488,14 +3488,14 @@ config.nameservers.push_back(IPEndPoint(dns_ip, dns_protocol::kDefaultPort)); config.dns_over_https_servers.push_back({DnsOverHttpsServerConfig( "https://dns.example.com/", true /* use_post */)}); - config.secure_dns_mode = DnsConfig::SecureDnsMode::OFF; + config.secure_dns_mode = SecureDnsMode::kOff; EXPECT_TRUE(config.IsValid()); return config; } DnsConfig CreateUpgradableDnsConfig() { DnsConfig config; - config.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + config.secure_dns_mode = SecureDnsMode::kAutomatic; config.allow_dns_over_https_upgrade = true; // Cloudflare upgradeable IPs IPAddress dns_ip0(1, 0, 0, 1); @@ -4438,8 +4438,7 @@ ChangeDnsConfig(CreateValidDnsConfig()); HostResolver::ResolveHostParameters secure_parameters; - secure_parameters.secure_dns_mode_override = - DnsConfig::SecureDnsMode::AUTOMATIC; + secure_parameters.secure_dns_mode_override = SecureDnsMode::kAutomatic; ResolveHostResponseHelper response_secure(resolver_->CreateRequest( HostPortPair("automatic", 80), NetworkIsolationKey(), NetLogWithSource(), secure_parameters, resolve_context_.get(), @@ -4809,8 +4808,7 @@ // Secure DnsTasks should not be affected. HostResolver::ResolveHostParameters secure_parameters; - secure_parameters.secure_dns_mode_override = - DnsConfig::SecureDnsMode::AUTOMATIC; + secure_parameters.secure_dns_mode_override = SecureDnsMode::kAutomatic; ResolveHostResponseHelper secure_response(resolver_->CreateRequest( HostPortPair("automatic", 80), NetworkIsolationKey(), NetLogWithSource(), secure_parameters, resolve_context_.get(), @@ -4986,15 +4984,14 @@ false /* delay */); UseMockDnsClient(CreateValidDnsConfig(), std::move(rules)); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); // Create three requests. One with a SECURE mode override, one with no // mode override, and one with an AUTOMATIC mode override (which is a no-op // since the DnsConfig uses AUTOMATIC). HostResolver::ResolveHostParameters parameters_secure_override; - parameters_secure_override.secure_dns_mode_override = - DnsConfig::SecureDnsMode::SECURE; + parameters_secure_override.secure_dns_mode_override = SecureDnsMode::kSecure; ResolveHostResponseHelper secure_response(resolver_->CreateRequest( HostPortPair("a", 80), NetworkIsolationKey(), NetLogWithSource(), parameters_secure_override, resolve_context_.get(), @@ -5008,7 +5005,7 @@ HostResolver::ResolveHostParameters parameters_automatic_override; parameters_automatic_override.secure_dns_mode_override = - DnsConfig::SecureDnsMode::AUTOMATIC; + SecureDnsMode::kAutomatic; ResolveHostResponseHelper automatic_response1(resolver_->CreateRequest( HostPortPair("a", 80), NetworkIsolationKey(), NetLogWithSource(), parameters_automatic_override, resolve_context_.get(), @@ -5117,7 +5114,7 @@ TEST_F(HostResolverManagerDnsTest, DeleteWithSecureTransactions) { ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); ResolveHostResponseHelper response(resolver_->CreateRequest( @@ -5255,7 +5252,7 @@ UseMockDnsClient(CreateValidDnsConfig(), std::move(rules)); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); ResolveHostResponseHelper response0(resolver_->CreateRequest( @@ -5370,7 +5367,7 @@ false /* delay */); UseMockDnsClient(CreateValidDnsConfig(), std::move(rules)); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); ResolveHostResponseHelper response(resolver_->CreateRequest( @@ -5403,7 +5400,7 @@ ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); const std::pair<const HostCache::Key, HostCache::Entry>* cache_result; @@ -5459,7 +5456,7 @@ TEST_F(HostResolverManagerDnsTest, SecureDnsMode_Automatic_SecureCache) { ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); // Populate cache with a secure entry. @@ -5490,7 +5487,7 @@ TEST_F(HostResolverManagerDnsTest, SecureDnsMode_Automatic_InsecureCache) { ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); // Populate cache with an insecure entry. @@ -5525,7 +5522,7 @@ DnsConfigOverrides overrides; std::vector<DnsOverHttpsServerConfig> doh_servers; overrides.dns_over_https_servers = doh_servers; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); const std::pair<const HostCache::Key, HostCache::Entry>* cache_result; @@ -5586,7 +5583,7 @@ TEST_F(HostResolverManagerDnsTest, SecureDnsMode_Automatic_Unavailable) { ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); dns_client_->SetForceDohServerAvailable(false); @@ -5622,7 +5619,7 @@ set_allow_fallback_to_proctask(false); ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); dns_client_->SetForceDohServerAvailable(false); @@ -5668,7 +5665,7 @@ set_allow_fallback_to_proctask(false); ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); dns_client_->SetForceDohServerAvailable(false); @@ -5701,7 +5698,7 @@ TEST_F(HostResolverManagerDnsTest, SecureDnsMode_Automatic_Stale) { ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); // Populate cache with insecure entry. @@ -5736,7 +5733,7 @@ ChangeDnsConfig(CreateValidDnsConfig()); resolver_->SetInsecureDnsClientEnabled(false); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); const std::pair<const HostCache::Key, HostCache::Entry>* cache_result; @@ -5802,7 +5799,7 @@ config.dns_over_tls_active = true; ChangeDnsConfig(config); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); const std::pair<const HostCache::Key, HostCache::Entry>* cache_result; @@ -5873,7 +5870,7 @@ ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); const std::pair<const HostCache::Key, HostCache::Entry>* cache_result; @@ -5920,7 +5917,7 @@ ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); const std::pair<const HostCache::Key, HostCache::Entry>* cache_result; @@ -5940,7 +5937,7 @@ TEST_F(HostResolverManagerDnsTest, SecureDnsMode_Secure_Local_CacheMiss) { ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); HostResolver::ResolveHostParameters source_none_parameters; @@ -5971,7 +5968,7 @@ TEST_F(HostResolverManagerDnsTest, SecureDnsMode_Secure_Local_CacheHit) { ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); HostResolver::ResolveHostParameters source_none_parameters; @@ -6227,8 +6224,7 @@ // Secure DnsTasks should not be affected. HostResolver::ResolveHostParameters secure_parameters; - secure_parameters.secure_dns_mode_override = - DnsConfig::SecureDnsMode::AUTOMATIC; + secure_parameters.secure_dns_mode_override = SecureDnsMode::kAutomatic; ResolveHostResponseHelper response_secure(resolver_->CreateRequest( HostPortPair("automatic", 80), NetworkIsolationKey(), NetLogWithSource(), secure_parameters, resolve_context_.get(), @@ -6563,7 +6559,7 @@ // Switch to automatic mode. DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); HostCache::Key insecure_key = @@ -6605,7 +6601,7 @@ // Switch to secure mode. DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); HostCache::Key insecure_key = @@ -6862,7 +6858,7 @@ DnsConfigOverrides overrides; overrides.dns_over_https_servers.emplace( {DnsOverHttpsServerConfig(server, true)}); - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); base::Value config = resolver_->GetDnsConfigAsValue(); base::Value* doh_servers = config.FindListKey("doh_servers"); @@ -6879,7 +6875,7 @@ EXPECT_TRUE(server_template); EXPECT_EQ(*server_template, server); EXPECT_EQ(config.FindKey("secure_dns_mode")->GetInt(), - static_cast<int>(DnsConfig::SecureDnsMode::AUTOMATIC)); + static_cast<int>(SecureDnsMode::kAutomatic)); } TEST_F(HostResolverManagerDnsTest, AddDnsOverHttpsServerBeforeConfig) { @@ -6890,7 +6886,7 @@ DnsConfigOverrides overrides; overrides.dns_over_https_servers.emplace( {DnsOverHttpsServerConfig(server, true)}); - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); notifier.mock_network_change_notifier()->SetConnectionType( @@ -6912,7 +6908,7 @@ EXPECT_TRUE(server_template); EXPECT_EQ(*server_template, server); EXPECT_EQ(config.FindKey("secure_dns_mode")->GetInt(), - static_cast<int>(DnsConfig::SecureDnsMode::AUTOMATIC)); + static_cast<int>(SecureDnsMode::kAutomatic)); } TEST_F(HostResolverManagerDnsTest, AddDnsOverHttpsServerBeforeClient) { @@ -6923,7 +6919,7 @@ DnsConfigOverrides overrides; overrides.dns_over_https_servers.emplace( {DnsOverHttpsServerConfig(server, true)}); - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); notifier.mock_network_change_notifier()->SetConnectionType( @@ -6945,7 +6941,7 @@ EXPECT_TRUE(server_template); EXPECT_EQ(*server_template, server); EXPECT_EQ(config.FindKey("secure_dns_mode")->GetInt(), - static_cast<int>(DnsConfig::SecureDnsMode::AUTOMATIC)); + static_cast<int>(SecureDnsMode::kAutomatic)); } TEST_F(HostResolverManagerDnsTest, AddDnsOverHttpsServerAndThenRemove) { @@ -6956,7 +6952,7 @@ DnsConfigOverrides overrides; overrides.dns_over_https_servers.emplace( {DnsOverHttpsServerConfig(server, true)}); - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + overrides.secure_dns_mode = SecureDnsMode::kAutomatic; resolver_->SetDnsConfigOverrides(overrides); notifier.mock_network_change_notifier()->SetConnectionType( @@ -6980,7 +6976,7 @@ EXPECT_TRUE(server_template); EXPECT_EQ(*server_template, server); EXPECT_EQ(config.FindKey("secure_dns_mode")->GetInt(), - static_cast<int>(DnsConfig::SecureDnsMode::AUTOMATIC)); + static_cast<int>(SecureDnsMode::kAutomatic)); resolver_->SetDnsConfigOverrides(DnsConfigOverrides()); config = resolver_->GetDnsConfigAsValue(); @@ -6990,7 +6986,7 @@ return; EXPECT_EQ(doh_servers->GetList().size(), 0u); EXPECT_EQ(config.FindKey("secure_dns_mode")->GetInt(), - static_cast<int>(DnsConfig::SecureDnsMode::OFF)); + static_cast<int>(SecureDnsMode::kOff)); } // Basic test socket factory that allows creation of UDP sockets, but those @@ -7059,8 +7055,7 @@ const std::vector<DnsOverHttpsServerConfig> dns_over_https_servers = { DnsOverHttpsServerConfig("dns.example.com", true)}; overrides.dns_over_https_servers = dns_over_https_servers; - const DnsConfig::SecureDnsMode secure_dns_mode = - DnsConfig::SecureDnsMode::SECURE; + const SecureDnsMode secure_dns_mode = SecureDnsMode::kSecure; overrides.secure_dns_mode = secure_dns_mode; overrides.allow_dns_over_https_upgrade = true; const std::vector<std::string> disabled_upgrade_providers = {"provider_name"}; @@ -7388,7 +7383,7 @@ // SafeBrowsing family filter, SafeBrowsing security filter, and other IPs // not associated with hardcoded DoH services. DnsConfig original_config = CreateUpgradableDnsConfig(); - original_config.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + original_config.secure_dns_mode = SecureDnsMode::kSecure; ChangeDnsConfig(original_config); const DnsConfig* fetched_config = client_ptr->GetEffectiveConfig(); @@ -7542,7 +7537,7 @@ // SafeBrowsing family filter, SafeBrowsing security filter, and other IPs // not associated with hardcoded DoH services. DnsConfig original_config = CreateUpgradableDnsConfig(); - original_config.secure_dns_mode = DnsConfig::SecureDnsMode::AUTOMATIC; + original_config.secure_dns_mode = SecureDnsMode::kAutomatic; original_config.dns_over_tls_active = true; // Google DoT hostname @@ -8703,7 +8698,7 @@ std::unique_ptr<ResolveHostResponseHelper> DoIntegrityQuery(bool use_secure) { if (use_secure) { DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); } @@ -9301,7 +9296,7 @@ set_allow_fallback_to_proctask(false); ChangeDnsConfig(CreateValidDnsConfig()); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); ASSERT_TRUE(dns_client_->GetCurrentSession()); @@ -9334,7 +9329,7 @@ set_allow_fallback_to_proctask(false); InvalidateDnsConfig(); DnsConfigOverrides overrides; - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; resolver_->SetDnsConfigOverrides(overrides); ASSERT_FALSE(dns_client_->GetCurrentSession());
diff --git a/net/dns/mock_host_resolver.h b/net/dns/mock_host_resolver.h index 2be07a23..24a9eb8 100644 --- a/net/dns/mock_host_resolver.h +++ b/net/dns/mock_host_resolver.h
@@ -21,11 +21,11 @@ #include "base/threading/thread_checker.h" #include "net/base/completion_once_callback.h" #include "net/base/network_isolation_key.h" -#include "net/dns/dns_config.h" #include "net/dns/host_resolver.h" #include "net/dns/host_resolver_proc.h" #include "net/dns/host_resolver_source.h" #include "net/dns/public/dns_query_type.h" +#include "net/dns/public/secure_dns_mode.h" namespace base { class TickClock; @@ -200,8 +200,7 @@ // Returns the SecureDnsMode override of the last call to Resolve() (or // base::nullopt if Resolve() hasn't been called yet). - const base::Optional<DnsConfig::SecureDnsMode>& - last_secure_dns_mode_override() const { + const base::Optional<SecureDnsMode>& last_secure_dns_mode_override() const { return last_secure_dns_mode_override_; } @@ -270,7 +269,7 @@ RequestPriority last_request_priority_; base::Optional<NetworkIsolationKey> last_request_network_isolation_key_; - base::Optional<DnsConfig::SecureDnsMode> last_secure_dns_mode_override_; + base::Optional<SecureDnsMode> last_secure_dns_mode_override_; bool synchronous_mode_; bool ondemand_mode_; std::map<HostResolverSource, scoped_refptr<RuleBasedHostResolverProc>>
diff --git a/net/dns/public/BUILD.gn b/net/dns/public/BUILD.gn index 832312d..a8f56f6 100644 --- a/net/dns/public/BUILD.gn +++ b/net/dns/public/BUILD.gn
@@ -2,6 +2,10 @@ # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. +if (is_android) { + import("//build/config/android/rules.gni") +} + source_set("public") { # Due to circular dependencies, should only be depended on through //net. # Limit visibility to //net and other source_sets with the same access @@ -23,6 +27,7 @@ "doh_provider_entry.h", "resolve_error_info.cc", "resolve_error_info.h", + "secure_dns_mode.h", "util.cc", "util.h", ] @@ -32,6 +37,12 @@ public_deps = [ "//net:net_public_deps" ] } +if (is_android) { + java_cpp_enum("secure_dns_mode_generated_enum") { + sources = [ "secure_dns_mode.h" ] + } +} + source_set("tests") { testonly = true sources = [
diff --git a/net/dns/public/doh_provider_entry.cc b/net/dns/public/doh_provider_entry.cc index cc3def34..78a46c4 100644 --- a/net/dns/public/doh_provider_entry.cc +++ b/net/dns/public/doh_provider_entry.cc
@@ -134,13 +134,14 @@ "https://nextdns.io/privacy" /* privacy_policy */, false /* display_globally */, {"US"} /* display_countries */), new DohProviderEntry( - "OpenDNS", base::nullopt /* provider_id_for_histogram */, + "OpenDNS", DohProviderIdForHistogram::kOpenDns, {"208.67.222.222", "208.67.220.220", "2620:119:35::35", "2620:119:53::53"}, {""} /* dns_over_tls_hostnames */, - "https://doh.opendns.com/dns-query{?dns}", "" /* ui_name */, - "" /* privacy_policy */, false /* display_globally */, - {} /* display_countries */), + "https://doh.opendns.com/dns-query{?dns}", "OpenDNS" /* ui_name */, + "https://www.cisco.com/c/en/us/about/legal/" + "privacy-full.html" /* privacy_policy */, + true /* display_globally */, {} /* display_countries */), new DohProviderEntry( "OpenDNSFamily", base::nullopt /* provider_id_for_histogram */, {"208.67.222.123", "208.67.220.123", "2620:119:35::123",
diff --git a/net/dns/public/doh_provider_entry.h b/net/dns/public/doh_provider_entry.h index 2db1bc2..5a43343 100644 --- a/net/dns/public/doh_provider_entry.h +++ b/net/dns/public/doh_provider_entry.h
@@ -28,7 +28,8 @@ kDnsSb = 6, kCznic = 7, kNextDns = 8, - kMaxValue = kNextDns, + kOpenDns = 9, + kMaxValue = kOpenDns, }; // Represents insecure DNS, DoT, and DoH services run by the same provider.
diff --git a/net/dns/public/secure_dns_mode.h b/net/dns/public/secure_dns_mode.h new file mode 100644 index 0000000..96a6977 --- /dev/null +++ b/net/dns/public/secure_dns_mode.h
@@ -0,0 +1,26 @@ +// Copyright 2020 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 NET_DNS_PUBLIC_SECURE_DNS_MODE_H_ +#define NET_DNS_PUBLIC_SECURE_DNS_MODE_H_ + +namespace net { + +// GENERATED_JAVA_ENUM_PACKAGE: org.chromium.net +// The SecureDnsMode specifies what types of lookups (secure/insecure) should +// be performed and in what order when resolving a specific query. The int +// values should not be changed as they are logged. +enum class SecureDnsMode : int { + // In OFF mode, no DoH lookups should be performed. + kOff = 0, + // In AUTOMATIC mode, DoH lookups should be performed first if DoH is + // available, and insecure DNS lookups should be performed as a fallback. + kAutomatic = 1, + // In SECURE mode, only DoH lookups should be performed. + kSecure = 2, +}; + +} // namespace net + +#endif // NET_DNS_PUBLIC_SECURE_DNS_MODE_H_
diff --git a/net/dns/resolve_context.cc b/net/dns/resolve_context.cc index 57b75f656..1a2b7fb 100644 --- a/net/dns/resolve_context.cc +++ b/net/dns/resolve_context.cc
@@ -108,7 +108,7 @@ std::unique_ptr<DnsServerIterator> ResolveContext::GetDohIterator( const DnsConfig& config, - const DnsConfig::SecureDnsMode& mode, + const SecureDnsMode& mode, const DnsSession* session) { // Make the iterator even if the session differs. The first call to the member // functions will catch the out of date session.
diff --git a/net/dns/resolve_context.h b/net/dns/resolve_context.h index bcbac64..1a96eff1 100644 --- a/net/dns/resolve_context.h +++ b/net/dns/resolve_context.h
@@ -18,6 +18,7 @@ #include "net/base/isolation_info.h" #include "net/base/net_export.h" #include "net/dns/dns_config.h" +#include "net/dns/public/secure_dns_mode.h" namespace net { @@ -68,10 +69,9 @@ ~ResolveContext() override; // Returns an iterator for DoH DNS servers. - std::unique_ptr<DnsServerIterator> GetDohIterator( - const DnsConfig& config, - const DnsConfig::SecureDnsMode& mode, - const DnsSession* session); + std::unique_ptr<DnsServerIterator> GetDohIterator(const DnsConfig& config, + const SecureDnsMode& mode, + const DnsSession* session); // Returns an iterator for classic DNS servers. std::unique_ptr<DnsServerIterator> GetClassicDnsIterator(
diff --git a/net/dns/resolve_context_unittest.cc b/net/dns/resolve_context_unittest.cc index 2b432fc..c246b34 100644 --- a/net/dns/resolve_context_unittest.cc +++ b/net/dns/resolve_context_unittest.cc
@@ -122,7 +122,7 @@ EXPECT_EQ(context.NumAvailableDohServers(session.get()), 0u); std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); } @@ -143,7 +143,7 @@ session.get()); EXPECT_EQ(context.NumAvailableDohServers(session.get()), 1u); std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -161,7 +161,7 @@ session.get()); std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); EXPECT_EQ(0u, context.NumAvailableDohServers(session.get())); @@ -187,7 +187,7 @@ session2.get()); std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session1->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session1.get()); + session1->config(), SecureDnsMode::kAutomatic, session1.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); EXPECT_EQ(0u, context.NumAvailableDohServers(session1.get())); @@ -216,7 +216,7 @@ session.get()); EXPECT_EQ(context.NumAvailableDohServers(session.get()), 1u); std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -234,7 +234,7 @@ false /* network_change */); std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); } @@ -250,7 +250,7 @@ false /* network_change */); std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::SECURE, session.get()); + session->config(), SecureDnsMode::kSecure, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -660,7 +660,7 @@ for (size_t i = 0; i < ResolveContext::kAutomaticModeFailureLimit; i++) { std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -670,7 +670,7 @@ ERR_FAILED, session.get()); } std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); EXPECT_FALSE(doh_itr->AttemptAvailable()); EXPECT_EQ(0u, context.NumAvailableDohServers(session.get())); @@ -696,7 +696,7 @@ for (size_t i = 0; i < ResolveContext::kAutomaticModeFailureLimit - 1; i++) { std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -706,7 +706,7 @@ } { std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -717,7 +717,7 @@ session.get()); { std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -730,7 +730,7 @@ ERR_FAILED, session.get()); { std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -768,7 +768,7 @@ session.get()); { std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 1u); @@ -845,7 +845,7 @@ // Expect server preference to change after |config.attempts| failures. for (int i = 0; i < config.attempts; i++) { std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 0u); @@ -861,7 +861,7 @@ } std::unique_ptr<DnsServerIterator> doh_itr = context.GetDohIterator( - session->config(), DnsConfig::SecureDnsMode::AUTOMATIC, session.get()); + session->config(), SecureDnsMode::kAutomatic, session.get()); ASSERT_TRUE(doh_itr->AttemptAvailable()); EXPECT_EQ(doh_itr->GetNextAttemptIndex(), 2u);
diff --git a/net/http/http_proxy_connect_job_unittest.cc b/net/http/http_proxy_connect_job_unittest.cc index 1a049b1..395322f0 100644 --- a/net/http/http_proxy_connect_job_unittest.cc +++ b/net/http/http_proxy_connect_job_unittest.cc
@@ -24,6 +24,7 @@ #include "net/base/network_isolation_key.h" #include "net/base/test_proxy_delegate.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/http/http_network_session.h" #include "net/nqe/network_quality_estimator_test_util.h" #include "net/socket/client_socket_handle.h" @@ -886,7 +887,7 @@ .has_value()); if (disable_secure_dns) { EXPECT_EQ( - net::DnsConfig::SecureDnsMode::OFF, + net::SecureDnsMode::kOff, session_deps_.host_resolver->last_secure_dns_mode_override().value()); } }
diff --git a/net/http/http_stream_factory_unittest.cc b/net/http/http_stream_factory_unittest.cc index 527ac742..c6f6e0f51 100644 --- a/net/http/http_stream_factory_unittest.cc +++ b/net/http/http_stream_factory_unittest.cc
@@ -32,6 +32,7 @@ #include "net/cert/mock_cert_verifier.h" #include "net/cert/multi_log_ct_verifier.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/http/bidirectional_stream_impl.h" #include "net/http/bidirectional_stream_request_info.h" #include "net/http/http_auth_handler_factory.h" @@ -1204,7 +1205,7 @@ waiter.WaitForStream(); EXPECT_EQ( - net::DnsConfig::SecureDnsMode::OFF, + net::SecureDnsMode::kOff, session_deps.host_resolver->last_secure_dns_mode_override().value()); EXPECT_EQ(GetSocketPoolGroupCount(ssl_pool), 2); }
diff --git a/net/http/transport_security_state_static.json b/net/http/transport_security_state_static.json index e8de50a2..0ef249e 100644 --- a/net/http/transport_security_state_static.json +++ b/net/http/transport_security_state_static.json
@@ -91,7 +91,9 @@ "Tor2", "Tor3", "LetsEncryptAuthorityPrimary_X1_X3", - "LetsEncryptAuthorityBackup_X2_X4" + "LetsEncryptAuthorityBackup_X2_X4", + "R3LetsEncrypt", + "R4LetsEncrypt" ] }, {
diff --git a/net/http/transport_security_state_static.pins b/net/http/transport_security_state_static.pins index 370bd53..27610e1a 100644 --- a/net/http/transport_security_state_static.pins +++ b/net/http/transport_security_state_static.pins
@@ -1650,6 +1650,72 @@ +YAL3YUmrvdoRBlASOTmNJmXSo9qvMYPa3DEomAPoFQFZqsSN6kuqDEIqMA= -----END CERTIFICATE----- +# From https://letsencrypt.org/certificates/ +R3LetsEncrypt +-----BEGIN CERTIFICATE----- +MIIFFjCCAv6gAwIBAgIRAJErCErPDBinU/bWLiWnX1owDQYJKoZIhvcNAQELBQAw +TzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh +cmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwHhcNMjAwOTA0MDAwMDAw +WhcNMjUwOTE1MTYwMDAwWjAyMQswCQYDVQQGEwJVUzEWMBQGA1UEChMNTGV0J3Mg +RW5jcnlwdDELMAkGA1UEAxMCUjMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK +AoIBAQC7AhUozPaglNMPEuyNVZLD+ILxmaZ6QoinXSaqtSu5xUyxr45r+XXIo9cP +R5QUVTVXjJ6oojkZ9YI8QqlObvU7wy7bjcCwXPNZOOftz2nwWgsbvsCUJCWH+jdx +sxPnHKzhm+/b5DtFUkWWqcFTzjTIUu61ru2P3mBw4qVUq7ZtDpelQDRrK9O8Zutm +NHz6a4uPVymZ+DAXXbpyb/uBxa3Shlg9F8fnCbvxK/eG3MHacV3URuPMrSXBiLxg +Z3Vms/EY96Jc5lP/Ooi2R6X/ExjqmAl3P51T+c8B5fWmcBcUr2Ok/5mzk53cU6cG +/kiFHaFpriV1uxPMUgP17VGhi9sVAgMBAAGjggEIMIIBBDAOBgNVHQ8BAf8EBAMC +AYYwHQYDVR0lBBYwFAYIKwYBBQUHAwIGCCsGAQUFBwMBMBIGA1UdEwEB/wQIMAYB +Af8CAQAwHQYDVR0OBBYEFBQusxe3WFbLrlAJQOYfr52LFMLGMB8GA1UdIwQYMBaA +FHm0WeZ7tuXkAXOACIjIGlj26ZtuMDIGCCsGAQUFBwEBBCYwJDAiBggrBgEFBQcw +AoYWaHR0cDovL3gxLmkubGVuY3Iub3JnLzAnBgNVHR8EIDAeMBygGqAYhhZodHRw +Oi8veDEuYy5sZW5jci5vcmcvMCIGA1UdIAQbMBkwCAYGZ4EMAQIBMA0GCysGAQQB +gt8TAQEBMA0GCSqGSIb3DQEBCwUAA4ICAQCFyk5HPqP3hUSFvNVneLKYY611TR6W +PTNlclQtgaDqw+34IL9fzLdwALduO/ZelN7kIJ+m74uyA+eitRY8kc607TkC53wl +ikfmZW4/RvTZ8M6UK+5UzhK8jCdLuMGYL6KvzXGRSgi3yLgjewQtCPkIVz6D2QQz +CkcheAmCJ8MqyJu5zlzyZMjAvnnAT45tRAxekrsu94sQ4egdRCnbWSDtY7kh+BIm +lJNXoB1lBMEKIq4QDUOXoRgffuDghje1WrG9ML+Hbisq/yFOGwXD9RiX8F6sw6W4 +avAuvDszue5L3sz85K+EC4Y/wFVDNvZo4TYXao6Z0f+lQKc0t8DQYzk1OXVu8rp2 +yJMC6alLbBfODALZvYH7n7do1AZls4I9d1P4jnkDrQoxB3UqQ9hVl3LEKQ73xF1O +yK5GhDDX8oVfGKF5u+decIsH4YaTw7mP3GFxJSqv3+0lUFJoi5Lc5da149p90Ids +hCExroL1+7mryIkXPeFM5TgO9r0rvZaBFOvV2z0gp35Z0+L4WPlbuEjN/lxPFin+ +HlUjr8gRsI3qfJOQFy/9rKIJR0Y/8Omwt/8oTWgy1mdeHmmjk7j1nYsvC9JSQ6Zv +MldlTTKB3zhThV1+XWYp6rjd5JW1zbVWEkLNxE7GJThEUG3szgBVGP7pSWTUTsqX +nLRbwHOoq7hHwg== +-----END CERTIFICATE----- + +# From https://letsencrypt.org/certificates/ +R4LetsEncrypt +-----BEGIN CERTIFICATE----- +MIIFFjCCAv6gAwIBAgIRAIp5IlCr5SxSbO7Pf8lC3WIwDQYJKoZIhvcNAQELBQAw +TzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh +cmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwHhcNMjAwOTA0MDAwMDAw +WhcNMjUwOTE1MTYwMDAwWjAyMQswCQYDVQQGEwJVUzEWMBQGA1UEChMNTGV0J3Mg +RW5jcnlwdDELMAkGA1UEAxMCUjQwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK +AoIBAQCzKNx3KdPnkb7ztwoAx/vyVQslImNTNq/pCCDfDa8oPs3Gq1e2naQlGaXS +Mm1Jpgi5xy+hm5PFIEBrhDEgoo4wYCVg79kaiT8faXGy2uo/c0HEkG9m/X2eWNh3 +z81ZdUTJoQp7nz8bDjpmb7Z1z4vLr53AcMX/0oIKr13N4uichZSk5gA16H5OOYHH +IYlgd+odlvKLg3tHxG0ywFJ+Ix5FtXHuo+8XwgOpk4nd9Z/buvHa4H6Xh3GBHhqC +VuQ+fBiiCOUWX6j6qOBIUU0YFKAMo+W2yrO1VRJrcsdafzuM+efZ0Y4STTMzAyrx +E+FCPMIuWWAubeAHRzNl39Jnyk2FAgMBAAGjggEIMIIBBDAOBgNVHQ8BAf8EBAMC +AYYwHQYDVR0lBBYwFAYIKwYBBQUHAwIGCCsGAQUFBwMBMBIGA1UdEwEB/wQIMAYB +Af8CAQAwHQYDVR0OBBYEFDadPuCxQPYnLHy/jZ0xivZUpkYmMB8GA1UdIwQYMBaA +FHm0WeZ7tuXkAXOACIjIGlj26ZtuMDIGCCsGAQUFBwEBBCYwJDAiBggrBgEFBQcw +AoYWaHR0cDovL3gxLmkubGVuY3Iub3JnLzAnBgNVHR8EIDAeMBygGqAYhhZodHRw +Oi8veDEuYy5sZW5jci5vcmcvMCIGA1UdIAQbMBkwCAYGZ4EMAQIBMA0GCysGAQQB +gt8TAQEBMA0GCSqGSIb3DQEBCwUAA4ICAQCJbu5CalWO+H+Az0lmIG14DXmlYHQE +k26umjuCyioWs2icOlZznPTcZvbfq02YPHGTCu3ctggVDULJ+fwOxKekzIqeyLNk +p8dyFwSAr23DYBIVeXDpxHhShvv0MLJzqqDFBTHYe1X5X2Y7oogy+UDJxV2N24/g +Z8lxG4Vr2/VEfUOrw4Tosl5Z+1uzOdvTyBcxD/E5rGgTLczmulctHy3IMTmdTFr0 +FnU0/HMQoquWQuODhFqzMqNcsdbjANUBwOEQrKI8Sy6+b84kHP7PtO+S4Ik8R2k7 +ZeMlE1JmxBi/PZU860YlwT8/qOYToCHVyDjhv8qutbf2QnUl3SV86th2I1QQE14s +0y7CdAHcHkw3sAEeYGkwCA74MO+VFtnYbf9B2JBOhyyWb5087rGzitu5MTAW41X9 +DwTeXEg+a24tAeht+Y1MionHUwa4j7FB/trN3Fnb/r90+4P66ZETVIEcjseUSMHO +w6yqv10/H/dw/8r2EDUincBBX3o9DL3SadqragkKy96HtMiLcqMMGAPm0gti1b6f +bnvOdr0mrIVIKX5nzOeGZORaYLoSD4C8qvFT7U+Um6DMo36cVDNsPmkF575/s3C2 +CxGiCPQqVxPgfNSh+2CPd2Xv04lNeuw6gG89DlOhHuoFKRlmPnom+gwqhz3ZXMfz +TfmvjrBokzCICA== +-----END CERTIFICATE----- + # From https://www.identrust.com/certificates/trustid/root-download-x3.html # (Linked from https://letsencrypt.org/certificates/#cross-signing ) DSTRootCAX3
diff --git a/net/quic/crypto/proof_verifier_chromium.cc b/net/quic/crypto/proof_verifier_chromium.cc index f8629d7d..2253e20 100644 --- a/net/quic/crypto/proof_verifier_chromium.cc +++ b/net/quic/crypto/proof_verifier_chromium.cc
@@ -43,7 +43,6 @@ quic::ProofVerifyDetails* ProofVerifyDetailsChromium::Clone() const { ProofVerifyDetailsChromium* other = new ProofVerifyDetailsChromium; other->cert_verify_result = cert_verify_result; - other->ct_verify_result = ct_verify_result; return other; } @@ -242,7 +241,7 @@ // external communication. cert_transparency_verifier_->Verify( hostname, cert_.get(), std::string(), cert_sct, - &verify_details_->ct_verify_result.scts, net_log_); + &verify_details_->cert_verify_result.scts, net_log_); // We call VerifySignature first to avoid copying of server_config and // signature. @@ -291,7 +290,7 @@ // external communication. cert_transparency_verifier_->Verify( hostname, cert_.get(), std::string(), cert_sct, - &verify_details_->ct_verify_result.scts, net_log_); + &verify_details_->cert_verify_result.scts, net_log_); return VerifyCert(hostname, port, ocsp_response, cert_sct, error_details, verify_details, std::move(callback)); @@ -421,16 +420,18 @@ // If the connection was good, check HPKP and CT status simultaneously, // but prefer to treat the HPKP error as more serious, if there was one. if (result == OK) { - ct::SCTList verified_scts = ct::SCTsMatchingStatus( - verify_details_->ct_verify_result.scts, ct::SCT_STATUS_OK); - - verify_details_->ct_verify_result.policy_compliance = + ct::SCTList verified_scts; + for (const auto& sct_and_status : cert_verify_result.scts) { + if (sct_and_status.status == ct::SCT_STATUS_OK) + verified_scts.push_back(sct_and_status.sct); + } + verify_details_->cert_verify_result.policy_compliance = policy_enforcer_->CheckCompliance( cert_verify_result.verified_cert.get(), verified_scts, net_log_); if (verify_details_->cert_verify_result.cert_status & CERT_STATUS_IS_EV) { - if (verify_details_->ct_verify_result.policy_compliance != + if (verify_details_->cert_verify_result.policy_compliance != ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS && - verify_details_->ct_verify_result.policy_compliance != + verify_details_->cert_verify_result.policy_compliance != ct::CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY) { verify_details_->cert_verify_result.cert_status |= CERT_STATUS_CT_COMPLIANCE_FAILED; @@ -443,7 +444,7 @@ if (verify_details_->cert_verify_result.is_issued_by_known_root) { UMA_HISTOGRAM_ENUMERATION( "Net.CertificateTransparency.EVCompliance2.QUIC", - verify_details_->ct_verify_result.policy_compliance, + cert_verify_result.policy_compliance, ct::CTPolicyCompliance::CT_POLICY_COUNT); } } @@ -453,7 +454,7 @@ if (verify_details_->cert_verify_result.is_issued_by_known_root) { UMA_HISTOGRAM_ENUMERATION( "Net.CertificateTransparency.ConnectionComplianceStatus2.QUIC", - verify_details_->ct_verify_result.policy_compliance, + verify_details_->cert_verify_result.policy_compliance, ct::CTPolicyCompliance::CT_POLICY_COUNT); } @@ -464,12 +465,11 @@ cert_verify_result.is_issued_by_known_root, cert_verify_result.public_key_hashes, cert_verify_result.verified_cert.get(), cert_.get(), - verify_details_->ct_verify_result.scts, + cert_verify_result.scts, TransportSecurityState::ENABLE_EXPECT_CT_REPORTS, - verify_details_->ct_verify_result.policy_compliance, + cert_verify_result.policy_compliance, proof_verifier_->network_isolation_key_); if (ct_requirement_status != TransportSecurityState::CT_NOT_REQUIRED) { - verify_details_->ct_verify_result.policy_compliance_required = true; if (verify_details_->cert_verify_result.is_issued_by_known_root) { // Record the CT compliance of connections for which compliance is // required; this helps answer the question: "Of all connections that @@ -478,19 +478,16 @@ UMA_HISTOGRAM_ENUMERATION( "Net.CertificateTransparency.CTRequiredConnectionComplianceStatus2." "QUIC", - verify_details_->ct_verify_result.policy_compliance, + cert_verify_result.policy_compliance, ct::CTPolicyCompliance::CT_POLICY_COUNT); } - } else { - verify_details_->ct_verify_result.policy_compliance_required = false; } if (sct_auditing_delegate_ && sct_auditing_delegate_->IsSCTAuditingEnabled()) { sct_auditing_delegate_->MaybeEnqueueReport( HostPortPair(hostname_, port_), - cert_verify_result.verified_cert.get(), - verify_details_->ct_verify_result.scts); + cert_verify_result.verified_cert.get(), cert_verify_result.scts); } switch (ct_requirement_status) {
diff --git a/net/quic/crypto/proof_verifier_chromium.h b/net/quic/crypto/proof_verifier_chromium.h index 4884840..8468a9d 100644 --- a/net/quic/crypto/proof_verifier_chromium.h +++ b/net/quic/crypto/proof_verifier_chromium.h
@@ -15,7 +15,6 @@ #include "net/base/net_export.h" #include "net/base/network_isolation_key.h" #include "net/cert/cert_verify_result.h" -#include "net/cert/ct_verify_result.h" #include "net/cert/x509_certificate.h" #include "net/log/net_log_with_source.h" #include "net/third_party/quiche/src/quic/core/crypto/proof_verifier.h" @@ -41,7 +40,6 @@ quic::ProofVerifyDetails* Clone() const override; CertVerifyResult cert_verify_result; - ct::CTVerifyResult ct_verify_result; // pinning_failure_log contains a message produced by // TransportSecurityState::PKPState::CheckPublicKeyPins in the event of a
diff --git a/net/quic/crypto/proof_verifier_chromium_test.cc b/net/quic/crypto/proof_verifier_chromium_test.cc index b176100..cc3852a0 100644 --- a/net/quic/crypto/proof_verifier_chromium_test.cc +++ b/net/quic/crypto/proof_verifier_chromium_test.cc
@@ -190,17 +190,17 @@ void CheckSCT(bool sct_expected_ok) { ProofVerifyDetailsChromium* proof_details = reinterpret_cast<ProofVerifyDetailsChromium*>(details_.get()); - const ct::CTVerifyResult& ct_verify_result = - proof_details->ct_verify_result; + const CertVerifyResult& cert_verify_result = + proof_details->cert_verify_result; if (sct_expected_ok) { - ASSERT_TRUE(ct::CheckForSingleVerifiedSCTInResult(ct_verify_result.scts, + EXPECT_TRUE(ct::CheckForSingleVerifiedSCTInResult(cert_verify_result.scts, kLogDescription)); - ASSERT_TRUE(ct::CheckForSCTOrigin( - ct_verify_result.scts, + EXPECT_TRUE(ct::CheckForSCTOrigin( + cert_verify_result.scts, ct::SignedCertificateTimestamp::SCT_FROM_TLS_EXTENSION)); } else { - EXPECT_EQ(1U, ct_verify_result.scts.size()); - EXPECT_EQ(ct::SCT_STATUS_LOG_UNKNOWN, ct_verify_result.scts[0].status); + ASSERT_EQ(1U, cert_verify_result.scts.size()); + EXPECT_EQ(ct::SCT_STATUS_LOG_UNKNOWN, cert_verify_result.scts[0].status); } } @@ -1066,112 +1066,6 @@ } } -// Tests that when CT is required but the connection is not compliant, the -// relevant flag is set in the CTVerifyResult. -TEST_F(ProofVerifierChromiumTest, CTRequirementsFlagNotMet) { - dummy_result_.is_issued_by_known_root = true; - MockCertVerifier dummy_verifier; - dummy_verifier.AddResultForCert(test_cert_.get(), dummy_result_, OK); - - // Set up CT. - MockRequireCTDelegate require_ct_delegate; - transport_security_state_.SetRequireCTDelegate(&require_ct_delegate); - EXPECT_CALL(require_ct_delegate, IsCTRequiredForHost(_, _, _)) - .WillRepeatedly(Return(TransportSecurityState::RequireCTDelegate:: - CTRequirementLevel::REQUIRED)); - EXPECT_CALL(ct_policy_enforcer_, CheckCompliance(_, _, _)) - .WillRepeatedly( - Return(ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS)); - - ProofVerifierChromium proof_verifier( - &dummy_verifier, &ct_policy_enforcer_, &transport_security_state_, - ct_verifier_.get(), nullptr, {}, NetworkIsolationKey()); - - { - std::unique_ptr<DummyProofVerifierCallback> callback( - new DummyProofVerifierCallback); - proof_verifier.VerifyProof( - kTestHostname, kTestPort, kTestConfig, kTestTransportVersion, - kTestChloHash, certs_, kTestEmptySCT, GetTestSignature(), - verify_context_.get(), &error_details_, &details_, std::move(callback)); - - // The flag should be set in the CTVerifyResult. - ProofVerifyDetailsChromium* proof_details = - reinterpret_cast<ProofVerifyDetailsChromium*>(details_.get()); - const ct::CTVerifyResult& ct_verify_result = - proof_details->ct_verify_result; - EXPECT_TRUE(ct_verify_result.policy_compliance_required); - } - - { - std::unique_ptr<DummyProofVerifierCallback> callback( - new DummyProofVerifierCallback); - proof_verifier.VerifyCertChain( - kTestHostname, kTestPort, certs_, kTestEmptyOCSPResponse, kTestEmptySCT, - verify_context_.get(), &error_details_, &details_, std::move(callback)); - - // The flag should be set in the CTVerifyResult. - ProofVerifyDetailsChromium* proof_details = - reinterpret_cast<ProofVerifyDetailsChromium*>(details_.get()); - const ct::CTVerifyResult& ct_verify_result = - proof_details->ct_verify_result; - EXPECT_TRUE(ct_verify_result.policy_compliance_required); - } -} - -// Tests that when CT is required and the connection is compliant, the relevant -// flag is set in the CTVerifyResult. -TEST_F(ProofVerifierChromiumTest, CTRequirementsFlagMet) { - dummy_result_.is_issued_by_known_root = true; - MockCertVerifier dummy_verifier; - dummy_verifier.AddResultForCert(test_cert_.get(), dummy_result_, OK); - - // Set up CT. - MockRequireCTDelegate require_ct_delegate; - transport_security_state_.SetRequireCTDelegate(&require_ct_delegate); - EXPECT_CALL(require_ct_delegate, IsCTRequiredForHost(_, _, _)) - .WillRepeatedly(Return(TransportSecurityState::RequireCTDelegate:: - CTRequirementLevel::REQUIRED)); - EXPECT_CALL(ct_policy_enforcer_, CheckCompliance(_, _, _)) - .WillRepeatedly( - Return(ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS)); - - ProofVerifierChromium proof_verifier( - &dummy_verifier, &ct_policy_enforcer_, &transport_security_state_, - ct_verifier_.get(), nullptr, {}, NetworkIsolationKey()); - - { - std::unique_ptr<DummyProofVerifierCallback> callback( - new DummyProofVerifierCallback); - proof_verifier.VerifyProof( - kTestHostname, kTestPort, kTestConfig, kTestTransportVersion, - kTestChloHash, certs_, kTestEmptySCT, GetTestSignature(), - verify_context_.get(), &error_details_, &details_, std::move(callback)); - - // The flag should be set in the CTVerifyResult. - ProofVerifyDetailsChromium* proof_details = - reinterpret_cast<ProofVerifyDetailsChromium*>(details_.get()); - const ct::CTVerifyResult& ct_verify_result = - proof_details->ct_verify_result; - EXPECT_TRUE(ct_verify_result.policy_compliance_required); - } - - { - std::unique_ptr<DummyProofVerifierCallback> callback( - new DummyProofVerifierCallback); - proof_verifier.VerifyCertChain( - kTestHostname, kTestPort, certs_, kTestEmptyOCSPResponse, kTestEmptySCT, - verify_context_.get(), &error_details_, &details_, std::move(callback)); - - // The flag should be set in the CTVerifyResult. - ProofVerifyDetailsChromium* proof_details = - reinterpret_cast<ProofVerifyDetailsChromium*>(details_.get()); - const ct::CTVerifyResult& ct_verify_result = - proof_details->ct_verify_result; - EXPECT_TRUE(ct_verify_result.policy_compliance_required); - } -} - TEST_F(ProofVerifierChromiumTest, UnknownRootRejected) { dummy_result_.is_issued_by_known_root = false;
diff --git a/net/quic/quic_chromium_client_session.cc b/net/quic/quic_chromium_client_session.cc index 5cf4c1c..2777e7d 100644 --- a/net/quic/quic_chromium_client_session.cc +++ b/net/quic/quic_chromium_client_session.cc
@@ -29,6 +29,7 @@ #include "net/base/network_isolation_key.h" #include "net/base/privacy_mode.h" #include "net/base/url_util.h" +#include "net/cert/signed_certificate_timestamp_and_status.h" #include "net/http/transport_security_state.h" #include "net/log/net_log_event_type.h" #include "net/log/net_log_source_type.h" @@ -1293,7 +1294,8 @@ ssl_info->pinning_failure_log = pinning_failure_log_; ssl_info->is_fatal_cert_error = is_fatal_cert_error_; - ssl_info->UpdateCertificateTransparencyInfo(*ct_verify_result_); + ssl_info->signed_certificate_timestamps = cert_verify_result_->scts; + ssl_info->ct_policy_compliance = cert_verify_result_->policy_compliance; const auto& crypto_params = crypto_stream_->crypto_negotiated_params(); uint16_t cipher_suite; @@ -2517,9 +2519,6 @@ cert_verify_result_.reset( new CertVerifyResult(verify_details_chromium->cert_verify_result)); pinning_failure_log_ = verify_details_chromium->pinning_failure_log; - std::unique_ptr<ct::CTVerifyResult> ct_verify_result_copy( - new ct::CTVerifyResult(verify_details_chromium->ct_verify_result)); - ct_verify_result_ = std::move(ct_verify_result_copy); logger_->OnCertificateVerified(*cert_verify_result_); pkp_bypassed_ = verify_details_chromium->pkp_bypassed; is_fatal_cert_error_ = verify_details_chromium->is_fatal_cert_error;
diff --git a/net/quic/quic_chromium_client_session.h b/net/quic/quic_chromium_client_session.h index c4d7513..7883a77f 100644 --- a/net/quic/quic_chromium_client_session.h +++ b/net/quic/quic_chromium_client_session.h
@@ -28,7 +28,6 @@ #include "net/base/net_error_details.h" #include "net/base/net_export.h" #include "net/base/proxy_server.h" -#include "net/cert/ct_verify_result.h" #include "net/log/net_log_with_source.h" #include "net/quic/quic_chromium_client_stream.h" #include "net/quic/quic_chromium_packet_reader.h" @@ -871,7 +870,6 @@ SSLConfigService* ssl_config_service_; std::unique_ptr<QuicServerInfo> server_info_; std::unique_ptr<CertVerifyResult> cert_verify_result_; - std::unique_ptr<ct::CTVerifyResult> ct_verify_result_; std::string pinning_failure_log_; bool pkp_bypassed_; bool is_fatal_cert_error_;
diff --git a/net/quic/quic_chromium_client_session_test.cc b/net/quic/quic_chromium_client_session_test.cc index 17b0895..31cb60f 100644 --- a/net/quic/quic_chromium_client_session_test.cc +++ b/net/quic/quic_chromium_client_session_test.cc
@@ -334,9 +334,8 @@ details.cert_verify_result.verified_cert = ImportCertFromFile(GetTestCertsDirectory(), "spdy_pooling.pem"); details.cert_verify_result.is_issued_by_known_root = true; - details.ct_verify_result.policy_compliance = + details.cert_verify_result.policy_compliance = ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS; - details.ct_verify_result.policy_compliance_required = true; CompleteCryptoHandshake(); session_->OnProofVerifyDetailsAvailable(details); @@ -351,10 +350,8 @@ EXPECT_EQ(details.cert_verify_result.cert_status, ssl_info.cert_status); EXPECT_EQ(details.cert_verify_result.is_issued_by_known_root, ssl_info.is_issued_by_known_root); - EXPECT_EQ(details.ct_verify_result.policy_compliance, + EXPECT_EQ(details.cert_verify_result.policy_compliance, ssl_info.ct_policy_compliance); - EXPECT_EQ(details.ct_verify_result.policy_compliance_required, - ssl_info.ct_policy_compliance_required); } // Just like GetSSLInfo1, but uses different values. @@ -373,9 +370,8 @@ details.cert_verify_result.verified_cert = ImportCertFromFile(GetTestCertsDirectory(), "spdy_pooling.pem"); details.cert_verify_result.is_issued_by_known_root = false; - details.ct_verify_result.policy_compliance = + details.cert_verify_result.policy_compliance = ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS; - details.ct_verify_result.policy_compliance_required = false; CompleteCryptoHandshake(); session_->OnProofVerifyDetailsAvailable(details); @@ -390,10 +386,8 @@ EXPECT_EQ(details.cert_verify_result.cert_status, ssl_info.cert_status); EXPECT_EQ(details.cert_verify_result.is_issued_by_known_root, ssl_info.is_issued_by_known_root); - EXPECT_EQ(details.ct_verify_result.policy_compliance, + EXPECT_EQ(details.cert_verify_result.policy_compliance, ssl_info.ct_policy_compliance); - EXPECT_EQ(details.ct_verify_result.policy_compliance_required, - ssl_info.ct_policy_compliance_required); } TEST_P(QuicChromiumClientSessionTest, IsFatalErrorNotSetForNonFatalError) { @@ -1690,7 +1684,7 @@ ImportCertFromFile(GetTestCertsDirectory(), "spdy_pooling.pem"); ASSERT_TRUE(details.cert_verify_result.verified_cert.get()); details.cert_verify_result.is_issued_by_known_root = true; - details.ct_verify_result.policy_compliance = + details.cert_verify_result.policy_compliance = ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS; CompleteCryptoHandshake();
diff --git a/net/quic/quic_stream_factory.cc b/net/quic/quic_stream_factory.cc index 0767433..ad845cba 100644 --- a/net/quic/quic_stream_factory.cc +++ b/net/quic/quic_stream_factory.cc
@@ -34,6 +34,7 @@ #include "net/cert/cert_verifier.h" #include "net/cert/ct_verifier.h" #include "net/dns/host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/net_log.h" #include "net/log/net_log_capture_mode.h" #include "net/log/net_log_event_type.h" @@ -677,7 +678,7 @@ HostResolver::ResolveHostParameters::CacheUsage::STALE_ALLOWED; } if (key_.session_key().disable_secure_dns()) - parameters.secure_dns_mode_override = DnsConfig::SecureDnsMode::OFF; + parameters.secure_dns_mode_override = SecureDnsMode::kOff; resolve_host_request_ = host_resolver_->CreateRequest( key_.destination(), key_.session_key().network_isolation_key(), net_log_, parameters);
diff --git a/net/quic/quic_stream_factory_test.cc b/net/quic/quic_stream_factory_test.cc index 9f0d098..73894530 100644 --- a/net/quic/quic_stream_factory_test.cc +++ b/net/quic/quic_stream_factory_test.cc
@@ -29,6 +29,7 @@ #include "net/dns/host_resolver_source.h" #include "net/dns/mock_host_resolver.h" #include "net/dns/public/dns_query_type.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/http/http_response_headers.h" #include "net/http/http_response_info.h" #include "net/http/http_server_properties.h" @@ -12178,7 +12179,7 @@ EXPECT_TRUE(stream.get()); ASSERT_TRUE(host_resolver_->last_secure_dns_mode_override().has_value()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, host_resolver_->last_secure_dns_mode_override().value()); ASSERT_TRUE(host_resolver_->last_request_network_isolation_key().has_value()); EXPECT_EQ(kNetworkIsolationKey,
diff --git a/net/socket/socks_client_socket.cc b/net/socket/socks_client_socket.cc index b6cd391..1108b50 100644 --- a/net/socket/socks_client_socket.cc +++ b/net/socket/socks_client_socket.cc
@@ -13,6 +13,7 @@ #include "base/sys_byteorder.h" #include "net/base/io_buffer.h" #include "net/dns/public/dns_query_type.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/net_log.h" #include "net/log/net_log_event_type.h" #include "net/traffic_annotation/network_traffic_annotation.h" @@ -310,7 +311,7 @@ parameters.dns_query_type = DnsQueryType::A; parameters.initial_priority = priority_; if (disable_secure_dns_) - parameters.secure_dns_mode_override = DnsConfig::SecureDnsMode::OFF; + parameters.secure_dns_mode_override = SecureDnsMode::kOff; resolve_host_request_ = host_resolver_->CreateRequest( destination_, network_isolation_key_, net_log_, parameters);
diff --git a/net/socket/socks_client_socket_unittest.cc b/net/socket/socks_client_socket_unittest.cc index 2095aa1..c5fd4ab 100644 --- a/net/socket/socks_client_socket_unittest.cc +++ b/net/socket/socks_client_socket_unittest.cc
@@ -16,6 +16,7 @@ #include "net/base/winsock_init.h" #include "net/dns/host_resolver.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/net_log_event_type.h" #include "net/log/test_net_log.h" #include "net/log/test_net_log_util.h" @@ -464,7 +465,7 @@ EXPECT_EQ(disable_secure_dns, host_resolver.last_secure_dns_mode_override().has_value()); if (disable_secure_dns) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, host_resolver.last_secure_dns_mode_override().value()); } }
diff --git a/net/socket/socks_connect_job_unittest.cc b/net/socket/socks_connect_job_unittest.cc index b3e23f6..0167484 100644 --- a/net/socket/socks_connect_job_unittest.cc +++ b/net/socket/socks_connect_job_unittest.cc
@@ -16,6 +16,7 @@ #include "net/base/net_errors.h" #include "net/base/network_isolation_key.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/net_log.h" #include "net/socket/client_socket_factory.h" #include "net/socket/client_socket_handle.h" @@ -392,7 +393,7 @@ EXPECT_EQ(disable_secure_dns, host_resolver_.last_secure_dns_mode_override().has_value()); if (disable_secure_dns) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, host_resolver_.last_secure_dns_mode_override().value()); } }
diff --git a/net/socket/ssl_client_socket_impl.cc b/net/socket/ssl_client_socket_impl.cc index cf4e52b..f8aca964 100644 --- a/net/socket/ssl_client_socket_impl.cc +++ b/net/socket/ssl_client_socket_impl.cc
@@ -45,6 +45,7 @@ #include "net/cert/ct_verifier.h" #include "net/cert/internal/parse_certificate.h" #include "net/cert/sct_auditing_delegate.h" +#include "net/cert/sct_status_flags.h" #include "net/cert/x509_certificate_net_log_param.h" #include "net/cert/x509_util.h" #include "net/der/parse_values.h" @@ -604,7 +605,8 @@ ssl_info->pinning_failure_log = pinning_failure_log_; ssl_info->ocsp_result = server_cert_verify_result_.ocsp_result; ssl_info->is_fatal_cert_error = is_fatal_cert_error_; - AddCTInfoToSSLInfo(ssl_info); + ssl_info->signed_certificate_timestamps = server_cert_verify_result_.scts; + ssl_info->ct_policy_compliance = server_cert_verify_result_.policy_compliance; const SSL_CIPHER* cipher = SSL_get_current_cipher(ssl_.get()); CHECK(cipher); @@ -1542,19 +1544,21 @@ // external communication. context_->cert_transparency_verifier()->Verify( host_and_port().host(), server_cert_verify_result_.verified_cert.get(), - ocsp_response, sct_list, &ct_verify_result_.scts, net_log_); + ocsp_response, sct_list, &server_cert_verify_result_.scts, net_log_); - ct::SCTList verified_scts = - ct::SCTsMatchingStatus(ct_verify_result_.scts, ct::SCT_STATUS_OK); - - ct_verify_result_.policy_compliance = + ct::SCTList verified_scts; + for (const auto& sct_and_status : server_cert_verify_result_.scts) { + if (sct_and_status.status == ct::SCT_STATUS_OK) + verified_scts.push_back(sct_and_status.sct); + } + server_cert_verify_result_.policy_compliance = context_->ct_policy_enforcer()->CheckCompliance( server_cert_verify_result_.verified_cert.get(), verified_scts, net_log_); if (server_cert_verify_result_.cert_status & CERT_STATUS_IS_EV) { - if (ct_verify_result_.policy_compliance != + if (server_cert_verify_result_.policy_compliance != ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS && - ct_verify_result_.policy_compliance != + server_cert_verify_result_.policy_compliance != ct::CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY) { server_cert_verify_result_.cert_status |= CERT_STATUS_CT_COMPLIANCE_FAILED; @@ -1566,7 +1570,7 @@ // compliance. if (server_cert_verify_result_.is_issued_by_known_root) { UMA_HISTOGRAM_ENUMERATION("Net.CertificateTransparency.EVCompliance2.SSL", - ct_verify_result_.policy_compliance, + server_cert_verify_result_.policy_compliance, ct::CTPolicyCompliance::CT_POLICY_COUNT); } } @@ -1576,7 +1580,7 @@ if (server_cert_verify_result_.is_issued_by_known_root) { UMA_HISTOGRAM_ENUMERATION( "Net.CertificateTransparency.ConnectionComplianceStatus2.SSL", - ct_verify_result_.policy_compliance, + server_cert_verify_result_.policy_compliance, ct::CTPolicyCompliance::CT_POLICY_COUNT); } @@ -1585,12 +1589,11 @@ host_and_port_, server_cert_verify_result_.is_issued_by_known_root, server_cert_verify_result_.public_key_hashes, server_cert_verify_result_.verified_cert.get(), server_cert_.get(), - ct_verify_result_.scts, + server_cert_verify_result_.scts, TransportSecurityState::ENABLE_EXPECT_CT_REPORTS, - ct_verify_result_.policy_compliance, + server_cert_verify_result_.policy_compliance, ssl_config_.network_isolation_key); if (ct_requirement_status != TransportSecurityState::CT_NOT_REQUIRED) { - ct_verify_result_.policy_compliance_required = true; if (server_cert_verify_result_.is_issued_by_known_root) { // Record the CT compliance of connections for which compliance is // required; this helps answer the question: "Of all connections that are @@ -1598,18 +1601,16 @@ UMA_HISTOGRAM_ENUMERATION( "Net.CertificateTransparency.CTRequiredConnectionComplianceStatus2." "SSL", - ct_verify_result_.policy_compliance, + server_cert_verify_result_.policy_compliance, ct::CTPolicyCompliance::CT_POLICY_COUNT); } - } else { - ct_verify_result_.policy_compliance_required = false; } if (context_->sct_auditing_delegate() && context_->sct_auditing_delegate()->IsSCTAuditingEnabled()) { context_->sct_auditing_delegate()->MaybeEnqueueReport( host_and_port_, server_cert_verify_result_.verified_cert.get(), - ct_verify_result_.scts); + server_cert_verify_result_.scts); } switch (ct_requirement_status) { @@ -1705,10 +1706,6 @@ return 1; } -void SSLClientSocketImpl::AddCTInfoToSSLInfo(SSLInfo* ssl_info) const { - ssl_info->UpdateCertificateTransparencyInfo(ct_verify_result_); -} - SSLClientSessionCache::Key SSLClientSocketImpl::GetSessionCacheKey( base::Optional<IPAddress> dest_ip_addr) const { SSLClientSessionCache::Key key;
diff --git a/net/socket/ssl_client_socket_impl.h b/net/socket/ssl_client_socket_impl.h index 7388274..d0113326 100644 --- a/net/socket/ssl_client_socket_impl.h +++ b/net/socket/ssl_client_socket_impl.h
@@ -22,7 +22,6 @@ #include "net/base/io_buffer.h" #include "net/cert/cert_verifier.h" #include "net/cert/cert_verify_result.h" -#include "net/cert/ct_verify_result.h" #include "net/log/net_log_with_source.h" #include "net/socket/next_proto.h" #include "net/socket/socket_bio_adapter.h" @@ -158,14 +157,6 @@ // Called from the SSL layer whenever a new session is established. int NewSessionCallback(SSL_SESSION* session); - // Adds the Certificate Transparency info from ct_verify_result_ to - // |ssl_info|. - // SCTs are held in three separate vectors in ct_verify_result, each - // vetor representing a particular verification state, this method associates - // each of the SCTs with the corresponding SCTVerifyStatus as it adds it to - // the |ssl_info|.signed_certificate_timestamps list. - void AddCTInfoToSSLInfo(SSLInfo* ssl_info) const; - // Returns a session cache key for this socket. SSLClientSessionCache::Key GetSessionCacheKey( base::Optional<IPAddress> dest_ip_addr) const; @@ -255,9 +246,6 @@ // Result from Cert Verifier. int cert_verification_result_; - // Certificate Transparency: Verifier and result holder. - ct::CTVerifyResult ct_verify_result_; - // OpenSSL stuff bssl::UniquePtr<SSL> ssl_;
diff --git a/net/socket/ssl_client_socket_unittest.cc b/net/socket/ssl_client_socket_unittest.cc index 9063ef48..0a3fe64d 100644 --- a/net/socket/ssl_client_socket_unittest.cc +++ b/net/socket/ssl_client_socket_unittest.cc
@@ -4319,76 +4319,6 @@ static_cast<int>(ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS), 1); } -// Test that when CT is required (in this case, by an Expect-CT opt-in) but the -// connection is not compliant, the relevant flag is set on the SSLInfo. -TEST_P(SSLClientSocketVersionTest, CTRequirementsFlagNotMet) { - ASSERT_TRUE( - StartEmbeddedTestServer(EmbeddedTestServer::CERT_OK, GetServerConfig())); - scoped_refptr<X509Certificate> server_cert = - embedded_test_server()->GetCertificate(); - - // Certificate is trusted and chains to a public root. - CertVerifyResult verify_result; - verify_result.is_issued_by_known_root = true; - verify_result.verified_cert = server_cert; - verify_result.public_key_hashes = - MakeHashValueVector(kGoodHashValueVectorInput); - cert_verifier_->AddResultForCert(server_cert.get(), verify_result, OK); - - // Set up the Expect-CT opt-in. - const base::Time current_time(base::Time::Now()); - const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); - transport_security_state_->AddExpectCT(host_port_pair().host(), expiry, - true /* enforce */, GURL(), - NetworkIsolationKey()); - - EXPECT_CALL(*ct_policy_enforcer_, CheckCompliance(server_cert.get(), _, _)) - .WillRepeatedly( - Return(ct::CTPolicyCompliance::CT_POLICY_NOT_ENOUGH_SCTS)); - - SSLConfig ssl_config; - int rv; - ASSERT_TRUE(CreateAndConnectSSLClientSocket(ssl_config, &rv)); - SSLInfo ssl_info; - ASSERT_TRUE(sock_->GetSSLInfo(&ssl_info)); - EXPECT_TRUE(ssl_info.ct_policy_compliance_required); -} - -// Test that when CT is required (in this case, by an Expect-CT opt-in) and the -// connection is compliant, the relevant flag is set on the SSLInfo. -TEST_P(SSLClientSocketVersionTest, CTRequirementsFlagMet) { - ASSERT_TRUE( - StartEmbeddedTestServer(EmbeddedTestServer::CERT_OK, GetServerConfig())); - scoped_refptr<X509Certificate> server_cert = - embedded_test_server()->GetCertificate(); - - // Certificate is trusted and chains to a public root. - CertVerifyResult verify_result; - verify_result.is_issued_by_known_root = true; - verify_result.verified_cert = server_cert; - verify_result.public_key_hashes = - MakeHashValueVector(kGoodHashValueVectorInput); - cert_verifier_->AddResultForCert(server_cert.get(), verify_result, OK); - - // Set up the Expect-CT opt-in. - const base::Time current_time(base::Time::Now()); - const base::Time expiry = current_time + base::TimeDelta::FromSeconds(1000); - transport_security_state_->AddExpectCT(host_port_pair().host(), expiry, - true /* enforce */, GURL(), - NetworkIsolationKey()); - - EXPECT_CALL(*ct_policy_enforcer_, CheckCompliance(server_cert.get(), _, _)) - .WillRepeatedly( - Return(ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS)); - - SSLConfig ssl_config; - int rv; - ASSERT_TRUE(CreateAndConnectSSLClientSocket(ssl_config, &rv)); - SSLInfo ssl_info; - ASSERT_TRUE(sock_->GetSSLInfo(&ssl_info)); - EXPECT_TRUE(ssl_info.ct_policy_compliance_required); -} - // Test that when CT is required (in this case, by a CT delegate), the CT // required histogram is not recorded for a locally installed root. TEST_P(SSLClientSocketVersionTest, CTRequiredHistogramNonCompliantLocalRoot) {
diff --git a/net/socket/ssl_connect_job_unittest.cc b/net/socket/ssl_connect_job_unittest.cc index 0d6d834..94932d4 100644 --- a/net/socket/ssl_connect_job_unittest.cc +++ b/net/socket/ssl_connect_job_unittest.cc
@@ -25,6 +25,7 @@ #include "net/cert/mock_cert_verifier.h" #include "net/cert/multi_log_ct_verifier.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/http/http_auth_handler_factory.h" #include "net/http/http_network_session.h" #include "net/http/http_proxy_connect_job.h" @@ -445,7 +446,7 @@ EXPECT_EQ(disable_secure_dns, host_resolver_.last_secure_dns_mode_override().has_value()); if (disable_secure_dns) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, host_resolver_.last_secure_dns_mode_override().value()); } }
diff --git a/net/socket/transport_client_socket_pool_unittest.cc b/net/socket/transport_client_socket_pool_unittest.cc index d7d14a6..89cc8a4 100644 --- a/net/socket/transport_client_socket_pool_unittest.cc +++ b/net/socket/transport_client_socket_pool_unittest.cc
@@ -29,6 +29,7 @@ #include "net/cert/ct_policy_enforcer.h" #include "net/cert/mock_cert_verifier.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/http/http_network_session.h" #include "net/http/http_proxy_connect_job.h" #include "net/http/transport_security_state.h" @@ -275,7 +276,7 @@ .has_value()); if (disable_secure_dns) { EXPECT_EQ( - net::DnsConfig::SecureDnsMode::OFF, + net::SecureDnsMode::kOff, session_deps_.host_resolver->last_secure_dns_mode_override().value()); } }
diff --git a/net/socket/transport_connect_job.cc b/net/socket/transport_connect_job.cc index 8d25667e..1576493 100644 --- a/net/socket/transport_connect_job.cc +++ b/net/socket/transport_connect_job.cc
@@ -19,6 +19,7 @@ #include "net/base/ip_endpoint.h" #include "net/base/net_errors.h" #include "net/base/trace_constants.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/net_log.h" #include "net/log/net_log_event_type.h" #include "net/log/net_log_source_type.h" @@ -269,7 +270,7 @@ HostResolver::ResolveHostParameters parameters; parameters.initial_priority = priority(); if (params_->disable_secure_dns()) - parameters.secure_dns_mode_override = DnsConfig::SecureDnsMode::OFF; + parameters.secure_dns_mode_override = SecureDnsMode::kOff; request_ = host_resolver()->CreateRequest(params_->destination(), params_->network_isolation_key(), net_log(), parameters);
diff --git a/net/socket/transport_connect_job_unittest.cc b/net/socket/transport_connect_job_unittest.cc index a94d60e6..9def530 100644 --- a/net/socket/transport_connect_job_unittest.cc +++ b/net/socket/transport_connect_job_unittest.cc
@@ -16,6 +16,7 @@ #include "net/base/net_errors.h" #include "net/base/test_completion_callback.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/test_net_log.h" #include "net/socket/connect_job_test_util.h" #include "net/socket/connection_attempts.h" @@ -273,7 +274,7 @@ EXPECT_EQ(disable_secure_dns, host_resolver_.last_secure_dns_mode_override().has_value()); if (disable_secure_dns) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, host_resolver_.last_secure_dns_mode_override().value()); } }
diff --git a/net/ssl/ssl_info.cc b/net/ssl/ssl_info.cc index 0ca220a..744b285 100644 --- a/net/ssl/ssl_info.cc +++ b/net/ssl/ssl_info.cc
@@ -20,14 +20,4 @@ *this = SSLInfo(); } -void SSLInfo::UpdateCertificateTransparencyInfo( - const ct::CTVerifyResult& ct_verify_result) { - signed_certificate_timestamps.insert(signed_certificate_timestamps.end(), - ct_verify_result.scts.begin(), - ct_verify_result.scts.end()); - - ct_policy_compliance = ct_verify_result.policy_compliance; - ct_policy_compliance_required = ct_verify_result.policy_compliance_required; -} - } // namespace net
diff --git a/net/ssl/ssl_info.h b/net/ssl/ssl_info.h index b8fe946..e7e14ec 100644 --- a/net/ssl/ssl_info.h +++ b/net/ssl/ssl_info.h
@@ -13,7 +13,6 @@ #include "net/base/net_export.h" #include "net/cert/cert_status_flags.h" #include "net/cert/ct_policy_status.h" -#include "net/cert/ct_verify_result.h" #include "net/cert/ocsp_verify_result.h" #include "net/cert/sct_status_flags.h" #include "net/cert/signed_certificate_timestamp_and_status.h" @@ -45,16 +44,6 @@ bool is_valid() const { return cert.get() != nullptr; } - // Adds the SignedCertificateTimestamps and policy compliance details - // from ct_verify_result to |signed_certificate_timestamps| and - // |ct_policy_compliance_details|. SCTs are held in three separate - // vectors in ct_verify_result, each vetor representing a particular - // verification state, this method associates each of the SCTs with - // the corresponding SCTVerifyStatus as it adds it to the - // |signed_certificate_timestamps| list. - void UpdateCertificateTransparencyInfo( - const ct::CTVerifyResult& ct_verify_result); - // The SSL certificate. scoped_refptr<X509Certificate> cert; @@ -119,11 +108,6 @@ ct::CTPolicyCompliance ct_policy_compliance = ct::CTPolicyCompliance::CT_POLICY_COMPLIANCE_DETAILS_NOT_AVAILABLE; - // True if the connection was required to comply with the CT cert policy. Only - // meaningful if |ct_policy_compliance| is not - // COMPLIANCE_DETAILS_NOT_AVAILABLE. - bool ct_policy_compliance_required = false; - // OCSP stapling details. OCSPVerifyResult ocsp_result;
diff --git a/net/test/ct_test_util.cc b/net/test/ct_test_util.cc index d01b59ca1..3ca286b 100644 --- a/net/test/ct_test_util.cc +++ b/net/test/ct_test_util.cc
@@ -15,7 +15,6 @@ #include "base/strings/stringprintf.h" #include "net/base/hex_utils.h" #include "net/cert/ct_serialization.h" -#include "net/cert/ct_verify_result.h" #include "net/cert/merkle_tree_leaf.h" #include "net/cert/signed_tree_head.h" #include "net/cert/x509_certificate.h"
diff --git a/net/url_request/http_with_dns_over_https_unittest.cc b/net/url_request/http_with_dns_over_https_unittest.cc index 4e21e25..8f574cd9 100644 --- a/net/url_request/http_with_dns_over_https_unittest.cc +++ b/net/url_request/http_with_dns_over_https_unittest.cc
@@ -17,6 +17,7 @@ #include "net/dns/host_resolver_manager.h" #include "net/dns/host_resolver_proc.h" #include "net/dns/public/dns_over_https_server_config.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/http/http_stream_factory_test_util.h" #include "net/log/net_log.h" #include "net/socket/transport_client_socket_pool.h" @@ -96,7 +97,7 @@ DnsConfigOverrides overrides; overrides.dns_over_https_servers.emplace( {DnsOverHttpsServerConfig(url.spec(), true /* use_post */)}); - overrides.secure_dns_mode = DnsConfig::SecureDnsMode::SECURE; + overrides.secure_dns_mode = SecureDnsMode::kSecure; overrides.use_local_ipv6 = true; resolver_->GetManagerForTesting()->SetDnsConfigOverrides( std::move(overrides));
diff --git a/net/url_request/url_request_http_job.cc b/net/url_request/url_request_http_job.cc index f5e754f..ac868d1 100644 --- a/net/url_request/url_request_http_job.cc +++ b/net/url_request/url_request_http_job.cc
@@ -149,15 +149,6 @@ "Net.CertificateTransparency.RequestComplianceStatus", ssl_info.ct_policy_compliance, net::ct::CTPolicyCompliance::CT_POLICY_COUNT); - // Record the CT compliance of each request which was required to be CT - // compliant. This gives a picture of the sites that are supposed to be - // compliant and how well they do at actually being compliant. - if (ssl_info.ct_policy_compliance_required) { - UMA_HISTOGRAM_ENUMERATION( - "Net.CertificateTransparency.CTRequiredRequestComplianceStatus", - ssl_info.ct_policy_compliance, - net::ct::CTPolicyCompliance::CT_POLICY_COUNT); - } } template <typename CookieWithMetadata>
diff --git a/net/url_request/url_request_http_job_unittest.cc b/net/url_request/url_request_http_job_unittest.cc index 723a911..2ea016c 100644 --- a/net/url_request/url_request_http_job_unittest.cc +++ b/net/url_request/url_request_http_job_unittest.cc
@@ -88,8 +88,6 @@ const char kCTComplianceHistogramName[] = "Net.CertificateTransparency.RequestComplianceStatus"; -const char kCTRequiredHistogramName[] = - "Net.CertificateTransparency.CTRequiredRequestComplianceStatus"; // Inherit from URLRequestHttpJob to expose the priority and some // other hidden functions. @@ -1040,7 +1038,6 @@ ssl_socket_data.ssl_info.cert = ImportCertFromFile(GetTestCertsDirectory(), "ok_cert.pem"); ssl_socket_data.ssl_info.is_issued_by_known_root = true; - ssl_socket_data.ssl_info.ct_policy_compliance_required = false; ssl_socket_data.ssl_info.ct_policy_compliance = ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS; @@ -1086,7 +1083,6 @@ ssl_socket_data.ssl_info.cert = ImportCertFromFile(GetTestCertsDirectory(), "ok_cert.pem"); ssl_socket_data.ssl_info.is_issued_by_known_root = true; - ssl_socket_data.ssl_info.ct_policy_compliance_required = false; ssl_socket_data.ssl_info.ct_policy_compliance = ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS; @@ -1113,9 +1109,6 @@ kCTComplianceHistogramName, static_cast<int32_t>(ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS), 1); - // CTRequiredRequestComplianceStatus should *not* have been recorded because - // it is only recorded for requests which are required to be compliant. - histograms.ExpectTotalCount(kCTRequiredHistogramName, 0); } // Tests that the CT compliance histograms are not recorded for @@ -1126,7 +1119,6 @@ ssl_socket_data.ssl_info.cert = ImportCertFromFile(GetTestCertsDirectory(), "ok_cert.pem"); ssl_socket_data.ssl_info.is_issued_by_known_root = false; - ssl_socket_data.ssl_info.ct_policy_compliance_required = false; ssl_socket_data.ssl_info.ct_policy_compliance = ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS; @@ -1150,7 +1142,6 @@ EXPECT_THAT(delegate.request_status(), IsOk()); histograms.ExpectTotalCount(kCTComplianceHistogramName, 0); - histograms.ExpectTotalCount(kCTRequiredHistogramName, 0); } // Tests that the CT compliance histogram is recorded when CT is required but @@ -1161,7 +1152,6 @@ ssl_socket_data.ssl_info.cert = ImportCertFromFile(GetTestCertsDirectory(), "ok_cert.pem"); ssl_socket_data.ssl_info.is_issued_by_known_root = true; - ssl_socket_data.ssl_info.ct_policy_compliance_required = true; ssl_socket_data.ssl_info.ct_policy_compliance = ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS; @@ -1188,10 +1178,6 @@ kCTComplianceHistogramName, static_cast<int32_t>(ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS), 1); - histograms.ExpectUniqueSample( - kCTRequiredHistogramName, - static_cast<int32_t>(ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS), - 1); } // Tests that the CT compliance histograms are not recorded when there is an @@ -1202,7 +1188,6 @@ ssl_socket_data.ssl_info.cert = ImportCertFromFile(GetTestCertsDirectory(), "ok_cert.pem"); ssl_socket_data.ssl_info.is_issued_by_known_root = true; - ssl_socket_data.ssl_info.ct_policy_compliance_required = true; ssl_socket_data.ssl_info.ct_policy_compliance = ct::CTPolicyCompliance::CT_POLICY_NOT_DIVERSE_SCTS; ssl_socket_data.ssl_info.cert_status = net::CERT_STATUS_DATE_INVALID; @@ -1227,7 +1212,6 @@ EXPECT_THAT(delegate.request_status(), IsOk()); histograms.ExpectTotalCount(kCTComplianceHistogramName, 0); - histograms.ExpectTotalCount(kCTRequiredHistogramName, 0); } TEST_F(URLRequestHttpJobWithMockSocketsTest, EncodingAdvertisementOnRange) {
diff --git a/net/url_request/url_request_unittest.cc b/net/url_request/url_request_unittest.cc index 2f92038..a0c62cc 100644 --- a/net/url_request/url_request_unittest.cc +++ b/net/url_request/url_request_unittest.cc
@@ -93,6 +93,7 @@ #include "net/cookies/test_cookie_access_delegate.h" #include "net/disk_cache/disk_cache.h" #include "net/dns/mock_host_resolver.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/http/http_byte_range.h" #include "net/http/http_cache.h" #include "net/http/http_network_layer.h" @@ -1355,7 +1356,7 @@ req->Start(); d.RunUntilComplete(); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, host_resolver.last_secure_dns_mode_override().value()); }
diff --git a/pdf/ppapi_migration/url_loader.cc b/pdf/ppapi_migration/url_loader.cc index 309cea8..6e2e378 100644 --- a/pdf/ppapi_migration/url_loader.cc +++ b/pdf/ppapi_migration/url_loader.cc
@@ -140,6 +140,11 @@ GURL(request.custom_referrer_url)); } + buffer_lower_threshold_ = request.buffer_lower_threshold; + buffer_upper_threshold_ = request.buffer_upper_threshold; + DCHECK_GT(buffer_lower_threshold_, 0u); + DCHECK_LE(buffer_lower_threshold_, buffer_upper_threshold_); + blink_request.SetRequestContext(blink::mojom::RequestContextType::PLUGIN); blink_request.SetRequestDestination( network::mojom::RequestDestination::kEmbed); @@ -235,6 +240,13 @@ return; buffer_.insert(buffer_.end(), data, data + data_length); + + // Defer loading if the buffer is too full. + if (!deferring_loading_ && buffer_.size() >= buffer_upper_threshold_) { + deferring_loading_ = true; + blink_loader_->SetDefersLoading(true); + } + RunReadCallback(); } @@ -301,6 +313,12 @@ auto read_end = read_begin + num_bytes; std::copy(read_begin, read_end, client_buffer_.data()); buffer_.erase(read_begin, read_end); + + // Resume loading if the buffer is too empty. + if (deferring_loading_ && buffer_.size() <= buffer_lower_threshold_) { + deferring_loading_ = false; + blink_loader_->SetDefersLoading(false); + } } else { DCHECK_EQ(state_, LoadingState::kLoadComplete); num_bytes = complete_result_;
diff --git a/pdf/ppapi_migration/url_loader.h b/pdf/ppapi_migration/url_loader.h index b1c249f8..b666e4d 100644 --- a/pdf/ppapi_migration/url_loader.h +++ b/pdf/ppapi_migration/url_loader.h
@@ -5,6 +5,7 @@ #ifndef PDF_PPAPI_MIGRATION_URL_LOADER_H_ #define PDF_PPAPI_MIGRATION_URL_LOADER_H_ +#include <stddef.h> #include <stdint.h> #include <memory> @@ -60,6 +61,16 @@ // Request body. std::string body; + + // Thresholds for throttling filling of the loader's internal buffer. Filling + // will stop after exceeding the upper threshold, and resume after dropping + // below the lower threshold. + // + // Default values taken from `ppapi/shared_impl/url_request_info_data.cc`. The + // PDF viewer never changes the defaults in production, so these fields mostly + // exist for testing purposes. + size_t buffer_lower_threshold = 50 * 1000 * 1000; + size_t buffer_upper_threshold = 100 * 1000 * 1000; }; // Properties returned from a URL request. Does not include the response body. @@ -211,7 +222,12 @@ bool ignore_redirects_ = false; ResultCallback open_callback_; + // Thresholds control buffer throttling, as defined in `UrlRequest`. + size_t buffer_lower_threshold_ = 0; + size_t buffer_upper_threshold_ = 0; + bool deferring_loading_ = false; base::circular_deque<char> buffer_; + ResultCallback read_callback_; base::span<char> client_buffer_; };
diff --git a/pdf/ppapi_migration/url_loader_unittest.cc b/pdf/ppapi_migration/url_loader_unittest.cc index bc94585..df79207c 100644 --- a/pdf/ppapi_migration/url_loader_unittest.cc +++ b/pdf/ppapi_migration/url_loader_unittest.cc
@@ -42,9 +42,9 @@ namespace chrome_pdf { namespace { -using ::testing::_; using ::testing::Each; using ::testing::ElementsAreArray; +using ::testing::InSequence; using ::testing::Invoke; using ::testing::NiceMock; using ::testing::Return; @@ -100,7 +100,9 @@ void Invalidate() { valid_ = false; } - MockWebAssociatedURLLoader& mock_url_loader() { return *mock_url_loader_; } + MockWebAssociatedURLLoader* mock_url_loader() { + return mock_url_loader_.get(); + } const blink::WebAssociatedURLLoaderOptions& saved_options() const { return saved_options_; @@ -148,7 +150,7 @@ class BlinkUrlLoaderTest : public testing::Test { protected: BlinkUrlLoaderTest() { - ON_CALL(fake_client_.mock_url_loader(), LoadAsynchronously(_, _)) + ON_CALL(*mock_url_loader_, LoadAsynchronously) .WillByDefault( Invoke(this, &BlinkUrlLoaderTest::FakeLoadAsynchronously)); loader_ = std::make_unique<BlinkUrlLoader>(fake_client_.GetWeakPtr()); @@ -160,10 +162,18 @@ EXPECT_EQ(loader_.get(), client); } + void StartLoadWithThresholds(size_t lower, size_t upper) { + UrlRequest request; + request.buffer_lower_threshold = lower; + request.buffer_upper_threshold = upper; + loader_->Open(request, mock_callback_.Get()); + loader_->DidReceiveResponse(blink::WebURLResponse()); + } + int32_t DidFailWithError(const blink::WebURLError& error) { int32_t result = 0; loader_->Open(UrlRequest(), mock_callback_.Get()); - EXPECT_CALL(mock_callback_, Run(_)).WillOnce(SaveArg<0>(&result)); + EXPECT_CALL(mock_callback_, Run).WillOnce(SaveArg<0>(&result)); loader_->DidFail(error); return result; @@ -173,6 +183,9 @@ NiceMock<base::MockCallback<ResultCallback>> mock_callback_; std::unique_ptr<BlinkUrlLoader> loader_; + // Becomes invalid if `loader_` is closed or destructed. + MockWebAssociatedURLLoader* mock_url_loader_ = fake_client_.mock_url_loader(); + blink::WebURLRequest saved_request_; }; @@ -183,8 +196,8 @@ } TEST_F(BlinkUrlLoaderTest, Open) { - EXPECT_CALL(fake_client_.mock_url_loader(), LoadAsynchronously(_, _)); - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(*mock_url_loader_, LoadAsynchronously); + EXPECT_CALL(mock_callback_, Run).Times(0); UrlRequest request; request.url = "http://example.com/fake.pdf"; @@ -205,8 +218,7 @@ } TEST_F(BlinkUrlLoaderTest, OpenWithInvalidatedClientWeakPtr) { - EXPECT_CALL(fake_client_.mock_url_loader(), LoadAsynchronously(_, _)) - .Times(0); + EXPECT_CALL(*mock_url_loader_, LoadAsynchronously).Times(0); EXPECT_CALL(mock_callback_, Run(PP_ERROR_FAILED)); fake_client_.InvalidateWeakPtrs(); @@ -214,8 +226,7 @@ } TEST_F(BlinkUrlLoaderTest, OpenWithInvalidatedClient) { - EXPECT_CALL(fake_client_.mock_url_loader(), LoadAsynchronously(_, _)) - .Times(0); + EXPECT_CALL(*mock_url_loader_, LoadAsynchronously).Times(0); EXPECT_CALL(mock_callback_, Run(PP_ERROR_FAILED)); fake_client_.Invalidate(); @@ -343,13 +354,46 @@ loader_->Open(UrlRequest(), mock_callback_.Get()); loader_->DidReceiveResponse(blink::WebURLResponse()); loader_->ReadResponseBody(buffer, mock_callback_.Get()); - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->DidReceiveData(kFakeData.data(), 0); EXPECT_THAT(buffer, Each(0)); } +TEST_F(BlinkUrlLoaderTest, DidReceiveDataBelowUpperThreshold) { + StartLoadWithThresholds(/*lower=*/2, /*upper=*/4); + EXPECT_CALL(*mock_url_loader_, SetDefersLoading).Times(0); + + char buffer[3] = {}; + loader_->DidReceiveData(buffer, sizeof(buffer)); +} + +TEST_F(BlinkUrlLoaderTest, DidReceiveDataCrossUpperThreshold) { + StartLoadWithThresholds(/*lower=*/2, /*upper=*/4); + + char read_buffer[1]; + loader_->ReadResponseBody(read_buffer, mock_callback_.Get()); + { + InSequence defer_before_read_callback; + EXPECT_CALL(*mock_url_loader_, SetDefersLoading(true)); + EXPECT_CALL(mock_callback_, Run); + } + + char buffer[4] = {}; + loader_->DidReceiveData(buffer, sizeof(buffer)); +} + +TEST_F(BlinkUrlLoaderTest, DidReceiveDataAboveUpperThreshold) { + StartLoadWithThresholds(/*lower=*/2, /*upper=*/4); + + char buffer[4] = {}; + loader_->DidReceiveData(buffer, sizeof(buffer)); + EXPECT_CALL(*mock_url_loader_, SetDefersLoading).Times(0); + + loader_->DidReceiveData(buffer, sizeof(buffer)); +} + TEST_F(BlinkUrlLoaderTest, ReadResponseBody) { loader_->Open(UrlRequest(), mock_callback_.Get()); loader_->DidReceiveResponse(blink::WebURLResponse()); @@ -362,14 +406,14 @@ EXPECT_THAT(buffer, ElementsAreArray(kFakeData)); // Verify no more data returned on next call. - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->ReadResponseBody(buffer, mock_callback_.Get()); } TEST_F(BlinkUrlLoaderTest, ReadResponseBodyWithoutData) { loader_->Open(UrlRequest(), mock_callback_.Get()); loader_->DidReceiveResponse(blink::WebURLResponse()); - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); char buffer[kFakeData.size()] = {}; loader_->ReadResponseBody(buffer, mock_callback_.Get()); @@ -420,7 +464,7 @@ EXPECT_THAT(buffer_span.subspan(kFakeData.size()), Each(0)); // Verify no more data returned on next call. - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->ReadResponseBody(buffer, mock_callback_.Get()); } @@ -468,10 +512,49 @@ EXPECT_THAT(buffer, Each(0)); } +TEST_F(BlinkUrlLoaderTest, ReadResponseBodyAboveLowerThreshold) { + StartLoadWithThresholds(/*lower=*/2, /*upper=*/4); + + char write_buffer[5] = {}; + loader_->DidReceiveData(write_buffer, sizeof(write_buffer)); + EXPECT_CALL(*mock_url_loader_, SetDefersLoading).Times(0); + + char buffer[2] = {}; + loader_->ReadResponseBody(buffer, mock_callback_.Get()); +} + +TEST_F(BlinkUrlLoaderTest, ReadResponseBodyCrossLowerThreshold) { + StartLoadWithThresholds(/*lower=*/2, /*upper=*/4); + + char write_buffer[5] = {}; + loader_->DidReceiveData(write_buffer, sizeof(write_buffer)); + { + InSequence resume_before_read_callback; + EXPECT_CALL(*mock_url_loader_, SetDefersLoading(false)); + EXPECT_CALL(mock_callback_, Run); + } + + char buffer[3] = {}; + loader_->ReadResponseBody(buffer, mock_callback_.Get()); +} + +TEST_F(BlinkUrlLoaderTest, ReadResponseBodyBelowLowerThreshold) { + StartLoadWithThresholds(/*lower=*/2, /*upper=*/4); + + char write_buffer[5] = {}; + loader_->DidReceiveData(write_buffer, sizeof(write_buffer)); + + char buffer[3] = {}; + loader_->ReadResponseBody(buffer, mock_callback_.Get()); + EXPECT_CALL(*mock_url_loader_, SetDefersLoading).Times(0); + + loader_->ReadResponseBody(buffer, mock_callback_.Get()); +} + TEST_F(BlinkUrlLoaderTest, DidFinishLoading) { loader_->Open(UrlRequest(), mock_callback_.Get()); loader_->DidReceiveResponse(blink::WebURLResponse()); - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->DidFinishLoading(); } @@ -527,7 +610,7 @@ } TEST_F(BlinkUrlLoaderTest, CloseWhileWaitingToOpen) { - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->Close(); } @@ -542,7 +625,7 @@ TEST_F(BlinkUrlLoaderTest, CloseWhileStreamingData) { loader_->Open(UrlRequest(), mock_callback_.Get()); loader_->DidReceiveResponse(blink::WebURLResponse()); - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->Close(); } @@ -561,7 +644,7 @@ loader_->Open(UrlRequest(), mock_callback_.Get()); loader_->DidReceiveResponse(blink::WebURLResponse()); loader_->DidFinishLoading(); - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->Close(); } @@ -569,7 +652,7 @@ TEST_F(BlinkUrlLoaderTest, CloseAgain) { loader_->Open(UrlRequest(), mock_callback_.Get()); loader_->Close(); - EXPECT_CALL(mock_callback_, Run(_)).Times(0); + EXPECT_CALL(mock_callback_, Run).Times(0); loader_->Close(); }
diff --git a/sandbox/linux/BUILD.gn b/sandbox/linux/BUILD.gn index 36c4c1fb..1b374ca2 100644 --- a/sandbox/linux/BUILD.gn +++ b/sandbox/linux/BUILD.gn
@@ -11,6 +11,13 @@ import("//build/config/android/rules.gni") } +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + declare_args() { compile_suid_client = is_linux || is_chromeos
diff --git a/services/network/host_resolver_unittest.cc b/services/network/host_resolver_unittest.cc index a7ba3ed9..c74df377 100644 --- a/services/network/host_resolver_unittest.cc +++ b/services/network/host_resolver_unittest.cc
@@ -30,6 +30,7 @@ #include "net/dns/host_resolver_manager.h" #include "net/dns/mock_host_resolver.h" #include "net/dns/public/dns_protocol.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/net_log.h" #include "net/net_buildflags.h" #include "testing/gmock/include/gmock/gmock.h" @@ -729,7 +730,7 @@ EXPECT_EQ(net::OK, response_client.result_error()); EXPECT_THAT(response_client.result_addresses().value().endpoints(), testing::ElementsAre(CreateExpectedEndPoint("127.0.0.1", 80))); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::SECURE, + EXPECT_EQ(net::SecureDnsMode::kSecure, inner_resolver->last_secure_dns_mode_override().value()); }
diff --git a/services/network/network_context.cc b/services/network/network_context.cc index 591c018..9144827 100644 --- a/services/network/network_context.cc +++ b/services/network/network_context.cc
@@ -49,7 +49,6 @@ #include "net/cert/caching_cert_verifier.h" #include "net/cert/cert_verifier.h" #include "net/cert/coalescing_cert_verifier.h" -#include "net/cert/ct_verify_result.h" #include "net/cert_net/cert_net_fetcher_url_request.h" #include "net/cookies/cookie_monster.h" #include "net/dns/host_cache.h" @@ -2352,7 +2351,6 @@ auto pending_cert_verify = std::move(iter->second); cert_verifier_requests_.erase(iter); - net::ct::CTVerifyResult ct_verify_result; #if BUILDFLAG(IS_CT_SUPPORTED) if (result == net::OK) { net::X509Certificate* verified_cert = @@ -2360,15 +2358,17 @@ url_request_context_->cert_transparency_verifier()->Verify( pending_cert_verify->url.host(), verified_cert, pending_cert_verify->ocsp_result, pending_cert_verify->sct_list, - &ct_verify_result.scts, + &pending_cert_verify->result->scts, net::NetLogWithSource::Make( network_service_ ? url_request_context_->net_log() : nullptr, net::NetLogSourceType::CERT_VERIFIER_JOB)); - net::ct::SCTList verified_scts = net::ct::SCTsMatchingStatus( - ct_verify_result.scts, net::ct::SCT_STATUS_OK); - - ct_verify_result.policy_compliance = + net::ct::SCTList verified_scts; + for (const auto& sct_and_status : pending_cert_verify->result->scts) { + if (sct_and_status.status == net::ct::SCT_STATUS_OK) + verified_scts.push_back(sct_and_status.sct); + } + pending_cert_verify->result->policy_compliance = url_request_context_->ct_policy_enforcer()->CheckCompliance( verified_cert, verified_scts, net::NetLogWithSource::Make( @@ -2378,9 +2378,9 @@ // TODO(https://crbug.com/803774): We should determine whether EV & SXG // should be a thing (due to the online/offline signing difference) if (pending_cert_verify->result->cert_status & net::CERT_STATUS_IS_EV && - ct_verify_result.policy_compliance != + pending_cert_verify->result->policy_compliance != net::ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS && - ct_verify_result.policy_compliance != + pending_cert_verify->result->policy_compliance != net::ct::CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY) { pending_cert_verify->result->cert_status |= net::CERT_STATUS_CT_COMPLIANCE_FAILED; @@ -2395,16 +2395,17 @@ net::HostPortPair::FromURL(pending_cert_verify->url), pending_cert_verify->result->is_issued_by_known_root, pending_cert_verify->result->public_key_hashes, verified_cert, - pending_cert_verify->certificate.get(), ct_verify_result.scts, + pending_cert_verify->certificate.get(), + pending_cert_verify->result->scts, net::TransportSecurityState::ENABLE_EXPECT_CT_REPORTS, - ct_verify_result.policy_compliance, + pending_cert_verify->result->policy_compliance, net::NetworkIsolationKey::Todo()); if (url_request_context_->sct_auditing_delegate() && url_request_context_->sct_auditing_delegate()->IsSCTAuditingEnabled()) { url_request_context_->sct_auditing_delegate()->MaybeEnqueueReport( net::HostPortPair::FromURL(pending_cert_verify->url), verified_cert, - ct_verify_result.scts); + pending_cert_verify->result->scts); } switch (ct_requirement_status) { @@ -2412,26 +2413,22 @@ result = net::ERR_CERTIFICATE_TRANSPARENCY_REQUIRED; break; case net::TransportSecurityState::CT_REQUIREMENTS_MET: - ct_verify_result.policy_compliance_required = true; break; case net::TransportSecurityState::CT_NOT_REQUIRED: // CT is not required if the certificate does not chain to a publicly // trusted root certificate. - if (!pending_cert_verify->result->is_issued_by_known_root) { - ct_verify_result.policy_compliance_required = false; + if (!pending_cert_verify->result->is_issued_by_known_root) break; - } // For old certificates (issued before 2018-05-01), // CheckCTRequirements() may return CT_NOT_REQUIRED, so we check the // compliance status here. // TODO(https://crbug.com/851778): Remove this condition once we require // signing certificates to have CanSignHttpExchanges extension, because // such certificates should be naturally after 2018-05-01. - if (ct_verify_result.policy_compliance == + if (pending_cert_verify->result->policy_compliance == net::ct::CTPolicyCompliance::CT_POLICY_COMPLIES_VIA_SCTS || - ct_verify_result.policy_compliance == + pending_cert_verify->result->policy_compliance == net::ct::CTPolicyCompliance::CT_POLICY_BUILD_NOT_TIMELY) { - ct_verify_result.policy_compliance_required = true; break; } // Require CT compliance, by overriding CT_NOT_REQUIRED and treat it as @@ -2442,7 +2439,7 @@ #endif // BUILDFLAG(IS_CT_SUPPORTED) std::move(pending_cert_verify->callback) - .Run(result, *pending_cert_verify->result.get(), ct_verify_result); + .Run(result, *pending_cert_verify->result.get()); } #if defined(OS_CHROMEOS)
diff --git a/services/network/network_context_unittest.cc b/services/network/network_context_unittest.cc index df66f69..e7b3686 100644 --- a/services/network/network_context_unittest.cc +++ b/services/network/network_context_unittest.cc
@@ -78,6 +78,7 @@ #include "net/dns/host_resolver_source.h" #include "net/dns/mock_host_resolver.h" #include "net/dns/public/dns_query_type.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/dns/resolve_context.h" #include "net/http/http_auth.h" #include "net/http/http_cache.h" @@ -4476,7 +4477,7 @@ EXPECT_EQ(disable_secure_dns, resolver->last_secure_dns_mode_override().has_value()); if (disable_secure_dns) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, resolver->last_secure_dns_mode_override().value()); } } @@ -4522,7 +4523,7 @@ EXPECT_EQ(disable_secure_dns, resolver.last_secure_dns_mode_override().has_value()); if (disable_secure_dns) { - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, resolver.last_secure_dns_mode_override().value()); } }
diff --git a/services/network/network_service.cc b/services/network/network_service.cc index dd365ae..6eceac36 100644 --- a/services/network/network_service.cc +++ b/services/network/network_service.cc
@@ -508,7 +508,7 @@ void NetworkService::ConfigureStubHostResolver( bool insecure_dns_client_enabled, - net::DnsConfig::SecureDnsMode secure_dns_mode, + net::SecureDnsMode secure_dns_mode, base::Optional<std::vector<mojom::DnsOverHttpsServerPtr>> dns_over_https_servers) { DCHECK(!dns_over_https_servers || !dns_over_https_servers->empty()); @@ -538,7 +538,7 @@ // a quick hack to increase the timeout for these requests. // TODO(crbug.com/1105138): Rethink the timeout logic to be less aggressive in // cases where there is no fallback, without needing to make so many retries. - if (secure_dns_mode == net::DnsConfig::SecureDnsMode::SECURE) + if (secure_dns_mode == net::SecureDnsMode::kSecure) overrides.doh_attempts = 3; host_resolver_manager_->SetDnsConfigOverrides(overrides);
diff --git a/services/network/network_service.h b/services/network/network_service.h index 85dcae89..21a0a6e 100644 --- a/services/network/network_service.h +++ b/services/network/network_service.h
@@ -27,7 +27,7 @@ #include "mojo/public/cpp/bindings/pending_remote.h" #include "mojo/public/cpp/bindings/receiver.h" #include "mojo/public/cpp/bindings/remote.h" -#include "net/dns/dns_config.h" +#include "net/dns/public/secure_dns_mode.h" #include "net/log/net_log.h" #include "net/log/trace_net_log_observer.h" #include "services/network/keepalive_statistics_recorder.h" @@ -163,7 +163,7 @@ mojom::NetworkContextParamsPtr params) override; void ConfigureStubHostResolver( bool insecure_dns_client_enabled, - net::DnsConfig::SecureDnsMode secure_dns_mode, + net::SecureDnsMode secure_dns_mode, base::Optional<std::vector<mojom::DnsOverHttpsServerPtr>> dns_over_https_servers) override; void DisableQuic() override;
diff --git a/services/network/network_service_unittest.cc b/services/network/network_service_unittest.cc index 542e895..d2d032a5 100644 --- a/services/network/network_service_unittest.cc +++ b/services/network/network_service_unittest.cc
@@ -470,27 +470,24 @@ std::move(dns_client)); service()->ConfigureStubHostResolver( - true /* insecure_dns_client_enabled */, - net::DnsConfig::SecureDnsMode::OFF, + true /* insecure_dns_client_enabled */, net::SecureDnsMode::kOff, base::nullopt /* dns_over_https_servers */); EXPECT_TRUE(dns_client_ptr->CanUseInsecureDnsTransactions()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, dns_client_ptr->GetEffectiveConfig()->secure_dns_mode); service()->ConfigureStubHostResolver( - false /* insecure_dns_client_enabled */, - net::DnsConfig::SecureDnsMode::OFF, + false /* insecure_dns_client_enabled */, net::SecureDnsMode::kOff, base::nullopt /* dns_over_https_servers */); EXPECT_FALSE(dns_client_ptr->CanUseInsecureDnsTransactions()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::OFF, + EXPECT_EQ(net::SecureDnsMode::kOff, dns_client_ptr->GetEffectiveConfig()->secure_dns_mode); service()->ConfigureStubHostResolver( - false /* insecure_dns_client_enabled */, - net::DnsConfig::SecureDnsMode::AUTOMATIC, + false /* insecure_dns_client_enabled */, net::SecureDnsMode::kAutomatic, base::nullopt /* dns_over_https_servers */); EXPECT_FALSE(dns_client_ptr->CanUseInsecureDnsTransactions()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, + EXPECT_EQ(net::SecureDnsMode::kAutomatic, dns_client_ptr->GetEffectiveConfig()->secure_dns_mode); std::vector<mojom::DnsOverHttpsServerPtr> dns_over_https_servers_ptr; @@ -500,10 +497,10 @@ dns_over_https_server->use_post = true; dns_over_https_servers_ptr.emplace_back(std::move(dns_over_https_server)); service()->ConfigureStubHostResolver(false /* insecure_dns_client_enabled */, - net::DnsConfig::SecureDnsMode::AUTOMATIC, + net::SecureDnsMode::kAutomatic, std::move(dns_over_https_servers_ptr)); EXPECT_FALSE(dns_client_ptr->CanUseInsecureDnsTransactions()); - EXPECT_EQ(net::DnsConfig::SecureDnsMode::AUTOMATIC, + EXPECT_EQ(net::SecureDnsMode::kAutomatic, dns_client_ptr->GetEffectiveConfig()->secure_dns_mode); } @@ -536,7 +533,7 @@ dns_over_https_servers_ptr.emplace_back(std::move(dns_over_https_server)); service()->ConfigureStubHostResolver(false /* insecure_dns_client_enabled */, - net::DnsConfig::SecureDnsMode::AUTOMATIC, + net::SecureDnsMode::kAutomatic, std::move(dns_over_https_servers_ptr)); EXPECT_TRUE( service()->host_resolver_manager()->GetDnsConfigAsValue().is_dict()); @@ -560,7 +557,7 @@ dns_over_https_servers_ptr.emplace_back(std::move(dns_over_https_server)); service()->ConfigureStubHostResolver(true /* insecure_dns_client_enabled */, - net::DnsConfig::SecureDnsMode::SECURE, + net::SecureDnsMode::kSecure, std::move(dns_over_https_servers_ptr)); EXPECT_TRUE( service()->host_resolver_manager()->GetDnsConfigAsValue().is_dict()); @@ -579,8 +576,7 @@ features::kDnsOverHttpsUpgrade, {{"DisabledProviders", "CleanBrowsingSecure, , Cloudflare,Unexpected"}}); service()->ConfigureStubHostResolver( - true /* insecure_dns_client_enabled */, - net::DnsConfig::SecureDnsMode::AUTOMATIC, + true /* insecure_dns_client_enabled */, net::SecureDnsMode::kAutomatic, base::nullopt /* dns_over_https_servers */); // Set valid DnsConfig.
diff --git a/services/network/public/cpp/host_resolver_mojom_traits.cc b/services/network/public/cpp/host_resolver_mojom_traits.cc index c2126c1..f8914dc 100644 --- a/services/network/public/cpp/host_resolver_mojom_traits.cc +++ b/services/network/public/cpp/host_resolver_mojom_traits.cc
@@ -111,32 +111,32 @@ } OptionalSecureDnsMode ToOptionalSecureDnsMode( - base::Optional<net::DnsConfig::SecureDnsMode> optional) { + base::Optional<net::SecureDnsMode> optional) { if (!optional) return OptionalSecureDnsMode::NO_OVERRIDE; switch (optional.value()) { - case net::DnsConfig::SecureDnsMode::OFF: + case net::SecureDnsMode::kOff: return OptionalSecureDnsMode::OFF; - case net::DnsConfig::SecureDnsMode::AUTOMATIC: + case net::SecureDnsMode::kAutomatic: return OptionalSecureDnsMode::AUTOMATIC; - case net::DnsConfig::SecureDnsMode::SECURE: + case net::SecureDnsMode::kSecure: return OptionalSecureDnsMode::SECURE; } } } // namespace -base::Optional<net::DnsConfig::SecureDnsMode> FromOptionalSecureDnsMode( +base::Optional<net::SecureDnsMode> FromOptionalSecureDnsMode( OptionalSecureDnsMode mode) { switch (mode) { case OptionalSecureDnsMode::NO_OVERRIDE: return base::nullopt; case OptionalSecureDnsMode::OFF: - return net::DnsConfig::SecureDnsMode::OFF; + return net::SecureDnsMode::kOff; case OptionalSecureDnsMode::AUTOMATIC: - return net::DnsConfig::SecureDnsMode::AUTOMATIC; + return net::SecureDnsMode::kAutomatic; case OptionalSecureDnsMode::SECURE: - return net::DnsConfig::SecureDnsMode::SECURE; + return net::SecureDnsMode::kSecure; } } @@ -383,14 +383,14 @@ // static network::mojom::SecureDnsMode -EnumTraits<network::mojom::SecureDnsMode, net::DnsConfig::SecureDnsMode>:: - ToMojom(net::DnsConfig::SecureDnsMode secure_dns_mode) { +EnumTraits<network::mojom::SecureDnsMode, net::SecureDnsMode>::ToMojom( + net::SecureDnsMode secure_dns_mode) { switch (secure_dns_mode) { - case net::DnsConfig::SecureDnsMode::OFF: + case net::SecureDnsMode::kOff: return network::mojom::SecureDnsMode::OFF; - case net::DnsConfig::SecureDnsMode::AUTOMATIC: + case net::SecureDnsMode::kAutomatic: return network::mojom::SecureDnsMode::AUTOMATIC; - case net::DnsConfig::SecureDnsMode::SECURE: + case net::SecureDnsMode::kSecure: return network::mojom::SecureDnsMode::SECURE; } NOTREACHED(); @@ -398,18 +398,18 @@ } // static -bool EnumTraits<network::mojom::SecureDnsMode, net::DnsConfig::SecureDnsMode>:: - FromMojom(network::mojom::SecureDnsMode in, - net::DnsConfig::SecureDnsMode* out) { +bool EnumTraits<network::mojom::SecureDnsMode, net::SecureDnsMode>::FromMojom( + network::mojom::SecureDnsMode in, + net::SecureDnsMode* out) { switch (in) { case network::mojom::SecureDnsMode::OFF: - *out = net::DnsConfig::SecureDnsMode::OFF; + *out = net::SecureDnsMode::kOff; return true; case network::mojom::SecureDnsMode::AUTOMATIC: - *out = net::DnsConfig::SecureDnsMode::AUTOMATIC; + *out = net::SecureDnsMode::kAutomatic; return true; case network::mojom::SecureDnsMode::SECURE: - *out = net::DnsConfig::SecureDnsMode::SECURE; + *out = net::SecureDnsMode::kSecure; return true; } return false;
diff --git a/services/network/public/cpp/host_resolver_mojom_traits.h b/services/network/public/cpp/host_resolver_mojom_traits.h index 9591057..1d30f3e 100644 --- a/services/network/public/cpp/host_resolver_mojom_traits.h +++ b/services/network/public/cpp/host_resolver_mojom_traits.h
@@ -18,11 +18,11 @@ #include "net/base/address_family.h" #include "net/base/ip_address.h" #include "net/base/ip_endpoint.h" -#include "net/dns/dns_config.h" #include "net/dns/dns_config_overrides.h" #include "net/dns/dns_hosts.h" #include "net/dns/host_resolver.h" #include "net/dns/public/dns_query_type.h" +#include "net/dns/public/secure_dns_mode.h" #include "services/network/public/mojom/host_resolver.mojom-forward.h" #include "services/network/public/mojom/host_resolver.mojom-shared.h" @@ -30,7 +30,7 @@ // This is made visible for use by network::HostResolver. Not intended to be // used elsewhere. -base::Optional<net::DnsConfig::SecureDnsMode> FromOptionalSecureDnsMode( +base::Optional<net::SecureDnsMode> FromOptionalSecureDnsMode( network::mojom::OptionalSecureDnsMode mode); template <> @@ -115,12 +115,11 @@ }; template <> -struct EnumTraits<network::mojom::SecureDnsMode, - net::DnsConfig::SecureDnsMode> { +struct EnumTraits<network::mojom::SecureDnsMode, net::SecureDnsMode> { static network::mojom::SecureDnsMode ToMojom( - net::DnsConfig::SecureDnsMode secure_dns_mode); + net::SecureDnsMode secure_dns_mode); static bool FromMojom(network::mojom::SecureDnsMode in, - net::DnsConfig::SecureDnsMode* out); + net::SecureDnsMode* out); }; template <>
diff --git a/services/network/public/cpp/host_resolver_mojom_traits_unittest.cc b/services/network/public/cpp/host_resolver_mojom_traits_unittest.cc index 448f384..e58f2f90 100644 --- a/services/network/public/cpp/host_resolver_mojom_traits_unittest.cc +++ b/services/network/public/cpp/host_resolver_mojom_traits_unittest.cc
@@ -44,7 +44,7 @@ original.use_local_ipv6 = false; original.dns_over_https_servers.emplace( {net::DnsOverHttpsServerConfig("example.com", false)}); - original.secure_dns_mode = net::DnsConfig::SecureDnsMode::SECURE; + original.secure_dns_mode = net::SecureDnsMode::kSecure; original.allow_dns_over_https_upgrade = true; original.disabled_upgrade_providers.emplace({std::string("provider_name")});
diff --git a/services/network/public/cpp/net_ipc_param_traits.cc b/services/network/public/cpp/net_ipc_param_traits.cc index bb2f1be..9567cfd 100644 --- a/services/network/public/cpp/net_ipc_param_traits.cc +++ b/services/network/public/cpp/net_ipc_param_traits.cc
@@ -74,6 +74,8 @@ WriteParam(m, p.is_issued_by_known_root); WriteParam(m, p.is_issued_by_additional_trust_anchor); WriteParam(m, p.ocsp_result); + WriteParam(m, p.scts); + WriteParam(m, p.policy_compliance); } bool ParamTraits<net::CertVerifyResult>::Read(const base::Pickle* m, @@ -87,7 +89,8 @@ ReadParam(m, iter, &r->public_key_hashes) && ReadParam(m, iter, &r->is_issued_by_known_root) && ReadParam(m, iter, &r->is_issued_by_additional_trust_anchor) && - ReadParam(m, iter, &r->ocsp_result); + ReadParam(m, iter, &r->ocsp_result) && ReadParam(m, iter, &r->scts) && + ReadParam(m, iter, &r->policy_compliance); } void ParamTraits<net::CertVerifyResult>::Log(const param_type& p, @@ -95,26 +98,6 @@ l->append("<CertVerifyResult>"); } -void ParamTraits<net::ct::CTVerifyResult>::Write(base::Pickle* m, - const param_type& p) { - WriteParam(m, p.scts); - WriteParam(m, p.policy_compliance); - WriteParam(m, p.policy_compliance_required); -} - -bool ParamTraits<net::ct::CTVerifyResult>::Read(const base::Pickle* m, - base::PickleIterator* iter, - param_type* r) { - return ReadParam(m, iter, &r->scts) && - ReadParam(m, iter, &r->policy_compliance) && - ReadParam(m, iter, &r->policy_compliance_required); -} - -void ParamTraits<net::ct::CTVerifyResult>::Log(const param_type& p, - std::string* l) { - l->append("<CTVerifyResult>"); -} - void ParamTraits<net::HashValue>::Write(base::Pickle* m, const param_type& p) { WriteParam(m, p.ToString()); }
diff --git a/services/network/public/cpp/net_ipc_param_traits.h b/services/network/public/cpp/net_ipc_param_traits.h index c3835ff3..53f7441 100644 --- a/services/network/public/cpp/net_ipc_param_traits.h +++ b/services/network/public/cpp/net_ipc_param_traits.h
@@ -21,7 +21,6 @@ #include "net/base/request_priority.h" #include "net/cert/cert_verify_result.h" #include "net/cert/ct_policy_status.h" -#include "net/cert/ct_verify_result.h" #include "net/cert/signed_certificate_timestamp.h" #include "net/cert/signed_certificate_timestamp_and_status.h" #include "net/cert/x509_certificate.h" @@ -82,16 +81,6 @@ }; template <> -struct COMPONENT_EXPORT(NETWORK_CPP_BASE) ParamTraits<net::ct::CTVerifyResult> { - typedef net::ct::CTVerifyResult param_type; - static void Write(base::Pickle* m, const param_type& p); - static bool Read(const base::Pickle* m, - base::PickleIterator* iter, - param_type* r); - static void Log(const param_type& p, std::string* l); -}; - -template <> struct COMPONENT_EXPORT(NETWORK_CPP_BASE) ParamTraits<net::HashValue> { typedef net::HashValue param_type; static void Write(base::Pickle* m, const param_type& p);
diff --git a/services/network/public/mojom/BUILD.gn b/services/network/public/mojom/BUILD.gn index 47cc972d..9a260665 100644 --- a/services/network/public/mojom/BUILD.gn +++ b/services/network/public/mojom/BUILD.gn
@@ -750,7 +750,7 @@ }, { mojom = "network.mojom.SecureDnsMode" - cpp = "::net::DnsConfig::SecureDnsMode" + cpp = "::net::SecureDnsMode" }, ] traits_headers =
diff --git a/services/network/public/mojom/host_resolver.mojom b/services/network/public/mojom/host_resolver.mojom index 7d48d2a..3b7041c 100644 --- a/services/network/public/mojom/host_resolver.mojom +++ b/services/network/public/mojom/host_resolver.mojom
@@ -31,9 +31,8 @@ // The secure DNS mode specifies what types of lookups (secure/insecure) should // be performed and in what order when resolving a specific query. This is -// an expanded version of DnsConfig::SecureDnsMode that includes representation -// of an optional SecureDnsMode. Needed because Mojo does not support optional -// enums. +// an expanded version of net::SecureDnsMode that includes representation of an +// optional SecureDnsMode. Needed because Mojo does not support optional enums. enum OptionalSecureDnsMode { NO_OVERRIDE, OFF, @@ -41,7 +40,7 @@ SECURE, }; -// This enum corresponds to DnsConfig::SecureDnsMode. +// This enum corresponds to net::SecureDnsMode. enum SecureDnsMode { OFF, AUTOMATIC,
diff --git a/services/network/public/mojom/network_context.mojom b/services/network/public/mojom/network_context.mojom index 4e4731b..cd4d614 100644 --- a/services/network/public/mojom/network_context.mojom +++ b/services/network/public/mojom/network_context.mojom
@@ -1310,8 +1310,7 @@ url.mojom.Url url, string ocsp_response, string sct_list) => (int32 error_code, - CertVerifyResult cv_result, - CTVerifyResult ct_result); + CertVerifyResult cv_result); // Parses response headers and returns a structured version to the caller. // This call originates from the browser process. Used for navigations when
diff --git a/services/network/public/mojom/network_param.mojom b/services/network/public/mojom/network_param.mojom index 41f3103..8f9f5d0 100644 --- a/services/network/public/mojom/network_param.mojom +++ b/services/network/public/mojom/network_param.mojom
@@ -14,9 +14,6 @@ struct CertVerifyResult; [Native] -struct CTVerifyResult; - -[Native] struct HttpResponseHeaders; struct HttpVersion {
diff --git a/services/network/trust_tokens/expiry_inspecting_record_expiry_delegate.cc b/services/network/trust_tokens/expiry_inspecting_record_expiry_delegate.cc index 0a893d96..4993575 100644 --- a/services/network/trust_tokens/expiry_inspecting_record_expiry_delegate.cc +++ b/services/network/trust_tokens/expiry_inspecting_record_expiry_delegate.cc
@@ -93,9 +93,10 @@ // changed (due to data corruption) or the commitments changed (due to an // overwrite by the key commitments' producer, or due to data corruption). // - // In both cases, the SRR's verification key doesn't correspond to the current - // key commitments we possess for the issuer, because we don't have any - // key commitments whatsoever for the issuer: mark the record as expired. + // In both cases, the SRR's associated token-issuance verification key isn't + // present in the current key commitments we possess for the issuer, because + // we don't have any key commitments whatsoever for the issuer: mark the + // record as expired. if (!key_commitments) return true;
diff --git a/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom b/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom index 195bd55..4afc007 100644 --- a/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom +++ b/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom
@@ -127,10 +127,9 @@ // Starts throttling the frame sinks specified by |frame_sink_ids| and all // their descendant sinks to send BeginFrames at an interval of |interval|. - // |interval| should be greater than zero. Calling this function before - // calling EndThrottling() to end a previous throttling operation will - // automatically end the previous operation before applying the current - // throttling operation. + // |interval| should be greater than zero. Previous throttling operation on + // any frame sinks must be first ended by calling EndThrottling() before + // applying the current throttling operation. StartThrottling( array<FrameSinkId> frame_sink_ids, mojo_base.mojom.TimeDelta interval);
diff --git a/services/viz/privileged/mojom/compositing/renderer_settings.mojom b/services/viz/privileged/mojom/compositing/renderer_settings.mojom index 36a5d07..ca57728 100644 --- a/services/viz/privileged/mojom/compositing/renderer_settings.mojom +++ b/services/viz/privileged/mojom/compositing/renderer_settings.mojom
@@ -18,7 +18,6 @@ bool should_clear_root_render_pass; int32 slow_down_compositing_scale_factor; bool use_skia_renderer; - bool record_sk_picture; bool allow_overlays; bool auto_resize_output_surface; bool requires_alpha_channel;
diff --git a/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.cc b/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.cc index eed93b40..7eea9d2 100644 --- a/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.cc +++ b/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.cc
@@ -40,7 +40,6 @@ out->slow_down_compositing_scale_factor = data.slow_down_compositing_scale_factor(); out->use_skia_renderer = data.use_skia_renderer(); - out->record_sk_picture = data.record_sk_picture(); out->allow_overlays = data.allow_overlays(); out->auto_resize_output_surface = data.auto_resize_output_surface(); out->requires_alpha_channel = data.requires_alpha_channel();
diff --git a/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.h b/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.h index 09efec4..708bca9 100644 --- a/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.h +++ b/services/viz/privileged/mojom/compositing/renderer_settings_mojom_traits.h
@@ -83,10 +83,6 @@ return input.use_skia_renderer; } - static bool record_sk_picture(const viz::RendererSettings& input) { - return input.record_sk_picture; - } - static bool allow_overlays(const viz::RendererSettings& input) { return input.allow_overlays; }
diff --git a/testing/buildbot/chromium.ci.json b/testing/buildbot/chromium.ci.json index 8625d2d..8ee2502b 100644 --- a/testing/buildbot/chromium.ci.json +++ b/testing/buildbot/chromium.ci.json
@@ -26096,7 +26096,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -27239,7 +27238,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -201627,7 +201625,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -202851,7 +202848,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -204040,7 +204036,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -205186,7 +205181,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": {
diff --git a/testing/buildbot/chromium.fyi.json b/testing/buildbot/chromium.fyi.json index 80176d36..170c3adb 100644 --- a/testing/buildbot/chromium.fyi.json +++ b/testing/buildbot/chromium.fyi.json
@@ -1862,214 +1862,6 @@ } ] }, - "Mojo Android": { - "gtest_tests": [] - }, - "Mojo ChromiumOS": { - "gtest_tests": [ - { - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "aura_unittests", - "test_id_prefix": "ninja://ui/aura:aura_unittests/" - }, - { - "args": [ - "--enable-features=NetworkService" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_browser_tests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 15 - }, - "test": "browser_tests", - "test_id_prefix": "ninja://chrome/test:browser_tests/" - }, - { - "args": [ - "--enable-features=NetworkService" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_components_browsertests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "components_browsertests", - "test_id_prefix": "ninja://components:components_browsertests/" - }, - { - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "compositor_unittests", - "test_id_prefix": "ninja://ui/compositor:compositor_unittests/" - }, - { - "args": [ - "--enable-features=NetworkService" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_content_browsertests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 2 - }, - "test": "content_browsertests", - "test_id_prefix": "ninja://content/test:content_browsertests/" - }, - { - "args": [ - "--enable-features=NetworkService" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_extensions_browsertests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "extensions_browsertests", - "test_id_prefix": "ninja://extensions:extensions_browsertests/" - }, - { - "args": [ - "--enable-features=NetworkService" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_interactive_ui_tests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 3 - }, - "test": "interactive_ui_tests", - "test_id_prefix": "ninja://chrome/test:interactive_ui_tests/" - }, - { - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "wayland_client_perftests", - "test_id_prefix": "ninja://components/exo/wayland:wayland_client_perftests/" - }, - { - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "wm_unittests", - "test_id_prefix": "ninja://ui/wm:wm_unittests/" - } - ] - }, - "Mojo Linux": { - "gtest_tests": [] - }, - "Mojo Windows": { - "gtest_tests": [ - { - "args": [ - "--enable-features=NetworkService,NetworkServiceInProcess" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_in_process_browser_tests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 15 - }, - "test": "browser_tests", - "test_id_prefix": "ninja://chrome/test:browser_tests/" - }, - { - "args": [ - "--enable-features=ForceWebRequestProxyForTest" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_web_request_proxy_browser_tests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 15 - }, - "test": "browser_tests", - "test_id_prefix": "ninja://chrome/test:browser_tests/" - }, - { - "args": [ - "--enable-features=NetworkService,NetworkServiceInProcess" - ], - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "name": "network_service_in_process_content_browsertests", - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 2 - }, - "test": "content_browsertests", - "test_id_prefix": "ninja://content/test:content_browsertests/" - }, - { - "merge": { - "args": [], - "script": "//testing/merge_scripts/standard_gtest_merge.py" - }, - "swarming": { - "can_use_on_swarming_builders": true, - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "services_unittests", - "test_id_prefix": "ninja://services:services_unittests/" - } - ] - }, "Site Isolation Android": { "additional_compile_targets": [ "content_browsertests", @@ -14257,261 +14049,6 @@ } ] }, - "android-mojo-webview-rel": { - "gtest_tests": [ - { - "args": [ - "--disable-features=NetworkServiceInProcess", - "--gs-results-bucket=chromium-result-details", - "--recover-devices", - "--git-revision=${got_revision}" - ], - "merge": { - "args": [ - "--bucket", - "chromium-result-details", - "--test-name", - "network_service_out_of_process_chrome_public_test_apk" - ], - "script": "//build/android/pylib/results/presentation/test_results_presentation.py" - }, - "name": "network_service_out_of_process_chrome_public_test_apk", - "precommit_args": [ - "--gerrit-issue=${patch_issue}", - "--gerrit-patchset=${patch_set}", - "--buildbucket-id=${buildbucket_build_id}" - ], - "swarming": { - "can_use_on_swarming_builders": true, - "cipd_packages": [ - { - "cipd_package": "infra/tools/luci/logdog/butler/${platform}", - "location": "bin", - "revision": "git_revision:ff387eadf445b24c935f1cf7d6ddd279f8a6b04c" - } - ], - "dimension_sets": [ - { - "device_os": "MMB29Q", - "device_os_type": "userdebug", - "device_type": "bullhead", - "os": "Android" - } - ], - "output_links": [ - { - "link": [ - "https://luci-logdog.appspot.com/v/?s", - "=android%2Fswarming%2Flogcats%2F", - "${TASK_ID}%2F%2B%2Funified_logcats" - ], - "name": "shard #${SHARD_INDEX} logcats" - } - ], - "service_account": "chrome-gold@chops-service-accounts.iam.gserviceaccount.com", - "shards": 20 - }, - "test": "chrome_public_test_apk", - "test_id_prefix": "ninja://chrome/android:chrome_public_test_apk/" - }, - { - "args": [ - "--disable-features=NetworkServiceInProcess", - "--gs-results-bucket=chromium-result-details", - "--recover-devices" - ], - "merge": { - "args": [ - "--bucket", - "chromium-result-details", - "--test-name", - "network_service_out_of_process_components_browsertests" - ], - "script": "//build/android/pylib/results/presentation/test_results_presentation.py" - }, - "name": "network_service_out_of_process_components_browsertests", - "swarming": { - "can_use_on_swarming_builders": true, - "cipd_packages": [ - { - "cipd_package": "infra/tools/luci/logdog/butler/${platform}", - "location": "bin", - "revision": "git_revision:ff387eadf445b24c935f1cf7d6ddd279f8a6b04c" - } - ], - "dimension_sets": [ - { - "device_os": "MMB29Q", - "device_os_type": "userdebug", - "device_type": "bullhead", - "os": "Android" - } - ], - "output_links": [ - { - "link": [ - "https://luci-logdog.appspot.com/v/?s", - "=android%2Fswarming%2Flogcats%2F", - "${TASK_ID}%2F%2B%2Funified_logcats" - ], - "name": "shard #${SHARD_INDEX} logcats" - } - ], - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" - }, - "test": "components_browsertests", - "test_id_prefix": "ninja://components:components_browsertests/" - }, - { - "args": [ - "--disable-features=NetworkServiceInProcess", - "--gs-results-bucket=chromium-result-details", - "--recover-devices" - ], - "merge": { - "args": [ - "--bucket", - "chromium-result-details", - "--test-name", - "network_service_out_of_process_content_browsertests" - ], - "script": "//build/android/pylib/results/presentation/test_results_presentation.py" - }, - "name": "network_service_out_of_process_content_browsertests", - "swarming": { - "can_use_on_swarming_builders": true, - "cipd_packages": [ - { - "cipd_package": "infra/tools/luci/logdog/butler/${platform}", - "location": "bin", - "revision": "git_revision:ff387eadf445b24c935f1cf7d6ddd279f8a6b04c" - } - ], - "dimension_sets": [ - { - "device_os": "MMB29Q", - "device_os_type": "userdebug", - "device_type": "bullhead", - "os": "Android" - } - ], - "output_links": [ - { - "link": [ - "https://luci-logdog.appspot.com/v/?s", - "=android%2Fswarming%2Flogcats%2F", - "${TASK_ID}%2F%2B%2Funified_logcats" - ], - "name": "shard #${SHARD_INDEX} logcats" - } - ], - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 5 - }, - "test": "content_browsertests", - "test_id_prefix": "ninja://content/test:content_browsertests/" - }, - { - "args": [ - "--disable-features=NetworkServiceInProcess", - "--gs-results-bucket=chromium-result-details", - "--recover-devices" - ], - "merge": { - "args": [ - "--bucket", - "chromium-result-details", - "--test-name", - "network_service_out_of_process_content_shell_test_apk" - ], - "script": "//build/android/pylib/results/presentation/test_results_presentation.py" - }, - "name": "network_service_out_of_process_content_shell_test_apk", - "swarming": { - "can_use_on_swarming_builders": true, - "cipd_packages": [ - { - "cipd_package": "infra/tools/luci/logdog/butler/${platform}", - "location": "bin", - "revision": "git_revision:ff387eadf445b24c935f1cf7d6ddd279f8a6b04c" - } - ], - "dimension_sets": [ - { - "device_os": "MMB29Q", - "device_os_type": "userdebug", - "device_type": "bullhead", - "os": "Android" - } - ], - "output_links": [ - { - "link": [ - "https://luci-logdog.appspot.com/v/?s", - "=android%2Fswarming%2Flogcats%2F", - "${TASK_ID}%2F%2B%2Funified_logcats" - ], - "name": "shard #${SHARD_INDEX} logcats" - } - ], - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 5 - }, - "test": "content_shell_test_apk", - "test_id_prefix": "ninja://content/shell/android:content_shell_test_apk/" - }, - { - "args": [ - "--enable-features=NetworkService,NetworkServiceInProcess", - "--test-launcher-filter-file=../../testing/buildbot/filters/mojo.fyi.network_webview_instrumentation_test_apk.filter", - "--gs-results-bucket=chromium-result-details", - "--recover-devices" - ], - "merge": { - "args": [ - "--bucket", - "chromium-result-details", - "--test-name", - "network_service_webview_instrumentation_test_apk" - ], - "script": "//build/android/pylib/results/presentation/test_results_presentation.py" - }, - "name": "network_service_webview_instrumentation_test_apk", - "swarming": { - "can_use_on_swarming_builders": true, - "cipd_packages": [ - { - "cipd_package": "infra/tools/luci/logdog/butler/${platform}", - "location": "bin", - "revision": "git_revision:ff387eadf445b24c935f1cf7d6ddd279f8a6b04c" - } - ], - "dimension_sets": [ - { - "device_os": "MMB29Q", - "device_os_type": "userdebug", - "device_type": "bullhead", - "os": "Android" - } - ], - "output_links": [ - { - "link": [ - "https://luci-logdog.appspot.com/v/?s", - "=android%2Fswarming%2Flogcats%2F", - "${TASK_ID}%2F%2B%2Funified_logcats" - ], - "name": "shard #${SHARD_INDEX} logcats" - } - ], - "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", - "shards": 20 - }, - "test": "webview_instrumentation_test_apk", - "test_id_prefix": "ninja://android_webview/test:webview_instrumentation_test_apk/" - } - ] - }, "chromeos-amd64-generic-lacros-rel": { "additional_compile_targets": [ "chrome" @@ -15294,7 +14831,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -16518,7 +16054,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -17707,7 +17242,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -18853,7 +18387,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -51801,7 +51334,6 @@ "all" ] }, - "mac-mojo-rel": {}, "mac-osxbeta-rel": { "gtest_tests": [ {
diff --git a/testing/buildbot/chromium.linux.json b/testing/buildbot/chromium.linux.json index dbcc700..40fda4d 100644 --- a/testing/buildbot/chromium.linux.json +++ b/testing/buildbot/chromium.linux.json
@@ -2518,7 +2518,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": { @@ -3661,7 +3660,6 @@ }, { "args": [ - "--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter", "--runner-logs-dir=${ISOLATED_OUTDIR}/runner_logs" ], "merge": {
diff --git a/testing/buildbot/filters/BUILD.gn b/testing/buildbot/filters/BUILD.gn index 1db0905..384e2fa3c 100644 --- a/testing/buildbot/filters/BUILD.gn +++ b/testing/buildbot/filters/BUILD.gn
@@ -129,7 +129,6 @@ "//testing/buildbot/filters/fuchsia.components_unittests.filter", "//testing/buildbot/filters/fuchsia.content_unittests.filter", "//testing/buildbot/filters/fuchsia.headless_browsertests.filter", - "//testing/buildbot/filters/fuchsia.mojo_unittests.filter", "//testing/buildbot/filters/fuchsia.net_perftests.filter", "//testing/buildbot/filters/fuchsia.net_unittests.filter", "//testing/buildbot/filters/fuchsia.services_unittests.filter",
diff --git a/testing/buildbot/filters/fuchsia.mojo_unittests.filter b/testing/buildbot/filters/fuchsia.mojo_unittests.filter deleted file mode 100644 index 08b60848..0000000 --- a/testing/buildbot/filters/fuchsia.mojo_unittests.filter +++ /dev/null
@@ -1,9 +0,0 @@ -# TODO(fuchsia): Fix the tests and delete this file. crbug.com/740791 - -# These tests are too slow under QEMU w/out KVM. See crbug.com/745801. --MessagePipeTest.ClosePipesStressTest --MessageTest.ExtendMessagePayloadLarge - -# crbug.com/780317 - These timeout under QEMU s/w emulation of ARM64. --MultiprocessMessagePipeTestWithPeerSupport.PingPongPipe* --MessagePipeTest.SharedBufferHandlePingPong
diff --git a/testing/buildbot/test_suites.pyl b/testing/buildbot/test_suites.pyl index f7e292c..f07295e4 100644 --- a/testing/buildbot/test_suites.pyl +++ b/testing/buildbot/test_suites.pyl
@@ -1456,9 +1456,6 @@ }, 'mojo_unittests': { 'mixins': ['fuchsia_runner_logs'], - 'args': [ - '--test-launcher-filter-file=../../testing/buildbot/filters/fuchsia.mojo_unittests.filter', - ], }, 'native_theme_unittests': { 'mixins': ['fuchsia_runner_logs'],
diff --git a/testing/buildbot/waterfalls.pyl b/testing/buildbot/waterfalls.pyl index 0e712b36..0572297 100644 --- a/testing/buildbot/waterfalls.pyl +++ b/testing/buildbot/waterfalls.pyl
@@ -1869,42 +1869,6 @@ 'isolated_scripts': 'chromium_mac_rel_isolated_scripts', }, }, - # TODO(https://crbug.com/1131163) Remove the mojo entries once the - # builders have started reading from the correct spec file - 'Mojo Android': { - 'swarming': { - 'dimension_sets': [ - { - 'device_os': 'MMB29Q', - 'device_type': 'bullhead', - 'os': 'Android', - }, - ], - 'hard_timeout': 3600, - }, - 'os_type': 'android', - 'test_suites': { - 'gtest_tests': 'mojo_android_gtests', - }, - }, - 'Mojo ChromiumOS': { - 'test_suites': { - 'gtest_tests': 'mojo_chromiumos_fyi_gtests', - }, - }, - 'Mojo Linux': { - 'mixins': [ - 'linux-xenial', - ], - 'test_suites': { - 'gtest_tests': 'mojo_linux_gtests', - }, - }, - 'Mojo Windows': { - 'test_suites': { - 'gtest_tests': 'mojo_windows_gtests', - }, - }, 'Site Isolation Android': { 'additional_compile_targets': [ 'content_browsertests', @@ -2013,23 +1977,6 @@ 'use_swarming': True, 'os_type': 'android', }, - # TODO(https://crbug.com/1131163) Remove the mojo entries once the - # builders have started reading from the correct spec file - 'android-mojo-webview-rel': { - 'swarming': { - 'dimension_sets': [ - { - 'device_os': 'MMB29Q', - 'device_type': 'bullhead', - 'os': 'Android', - }, - ], - }, - 'os_type': 'android', - 'test_suites': { - 'gtest_tests': 'network_service_android_gtests', - }, - }, 'chromeos-amd64-generic-lacros-rel': { 'additional_compile_targets': [ 'chrome', @@ -2428,14 +2375,6 @@ 'all', ], }, - # TODO(https://crbug.com/1131163) Remove the mojo entries once the - # builders have started reading from the correct spec file - 'mac-mojo-rel': { - 'mixins': [ - 'mac_10.13', - 'no_gpu', - ], - }, 'mac-osxbeta-rel': { 'mixins': [ 'intel_iris_5100',
diff --git a/testing/scripts/check_static_initializers.py b/testing/scripts/check_static_initializers.py index ac600da9..c1706d9d 100755 --- a/testing/scripts/check_static_initializers.py +++ b/testing/scripts/check_static_initializers.py
@@ -45,7 +45,6 @@ 'protobuf_http_status.cc', # TODO(crbug.com/537099): Remove. 'rpc.pb.cc', # TODO(crbug.com/537099): Remove. 'switch_access_menu_view.cc', # TODO(crbug.com/537099): Remove. - 'uri_impl.cc', # TODO(crbug.com/537099): Remove. ], 'nacl_helper_bootstrap': [], }
diff --git a/testing/variations/fieldtrial_testing_config.json b/testing/variations/fieldtrial_testing_config.json index 136492e..7f25e75f 100644 --- a/testing/variations/fieldtrial_testing_config.json +++ b/testing/variations/fieldtrial_testing_config.json
@@ -4547,31 +4547,6 @@ ] } ], - "NewTabInProductHelp": [ - { - "platforms": [ - "linux", - "windows" - ], - "experiments": [ - { - "name": "Enabled_1", - "params": { - "availability": "any", - "event_new_tab_session_time_met": "name:new_tab_session_time_met;comparator:>=1;window:3650;storage:3650", - "event_omnibox_used": "name:omnibox_used;comparator:>=1;window:3650;storage:3650", - "event_trigger": "name:new_tab_trigger;comparator:==0;window:3650;storage:3650", - "event_used": "name:new_tab_opened;comparator:==0;window:3650;storage:3650", - "session_rate": "<0", - "x_promo_string": "0" - }, - "enable_features": [ - "IPH_NewTab" - ] - } - ] - } - ], "NewUsbBackend": [ { "platforms": [ @@ -5688,7 +5663,8 @@ "params": { "connection_options": "5RTO", "enable_quic": "true", - "quic_version": "h3-Q050" + "quic_version": "h3-Q050", + "retransmittable_on_wire_timeout_milliseconds": "200" }, "enable_features": [ "QuicDoesNotUseFeatures" @@ -6482,21 +6458,6 @@ ] } ], - "Show109ObsoleteInfobar": [ - { - "platforms": [ - "mac" - ], - "experiments": [ - { - "name": "Enabled", - "enable_features": [ - "Show109ObsoleteInfobar" - ] - } - ] - } - ], "SimplifiedUrlDisplay": [ { "platforms": [
diff --git a/third_party/android_deps/BUILD.gn b/third_party/android_deps/BUILD.gn index fbc7046..9b1a6eb8 100644 --- a/third_party/android_deps/BUILD.gn +++ b/third_party/android_deps/BUILD.gn
@@ -192,6 +192,14 @@ } # This is generated, do not edit. Update BuildConfigGenerator.groovy instead. +java_prebuilt("androidx_arch_core_core_common_java") { + jar_path = "libs/androidx_arch_core_core_common/core-common-2.1.0.jar" + output_name = "androidx_arch_core_core_common" + supports_android = true + deps = [ ":androidx_annotation_annotation_java" ] +} + +# This is generated, do not edit. Update BuildConfigGenerator.groovy instead. android_aar_prebuilt("androidx_asynclayoutinflater_asynclayoutinflater_java") { aar_path = "libs/androidx_asynclayoutinflater_asynclayoutinflater/asynclayoutinflater-1.0.0.aar" info_path = "libs/androidx_asynclayoutinflater_asynclayoutinflater/androidx_asynclayoutinflater_asynclayoutinflater.info" @@ -1864,18 +1872,6 @@ } # This is generated, do not edit. Update BuildConfigGenerator.groovy instead. -java_prebuilt("androidx_arch_core_core_common_java") { - jar_path = "libs/androidx_arch_core_core_common/core-common-2.1.0.jar" - output_name = "androidx_arch_core_core_common" - supports_android = true - - # To remove visibility constraint, add this dependency to - # //third_party/android_deps/build.gradle. - visibility = [ ":*" ] - deps = [ ":androidx_annotation_annotation_java" ] -} - -# This is generated, do not edit. Update BuildConfigGenerator.groovy instead. android_aar_prebuilt("androidx_arch_core_core_runtime_java") { aar_path = "libs/androidx_arch_core_core_runtime/core-runtime-2.1.0.aar" info_path = "libs/androidx_arch_core_core_runtime/androidx_arch_core_core_runtime.info"
diff --git a/third_party/android_deps/build.gradle b/third_party/android_deps/build.gradle index 051557b..ffe68b2b 100644 --- a/third_party/android_deps/build.gradle +++ b/third_party/android_deps/build.gradle
@@ -82,7 +82,8 @@ compile "androidx.window:window:1.0.0-alpha01" compile "androidx.exifinterface:exifinterface:${androidXSupportLibVersion}" - // Those are for use by doubledown material design + // Those are for use by doubledown libraries. + compile "androidx.arch.core:core-common:2.1.0" compile "androidx.annotation:annotation-experimental:${androidXSupportLibVersion}" compile "androidx.annotation:annotation:${androidXSupportLibVersion}" compile "androidx.lifecycle:lifecycle-runtime:${androidXSupportLibVersion}"
diff --git a/third_party/blink/perf_tests/dom/OWNERS b/third_party/blink/perf_tests/dom/OWNERS new file mode 100644 index 0000000..2757923f --- /dev/null +++ b/third_party/blink/perf_tests/dom/OWNERS
@@ -0,0 +1 @@ +file://third_party/blink/renderer/core/dom/OWNERS
diff --git a/third_party/blink/perf_tests/parser/OWNERS b/third_party/blink/perf_tests/parser/OWNERS new file mode 100644 index 0000000..67eaaa7 --- /dev/null +++ b/third_party/blink/perf_tests/parser/OWNERS
@@ -0,0 +1 @@ +file://third_party/blink/renderer/core/html/parser/OWNERS
diff --git a/third_party/blink/perf_tests/parser/declarative-shadow-dom.html b/third_party/blink/perf_tests/parser/declarative-shadow-dom.html new file mode 100644 index 0000000..5920a52c --- /dev/null +++ b/third_party/blink/perf_tests/parser/declarative-shadow-dom.html
@@ -0,0 +1,35 @@ +<!DOCTYPE html> +<html> +<body> +<script src="../resources/runner.js"></script> +<script> + +function checkOne(mode,wrapper) { + const div = document.createElement('div'); + wrapper.appendChild(div); + div.innerHTML = `<div id="host"><template shadowroot="${mode}"><slot name="slot1"></slot></template><div slot="slot1"></div></div>` +} + +PerfTestRunner.measureRunsPerSecond({ + description: "This benchmark tests declarative Shadow DOM attachment", + + setup: function() { + const wrapper = document.createElement('div'); + wrapper.id = 'wrapper'; + document.body.appendChild(wrapper); + }, + + run: function() { + for (var i = 0; i < 1000; i++) { + checkOne('open',wrapper); + checkOne('closed',wrapper); + } + }, + + teardown: function() { + wrapper.remove(); + }}); + +</script> +</body> +</html> \ No newline at end of file
diff --git a/third_party/blink/perf_tests/shadow_dom/OWNERS b/third_party/blink/perf_tests/shadow_dom/OWNERS new file mode 100644 index 0000000..2757923f --- /dev/null +++ b/third_party/blink/perf_tests/shadow_dom/OWNERS
@@ -0,0 +1 @@ +file://third_party/blink/renderer/core/dom/OWNERS
diff --git a/third_party/blink/public/mojom/web_feature/web_feature.mojom b/third_party/blink/public/mojom/web_feature/web_feature.mojom index d3ddd7d..6e19b799 100644 --- a/third_party/blink/public/mojom/web_feature/web_feature.mojom +++ b/third_party/blink/public/mojom/web_feature/web_feature.mojom
@@ -2873,7 +2873,7 @@ kV8HIDDevice_ProductId_AttributeGetter = 3543, kV8HIDDevice_ProductName_AttributeGetter = 3544, kV8HIDDevice_VendorId_AttributeGetter = 3545, - kIdentifiabilityStudyReserved3546 = 3546, + kV8BeforeInstallPromptEvent_Platforms_AttributeGetter = 3546, kV8HIDReportItem_HasNull_AttributeGetter = 3547, kV8HIDReportItem_IsAbsolute_AttributeGetter = 3548, kV8HIDReportItem_IsArray_AttributeGetter = 3549,
diff --git a/third_party/blink/renderer/core/editing/BUILD.gn b/third_party/blink/renderer/core/editing/BUILD.gn index 3577f4c..928a70e 100644 --- a/third_party/blink/renderer/core/editing/BUILD.gn +++ b/third_party/blink/renderer/core/editing/BUILD.gn
@@ -4,6 +4,13 @@ import("//third_party/blink/renderer/core/core.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + blink_core_sources("editing") { sources = [ "bidi_adjustment.cc",
diff --git a/third_party/blink/renderer/core/exported/web_frame_test.cc b/third_party/blink/renderer/core/exported/web_frame_test.cc index 340c520..72ce6b86 100644 --- a/third_party/blink/renderer/core/exported/web_frame_test.cc +++ b/third_party/blink/renderer/core/exported/web_frame_test.cc
@@ -8356,7 +8356,8 @@ return true; } layer.CapturePaintRecord(); - if (!layer.GetPaintController().GetPaintArtifact().IsEmpty()) + if (layer.GetPaintController().GetDisplayItemList().size() > 0 || + layer.GetPaintController().PaintChunks().size() > 0) ++actively_painting_layers; return true; }); @@ -8489,7 +8490,8 @@ return true; } layer.CapturePaintRecord(); - if (!layer.GetPaintController().GetPaintArtifact().IsEmpty()) + if (layer.GetPaintController().GetDisplayItemList().size() > 0 || + layer.GetPaintController().PaintChunks().size() > 0) ++actively_painting_layers; return true; });
diff --git a/third_party/blink/renderer/core/frame/web_frame_widget_impl.cc b/third_party/blink/renderer/core/frame/web_frame_widget_impl.cc index 683035c9..82b09a9 100644 --- a/third_party/blink/renderer/core/frame/web_frame_widget_impl.cc +++ b/third_party/blink/renderer/core/frame/web_frame_widget_impl.cc
@@ -300,8 +300,16 @@ if (!LocalRootImpl()) return; + // Dirty bit on MouseEventManager is not cleared in OOPIFs after scroll + // or layout changes. Ensure the hover state is recomputed if necessary. + LocalRootImpl() + ->GetFrame() + ->GetEventHandler() + .RecomputeMouseHoverStateIfNeeded(); + DocumentLifecycle::AllowThrottlingScope throttling_scope( LocalRootImpl()->GetFrame()->GetDocument()->Lifecycle()); + if (WidgetBase::ShouldRecordBeginMainFrameMetrics()) { SCOPED_UMA_AND_UKM_TIMER( LocalRootImpl()->GetFrame()->View()->EnsureUkmAggregator(),
diff --git a/third_party/blink/renderer/core/html/forms/internal_popup_menu.cc b/third_party/blink/renderer/core/html/forms/internal_popup_menu.cc index 98fa373..ec97640 100644 --- a/third_party/blink/renderer/core/html/forms/internal_popup_menu.cc +++ b/third_party/blink/renderer/core/html/forms/internal_popup_menu.cc
@@ -10,7 +10,9 @@ #include "third_party/blink/public/platform/task_type.h" #include "third_party/blink/renderer/core/css/css_font_selector.h" #include "third_party/blink/renderer/core/css/css_value_id_mappings.h" +#include "third_party/blink/renderer/core/css/pseudo_style_request.h" #include "third_party/blink/renderer/core/css/style_engine.h" +#include "third_party/blink/renderer/core/dom/element.h" #include "third_party/blink/renderer/core/dom/element_traversal.h" #include "third_party/blink/renderer/core/dom/events/scoped_event_queue.h" #include "third_party/blink/renderer/core/dom/node_computed_style.h" @@ -25,9 +27,11 @@ #include "third_party/blink/renderer/core/html/parser/html_parser_idioms.h" #include "third_party/blink/renderer/core/html_names.h" #include "third_party/blink/renderer/core/input/event_handler.h" +#include "third_party/blink/renderer/core/layout/layout_box.h" #include "third_party/blink/renderer/core/layout/layout_theme.h" #include "third_party/blink/renderer/core/page/chrome_client.h" #include "third_party/blink/renderer/core/page/page_popup.h" +#include "third_party/blink/renderer/core/scroll/scrollable_area.h" #include "third_party/blink/renderer/platform/fonts/font_selector.h" #include "third_party/blink/renderer/platform/fonts/font_selector_client.h" #include "third_party/blink/renderer/platform/geometry/int_rect.h" @@ -59,6 +63,37 @@ value->CssText().Utf8().c_str()); } +ScrollbarPart ScrollbarPartFromPseudoId(PseudoId id) { + switch (id) { + case kPseudoIdScrollbar: + return kScrollbarBGPart; + case kPseudoIdScrollbarThumb: + return kThumbPart; + case kPseudoIdScrollbarTrack: + case kPseudoIdScrollbarTrackPiece: + return kBackTrackPart; + default: + break; + } + return kNoPart; +} + +scoped_refptr<const ComputedStyle> StyleForHoveredScrollbarPart( + HTMLSelectElement& element, + const ComputedStyle* style, + Scrollbar* scrollbar, + PseudoId target_id) { + ScrollbarPart part = ScrollbarPartFromPseudoId(target_id); + if (part == kNoPart) + return nullptr; + scrollbar->SetHoveredPart(part); + scoped_refptr<const ComputedStyle> part_style = element.StyleForPseudoElement( + PseudoElementStyleRequest(target_id, To<CustomScrollbar>(scrollbar), + part), + style); + return part_style; +} + } // anonymous namespace class PopupMenuCSSFontSelector : public CSSFontSelector, @@ -236,30 +271,41 @@ "<!DOCTYPE html><head><meta charset='UTF-8'><style>\n", data); LayoutObject* owner_layout = owner_element.GetLayoutObject(); - if (const ComputedStyle* style = - owner_layout->GetCachedPseudoElementStyle(kPseudoIdScrollbar)) { - AppendOwnerElementPseudoStyles("select::-webkit-scrollbar", data, *style); + + std::pair<PseudoId, const String> targets[] = { + {kPseudoIdScrollbar, "select::-webkit-scrollbar"}, + {kPseudoIdScrollbarThumb, "select::-webkit-scrollbar-thumb"}, + {kPseudoIdScrollbarTrack, "select::-webkit-scrollbar-track"}, + {kPseudoIdScrollbarTrackPiece, "select::-webkit-scrollbar-track-piece"}, + {kPseudoIdScrollbarCorner, "select::-webkit-scrollbar-corner"}}; + + Scrollbar* temp_scrollbar = nullptr; + const LayoutBox* box = owner_element.InnerElement().GetLayoutBox(); + if (box && box->GetScrollableArea()) { + if (ScrollableArea* scrollable = box->GetScrollableArea()) { + temp_scrollbar = MakeGarbageCollected<CustomScrollbar>( + scrollable, kVerticalScrollbar, &owner_element.InnerElement()); + } } - if (const ComputedStyle* style = - owner_layout->GetCachedPseudoElementStyle(kPseudoIdScrollbarThumb)) { - AppendOwnerElementPseudoStyles("select::-webkit-scrollbar-thumb", data, - *style); + for (auto target : targets) { + if (const ComputedStyle* style = + owner_layout->GetCachedPseudoElementStyle(target.first)) { + AppendOwnerElementPseudoStyles(target.second, data, *style); + } + // For Pseudo-class styles, Style should be calculated via that status. + if (temp_scrollbar) { + scoped_refptr<const ComputedStyle> part_style = + StyleForHoveredScrollbarPart(owner_element, + owner_element.GetComputedStyle(), + temp_scrollbar, target.first); + if (part_style) { + AppendOwnerElementPseudoStyles(target.second + ":hover", data, + *part_style); + } + } } - if (const ComputedStyle* style = - owner_layout->GetCachedPseudoElementStyle(kPseudoIdScrollbarTrack)) { - AppendOwnerElementPseudoStyles("select::-webkit-scrollbar-track", data, - *style); - } - if (const ComputedStyle* style = owner_layout->GetCachedPseudoElementStyle( - kPseudoIdScrollbarTrackPiece)) { - AppendOwnerElementPseudoStyles("select::-webkit-scrollbar-track-piece", - data, *style); - } - if (const ComputedStyle* style = - owner_layout->GetCachedPseudoElementStyle(kPseudoIdScrollbarCorner)) { - AppendOwnerElementPseudoStyles("select::-webkit-scrollbar-corner", data, - *style); - } + if (temp_scrollbar) + temp_scrollbar->DisconnectFromScrollableArea(); data->Append(ChooserResourceLoader::GetPickerCommonStyleSheet()); data->Append(ChooserResourceLoader::GetListPickerStyleSheet());
diff --git a/third_party/blink/renderer/core/html/html_view_source_document.cc b/third_party/blink/renderer/core/html/html_view_source_document.cc index 4371b90b..3176975 100644 --- a/third_party/blink/renderer/core/html/html_view_source_document.cc +++ b/third_party/blink/renderer/core/html/html_view_source_document.cc
@@ -70,8 +70,7 @@ body->ParserAppendChild(div); auto* table = MakeGarbageCollected<HTMLTableElement>(*this); - table->SetInlineStyleProperty(CSSPropertyID::kWordBreak, - PlatformEnumToCSSValueID(EWordBreak::kKeepAll)); + table->SetInlineStyleProperty(CSSPropertyID::kWhiteSpace, CSSValueID::kPre); body->ParserAppendChild(table); tbody_ = MakeGarbageCollected<HTMLTableSectionElement>(html_names::kTbodyTag, *this);
diff --git a/third_party/blink/renderer/core/html/html_view_source_document_test.cc b/third_party/blink/renderer/core/html/html_view_source_document_test.cc index 2998846..391645e 100644 --- a/third_party/blink/renderer/core/html/html_view_source_document_test.cc +++ b/third_party/blink/renderer/core/html/html_view_source_document_test.cc
@@ -38,8 +38,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"> <span " @@ -92,8 +92,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"> <span " @@ -145,8 +145,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"> <span " @@ -211,8 +211,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"> <span " @@ -280,8 +280,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"><br></td></tr><tr><td " @@ -313,8 +313,8 @@ LoadMainResource((many_spaces + std::string(" <b>A</b> ")).c_str()); std::string expected_beginning( "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td class=\"line-content\"> " " "); std::string expected_ending( @@ -330,8 +330,8 @@ LoadMainResource("1234567"); EXPECT_EQ(GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\">1234567<span " "class=\"html-end-of-file\"></span></td></tr></tbody></table></" @@ -353,8 +353,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"> <span " @@ -421,8 +421,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"> <span " @@ -453,8 +453,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td " "class=\"line-content\"><br></td></tr><tr><td class=\"line-number\" " "value=\"2\"></td><td class=\"line-content\"> Incomplete token " @@ -476,8 +476,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td class=\"line-content\"><span " "class=\"html-tag\"><textarea></span>foobar in " "textarea</td></tr><tr><td class=\"line-number\" value=\"2\"></td><td " @@ -492,8 +492,8 @@ EXPECT_EQ( GetDocument().documentElement()->outerHTML(), "<html><head></head><body><div " - "class=\"line-gutter-backdrop\"></div><table style=\"word-break: " - "keep-all;\"><tbody><tr><td " + "class=\"line-gutter-backdrop\"></div><table style=\"white-space: " + "pre;\"><tbody><tr><td " "class=\"line-number\" value=\"1\"></td><td class=\"line-content\"><span " "class=\"html-tag\"><script></span>foobar in " "script</td></tr><tr><td class=\"line-number\" value=\"2\"></td><td "
diff --git a/third_party/blink/renderer/core/html/text_document.cc b/third_party/blink/renderer/core/html/text_document.cc index 7b7db8d..9ee3ed7b 100644 --- a/third_party/blink/renderer/core/html/text_document.cc +++ b/third_party/blink/renderer/core/html/text_document.cc
@@ -32,7 +32,7 @@ TextDocument::TextDocument(const DocumentInit& initializer) : HTMLDocument(initializer) { - SetCompatibilityMode(kQuirksMode); + SetCompatibilityMode(kNoQuirksMode); LockCompatibilityMode(); }
diff --git a/third_party/blink/renderer/core/inspector/inspector_css_agent.cc b/third_party/blink/renderer/core/inspector/inspector_css_agent.cc index 612d6a1..a3de431 100644 --- a/third_party/blink/renderer/core/inspector/inspector_css_agent.cc +++ b/third_party/blink/renderer/core/inspector/inspector_css_agent.cc
@@ -2229,8 +2229,6 @@ StyleChangeReasonForTracing::Create(style_change_reason::kInspector)); } -void InspectorCSSAgent::DidRemoveDocument(Document* document) {} - void InspectorCSSAgent::WillRemoveDOMNode(Node* node) { DCHECK(node);
diff --git a/third_party/blink/renderer/core/inspector/inspector_css_agent.h b/third_party/blink/renderer/core/inspector/inspector_css_agent.h index 0de4ab3..14eeeb7c 100644 --- a/third_party/blink/renderer/core/inspector/inspector_css_agent.h +++ b/third_party/blink/renderer/core/inspector/inspector_css_agent.h
@@ -319,7 +319,6 @@ // InspectorDOMAgent::DOMListener implementation void DidAddDocument(Document*) override; - void DidRemoveDocument(Document*) override; void WillRemoveDOMNode(Node*) override; void DidModifyDOMAttr(Element*) override;
diff --git a/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc b/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc index 36a5ea0..b8ee4b9 100644 --- a/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc +++ b/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc
@@ -270,11 +270,6 @@ listener->DidAddDocument(document); } -void InspectorDOMAgent::NotifyDidRemoveDocument(Document* document) { - for (DOMListener* listener : dom_listeners_) - listener->DidRemoveDocument(document); -} - void InspectorDOMAgent::NotifyWillRemoveDOMNode(Node* node) { for (DOMListener* listener : dom_listeners_) listener->WillRemoveDOMNode(node); @@ -329,9 +324,6 @@ id_to_node_.erase(id); id_to_nodes_map_.erase(id); - if (IsA<Document>(node)) - NotifyDidRemoveDocument(To<Document>(node)); - if (auto* frame_owner = DynamicTo<HTMLFrameOwnerElement>(node)) { Document* content_document = frame_owner->contentDocument(); if (content_document)
diff --git a/third_party/blink/renderer/core/inspector/inspector_dom_agent.h b/third_party/blink/renderer/core/inspector/inspector_dom_agent.h index 0460dda..3e95147 100644 --- a/third_party/blink/renderer/core/inspector/inspector_dom_agent.h +++ b/third_party/blink/renderer/core/inspector/inspector_dom_agent.h
@@ -75,7 +75,6 @@ struct CORE_EXPORT DOMListener : public GarbageCollectedMixin { virtual ~DOMListener() = default; virtual void DidAddDocument(Document*) = 0; - virtual void DidRemoveDocument(Document*) = 0; virtual void WillRemoveDOMNode(Node*) = 0; virtual void DidModifyDOMAttr(Element*) = 0; }; @@ -325,7 +324,6 @@ void EnableAndReset(); void NotifyDidAddDocument(Document*); - void NotifyDidRemoveDocument(Document*); void NotifyWillRemoveDOMNode(Node*); void NotifyDidModifyDOMAttr(Element*);
diff --git a/third_party/blink/renderer/core/layout/BUILD.gn b/third_party/blink/renderer/core/layout/BUILD.gn index dd579f38..673ee11 100644 --- a/third_party/blink/renderer/core/layout/BUILD.gn +++ b/third_party/blink/renderer/core/layout/BUILD.gn
@@ -4,6 +4,13 @@ import("//third_party/blink/renderer/core/core.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + blink_core_sources("layout") { sources = [ "api/hit_test_action.h",
diff --git a/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.cc b/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.cc index 75349fc..fc178d9 100644 --- a/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.cc +++ b/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.cc
@@ -20,6 +20,7 @@ DCHECK(!params.break_token); container_builder_.SetIsNewFormattingContext(true); + border_box_size_ = container_builder_.InitialBorderBoxSize(); child_percentage_size_ = CalculateChildPercentageSize( ConstraintSpace(), Node(), ChildAvailableSize()); } @@ -72,8 +73,17 @@ } } - // TODO(kschmi): Calculate correct block-size. - container_builder_.SetFragmentsTotalBlockSize(LayoutUnit()); + // TODO(ansollan): Calculate the intrinsic-block-size from the tracks. + LayoutUnit intrinsic_block_size = BorderScrollbarPadding().BlockSum(); + intrinsic_block_size = + ClampIntrinsicBlockSize(ConstraintSpace(), Node(), + BorderScrollbarPadding(), intrinsic_block_size); + LayoutUnit block_size = ComputeBlockSizeForFragment( + ConstraintSpace(), Style(), BorderPadding(), intrinsic_block_size, + border_box_size_.inline_size); + + container_builder_.SetIntrinsicBlockSize(intrinsic_block_size); + container_builder_.SetFragmentsTotalBlockSize(block_size); NGOutOfFlowLayoutPart(Node(), ConstraintSpace(), &container_builder_).Run(); return container_builder_.ToBoxFragment(); }
diff --git a/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.h b/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.h index 0a7e379..b8ef503 100644 --- a/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.h +++ b/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm.h
@@ -117,6 +117,7 @@ void PlaceGridItems(); GridLayoutAlgorithmState state_; + LogicalSize border_box_size_; LogicalSize child_percentage_size_; Vector<GridItemData> items_;
diff --git a/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm_test.cc b/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm_test.cc index 0d881329..863d565 100644 --- a/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm_test.cc +++ b/third_party/blink/renderer/core/layout/ng/grid/ng_grid_layout_algorithm_test.cc
@@ -135,9 +135,7 @@ NGBlockNode container(ToLayoutBox(element->GetLayoutObject())); NGConstraintSpace space = ConstructBlockLayoutTestConstraintSpace( WritingMode::kHorizontalTb, TextDirection::kLtr, - LogicalSize(LayoutUnit(1000), kIndefiniteSize), - /* shrink_to_fit */ false, - /* is_new_formatting_context */ true); + LogicalSize(LayoutUnit(1000), kIndefiniteSize)); return NGBaseLayoutAlgorithmTest::RunBlockLayoutAlgorithm(container, space); } @@ -741,25 +739,28 @@ } </style> - <div id="grid"> - <div class="grid_item">1</div> - <div class="grid_item">2</div> - <div class="grid_item">3</div> - <div class="grid_item">4</div> + <div id="wrapper"> + <div id="grid"> + <div class="grid_item">1</div> + <div class="grid_item">2</div> + <div class="grid_item">3</div> + <div class="grid_item">4</div> + </div> </div> )HTML"); - String dump = DumpFragmentTree(GetElementById("grid")); + String dump = DumpFragmentTree(GetElementById("wrapper")); String expectation = R"DUMP(.:: LayoutNG Physical Fragment Tree ::. - offset:unplaced size:200x200 - offset:0,0 size:100x100 - offset:0,0 size:10x10 - offset:0,100 size:100x100 - offset:0,0 size:10x10 - offset:0,200 size:100x100 - offset:0,0 size:10x10 - offset:0,300 size:100x100 - offset:0,0 size:10x10 + offset:unplaced size:1000x200 + offset:0,0 size:200x200 + offset:0,0 size:100x100 + offset:0,0 size:10x10 + offset:100,0 size:100x100 + offset:0,0 size:10x10 + offset:0,100 size:100x100 + offset:0,0 size:10x10 + offset:100,100 size:100x100 + offset:0,0 size:10x10 )DUMP"; EXPECT_EQ(expectation, dump); }
diff --git a/third_party/blink/renderer/core/layout/ng/ng_block_node.cc b/third_party/blink/renderer/core/layout/ng/ng_block_node.cc index d5164e3..b3e5e79 100644 --- a/third_party/blink/renderer/core/layout/ng/ng_block_node.cc +++ b/third_party/blink/renderer/core/layout/ng/ng_block_node.cc
@@ -1198,6 +1198,14 @@ // relatively to the block-start of the flow thread. const auto* column = To<NGPhysicalBoxFragment>(child.get()); PlaceChildrenInLayoutBox(*column, previous_break_token); + + // If the multicol container has inline children, there may still be floats + // there, but they aren't stored as child fragments of |column| in that case + // (but rather inside fragment items). Make sure that they get positioned, + // too. + if (const NGFragmentItems* items = column->Items()) + CopyFragmentItemsToLayoutBox(*column, *items); + previous_break_token = To<NGBlockBreakToken>(column->BreakToken()); } }
diff --git a/third_party/blink/renderer/core/page/scrolling/scrolling_coordinator.cc b/third_party/blink/renderer/core/page/scrolling/scrolling_coordinator.cc index 3c2bf0c..293e524 100644 --- a/third_party/blink/renderer/core/page/scrolling/scrolling_coordinator.cc +++ b/third_party/blink/renderer/core/page/scrolling/scrolling_coordinator.cc
@@ -167,9 +167,11 @@ auto offset = layer.GetOffsetFromTransformNode(); gfx::Vector2dF layer_offset = gfx::Vector2dF(offset.X(), offset.Y()); + PaintChunkSubset paint_chunks = + PaintChunkSubset(layer.GetPaintController().PaintChunks()); PaintArtifactCompositor::UpdateNonFastScrollableRegions( layer.CcLayer(), layer_offset, layer.GetPropertyTreeState().Unalias(), - layer.GetPaintController().PaintChunks()); + paint_chunks); } // Compute the regions of the page where we can't handle scroll gestures on @@ -196,9 +198,11 @@ auto offset = layer.GetOffsetFromTransformNode(); gfx::Vector2dF layer_offset = gfx::Vector2dF(offset.X(), offset.Y()); + PaintChunkSubset paint_chunks = + PaintChunkSubset(layer.GetPaintController().PaintChunks()); PaintArtifactCompositor::UpdateTouchActionRects( layer.CcLayer(), layer_offset, layer.GetPropertyTreeState().Unalias(), - layer.GetPaintController().PaintChunks()); + paint_chunks); } void ScrollingCoordinator::WillDestroyScrollableArea(
diff --git a/third_party/blink/renderer/core/paint/block_painter_test.cc b/third_party/blink/renderer/core/paint/block_painter_test.cc index b3e3d519..4800916 100644 --- a/third_party/blink/renderer/core/paint/block_painter_test.cc +++ b/third_party/blink/renderer/core/paint/block_painter_test.cc
@@ -497,12 +497,12 @@ scroller->FirstFragment().ContentsProperties(), &scrolled_hit_test_data, IntRect(0, 0, 200, 50)))); - const auto& scroller_paint_chunk = paint_chunks[{0, 1}]; + const auto& scroller_paint_chunk = paint_chunks[1]; // The hit test rect for the scroller itself should not be scrolled. EXPECT_FALSE( ToUnaliased(scroller_paint_chunk.properties.Transform()).ScrollNode()); - const auto& scrolled_paint_chunk = paint_chunks[{0, 3}]; + const auto& scrolled_paint_chunk = paint_chunks[3]; // The hit test rect for the scrolled contents should be scrolled. EXPECT_TRUE( ToUnaliased(scrolled_paint_chunk.properties.Transform()).ScrollNode());
diff --git a/third_party/blink/renderer/core/paint/box_painter_test.cc b/third_party/blink/renderer/core/paint/box_painter_test.cc index 6a35bd7..42c51d8 100644 --- a/third_party/blink/renderer/core/paint/box_painter_test.cc +++ b/third_party/blink/renderer/core/paint/box_painter_test.cc
@@ -290,8 +290,8 @@ } // We always create scroll node for the root layer. - PaintChunkIndex chunk_index{ - 0, RuntimeEnabledFeatures::CompositeAfterPaintEnabled() ? 1 : 0}; + wtf_size_t chunk_index = + RuntimeEnabledFeatures::CompositeAfterPaintEnabled() ? 1 : 0; const auto& root_transform = ToUnaliased(paint_chunks[chunk_index].properties.Transform()); EXPECT_NE(nullptr, root_transform.ScrollNode()); @@ -299,16 +299,14 @@ // The container's background chunk should not scroll and therefore should use // the root transform. Its local transform is actually a paint offset // transform. - ++chunk_index.chunk_index; const auto& container_transform = - ToUnaliased(paint_chunks[chunk_index].properties.Transform()); + ToUnaliased(paint_chunks[++chunk_index].properties.Transform()); EXPECT_EQ(&root_transform, container_transform.Parent()); EXPECT_EQ(nullptr, container_transform.ScrollNode()); // The scroll hit test should not be scrolled and should not be clipped. // Its local transform is actually a paint offset transform. - ++chunk_index.chunk_index; - const auto& scroll_hit_test_chunk = paint_chunks[chunk_index]; + const auto& scroll_hit_test_chunk = paint_chunks[++chunk_index]; const auto& scroll_hit_test_transform = ToUnaliased(scroll_hit_test_chunk.properties.Transform()); EXPECT_EQ(nullptr, scroll_hit_test_transform.ScrollNode()); @@ -319,8 +317,7 @@ scroll_hit_test_clip.UnsnappedClipRect().Rect()); // The scrolled contents should be scrolled and clipped. - ++chunk_index.chunk_index; - const auto& contents_chunk = paint_chunks[chunk_index]; + const auto& contents_chunk = paint_chunks[++chunk_index]; const auto& contents_transform = ToUnaliased(contents_chunk.properties.Transform()); const auto* contents_scroll = contents_transform.ScrollNode();
diff --git a/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder.cc b/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder.cc index 01bc769..d3d8032 100644 --- a/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder.cc +++ b/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder.cc
@@ -186,7 +186,7 @@ CompositingReasonFinder::DirectReasonsForSVGChildPaintProperties( const LayoutObject& object) { DCHECK(object.IsSVGChild()); - if (RuntimeEnabledFeatures::CompositeSVGEnabled()) { + if (RuntimeEnabledFeatures::CompositeSVGEnabled() && !object.IsText()) { const ComputedStyle& style = object.StyleRef(); auto reasons = CompositingReasonsForAnimation(object) | CompositingReasonsForWillChange(style);
diff --git a/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder_test.cc b/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder_test.cc index 18ac27bd..359e6be 100644 --- a/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder_test.cc +++ b/third_party/blink/renderer/core/paint/compositing/compositing_reason_finder_test.cc
@@ -366,4 +366,21 @@ EXPECT_EQ(kPaintsIntoOwnBacking, target_layer->GetCompositingState()); } +TEST_F(CompositingReasonFinderTest, CompositedSVGText) { + SetBodyInnerHTML(R"HTML( + <svg> + <text id="text" style="will-change: opacity">Text</text> + </svg> + )HTML"); + + auto* svg_text = GetLayoutObjectByElementId("text"); + EXPECT_EQ( + CompositingReason::kWillChangeOpacity, + CompositingReasonFinder::DirectReasonsForPaintProperties(*svg_text)); + auto* text = svg_text->SlowFirstChild(); + ASSERT_TRUE(text->IsText()); + EXPECT_EQ(CompositingReason::kNone, + CompositingReasonFinder::DirectReasonsForPaintProperties(*text)); +} + } // namespace blink
diff --git a/third_party/blink/renderer/core/paint/paint_layer_painter_test.cc b/third_party/blink/renderer/core/paint/paint_layer_painter_test.cc index e2fed4f..d2931d4 100644 --- a/third_party/blink/renderer/core/paint/paint_layer_painter_test.cc +++ b/third_party/blink/renderer/core/paint/paint_layer_painter_test.cc
@@ -12,7 +12,6 @@ #include "third_party/blink/renderer/platform/testing/paint_property_test_helpers.h" #include "third_party/blink/renderer/platform/testing/runtime_enabled_features_test_helpers.h" -using testing::_; using testing::ElementsAre; using testing::UnorderedElementsAre; @@ -476,8 +475,8 @@ IsSameId(content1, kBackgroundType))); // |target| created subsequence. EXPECT_SUBSEQUENCE(*target_layer, 2, 4); - EXPECT_THAT(RootPaintController().PaintChunks(), - ElementsAre(_, _, IsPaintChunk(1, 1), IsPaintChunk(1, 2))); + EXPECT_EQ(0u, RootPaintController().PaintChunks()[2].size()); + EXPECT_EQ(1u, RootPaintController().PaintChunks()[3].size()); } else { EXPECT_EQ(CullRect(IntRect(0, 0, 800, 4600)), target_layer->PreviousCullRect()); @@ -487,8 +486,7 @@ IsSameId(content1, kBackgroundType))); // |target| created subsequence. EXPECT_SUBSEQUENCE(*target_layer, 1, 2); - EXPECT_THAT(RootPaintController().PaintChunks(), - ElementsAre(_, IsPaintChunk(1, 2))); + EXPECT_EQ(1u, RootPaintController().PaintChunks()[1].size()); } // Change something that triggers a repaint but |target| should use cached @@ -514,8 +512,8 @@ IsSameId(content1, kBackgroundType))); // |target| still created subsequence (cached). EXPECT_SUBSEQUENCE(*target_layer, 2, 4); - EXPECT_THAT(RootPaintController().PaintChunks(), - ElementsAre(_, _, IsPaintChunk(1, 1), IsPaintChunk(1, 2))); + EXPECT_EQ(0u, RootPaintController().PaintChunks()[2].size()); + EXPECT_EQ(1u, RootPaintController().PaintChunks()[3].size()); } else { EXPECT_EQ(CullRect(IntRect(0, 0, 800, 4600)), target_layer->PreviousCullRect()); @@ -524,8 +522,7 @@ IsSameId(content1, kBackgroundType))); // |target| still created subsequence (cached). EXPECT_SUBSEQUENCE(*target_layer, 1, 2); - EXPECT_THAT(RootPaintController().PaintChunks(), - ElementsAre(_, IsPaintChunk(1, 2))); + EXPECT_EQ(1u, RootPaintController().PaintChunks()[1].size()); } // Scroll the view so that both |content1| and |content2| are in the interest @@ -555,8 +552,8 @@ IsSameId(content2, kBackgroundType))); // |target| still created subsequence (repainted). EXPECT_SUBSEQUENCE(*target_layer, 2, 4); - EXPECT_THAT(RootPaintController().PaintChunks(), - ElementsAre(_, _, IsPaintChunk(1, 1), IsPaintChunk(1, 3))); + EXPECT_EQ(0u, RootPaintController().PaintChunks()[2].size()); + EXPECT_EQ(2u, RootPaintController().PaintChunks()[3].size()); } else { EXPECT_EQ(CullRect(IntRect(0, 0, 800, 7600)), target_layer->PreviousCullRect()); @@ -567,8 +564,7 @@ IsSameId(content2, kBackgroundType))); // |target| still created subsequence (repainted). EXPECT_SUBSEQUENCE(*target_layer, 1, 2); - EXPECT_THAT(RootPaintController().PaintChunks(), - ElementsAre(_, IsPaintChunk(1, 3))); + EXPECT_EQ(2u, RootPaintController().PaintChunks()[1].size()); } }
diff --git a/third_party/blink/renderer/core/paint/pre_paint_tree_walk.cc b/third_party/blink/renderer/core/paint/pre_paint_tree_walk.cc index 77968cf..07dd281 100644 --- a/third_party/blink/renderer/core/paint/pre_paint_tree_walk.cc +++ b/third_party/blink/renderer/core/paint/pre_paint_tree_walk.cc
@@ -648,16 +648,23 @@ DCHECK((*iterator)->BoxFragment()->IsFragmentainerBox()); PhysicalOffset offset = (*iterator)->Link().offset; PaintPropertyTreeBuilderFragmentContext::ContainingBlockContext* - fragment_context = nullptr; + containing_block_context = nullptr; if (context_storage_.back().tree_builder_context) { PaintPropertyTreeBuilderContext& tree_builder_context = context_storage_.back().tree_builder_context.value(); - fragment_context = &tree_builder_context.fragments[0].current; - fragment_context->paint_offset += offset; + PaintPropertyTreeBuilderFragmentContext& context = + tree_builder_context.fragments[0]; + containing_block_context = &context.current; + containing_block_context->paint_offset += offset; + + if (box_fragment->IsFragmentainerBox()) { + context.absolute_position = *containing_block_context; + context.fixed_position = *containing_block_context; + } } WalkChildren(/* parent */ nullptr, iterator); - if (fragment_context) - fragment_context->paint_offset -= offset; + if (containing_block_context) + containing_block_context->paint_offset -= offset; continue; } Walk(*object, iterator);
diff --git a/third_party/blink/renderer/core/paint/view_painter_test.cc b/third_party/blink/renderer/core/paint/view_painter_test.cc index 6a043505..802684e 100644 --- a/third_party/blink/renderer/core/paint/view_painter_test.cc +++ b/third_party/blink/renderer/core/paint/view_painter_test.cc
@@ -203,8 +203,7 @@ view_contents_properties))); // The scroll hit test should not be scrolled and should not be clipped. - const auto& scroll_hit_test_chunk = - RootPaintController().PaintChunks()[{0, 0}]; + const auto& scroll_hit_test_chunk = RootPaintController().PaintChunks()[0]; const auto& scroll_hit_test_transform = ToUnaliased(scroll_hit_test_chunk.properties.Transform()); EXPECT_EQ(nullptr, scroll_hit_test_transform.ScrollNode()); @@ -214,7 +213,7 @@ scroll_hit_test_clip.UnsnappedClipRect().Rect()); // The scrolled contents should be scrolled and clipped. - const auto& contents_chunk = RootPaintController().PaintChunks()[{0, 1}]; + const auto& contents_chunk = RootPaintController().PaintChunks()[1]; const auto& contents_transform = ToUnaliased(contents_chunk.properties.Transform()); const auto* contents_scroll = contents_transform.ScrollNode();
diff --git a/third_party/blink/renderer/modules/app_banner/before_install_prompt_event.idl b/third_party/blink/renderer/modules/app_banner/before_install_prompt_event.idl index a7a5a2c..8a5a44c3 100644 --- a/third_party/blink/renderer/modules/app_banner/before_install_prompt_event.idl +++ b/third_party/blink/renderer/modules/app_banner/before_install_prompt_event.idl
@@ -7,7 +7,7 @@ Exposed=Window ] interface BeforeInstallPromptEvent : Event { [CallWith=ExecutionContext] constructor(DOMString type, optional BeforeInstallPromptEventInit eventInitDict = {}); - readonly attribute FrozenArray<DOMString> platforms; + [HighEntropy=Direct, Measure] readonly attribute FrozenArray<DOMString> platforms; [CallWith=ScriptState, RaisesException] readonly attribute Promise<AppBannerPromptResult> userChoice; [CallWith=ScriptState, RaisesException] Promise<void> prompt(); };
diff --git a/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.cc b/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.cc index 908dd10..a000dc3 100644 --- a/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.cc +++ b/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.cc
@@ -320,9 +320,61 @@ } virtual_read_index = read_index; } else { - virtual_read_index = RenderFromBufferKernel( - write_index, frames_to_process, virtual_read_index, virtual_end_frame, - virtual_delta_frames, computed_playback_rate, buffer_length, bus); + while (frames_to_process--) { + unsigned read_index = static_cast<unsigned>(virtual_read_index); + double interpolation_factor = virtual_read_index - read_index; + + // For linear interpolation we need the next sample-frame too. + unsigned read_index2 = read_index + 1; + if (read_index2 >= buffer_length) { + if (Loop()) { + // Make sure to wrap around at the end of the buffer. + read_index2 = static_cast<unsigned>(virtual_read_index + 1 - + virtual_delta_frames); + } else { + read_index2 = read_index; + } + } + + // Final sanity check on buffer access. + // FIXME: as an optimization, try to get rid of this inner-loop check and + // put assertions and guards before the loop. + if (read_index >= buffer_length || read_index2 >= buffer_length) + break; + + // Linear interpolation. + for (unsigned i = 0; i < number_of_channels; ++i) { + float* destination = destination_channels[i]; + const float* source = source_channels[i]; + double sample; + + if (read_index == read_index2 && read_index >= 1) { + // We're at the end of the buffer, so just linearly extrapolate from + // the last two samples. + double sample1 = source[read_index - 1]; + double sample2 = source[read_index]; + sample = sample2 + (sample2 - sample1) * interpolation_factor; + } else { + double sample1 = source[read_index]; + double sample2 = source[read_index2]; + sample = (1.0 - interpolation_factor) * sample1 + + interpolation_factor * sample2; + } + destination[write_index] = clampTo<float>(sample); + } + write_index++; + + virtual_read_index += computed_playback_rate; + + // Wrap-around, retaining sub-sample position since virtualReadIndex is + // floating-point. + if (virtual_read_index >= virtual_end_frame) { + virtual_read_index -= virtual_delta_frames; + if (RenderSilenceAndFinishIfNotLooping(bus, write_index, + frames_to_process)) + break; + } + } } bus->ClearSilentFlag(); @@ -332,167 +384,6 @@ return true; } -std::tuple<double, int, bool> AudioBufferSourceHandler::ComputeIndices( - const struct InterpolationInfo& interp_info, - const struct IndicesInfo& indices_info, - int frames_to_process, - uint32_t buffer_length, - bool is_looping) const { - int frames_processed = frames_to_process; - bool end_of_buffer_reached = false; - - unsigned* read0 = interp_info.read0; - unsigned* read1 = interp_info.read1; - float* interp_factor = interp_info.interp_factor; - auto virtual_read_index = indices_info.virtual_read_index; - auto computed_playback_rate = indices_info.computed_playback_rate; - auto virtual_end_frame = indices_info.virtual_end_frame; - auto virtual_delta_frames = indices_info.virtual_delta_frames; - - for (int k = 0; k < frames_to_process; ++k) { - unsigned read_index = static_cast<unsigned>(virtual_read_index); - double interpolation_factor = virtual_read_index - read_index; - - // For linear interpolation we need the next sample-frame too. - unsigned read_index2 = read_index + 1; - if (read_index2 >= buffer_length) { - if (is_looping) { - // Make sure to wrap around at the end of the buffer. - read_index2 = static_cast<unsigned>(virtual_read_index + 1 - - virtual_delta_frames); - } else { - read_index2 = read_index; - } - } - - // Final sanity check on buffer access. - // FIXME: as an optimization, try to get rid of this inner-loop check and - // put assertions and guards before the loop. - CHECK_LT(read_index, buffer_length); - CHECK_LT(read_index2, buffer_length); - if (read_index >= buffer_length || read_index2 >= buffer_length) { - // Informs ComputeOutput how many frames we processed so that it only - // processes that many output samples. The read indices and interpolation - // factor are invalid after this point. - frames_processed = k; - break; - } - - read0[k] = read_index; - read1[k] = read_index2; - interp_factor[k] = interpolation_factor; - - virtual_read_index += computed_playback_rate; - - // Wrap-around, retaining sub-sample position since virtualReadIndex is - // floating-point. - if (virtual_read_index >= virtual_end_frame) { - virtual_read_index -= virtual_delta_frames; - if (!is_looping) { - frames_processed = k + 1; - end_of_buffer_reached = true; - break; - } - } - } - - return std::make_tuple(virtual_read_index, frames_processed, - end_of_buffer_reached); -} - -unsigned AudioBufferSourceHandler::ComputeOutput( - float** destination_channels, - const float** source_channels, - const struct InterpolationInfo& interp_info, - int frames_processed, - unsigned write_index, - unsigned number_of_channels, - unsigned buffer_length) const { - unsigned* read0 = interp_info.read0; - unsigned* read1 = interp_info.read1; - float* interp_factor = interp_info.interp_factor; - - for (int k = 0; k < frames_processed; ++k) { - // Linear interpolation. - for (unsigned i = 0; i < number_of_channels; ++i) { - float* destination = destination_channels[i]; - const float* source = source_channels[i]; - float sample; - - if (read0[k] == read1[k] && read0[k] >= 1) { - // We're at the end of the buffer, so just linearly extrapolate from - // the last two samples. - // TODO(crbug.com/1116104). Remove this CHECK once the problem is - // solved. - CHECK_LT(read0[k], buffer_length); - float sample1 = source[read0[k] - 1]; - float sample2 = source[read0[k]]; - sample = sample2 + (sample2 - sample1) * interp_factor[k]; - } else { - CHECK_LT(read0[k], buffer_length); - CHECK_LT(read1[k], buffer_length); - // TODO(crbug.com/1116104). If read1[k] is out-of-bounds, just return - // 0. Remove this when the underlying problem is fixed. - if (read1[k] >= buffer_length) { - VLOG(1) << "k = " << k << "frames = " << frames_processed - << "read1 = " << read1[k]; - } - float sample1 = source[read0[k]]; - float sample2 = read1[k] < buffer_length ? source[read1[k]] : 0; - sample = sample1 + interp_factor[k] * (sample2 - sample1); - } - destination[write_index] = sample; - } - write_index++; - } - - return write_index; -} - -double AudioBufferSourceHandler::RenderFromBufferKernel( - unsigned write_index, - int frames_to_process, - double virtual_read_index, - double virtual_end_frame, - double virtual_delta_frames, - double computed_playback_rate, - uint32_t buffer_length, - AudioBus* bus) { - unsigned number_of_channels = this->NumberOfChannels(); - const float** source_channels = source_channels_.get(); - float** destination_channels = destination_channels_.get(); - - unsigned read0[audio_utilities::kRenderQuantumFrames]; - unsigned read1[audio_utilities::kRenderQuantumFrames]; - float interp_factor[audio_utilities::kRenderQuantumFrames]; - - int frames_processed; - bool end_of_buffer_reached; - struct InterpolationInfo interp_info = {read0, read1, interp_factor}; - struct IndicesInfo indices_info = {virtual_read_index, computed_playback_rate, - virtual_delta_frames, virtual_end_frame}; - - std::tie<double, int, bool>(virtual_read_index, frames_processed, - end_of_buffer_reached) = - ComputeIndices(interp_info, indices_info, frames_to_process, - buffer_length, Loop()); - - // TODO(crbug.com/1116104): Debugging possible error cases. Remove this (or - // convert to DCHECK) when the underlying issue is fixed. - CHECK_LE(frames_processed, - static_cast<int>(audio_utilities::kRenderQuantumFrames)); - write_index = ComputeOutput(destination_channels, source_channels, - interp_info, frames_processed, write_index, - number_of_channels, buffer_length); - - if (end_of_buffer_reached) { - RenderSilenceAndFinishIfNotLooping(bus, write_index, - frames_to_process - frames_processed); - } - - return virtual_read_index; -} - void AudioBufferSourceHandler::SetBuffer(AudioBuffer* buffer, ExceptionState& exception_state) { DCHECK(IsMainThread());
diff --git a/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.h b/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.h index 4b49a12..68ca60f 100644 --- a/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.h +++ b/third_party/blink/renderer/modules/webaudio/audio_buffer_source_node.h
@@ -125,63 +125,6 @@ uint32_t number_of_frames, double start_time_offset); - // Structure for passing in information needed to compute indices for - // interpolation. - struct InterpolationInfo { - unsigned* read0; - unsigned* read1; - float* interp_factor; - }; - - // Structure for passing information about the virtual read index needed for - // computing indices. - struct IndicesInfo { - double virtual_read_index; - double computed_playback_rate; - double virtual_delta_frames; - double virtual_end_frame; - }; - - // Handles the general case of rendering from a buffer where the playback rate - // is not 1 or other situations where interpolation is required. - double RenderFromBufferKernel(unsigned write_index, - int frames_to_process, - double virtual_read_index, - double virtual_end_frame, - double virtual_delta_frames, - double computed_playback_rate, - uint32_t buffer_length, - AudioBus* bus); - - // Helper routines for RenderFromBufferKernel that don't need access to any - // internals. - - // ComputeIndices computes the indices needed for - // interpolation/extrapolation. Returns three values: - // - // 1: the updated virtual_read_index - // - // 2: how many frames were processed (possibly less trhan frames_to_process - // because the buffer end was reached) - // 3: a boolean indicating if we did reach the end of the buffer. - inline std::tuple<double, int, bool> ComputeIndices( - const struct InterpolationInfo& interp_info, - const struct IndicesInfo& indices_info, - int frames_to_process, - uint32_t buffer_length, - bool is_looping) const; - - // ComputeOutput takes the indices from ComputeIndices and performs - // interpolates/extrapolates the data to produce the desired output. Returns - // the update write index where the next output should be written to. - inline unsigned ComputeOutput(float** destination_channels, - const float** source_channels, - const struct InterpolationInfo& interp_info, - int frames_processed, - unsigned write_index, - unsigned number_of_channels, - unsigned buffer_length) const; - // Render silence starting from "index" frame in AudioBus. inline bool RenderSilenceAndFinishIfNotLooping(AudioBus*, unsigned index,
diff --git a/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.cc b/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.cc index 419bc929..4b9f7fa 100644 --- a/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.cc +++ b/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.cc
@@ -64,7 +64,7 @@ WTF::CrossThreadOnceFunction<void(media::Status status, base::Optional<DecoderDetails>)>; using CrossThreadOnceDecodeCB = - WTF::CrossThreadOnceFunction<void(media::DecodeStatus)>; + WTF::CrossThreadOnceFunction<void(media::Status)>; using CrossThreadOnceResetCB = WTF::CrossThreadOnceClosure; MediaAudioTaskWrapper( @@ -217,13 +217,13 @@ weak_client_, std::move(buffer))); } - void OnDecodeDone(int cb_id, media::DecodeStatus status) { + void OnDecodeDone(int cb_id, media::Status status) { DVLOG(2) << __func__; DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); PostCrossThreadTask( *main_task_runner_, FROM_HERE, WTF::CrossThreadBindOnce(&CrossThreadAudioDecoderClient::OnDecodeDone, - weak_client_, cb_id, status)); + weak_client_, cb_id, std::move(status))); } void OnReset(int cb_id) { @@ -347,7 +347,7 @@ buffer, callback_id)); } -void AudioDecoderBroker::OnDecodeDone(int cb_id, media::DecodeStatus status) { +void AudioDecoderBroker::OnDecodeDone(int cb_id, media::Status status) { DVLOG(2) << __func__; DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); DCHECK(pending_decode_cb_map_.Contains(cb_id)); @@ -358,7 +358,7 @@ // Do this last. Caller may destruct |this| in response to the callback while // this method is still on the stack. - std::move(decode_cb).Run(status); + std::move(decode_cb).Run(std::move(status)); } void AudioDecoderBroker::Reset(base::OnceClosure reset_cb) {
diff --git a/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.h b/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.h index 1bae54e..c99ade4 100644 --- a/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.h +++ b/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker.h
@@ -41,7 +41,7 @@ virtual void OnInitialize(media::Status status, base::Optional<DecoderDetails> details) = 0; - virtual void OnDecodeDone(int cb_id, media::DecodeStatus status) = 0; + virtual void OnDecodeDone(int cb_id, media::Status status) = 0; virtual void OnDecodeOutput(scoped_refptr<media::AudioBuffer> buffer) = 0; @@ -91,7 +91,7 @@ // MediaAudioTaskWrapper::CrossThreadAudioDecoderClient void OnInitialize(media::Status status, base::Optional<DecoderDetails> details) override; - void OnDecodeDone(int cb_id, media::DecodeStatus status) override; + void OnDecodeDone(int cb_id, media::Status status) override; void OnDecodeOutput(scoped_refptr<media::AudioBuffer> buffer) override; void OnReset(int cb_id) override;
diff --git a/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker_test.cc b/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker_test.cc index 1c941199..3d7115a 100644 --- a/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker_test.cc +++ b/third_party/blink/renderer/modules/webcodecs/audio_decoder_broker_test.cc
@@ -160,8 +160,8 @@ done_cb.Run(); } void OnDecodeDoneWithClosure(base::RepeatingClosure done_cb, - media::DecodeStatus status) { - OnDecodeDone(status); + media::Status status) { + OnDecodeDone(std::move(status)); done_cb.Run(); } @@ -171,7 +171,7 @@ } MOCK_METHOD1(OnInit, void(media::Status status)); - MOCK_METHOD1(OnDecodeDone, void(media::DecodeStatus)); + MOCK_METHOD1(OnDecodeDone, void(media::Status)); MOCK_METHOD0(OnResetDone, void()); void OnOutput(scoped_refptr<media::AudioBuffer> buffer) { @@ -210,9 +210,9 @@ void DecodeBuffer( scoped_refptr<media::DecoderBuffer> buffer, - media::DecodeStatus expected_status = media::DecodeStatus::OK) { + media::StatusCode expected_status = media::StatusCode::kOk) { base::RunLoop run_loop; - EXPECT_CALL(*this, OnDecodeDone(expected_status)); + EXPECT_CALL(*this, OnDecodeDone(HasStatusCode(expected_status))); decoder_broker_->Decode( buffer, WTF::Bind(&AudioDecoderBrokerTest::OnDecodeDoneWithClosure, WTF::Unretained(this), run_loop.QuitClosure()));
diff --git a/third_party/blink/renderer/modules/webcodecs/decoder_template.cc b/third_party/blink/renderer/modules/webcodecs/decoder_template.cc index 47772f51..533c72d 100644 --- a/third_party/blink/renderer/modules/webcodecs/decoder_template.cc +++ b/third_party/blink/renderer/modules/webcodecs/decoder_template.cc
@@ -382,7 +382,7 @@ } template <typename Traits> -void DecoderTemplate<Traits>::OnConfigureFlushDone(media::DecodeStatus status) { +void DecoderTemplate<Traits>::OnConfigureFlushDone(media::Status status) { DVLOG(3) << __func__; if (IsClosed()) return; @@ -390,7 +390,7 @@ DCHECK(pending_request_); DCHECK_EQ(pending_request_->type, Request::Type::kConfigure); - if (status != media::DecodeStatus::OK) { + if (!status.is_ok()) { HandleError(); return; } @@ -425,14 +425,12 @@ } template <typename Traits> -void DecoderTemplate<Traits>::OnDecodeDone(uint32_t id, - media::DecodeStatus status) { +void DecoderTemplate<Traits>::OnDecodeDone(uint32_t id, media::Status status) { DVLOG(3) << __func__; if (IsClosed()) return; - if (status != media::DecodeStatus::OK && - status != media::DecodeStatus::ABORTED) { + if (!status.is_ok() && status.code() != media::StatusCode::kAborted) { HandleError(); return; } @@ -444,7 +442,7 @@ } template <typename Traits> -void DecoderTemplate<Traits>::OnFlushDone(media::DecodeStatus status) { +void DecoderTemplate<Traits>::OnFlushDone(media::Status status) { DVLOG(3) << __func__; if (IsClosed()) return; @@ -452,7 +450,7 @@ DCHECK(pending_request_); DCHECK_EQ(pending_request_->type, Request::Type::kFlush); - if (status != media::DecodeStatus::OK) { + if (!status.is_ok()) { HandleError(); return; }
diff --git a/third_party/blink/renderer/modules/webcodecs/decoder_template.h b/third_party/blink/renderer/modules/webcodecs/decoder_template.h index 6369944e..6ec9641 100644 --- a/third_party/blink/renderer/modules/webcodecs/decoder_template.h +++ b/third_party/blink/renderer/modules/webcodecs/decoder_template.h
@@ -99,9 +99,9 @@ // Called by |decoder_|. void OnInitializeDone(media::Status status); - void OnDecodeDone(uint32_t id, media::DecodeStatus); - void OnFlushDone(media::DecodeStatus); - void OnConfigureFlushDone(media::DecodeStatus); + void OnDecodeDone(uint32_t id, media::Status); + void OnFlushDone(media::Status); + void OnConfigureFlushDone(media::Status); void OnResetDone(); void OnOutput(scoped_refptr<MediaOutputType>);
diff --git a/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.cc b/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.cc index 3e138124..4b333995 100644 --- a/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.cc +++ b/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.cc
@@ -70,7 +70,7 @@ WTF::CrossThreadOnceFunction<void(media::Status status, base::Optional<DecoderDetails>)>; using CrossThreadOnceDecodeCB = - WTF::CrossThreadOnceFunction<void(media::DecodeStatus)>; + WTF::CrossThreadOnceFunction<void(const media::Status&)>; using CrossThreadOnceResetCB = WTF::CrossThreadOnceClosure; MediaVideoTaskWrapper( @@ -244,14 +244,14 @@ decoder_->CanReadWithoutStalling())); } - void OnDecodeDone(int cb_id, media::DecodeStatus status) { + void OnDecodeDone(int cb_id, media::Status status) { DVLOG(2) << __func__; DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); PostCrossThreadTask( *main_task_runner_, FROM_HERE, WTF::CrossThreadBindOnce(&CrossThreadVideoDecoderClient::OnDecodeDone, - weak_client_, cb_id, status)); + weak_client_, cb_id, std::move(status))); } void OnReset(int cb_id) { @@ -390,7 +390,7 @@ buffer, callback_id)); } -void VideoDecoderBroker::OnDecodeDone(int cb_id, media::DecodeStatus status) { +void VideoDecoderBroker::OnDecodeDone(int cb_id, media::Status status) { DVLOG(2) << __func__; DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); DCHECK(pending_decode_cb_map_.Contains(cb_id)); @@ -401,7 +401,7 @@ // Do this last. Caller may destruct |this| in response to the callback while // this method is still on the stack. - std::move(decode_cb).Run(status); + std::move(decode_cb).Run(std::move(status)); } void VideoDecoderBroker::Reset(base::OnceClosure reset_cb) {
diff --git a/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.h b/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.h index a2e461c..62115c4b 100644 --- a/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.h +++ b/third_party/blink/renderer/modules/webcodecs/video_decoder_broker.h
@@ -50,7 +50,7 @@ virtual void OnInitialize(media::Status status, base::Optional<DecoderDetails> details) = 0; - virtual void OnDecodeDone(int cb_id, media::DecodeStatus status) = 0; + virtual void OnDecodeDone(int cb_id, media::Status status) = 0; virtual void OnDecodeOutput(scoped_refptr<media::VideoFrame> frame, bool can_read_without_stalling) = 0; @@ -107,7 +107,7 @@ // MediaVideoTaskWrapper::CrossThreadVideoDecoderClient void OnInitialize(media::Status status, base::Optional<DecoderDetails> details) override; - void OnDecodeDone(int cb_id, media::DecodeStatus status) override; + void OnDecodeDone(int cb_id, media::Status status) override; void OnDecodeOutput(scoped_refptr<media::VideoFrame> frame, bool can_read_without_stalling) override; void OnReset(int cb_id) override;
diff --git a/third_party/blink/renderer/modules/webcodecs/video_decoder_broker_test.cc b/third_party/blink/renderer/modules/webcodecs/video_decoder_broker_test.cc index 8c26091..97ec506 100644 --- a/third_party/blink/renderer/modules/webcodecs/video_decoder_broker_test.cc +++ b/third_party/blink/renderer/modules/webcodecs/video_decoder_broker_test.cc
@@ -169,8 +169,8 @@ done_cb.Run(); } void OnDecodeDoneWithClosure(base::RepeatingClosure done_cb, - media::DecodeStatus status) { - OnDecodeDone(status); + media::Status status) { + OnDecodeDone(std::move(status)); done_cb.Run(); } @@ -180,7 +180,7 @@ } MOCK_METHOD1(OnInit, void(media::Status status)); - MOCK_METHOD1(OnDecodeDone, void(media::DecodeStatus)); + MOCK_METHOD1(OnDecodeDone, void(media::Status)); MOCK_METHOD0(OnResetDone, void()); void OnOutput(scoped_refptr<media::VideoFrame> frame) { @@ -238,9 +238,9 @@ void DecodeBuffer( scoped_refptr<media::DecoderBuffer> buffer, - media::DecodeStatus expected_status = media::DecodeStatus::OK) { + media::StatusCode expected_status = media::StatusCode::kOk) { base::RunLoop run_loop; - EXPECT_CALL(*this, OnDecodeDone(expected_status)); + EXPECT_CALL(*this, OnDecodeDone(HasStatusCode(expected_status))); decoder_broker_->Decode( buffer, WTF::Bind(&VideoDecoderBrokerTest::OnDecodeDoneWithClosure, WTF::Unretained(this), run_loop.QuitClosure()));
diff --git a/third_party/blink/renderer/modules/webcodecs/video_frame.cc b/third_party/blink/renderer/modules/webcodecs/video_frame.cc index fd90c0f..63865713 100644 --- a/third_party/blink/renderer/modules/webcodecs/video_frame.cc +++ b/third_party/blink/renderer/modules/webcodecs/video_frame.cc
@@ -402,13 +402,8 @@ auto release_callback = viz::SingleReleaseCallback::Create(base::BindOnce( [](gpu::SharedImageInterface* sii, gpu::Mailbox mailbox, - const gpu::SyncToken& sync_token, bool is_lost) { - // Ideally the SharedImage could be release here this way: - // sii->DestroySharedImage(sync_token, mailbox); - // But AcceleratedStaticBitmapImage leaks it when - // PaintImageForCurrentFrame() is called by ImageBitmap. So the - // 'sync_token' is not precise to destroy the mailbox. - }, + const gpu::SyncToken& sync_token, + bool is_lost) { sii->DestroySharedImage(sync_token, mailbox); }, base::Unretained(shared_image_interface), dest_holder.mailbox)); const SkImageInfo sk_image_info =
diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_base.cc b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_base.cc index 1f29b0a..c0f0705 100644 --- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_base.cc +++ b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_base.cc
@@ -38,7 +38,7 @@ #include "gpu/config/gpu_feature_info.h" #include "third_party/blink/public/common/features.h" #include "third_party/blink/public/common/privacy_budget/identifiability_metric_builder.h" -#include "third_party/blink/public/common/privacy_budget/identifiability_study_participation.h" +#include "third_party/blink/public/common/privacy_budget/identifiability_study_settings.h" #include "third_party/blink/public/common/thread_safe_browser_interface_broker_proxy.h" #include "third_party/blink/public/mojom/gpu/gpu.mojom-blink.h" #include "third_party/blink/public/platform/platform.h" @@ -819,7 +819,7 @@ if (xr_compatible_) return ScriptPromise::CastUndefined(script_state); - if (!base::FeatureList::IsEnabled(features::kWebXrMultiGpu)) { + if (!RuntimeEnabledFeatures::WebXRMultiGpuEnabled()) { xr_compatible_ = true; return ScriptPromise::CastUndefined(script_state); } @@ -859,7 +859,7 @@ bool WebGLRenderingContextBase::MakeXrCompatibleSync( CanvasRenderingContextHost* host) { - if (!base::FeatureList::IsEnabled(features::kWebXrMultiGpu)) + if (!RuntimeEnabledFeatures::WebXRMultiGpuEnabled()) return true; device::mojom::blink::XrCompatibleResult xr_compatible_result = @@ -3294,8 +3294,10 @@ WebGLDebugRendererInfo::kUnmaskedVendorWebgl, }; -bool IsIdentifiableGLParam(GLenum pname) { - return std::find(std::begin(kIdentifiableGLParams), +bool ShouldMeasureGLParam(GLenum pname) { + return IdentifiabilityStudySettings::Get()->IsTypeAllowed( + blink::IdentifiableSurface::Type::kWebGLParameter) && + std::find(std::begin(kIdentifiableGLParams), std::end(kIdentifiableGLParams), pname) != std::end(kIdentifiableGLParams); } @@ -3305,7 +3307,7 @@ void WebGLRenderingContextBase::RecordIdentifiableGLParameterDigest( GLenum pname, IdentifiableToken value) { - if (!IsUserInIdentifiabilityStudy() || !IsIdentifiableGLParam(pname)) + if (!ShouldMeasureGLParam(pname)) return; if (const auto& ukm_params = GetUkmParameters()) { blink::IdentifiabilityMetricBuilder(ukm_params->source_id) @@ -3455,7 +3457,7 @@ case GL_SCISSOR_TEST: return GetBooleanParameter(script_state, pname); case GL_SHADING_LANGUAGE_VERSION: - if (IsUserInIdentifiabilityStudy()) { + if (IdentifiabilityStudySettings::Get()->IsActive()) { RecordIdentifiableGLParameterDigest( pname, IdentifiabilityBenignStringToken(String( ContextGL()->GetString(GL_SHADING_LANGUAGE_VERSION)))); @@ -3522,7 +3524,7 @@ case GL_VENDOR: return WebGLAny(script_state, String("WebKit")); case GL_VERSION: - if (IsUserInIdentifiabilityStudy()) { + if (IdentifiabilityStudySettings::Get()->IsActive()) { RecordIdentifiableGLParameterDigest( pname, IdentifiabilityBenignStringToken( String(ContextGL()->GetString(GL_VERSION)))); @@ -3542,7 +3544,7 @@ return ScriptValue::CreateNull(script_state->GetIsolate()); case WebGLDebugRendererInfo::kUnmaskedRendererWebgl: if (ExtensionEnabled(kWebGLDebugRendererInfoName)) { - if (IsUserInIdentifiabilityStudy()) { + if (IdentifiabilityStudySettings::Get()->IsActive()) { RecordIdentifiableGLParameterDigest( pname, IdentifiabilityBenignStringToken( String(ContextGL()->GetString(GL_RENDERER)))); @@ -3556,7 +3558,7 @@ return ScriptValue::CreateNull(script_state->GetIsolate()); case WebGLDebugRendererInfo::kUnmaskedVendorWebgl: if (ExtensionEnabled(kWebGLDebugRendererInfoName)) { - if (IsUserInIdentifiabilityStudy()) { + if (IdentifiabilityStudySettings::Get()->IsActive()) { RecordIdentifiableGLParameterDigest( pname, IdentifiabilityBenignStringToken( String(ContextGL()->GetString(GL_VENDOR)))); @@ -4604,7 +4606,7 @@ GLenum format, GLenum type, MaybeShared<DOMArrayBufferView> pixels) { - if (IsUserInIdentifiabilityStudy()) { + if (IdentifiabilityStudySettings::Get()->IsActive()) { if (const auto& ukm_params = GetUkmParameters()) { blink::IdentifiabilityMetricBuilder(ukm_params->source_id) .Set(blink::IdentifiableSurface::FromTypeAndInput( @@ -7161,7 +7163,8 @@ default: NOTIMPLEMENTED(); } - if (IsUserInIdentifiabilityStudy() && IsIdentifiableGLParam(pname)) { + if (IdentifiabilityStudySettings::Get()->IsActive() && + ShouldMeasureGLParam(pname)) { blink::IdentifiableTokenBuilder builder; for (unsigned i = 0; i < length; i++) { builder.AddToken(value[i]); @@ -7189,7 +7192,8 @@ default: NOTIMPLEMENTED(); } - if (IsUserInIdentifiabilityStudy() && IsIdentifiableGLParam(pname)) { + if (IdentifiabilityStudySettings::Get()->IsActive() && + ShouldMeasureGLParam(pname)) { blink::IdentifiableTokenBuilder builder; for (unsigned i = 0; i < length; i++) { builder.AddToken(value[i]);
diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn index ef57ba1..892a496 100644 --- a/third_party/blink/renderer/platform/BUILD.gn +++ b/third_party/blink/renderer/platform/BUILD.gn
@@ -1022,6 +1022,8 @@ "graphics/interpolation_space.h", "graphics/logging_canvas.cc", "graphics/logging_canvas.h", + "graphics/mailbox_ref.cc", + "graphics/mailbox_ref.h", "graphics/mailbox_texture_backing.cc", "graphics/mailbox_texture_backing.h", "graphics/main_thread_mutator_client.cc", @@ -1073,7 +1075,6 @@ "graphics/paint/paint_canvas.h", "graphics/paint/paint_chunk.cc", "graphics/paint/paint_chunk.h", - "graphics/paint/paint_chunk_subset.cc", "graphics/paint/paint_chunk_subset.h", "graphics/paint/paint_chunker.cc", "graphics/paint/paint_chunker.h",
diff --git a/third_party/blink/renderer/platform/fonts/font_matching_metrics.cc b/third_party/blink/renderer/platform/fonts/font_matching_metrics.cc index 4fea14e..e7060c5 100644 --- a/third_party/blink/renderer/platform/fonts/font_matching_metrics.cc +++ b/third_party/blink/renderer/platform/fonts/font_matching_metrics.cc
@@ -11,7 +11,6 @@ #include "third_party/blink/public/common/privacy_budget/identifiability_study_settings.h" #include "third_party/blink/public/common/privacy_budget/identifiable_surface.h" #include "third_party/blink/public/common/privacy_budget/identifiable_token.h" -#include "third_party/blink/public/common/privacy_budget/identifiable_token_builder.h" #include "third_party/blink/renderer/platform/fonts/font_global_context.h" #include "third_party/blink/renderer/platform/privacy_budget/identifiability_digest_helpers.h" @@ -85,6 +84,23 @@ local_fonts_failed_.insert(font_name); } +void FontMatchingMetrics::InsertFontHashIntoMap(IdentifiableTokenKey input_key, + SimpleFontData* font_data, + TokenToTokenHashMap hash_map) { + if (hash_map.Contains(input_key)) + return; + IdentifiableToken output_token(GetHashForFontData(font_data)); + hash_map.insert(input_key, output_token); +} + +IdentifiableTokenBuilder +FontMatchingMetrics::GetTokenBuilderWithFontSelectionRequest( + const FontDescription& font_description) { + IdentifiableTokenBuilder builder; + builder.AddValue(font_description.GetFontSelectionRequest().GetHash()); + return builder; +} + void FontMatchingMetrics::ReportFontLookupByUniqueOrFamilyName( const AtomicString& name, const FontDescription& font_description, @@ -94,17 +110,15 @@ } OnFontLookup(); - IdentifiableTokenBuilder builder; + IdentifiableTokenBuilder builder = + GetTokenBuilderWithFontSelectionRequest(font_description); // Font name lookups are case-insensitive. - builder.AddToken(IdentifiabilityBenignCaseFoldingStringToken(name)) - .AddValue(font_description.GetFontSelectionRequest().GetHash()); - IdentifiableTokenKey input_key(builder.GetToken()); + builder.AddToken(IdentifiabilityBenignCaseFoldingStringToken(name)); - if (font_lookups_by_unique_or_family_name_.Contains(input_key)) - return; - IdentifiableToken output_token(GetHashForFontData(resulting_font_data)); - font_lookups_by_unique_or_family_name_.insert(input_key, output_token); + IdentifiableTokenKey input_key(builder.GetToken()); + InsertFontHashIntoMap(input_key, resulting_font_data, + font_lookups_by_unique_or_family_name_); } void FontMatchingMetrics::ReportFontLookupByUniqueNameOnly( @@ -119,17 +133,15 @@ } OnFontLookup(); - IdentifiableTokenBuilder builder; + IdentifiableTokenBuilder builder = + GetTokenBuilderWithFontSelectionRequest(font_description); // Font name lookups are case-insensitive. - builder.AddToken(IdentifiabilityBenignCaseFoldingStringToken(name)) - .AddValue(font_description.GetFontSelectionRequest().GetHash()); - IdentifiableTokenKey input_key(builder.GetToken()); + builder.AddToken(IdentifiabilityBenignCaseFoldingStringToken(name)); - if (font_lookups_by_unique_name_only_.Contains(input_key)) - return; - IdentifiableToken output_token(GetHashForFontData(resulting_font_data)); - font_lookups_by_unique_name_only_.insert(input_key, output_token); + IdentifiableTokenKey input_key(builder.GetToken()); + InsertFontHashIntoMap(input_key, resulting_font_data, + font_lookups_by_unique_name_only_); } void FontMatchingMetrics::ReportFontLookupByFallbackCharacter( @@ -142,16 +154,14 @@ } OnFontLookup(); - IdentifiableTokenBuilder builder; + IdentifiableTokenBuilder builder = + GetTokenBuilderWithFontSelectionRequest(font_description); builder.AddValue(fallback_character) - .AddToken(IdentifiableToken(fallback_priority)) - .AddValue(font_description.GetFontSelectionRequest().GetHash()); - IdentifiableTokenKey input_key(builder.GetToken()); + .AddToken(IdentifiableToken(fallback_priority)); - if (font_lookups_by_fallback_character_.Contains(input_key)) - return; - IdentifiableToken output_token(GetHashForFontData(resulting_font_data)); - font_lookups_by_fallback_character_.insert(input_key, output_token); + IdentifiableTokenKey input_key(builder.GetToken()); + InsertFontHashIntoMap(input_key, resulting_font_data, + font_lookups_by_fallback_character_); } void FontMatchingMetrics::ReportLastResortFallbackFontLookup( @@ -162,14 +172,12 @@ } OnFontLookup(); - IdentifiableTokenBuilder builder; - builder.AddValue(font_description.GetFontSelectionRequest().GetHash()); - IdentifiableTokenKey input_key(builder.GetToken()); + IdentifiableTokenBuilder builder = + GetTokenBuilderWithFontSelectionRequest(font_description); - if (font_lookups_as_last_resort_.Contains(input_key)) - return; - IdentifiableToken output_token(GetHashForFontData(resulting_font_data)); - font_lookups_as_last_resort_.insert(input_key, output_token); + IdentifiableTokenKey input_key(builder.GetToken()); + InsertFontHashIntoMap(input_key, resulting_font_data, + font_lookups_as_last_resort_); } void FontMatchingMetrics::ReportFontFamilyLookupByGenericFamily( @@ -207,48 +215,30 @@ IdentifiabilityMetricBuilder builder(source_id_); - for (const auto& entry : font_lookups_by_unique_or_family_name_) { - builder.Set( - IdentifiableSurface::FromTypeAndToken( - IdentifiableSurface::Type::kLocalFontLookupByUniqueOrFamilyName, - entry.key.token), - entry.value); - } - font_lookups_by_unique_or_family_name_.clear(); + std::pair<TokenToTokenHashMap*, IdentifiableSurface::Type> + hash_maps_with_corresponding_surface_types[] = { + {&font_lookups_by_unique_or_family_name_, + IdentifiableSurface::Type::kLocalFontLookupByUniqueOrFamilyName}, + {&font_lookups_by_unique_name_only_, + IdentifiableSurface::Type::kLocalFontLookupByUniqueOrFamilyName}, + {&font_lookups_by_fallback_character_, + IdentifiableSurface::Type::kLocalFontLookupByFallbackCharacter}, + {&font_lookups_as_last_resort_, + IdentifiableSurface::Type::kLocalFontLookupAsLastResort}, + {&generic_font_lookups_, + IdentifiableSurface::Type::kGenericFontLookup}, + }; - for (const auto& entry : font_lookups_by_unique_name_only_) { - builder.Set( - IdentifiableSurface::FromTypeAndToken( - IdentifiableSurface::Type::kLocalFontLookupByUniqueOrFamilyName, - entry.key.token), - entry.value); + for (const auto& surface_entry : hash_maps_with_corresponding_surface_types) { + TokenToTokenHashMap* hash_map = surface_entry.first; + const IdentifiableSurface::Type& surface_type = surface_entry.second; + for (const auto& individual_lookup : *hash_map) { + builder.Set(IdentifiableSurface::FromTypeAndToken( + surface_type, individual_lookup.key.token), + individual_lookup.value); + } + hash_map->clear(); } - font_lookups_by_unique_name_only_.clear(); - - for (const auto& entry : font_lookups_by_fallback_character_) { - builder.Set( - IdentifiableSurface::FromTypeAndToken( - IdentifiableSurface::Type::kLocalFontLookupByFallbackCharacter, - entry.key.token), - entry.value); - } - font_lookups_by_fallback_character_.clear(); - - for (const auto& entry : font_lookups_as_last_resort_) { - builder.Set(IdentifiableSurface::FromTypeAndToken( - IdentifiableSurface::Type::kLocalFontLookupAsLastResort, - entry.key.token), - entry.value); - } - font_lookups_as_last_resort_.clear(); - - for (const auto& entry : generic_font_lookups_) { - builder.Set( - IdentifiableSurface::FromTypeAndToken( - IdentifiableSurface::Type::kGenericFontLookup, entry.key.token), - entry.value); - } - generic_font_lookups_.clear(); builder.Record(ukm_recorder_); }
diff --git a/third_party/blink/renderer/platform/fonts/font_matching_metrics.h b/third_party/blink/renderer/platform/fonts/font_matching_metrics.h index 76b04f0..c3933bf 100644 --- a/third_party/blink/renderer/platform/fonts/font_matching_metrics.h +++ b/third_party/blink/renderer/platform/fonts/font_matching_metrics.h
@@ -7,6 +7,7 @@ #include "services/metrics/public/cpp/ukm_source_id.h" #include "third_party/blink/public/common/privacy_budget/identifiable_token.h" +#include "third_party/blink/public/common/privacy_budget/identifiable_token_builder.h" #include "third_party/blink/renderer/platform/fonts/font_description.h" #include "third_party/blink/renderer/platform/fonts/font_fallback_priority.h" #include "third_party/blink/renderer/platform/fonts/simple_font_data.h" @@ -172,6 +173,26 @@ private: void IdentifiabilityMetricsTimerFired(TimerBase*); + // This HashMap generically stores details of font lookups, i.e. what was used + // to search for the font, and what the resulting font was. The key is an + // IdentifiableTokenKey representing a wrapper around a digest of the lookup + // parameters. The value is an IdentifiableToken representing either a digest + // of the returned typeface or 0, if no valid typeface was found. + using TokenToTokenHashMap = HashMap<IdentifiableTokenKey, + IdentifiableToken, + IdentifiableTokenKeyHash, + IdentifiableTokenKeyHashTraits>; + + // Adds a digest of the |font_data|'s typeface to |hash_map| using the key + // |input_key|, unless that key is already present. + void InsertFontHashIntoMap(IdentifiableTokenKey input_key, + SimpleFontData* font_data, + TokenToTokenHashMap hash_map); + + // Constructs a builder with a hash of the FontSelectionRequest already added. + IdentifiableTokenBuilder GetTokenBuilderWithFontSelectionRequest( + const FontDescription& font_description); + // Get a hash that uniquely represents the font data. Returns 0 if |font_data| // is nullptr. int64_t GetHashForFontData(SimpleFontData* font_data); @@ -198,15 +219,6 @@ // otherwise. const bool top_level_ = false; - // This HashMap generically stores details of font lookups, i.e. what was used - // to search for the font, and what the resulting font was. The key is an - // IdentifiableTokenKey representing a wrapper around a digest of the lookup - // parameters. The value is an IdentifiableToken representing either a digest - // of the returned typeface or 0, if no valid typeface was found. - using TokenToTokenHashMap = HashMap<IdentifiableTokenKey, - IdentifiableToken, - IdentifiableTokenKeyHash, - IdentifiableTokenKeyHashTraits>; TokenToTokenHashMap font_lookups_by_unique_or_family_name_; TokenToTokenHashMap font_lookups_by_unique_name_only_; TokenToTokenHashMap font_lookups_by_fallback_character_;
diff --git a/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.cc b/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.cc index 8d098ee..6d4999b 100644 --- a/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.cc +++ b/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.cc
@@ -18,46 +18,14 @@ #include "third_party/blink/public/platform/web_graphics_context_3d_provider.h" #include "third_party/blink/renderer/platform/graphics/canvas_resource_provider.h" #include "third_party/blink/renderer/platform/graphics/gpu/shared_gpu_context.h" +#include "third_party/blink/renderer/platform/graphics/mailbox_ref.h" #include "third_party/blink/renderer/platform/graphics/mailbox_texture_backing.h" #include "third_party/blink/renderer/platform/graphics/skia/skia_utils.h" #include "third_party/blink/renderer/platform/graphics/unaccelerated_static_bitmap_image.h" -#include "third_party/blink/renderer/platform/scheduler/public/post_cross_thread_task.h" -#include "third_party/blink/renderer/platform/wtf/cross_thread_functional.h" #include "third_party/skia/include/core/SkImage.h" #include "third_party/skia/include/gpu/GrDirectContext.h" namespace blink { -namespace { - -void ReleaseCallbackOnContextThread( - std::unique_ptr<viz::SingleReleaseCallback> callback, - const gpu::SyncToken sync_token) { - callback->Run(sync_token, /* is_lost = */ false); -} - -} // namespace - -AcceleratedStaticBitmapImage::MailboxRef::MailboxRef( - const gpu::SyncToken& sync_token, - base::PlatformThreadRef context_thread_ref, - scoped_refptr<base::SingleThreadTaskRunner> context_task_runner, - std::unique_ptr<viz::SingleReleaseCallback> release_callback) - : sync_token_(sync_token), - context_thread_ref_(context_thread_ref), - context_task_runner_(std::move(context_task_runner)), - release_callback_(std::move(release_callback)) { - DCHECK(sync_token.HasData()); -} - -AcceleratedStaticBitmapImage::MailboxRef::~MailboxRef() { - if (context_thread_ref_ == base::PlatformThread::CurrentRef()) { - ReleaseCallbackOnContextThread(std::move(release_callback_), sync_token_); - } else { - context_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&ReleaseCallbackOnContextThread, - std::move(release_callback_), sync_token_)); - } -} // static void AcceleratedStaticBitmapImage::ReleaseTexture(void* ctx) { @@ -271,7 +239,8 @@ DCHECK_EQ(shared_image_texture_id, 0u); skia_context_provider_wrapper_ = context_provider_wrapper; texture_backing_ = sk_make_sp<MailboxTextureBacking>( - mailbox_, sk_image_info_, std::move(context_provider_wrapper)); + mailbox_, mailbox_ref_, sk_image_info_, + std::move(context_provider_wrapper)); return; } @@ -318,9 +287,9 @@ if (sk_image) { skia_context_provider_wrapper_ = context_provider_wrapper; - texture_backing_ = - sk_make_sp<MailboxTextureBacking>(std::move(sk_image), sk_image_info_, - std::move(context_provider_wrapper)); + texture_backing_ = sk_make_sp<MailboxTextureBacking>( + std::move(sk_image), mailbox_ref_, sk_image_info_, + std::move(context_provider_wrapper)); } }
diff --git a/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.h b/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.h index e9f9802..8ed9660 100644 --- a/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.h +++ b/third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.h
@@ -10,6 +10,7 @@ #include "base/memory/weak_ptr.h" #include "base/single_thread_task_runner.h" #include "base/threading/thread_checker.h" +#include "third_party/blink/renderer/platform/graphics/mailbox_ref.h" #include "third_party/blink/renderer/platform/graphics/static_bitmap_image.h" #include "third_party/blink/renderer/platform/scheduler/public/thread.h" @@ -120,31 +121,6 @@ PaintImage PaintImageForCurrentFrame() override; private: - class MailboxRef : public ThreadSafeRefCounted<MailboxRef> { - public: - MailboxRef(const gpu::SyncToken& sync_token, - base::PlatformThreadRef context_thread_ref, - scoped_refptr<base::SingleThreadTaskRunner> context_task_runner, - std::unique_ptr<viz::SingleReleaseCallback> release_callback); - ~MailboxRef(); - - bool is_cross_thread() const { - return base::PlatformThread::CurrentRef() != context_thread_ref_; - } - void set_sync_token(gpu::SyncToken token) { - DCHECK(sync_token_.HasData()); - sync_token_ = token; - } - const gpu::SyncToken& sync_token() const { return sync_token_; } - bool verified_flush() { return sync_token_.verified_flush(); } - - private: - gpu::SyncToken sync_token_; - const base::PlatformThreadRef context_thread_ref_; - const scoped_refptr<base::SingleThreadTaskRunner> context_task_runner_; - std::unique_ptr<viz::SingleReleaseCallback> release_callback_; - }; - struct ReleaseContext { scoped_refptr<MailboxRef> mailbox_ref; GLuint texture_id = 0u;
diff --git a/third_party/blink/renderer/platform/graphics/canvas_resource_provider.h b/third_party/blink/renderer/platform/graphics/canvas_resource_provider.h index 5b1d946..1ee50ad 100644 --- a/third_party/blink/renderer/platform/graphics/canvas_resource_provider.h +++ b/third_party/blink/renderer/platform/graphics/canvas_resource_provider.h
@@ -66,13 +66,13 @@ // These values are persisted to logs. Entries should not be renumbered and // numeric values should never be reused. enum ResourceProviderType { - kTexture = 0, + kTexture [[deprecated]] = 0, kBitmap = 1, kSharedBitmap = 2, - kTextureGpuMemoryBuffer = 3, - kBitmapGpuMemoryBuffer = 4, + kTextureGpuMemoryBuffer [[deprecated]] = 3, + kBitmapGpuMemoryBuffer [[deprecated]] = 4, kSharedImage = 5, - kDirectGpuMemoryBuffer = 6, + kDirectGpuMemoryBuffer [[deprecated]] = 6, kPassThrough = 7, kSwapChain = 8, kSkiaDawnSharedImage = 9,
diff --git a/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.cc b/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.cc index 8674591..967d92f0 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.cc +++ b/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.cc
@@ -59,23 +59,26 @@ } scoped_refptr<cc::PictureLayer> ContentLayerClientImpl::UpdateCcPictureLayer( + scoped_refptr<const PaintArtifact> paint_artifact, const PaintChunkSubset& paint_chunks, const gfx::Rect& layer_bounds, const PropertyTreeState& layer_state) { - if (paint_chunks.begin()->is_cacheable) - id_.emplace(paint_chunks.begin()->id); + if (paint_chunks[0].is_cacheable) + id_.emplace(paint_chunks[0].id); else id_ = base::nullopt; + const auto& display_item_list = paint_artifact->GetDisplayItemList(); + #if DCHECK_IS_ON() paint_chunk_debug_data_ = std::make_unique<JSONArray>(); - for (auto it = paint_chunks.begin(); it != paint_chunks.end(); ++it) { + for (const auto& chunk : paint_chunks) { auto json = std::make_unique<JSONObject>(); - json->SetString("data", it->ToString()); - json->SetArray( - "displayItems", - DisplayItemList::DisplayItemsAsJSON( - it.DisplayItems(), DisplayItemList::kShowOnlyDisplayItemTypes)); + json->SetString("data", chunk.ToString()); + json->SetArray("displayItems", + paint_artifact->GetDisplayItemList().DisplayItemsAsJSON( + chunk.begin_index, chunk.end_index, + DisplayItemList::kShowOnlyDisplayItemTypes)); paint_chunk_debug_data_->PushObject(std::move(json)); } #endif @@ -88,8 +91,8 @@ raster_invalidated_ = false; gfx::Size old_layer_size = raster_invalidator_.LayerBounds().size(); DCHECK_EQ(old_layer_size, cc_picture_layer_->bounds()); - raster_invalidator_.Generate(raster_invalidation_function_, paint_chunks, - layer_bounds, layer_state); + raster_invalidator_.Generate(raster_invalidation_function_, paint_artifact, + paint_chunks, layer_bounds, layer_state); layer_state_ = layer_state; base::Optional<RasterUnderInvalidationCheckingParams> @@ -98,7 +101,7 @@ raster_under_invalidation_params.emplace( *raster_invalidator_.GetTracking(), IntRect(0, 0, layer_bounds.width(), layer_bounds.height()), - paint_chunks.begin()->id.client.DebugName()); + paint_chunks[0].id.client.DebugName()); } // Note: cc::Layer API assumes the layer bounds start at (0, 0), but the @@ -120,7 +123,7 @@ cc_display_item_list_ = PaintChunksToCcLayer::Convert( paint_chunks, layer_state, layer_bounds.OffsetFromOrigin(), - cc::DisplayItemList::kTopLevelDisplayItemList, + display_item_list, cc::DisplayItemList::kTopLevelDisplayItemList, base::OptionalOrNullptr(raster_under_invalidation_params)); cc_picture_layer_->SetBounds(layer_bounds.size()); @@ -132,7 +135,7 @@ layer_state.Effect().HasBackdropEffect() || !layer_state.Effect().Filter().IsEmpty()); - PaintChunksToCcLayer::UpdateBackgroundColor(*cc_picture_layer_, paint_chunks); + paint_artifact->UpdateBackgroundColor(cc_picture_layer_.get(), paint_chunks); return cc_picture_layer_; }
diff --git a/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.h b/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.h index de6bf2db..a9b13f4 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.h +++ b/third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.h
@@ -19,6 +19,7 @@ class JSONArray; class JSONObject; +class PaintArtifact; class PaintChunkSubset; class PLATFORM_EXPORT ContentLayerClientImpl : public cc::ContentLayerClient, @@ -56,6 +57,7 @@ } scoped_refptr<cc::PictureLayer> UpdateCcPictureLayer( + scoped_refptr<const PaintArtifact>, const PaintChunkSubset&, const gfx::Rect& layer_bounds, const PropertyTreeState&);
diff --git a/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.cc b/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.cc index 8635b37..8a422bc5 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.cc +++ b/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.cc
@@ -15,7 +15,6 @@ #include "third_party/blink/public/platform/platform.h" #include "third_party/blink/renderer/platform/geometry/geometry_as_json.h" #include "third_party/blink/renderer/platform/graphics/compositing/content_layer_client_impl.h" -#include "third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.h" #include "third_party/blink/renderer/platform/graphics/graphics_context.h" #include "third_party/blink/renderer/platform/graphics/graphics_layer.h" #include "third_party/blink/renderer/platform/graphics/paint/clip_paint_property_node.h" @@ -125,9 +124,10 @@ } static void UpdateLayerProperties(const GraphicsLayer& graphics_layer) { - PaintChunksToCcLayer::UpdateBackgroundColor( - graphics_layer.CcLayer(), - graphics_layer.GetPaintController().PaintChunks()); + cc::PictureLayer& cc_layer = graphics_layer.CcLayer(); + const PaintArtifact& paint_artifact = + graphics_layer.GetPaintController().GetPaintArtifact(); + paint_artifact.UpdateBackgroundColor(&cc_layer, paint_artifact.PaintChunks()); } scoped_refptr<cc::Layer> PaintArtifactCompositor::WrappedCcLayerForPendingLayer( @@ -289,10 +289,10 @@ Vector<scoped_refptr<cc::Layer>>& new_scroll_hit_test_layers, Vector<scoped_refptr<cc::ScrollbarLayerBase>>& new_scrollbar_layers, const HashSet<const GraphicsLayer*>& repainted_layers) { - PaintChunkSubset paint_chunks(pending_layer.paint_artifact, - pending_layer.paint_chunk_indices); - DCHECK(!paint_chunks.IsEmpty()); - const PaintChunk& first_paint_chunk = *paint_chunks.begin(); + auto paint_chunks = pending_layer.paint_artifact->GetPaintChunkSubset( + pending_layer.paint_chunk_indices); + DCHECK(paint_chunks.size()); + const PaintChunk& first_paint_chunk = paint_chunks[0]; // If the paint chunk is a foreign layer or placeholder for a GraphicsLayer, // just return its cc::Layer. @@ -318,7 +318,8 @@ IntRect cc_combined_bounds = EnclosingIntRect(pending_layer.bounds); auto cc_layer = content_layer_client->UpdateCcPictureLayer( - paint_chunks, cc_combined_bounds, pending_layer.property_tree_state); + pending_layer.paint_artifact, paint_chunks, cc_combined_bounds, + pending_layer.property_tree_state); new_content_layer_clients.push_back(std::move(content_layer_client)); @@ -428,19 +429,19 @@ } PaintArtifactCompositor::PendingLayer::PendingLayer( - const PaintChunkSubset& chunks, - PaintChunkIndex first_chunk_index, + scoped_refptr<const PaintArtifact> paint_artifact, + const PaintChunk& first_paint_chunk, + wtf_size_t chunk_index, CompositingType compositing_type) - : bounds(chunks[first_chunk_index].bounds), + : bounds(first_paint_chunk.bounds), rect_known_to_be_opaque( - chunks[first_chunk_index].known_to_be_opaque ? bounds : FloatRect()), - paint_artifact(&chunks.GetPaintArtifact()), - property_tree_state(chunks[first_chunk_index] - .properties.GetPropertyTreeState() - .Unalias()), + first_paint_chunk.known_to_be_opaque ? bounds : FloatRect()), + paint_artifact(std::move(paint_artifact)), + property_tree_state( + first_paint_chunk.properties.GetPropertyTreeState().Unalias()), compositing_type(compositing_type) { - DCHECK(!RequiresOwnLayer() || chunks[first_chunk_index].size() <= 1u); - paint_chunk_indices.push_back(first_chunk_index); + DCHECK(!RequiresOwnLayer() || first_paint_chunk.size() <= 1u); + paint_chunk_indices.push_back(chunk_index); } FloatRect PaintArtifactCompositor::PendingLayer::UniteRectsKnownToBeOpaque( @@ -498,16 +499,14 @@ result->SetArray("offset_of_decomposited_transforms", PointAsJSONArray(offset_of_decomposited_transforms)); std::unique_ptr<JSONArray> chunks = std::make_unique<JSONArray>(); - for (auto chunk_index : paint_chunk_indices) { + for (wtf_size_t chunk_index : paint_chunk_indices) { if (paint_artifact) { StringBuilder sb; - sb.Append("index="); - sb.Append(chunk_index.ToString()); - sb.Append(" "); - sb.Append(paint_artifact->GetChunk(chunk_index).ToString()); + sb.AppendFormat("index=%i ", chunk_index); + sb.Append(paint_artifact->PaintChunks()[chunk_index].ToString()); chunks->PushString(sb.ToString()); } else { - chunks->PushString(chunk_index.ToString()); + chunks->PushInteger(chunk_index); } } result->SetArray("paint_chunks", std::move(chunks)); @@ -555,7 +554,7 @@ const PaintChunk& PaintArtifactCompositor::PendingLayer::FirstPaintChunk() const { DCHECK(!RequiresOwnLayer() || paint_chunk_indices.size() == 1); - return paint_artifact->GetChunk(paint_chunk_indices[0]); + return paint_artifact->PaintChunks()[paint_chunk_indices[0]]; } const DisplayItem& PaintArtifactCompositor::PendingLayer::FirstDisplayItem() @@ -782,9 +781,9 @@ } static bool SkipGroupIfEffectivelyInvisible( - const PaintChunkSubset& chunks, + const PaintArtifact& paint_artifact, const EffectPaintPropertyNode& group, - PaintChunkIterator& chunk_cursor) { + Vector<PaintChunk>::const_iterator& chunk_it) { // In pre-CompositeAfterPaint, existence of composited layers is decided // during compositing update before paint. Each chunk contains a foreign // layer corresponding a composited layer. We should not skip any of them to @@ -808,9 +807,9 @@ // Fast-forward to just past the end of the chunk sequence within this // effect group. - DCHECK(EffectGroupContainsChunk(group, *chunk_cursor)); - while (++chunk_cursor != chunks.end()) { - if (!EffectGroupContainsChunk(group, *chunk_cursor)) + DCHECK(EffectGroupContainsChunk(group, *chunk_it)); + while (++chunk_it != paint_artifact.PaintChunks().end()) { + if (!EffectGroupContainsChunk(group, *chunk_it)) break; } return true; @@ -834,12 +833,12 @@ } void PaintArtifactCompositor::LayerizeGroup( - const PaintChunkSubset& chunks, + scoped_refptr<const PaintArtifact> paint_artifact, const EffectPaintPropertyNode& current_group, - PaintChunkIterator& chunk_cursor) { + Vector<PaintChunk>::const_iterator& chunk_it) { // Skip paint chunks that are effectively invisible due to opacity and don't // have a direct compositing reason. - if (SkipGroupIfEffectivelyInvisible(chunks, current_group, chunk_cursor)) + if (SkipGroupIfEffectivelyInvisible(*paint_artifact, current_group, chunk_it)) return; wtf_size_t first_layer_in_current_group = pending_layers_.size(); @@ -861,19 +860,20 @@ // previous layer. Again finding the host costs O(qd). Merging would cost // O(p) due to copying the chunk list. Subtotal: O((qd + p)d) = O(qd^2 + pd) // Assuming p > d, the total complexity would be O(pqd + qd^2 + pd) = O(pqd) - while (chunk_cursor != chunks.end()) { + while (chunk_it != paint_artifact->PaintChunks().end()) { // Look at the effect node of the next chunk. There are 3 possible cases: // A. The next chunk belongs to the current group but no subgroup. // B. The next chunk does not belong to the current group. // C. The next chunk belongs to some subgroup of the current group. - const auto& chunk_effect = chunk_cursor->properties.Effect().Unalias(); + const auto& chunk_effect = chunk_it->properties.Effect().Unalias(); if (&chunk_effect == ¤t_group) { // Case A: The next chunk belongs to the current group but no subgroup. PendingLayer::CompositingType compositing_type = PendingLayer::kOther; - if (IsCompositedScrollHitTest(*chunk_cursor)) { + if (IsCompositedScrollHitTest(*chunk_it)) { compositing_type = PendingLayer::kScrollHitTestLayer; - } else if (chunk_cursor->size()) { - const auto& first_display_item = *chunk_cursor.DisplayItems().begin(); + } else if (chunk_it->size()) { + const auto& first_display_item = + paint_artifact->GetDisplayItemList()[chunk_it->begin_index]; if (first_display_item.IsForeignLayer()) { compositing_type = PendingLayer::kForeignLayer; } else if (IsCompositedScrollbar(first_display_item)) { @@ -884,24 +884,27 @@ .GetGraphicsLayer(); if (graphics_layer.ShouldCreateLayersAfterPaint()) { DCHECK(RuntimeEnabledFeatures::CompositeSVGEnabled()); - auto sub_chunks = graphics_layer.GetPaintController().PaintChunks(); - auto cursor = sub_chunks.begin(); + scoped_refptr<const PaintArtifact> sub_paint_artifact = + graphics_layer.GetPaintController().GetPaintArtifactShared(); + Vector<PaintChunk>::const_iterator cursor = + sub_paint_artifact->PaintChunks().begin(); LayerizeGroup( - sub_chunks, + sub_paint_artifact, graphics_layer.GetPropertyTreeState().Unalias().Effect(), cursor); - DCHECK_EQ(sub_chunks.end(), cursor); + DCHECK_EQ(sub_paint_artifact->PaintChunks().end(), cursor); - ++chunk_cursor; + chunk_it++; continue; } compositing_type = PendingLayer::kGraphicsLayerWrapper; } } - pending_layers_.emplace_back(chunks, chunk_cursor.Index(), - compositing_type); - ++chunk_cursor; + pending_layers_.emplace_back( + paint_artifact, *chunk_it, + chunk_it - paint_artifact->PaintChunks().begin(), compositing_type); + chunk_it++; if (pending_layers_.back().RequiresOwnLayer()) continue; } else { @@ -914,7 +917,7 @@ // Case C: The following chunks belong to a subgroup. Process them by // a recursion call. wtf_size_t first_layer_in_subgroup = pending_layers_.size(); - LayerizeGroup(chunks, *subgroup, chunk_cursor); + LayerizeGroup(paint_artifact, *subgroup, chunk_it); // The above LayerizeGroup generated new layers in pending_layers_ // [first_layer_in_subgroup .. pending_layers.size() - 1]. If it // generated 2 or more layer that we already know can't be merged @@ -952,12 +955,12 @@ void PaintArtifactCompositor::CollectPendingLayers( scoped_refptr<const PaintArtifact> paint_artifact) { - auto chunks = paint_artifact->Chunks(); - auto cursor = chunks.begin(); + Vector<PaintChunk>::const_iterator cursor = + paint_artifact->PaintChunks().begin(); // Shrink, but do not release the backing. Re-use it from the last frame. pending_layers_.Shrink(0); - LayerizeGroup(chunks, EffectPaintPropertyNode::Root(), cursor); - DCHECK_EQ(chunks.end(), cursor); + LayerizeGroup(paint_artifact, EffectPaintPropertyNode::Root(), cursor); + DCHECK_EQ(paint_artifact->PaintChunks().end(), cursor); pending_layers_.ShrinkToReasonableCapacity(); } @@ -1297,8 +1300,8 @@ // In Pre-CompositeAfterPaint, touch action rects and non-fast scrollable // regions are updated through ScrollingCoordinator. if (RuntimeEnabledFeatures::CompositeAfterPaintEnabled()) { - PaintChunkSubset paint_chunks(paint_artifact, - pending_layer.paint_chunk_indices); + auto paint_chunks = paint_artifact->GetPaintChunkSubset( + pending_layer.paint_chunk_indices); UpdateTouchActionRects(*layer, layer->offset_to_transform_parent(), property_state, paint_chunks); UpdateNonFastScrollableRegions(
diff --git a/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.h b/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.h index bc89dd98..147c8a5f 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.h +++ b/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor.h
@@ -19,7 +19,6 @@ #include "third_party/blink/renderer/platform/graphics/compositing_reasons.h" #include "third_party/blink/renderer/platform/graphics/graphics_layer_client.h" #include "third_party/blink/renderer/platform/graphics/paint/geometry_mapper.h" -#include "third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h" #include "third_party/blink/renderer/platform/graphics/paint/paint_controller.h" #include "third_party/blink/renderer/platform/platform_export.h" #include "third_party/blink/renderer/platform/wtf/vector.h" @@ -40,8 +39,10 @@ class ContentLayerClientImpl; class JSONObject; +class PaintArtifact; class PropertyTreeManager; class SynthesizedClip; +struct PaintChunk; using CompositorScrollCallbacks = cc::ScrollCallbacks; @@ -228,8 +229,9 @@ kOther, }; - PendingLayer(const PaintChunkSubset&, - PaintChunkIndex first_chunk_index, + PendingLayer(scoped_refptr<const PaintArtifact>, + const PaintChunk& first_paint_chunk, + wtf_size_t first_chunk_index, CompositingType compositng_type = kOther); // Merges |guest| into |this| if it can, by appending chunks of |guest| @@ -278,7 +280,7 @@ FloatRect rect_known_to_be_opaque; scoped_refptr<const PaintArtifact> paint_artifact; // Paint chunk indices from |paint_artifact.PaintChunks()|. - Vector<PaintChunkIndex> paint_chunk_indices; + Vector<wtf_size_t> paint_chunk_indices; PropertyTreeState property_tree_state; FloatPoint offset_of_decomposited_transforms; CompositingType compositing_type; @@ -310,9 +312,9 @@ // recursion, the layerization of the subgroup may be tested for merge & // overlap with other chunks in the parent group, if grouping requirement // can be satisfied (and the effect node has no direct reason). - void LayerizeGroup(const PaintChunkSubset&, + void LayerizeGroup(scoped_refptr<const PaintArtifact>, const EffectPaintPropertyNode&, - PaintChunkIterator& chunk_cursor); + Vector<PaintChunk>::const_iterator& chunk_cursor); static bool MightOverlap(const PendingLayer&, const PendingLayer&); bool DecompositeEffect(const EffectPaintPropertyNode& parent_effect, wtf_size_t first_layer_in_parent_group_index,
diff --git a/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor_test.cc b/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor_test.cc index eba0ab4..ad71c43 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor_test.cc +++ b/third_party/blink/renderer/platform/graphics/compositing/paint_artifact_compositor_test.cc
@@ -42,9 +42,17 @@ namespace blink { -using testing::ElementsAre; using testing::Pointee; +PaintChunk::Id DefaultId() { + DEFINE_STATIC_LOCAL(FakeDisplayItemClient, fake_client, ()); + return PaintChunk::Id(fake_client, DisplayItem::kDrawingFirst); +} + +PaintChunk DefaultChunk() { + return PaintChunk(0, 1, DefaultId(), PropertyTreeState::Root()); +} + gfx::Transform Translation(SkScalar x, SkScalar y) { gfx::Transform transform; transform.Translate(x, y); @@ -287,7 +295,7 @@ cc::MainThreadScrollingReason::kNotScrollingOnMain; TEST_P(PaintArtifactCompositorTest, EmptyPaintArtifact) { - Update(base::MakeRefCounted<PaintArtifact>()); + Update(PaintArtifact::Empty()); EXPECT_TRUE(RootLayer()->children().empty()); } @@ -977,7 +985,9 @@ test_artifact.Chunk().ForeignLayer(layer, IntPoint(50, 60)); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 100, 100), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(3u, LayerCount()); EXPECT_EQ(layer, LayerAt(1)); @@ -1424,7 +1434,10 @@ test_artifact.Chunk().RectDrawing(IntRect(0, 0, 100, 100), Color::kWhite); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(2u, artifact->PaintChunks().size()); + Update(artifact); + ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1448,7 +1461,10 @@ .RectDrawing(IntRect(0, 0, 200, 300), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 300, 400), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1477,7 +1493,10 @@ .RectDrawing(IntRect(0, 0, 100, 100), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); + ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1510,7 +1529,9 @@ test_artifact.Chunk(*transform2, c0(), e0()) .RectDrawing(IntRect(0, 0, 100, 100), Color::kBlack); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(2u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1536,7 +1557,9 @@ .RectDrawing(IntRect(0, 0, 100, 100), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1564,7 +1587,9 @@ .RectDrawing(IntRect(0, 0, 100, 100), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1594,7 +1619,9 @@ .RectDrawing(IntRect(0, 0, 100, 100), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1633,7 +1660,9 @@ .RectDrawing(IntRect(0, 0, 100, 100), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1655,13 +1684,13 @@ TEST_P(PaintArtifactCompositorTest, CanNotMergeAcrossPaintArtifacts) { TestPaintArtifact test_artifact_a; test_artifact_a.Chunk().RectDrawing(IntRect(0, 0, 100, 100), Color::kWhite); - auto chunks_a = test_artifact_a.Build()->Chunks(); - PendingLayer layer_a(chunks_a, PaintChunkIndex{0, 0}); + auto artifact_a = test_artifact_a.Build(); + PendingLayer layer_a(artifact_a, artifact_a->PaintChunks()[0], 0); TestPaintArtifact test_artifact_b; test_artifact_b.Chunk().RectDrawing(IntRect(0, 0, 100, 100), Color::kGray); - auto chunks_b = test_artifact_b.Build()->Chunks(); - PendingLayer layer_b(chunks_b, PaintChunkIndex{0, 0}); + auto artifact_b = test_artifact_b.Build(); + PendingLayer layer_b(artifact_b, artifact_b->PaintChunks()[0], 0); EXPECT_FALSE(layer_a.CanMerge(layer_b, layer_b.property_tree_state)); } @@ -1684,7 +1713,9 @@ .RectDrawing(IntRect(0, 0, 300, 400), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1725,7 +1756,9 @@ .RectDrawing(IntRect(0, 0, 300, 400), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1764,7 +1797,9 @@ .RectDrawing(IntRect(0, 0, 300, 400), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1797,7 +1832,9 @@ .RectDrawing(IntRect(0, 0, 300, 400), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1827,7 +1864,9 @@ .RectDrawing(IntRect(0, 0, 300, 400), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1859,7 +1898,9 @@ .RectDrawing(IntRect(0, 0, 300, 400), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); ASSERT_EQ(1u, LayerCount()); { Vector<RectWithColor> rects_with_color; @@ -1886,7 +1927,9 @@ .RectDrawing(IntRect(0, 0, 100, 100), Color::kBlack); test_artifact.Chunk().RectDrawing(IntRect(0, 0, 200, 300), Color::kGray); - Update(test_artifact.Build()); + auto artifact = test_artifact.Build(); + ASSERT_EQ(3u, artifact->PaintChunks().size()); + Update(artifact); // The third paint chunk overlaps the second but can't merge due to // incompatible transform. The second paint chunk can't merge into the first // due to a direct compositing reason. @@ -1894,30 +1937,43 @@ } TEST_P(PaintArtifactCompositorTest, MightOverlap) { - TestPaintArtifact artifact; - artifact.Chunk().Bounds(IntRect(0, 0, 100, 100)); - artifact.Chunk().Bounds(IntRect(0, 0, 100, 100)); - auto t2 = CreateTransform(t0(), TransformationMatrix().Translate(99, 0), - FloatPoint3D(100, 100, 0)); - artifact.Chunk(*t2, c0(), e0()).Bounds(IntRect(0, 0, 100, 100)); - auto t3 = CreateTransform(t0(), TransformationMatrix().Translate(100, 0), - FloatPoint3D(100, 100, 0)); - artifact.Chunk(*t3, c0(), e0()).Bounds(IntRect(0, 0, 100, 100)); - auto t4 = + PaintChunk paint_chunk = DefaultChunk(); + paint_chunk.bounds = IntRect(0, 0, 100, 100); + PendingLayer pending_layer(nullptr, paint_chunk, 0); + + PaintChunk paint_chunk2 = DefaultChunk(); + paint_chunk2.bounds = IntRect(0, 0, 100, 100); + + { + PendingLayer pending_layer2(nullptr, paint_chunk2, 1); + EXPECT_TRUE(MightOverlap(pending_layer, pending_layer2)); + } + + auto transform = CreateTransform( + t0(), TransformationMatrix().Translate(99, 0), FloatPoint3D(100, 100, 0)); + { + SetTransform(paint_chunk2, *transform); + PendingLayer pending_layer2(nullptr, paint_chunk2, 1); + EXPECT_TRUE(MightOverlap(pending_layer, pending_layer2)); + } + + auto transform2 = + CreateTransform(t0(), TransformationMatrix().Translate(100, 0), + FloatPoint3D(100, 100, 0)); + { + SetTransform(paint_chunk2, *transform2); + PendingLayer pending_layer2(nullptr, paint_chunk2, 1); + EXPECT_FALSE(MightOverlap(pending_layer, pending_layer2)); + } + + auto transform3 = CreateAnimatingTransform(t0(), TransformationMatrix().Translate(100, 0), FloatPoint3D(100, 100, 0)); - artifact.Chunk(*t4, c0(), e0()).Bounds(IntRect(0, 0, 100, 100)); - auto chunks = artifact.Build()->Chunks(); - - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - EXPECT_TRUE( - MightOverlap(pending_layer, PendingLayer(chunks, PaintChunkIndex{0, 1}))); - EXPECT_TRUE( - MightOverlap(pending_layer, PendingLayer(chunks, PaintChunkIndex{0, 2}))); - EXPECT_FALSE( - MightOverlap(pending_layer, PendingLayer(chunks, PaintChunkIndex{0, 3}))); - EXPECT_TRUE( - MightOverlap(pending_layer, PendingLayer(chunks, PaintChunkIndex{0, 4}))); + { + SetTransform(paint_chunk2, *transform3); + PendingLayer pending_layer2(nullptr, paint_chunk2, 1); + EXPECT_TRUE(MightOverlap(pending_layer, pending_layer2)); + } } TEST_P(PaintArtifactCompositorTest, UniteRectsKnownToBeOpaque) { @@ -1965,165 +2021,205 @@ } TEST_P(PaintArtifactCompositorTest, PendingLayer) { - TestPaintArtifact artifact; - artifact.Chunk().Bounds(IntRect(0, 0, 30, 40)).KnownToBeOpaque(); - artifact.Chunk().Bounds(IntRect(10, 20, 30, 40)).KnownToBeOpaque(); - artifact.Chunk().Bounds(IntRect(-5, -25, 20, 20)).KnownToBeOpaque(); - auto chunks = artifact.Build()->Chunks(); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState::Root(); + chunk1.known_to_be_opaque = true; + chunk1.bounds = IntRect(0, 0, 30, 40); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); + PendingLayer pending_layer(nullptr, chunk1, 0); EXPECT_EQ(FloatRect(0, 0, 30, 40), pending_layer.bounds); - EXPECT_THAT(pending_layer.paint_chunk_indices, - ElementsAre(PaintChunkIndex{0, 0})); + EXPECT_EQ((Vector<wtf_size_t>{0}), pending_layer.paint_chunk_indices); EXPECT_EQ(pending_layer.bounds, pending_layer.rect_known_to_be_opaque); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = chunk1.properties; + chunk2.known_to_be_opaque = true; + chunk2.bounds = IntRect(10, 20, 30, 40); + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); // Bounds not equal to one PaintChunk. EXPECT_EQ(FloatRect(0, 0, 40, 60), pending_layer.bounds); - EXPECT_THAT(pending_layer.paint_chunk_indices, - ElementsAre(PaintChunkIndex{0, 0}, PaintChunkIndex{0, 1})); + EXPECT_EQ((Vector<wtf_size_t>{0, 1}), pending_layer.paint_chunk_indices); EXPECT_EQ(FloatRect(0, 0, 30, 40), pending_layer.rect_known_to_be_opaque); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 2}))); + PaintChunk chunk3 = DefaultChunk(); + chunk3.properties = chunk1.properties; + chunk3.known_to_be_opaque = true; + chunk3.bounds = IntRect(-5, -25, 20, 20); + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk3, 2))); EXPECT_EQ(FloatRect(-5, -25, 45, 85), pending_layer.bounds); - EXPECT_THAT(pending_layer.paint_chunk_indices, - ElementsAre(PaintChunkIndex{0, 0}, PaintChunkIndex{0, 1}, - PaintChunkIndex{0, 2})); + EXPECT_EQ((Vector<wtf_size_t>{0, 1, 2}), pending_layer.paint_chunk_indices); EXPECT_EQ(FloatRect(0, 0, 30, 40), pending_layer.rect_known_to_be_opaque); } TEST_P(PaintArtifactCompositorTest, PendingLayerMergeWithGuestTransform) { - TestPaintArtifact artifact; - artifact.Chunk().Bounds(IntRect(0, 0, 30, 40)); auto transform = Create2DTranslation(t0(), 20, 25); - artifact.Chunk(*transform, c0(), e0()).Bounds(IntRect(0, 0, 50, 60)); - auto chunks = artifact.Build()->Chunks(); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState::Root(); + chunk1.bounds = IntRect(0, 0, 30, 40); + + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = chunk1.properties; + SetTransform(chunk2, *transform); + chunk2.bounds = IntRect(0, 0, 50, 60); + + PendingLayer pending_layer(nullptr, chunk1, 0); + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); EXPECT_EQ(FloatRect(0, 0, 70, 85), pending_layer.bounds); EXPECT_EQ(PropertyTreeState::Root(), pending_layer.property_tree_state); } TEST_P(PaintArtifactCompositorTest, PendingLayerMergeWithHomeTransform) { - TestPaintArtifact artifact; auto transform = Create2DTranslation(t0(), 20, 25); - artifact.Chunk(*transform, c0(), e0()).Bounds(IntRect(0, 0, 30, 40)); - artifact.Chunk().Bounds(IntRect(0, 0, 50, 60)); - auto chunks = artifact.Build()->Chunks(); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState::Root(); + SetTransform(chunk1, *transform); + chunk1.bounds = IntRect(0, 0, 30, 40); + + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = PropertyTreeState::Root(); + chunk2.bounds = IntRect(0, 0, 50, 60); + + PendingLayer pending_layer(nullptr, chunk1, 0); + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); EXPECT_EQ(FloatRect(0, 0, 50, 65), pending_layer.bounds); EXPECT_EQ(PropertyTreeState::Root(), pending_layer.property_tree_state); } TEST_P(PaintArtifactCompositorTest, PendingLayerMergeWithBothTransforms) { - TestPaintArtifact artifact; auto t1 = Create2DTranslation(t0(), 20, 25); - artifact.Chunk(*t1, c0(), e0()).Bounds(IntRect(0, 0, 30, 40)); auto t2 = Create2DTranslation(t0(), -20, -25); - artifact.Chunk(*t2, c0(), e0()).Bounds(IntRect(0, 0, 50, 60)); - auto chunks = artifact.Build()->Chunks(); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState::Root(); + SetTransform(chunk1, *t1); + chunk1.bounds = IntRect(0, 0, 30, 40); + + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = PropertyTreeState::Root(); + SetTransform(chunk2, *t2); + chunk2.bounds = IntRect(0, 0, 50, 60); + + PendingLayer pending_layer(nullptr, chunk1, 0); + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); EXPECT_EQ(FloatRect(-20, -25, 70, 90), pending_layer.bounds); EXPECT_EQ(PropertyTreeState::Root(), pending_layer.property_tree_state); } TEST_P(PaintArtifactCompositorTest, PendingLayerDontMergeSparse) { - TestPaintArtifact artifact; - artifact.Chunk().Bounds(IntRect(0, 0, 30, 40)).KnownToBeOpaque(); - artifact.Chunk().Bounds(IntRect(200, 200, 30, 40)).KnownToBeOpaque(); - auto chunks = artifact.Build()->Chunks(); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState::Root(); // (t0(), c0(), *e1); + chunk1.known_to_be_opaque = true; + chunk1.bounds = IntRect(0, 0, 30, 40); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - ASSERT_FALSE( - pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = chunk1.properties; + chunk2.known_to_be_opaque = true; + chunk2.bounds = IntRect(200, 200, 30, 40); + + PendingLayer pending_layer(nullptr, chunk1, 0); + ASSERT_FALSE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); EXPECT_EQ(FloatRect(0, 0, 30, 40), pending_layer.bounds); - EXPECT_EQ(chunks.begin()->properties, pending_layer.property_tree_state); - EXPECT_THAT(pending_layer.paint_chunk_indices, - ElementsAre(PaintChunkIndex{0, 0})); + EXPECT_EQ(chunk1.properties, pending_layer.property_tree_state); + EXPECT_EQ(Vector<wtf_size_t>{0}, pending_layer.paint_chunk_indices); } TEST_P(PaintArtifactCompositorTest, PendingLayerDontMergeSparseWithTransforms) { - TestPaintArtifact artifact; auto t1 = Create2DTranslation(t0(), 20, 25); - artifact.Chunk(*t1, c0(), e0()).Bounds(IntRect(0, 0, 30, 40)); auto t2 = Create2DTranslation(t0(), 1000, 1000); - artifact.Chunk(*t2, c0(), e0()).Bounds(IntRect(0, 0, 50, 60)); - auto chunks = artifact.Build()->Chunks(); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - ASSERT_FALSE( - pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState::Root(); + SetTransform(chunk1, *t1); + chunk1.bounds = IntRect(0, 0, 30, 40); + + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = PropertyTreeState::Root(); + SetTransform(chunk2, *t2); + chunk2.bounds = IntRect(0, 0, 50, 60); + + PendingLayer pending_layer(nullptr, chunk1, 0); + ASSERT_FALSE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); EXPECT_EQ(FloatRect(0, 0, 30, 40), pending_layer.bounds); - EXPECT_EQ(chunks.begin()->properties, pending_layer.property_tree_state); - EXPECT_THAT(pending_layer.paint_chunk_indices, - ElementsAre(PaintChunkIndex{0, 0})); + EXPECT_EQ(chunk1.properties, pending_layer.property_tree_state); + EXPECT_EQ(Vector<wtf_size_t>{0}, pending_layer.paint_chunk_indices); } TEST_P(PaintArtifactCompositorTest, PendingLayerDontMergeSparseInCompositedEffect) { - TestPaintArtifact artifact; auto t1 = Create2DTranslation(t0(), 20, 25); + auto t2 = Create2DTranslation(t0(), 1000, 1000); auto e1 = CreateOpacityEffect(e0(), 1.0f, CompositingReason::kWillChangeOpacity); - artifact.Chunk(*t1, c0(), *e1).Bounds(IntRect(0, 0, 30, 40)); - auto t2 = Create2DTranslation(t0(), 1000, 1000); - artifact.Chunk(*t2, c0(), *e1).Bounds(IntRect(0, 0, 50, 60)); - auto chunks = artifact.Build()->Chunks(); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - ASSERT_FALSE( - pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState(*t1, c0(), *e1); + chunk1.bounds = IntRect(0, 0, 30, 40); + + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = PropertyTreeState(*t2, c0(), *e1); + chunk2.bounds = IntRect(0, 0, 50, 60); + + PendingLayer pending_layer(nullptr, chunk1, 0); + ASSERT_FALSE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); EXPECT_EQ(FloatRect(0, 0, 30, 40), pending_layer.bounds); - EXPECT_EQ(chunks.begin()->properties, pending_layer.property_tree_state); - EXPECT_THAT(pending_layer.paint_chunk_indices, - ElementsAre(PaintChunkIndex{0, 0})); + EXPECT_EQ(chunk1.properties, pending_layer.property_tree_state); + EXPECT_EQ(Vector<wtf_size_t>{0}, pending_layer.paint_chunk_indices); } TEST_P(PaintArtifactCompositorTest, PendingLayerMergeSparseInNonCompositedEffect) { - TestPaintArtifact artifact; auto t1 = Create2DTranslation(t0(), 20, 25); auto t2 = Create2DTranslation(t0(), 1000, 1000); auto e1 = CreateOpacityEffect(e0(), 1.0f, CompositingReason::kNone); - artifact.Chunk(*t1, c0(), *e1).Bounds(IntRect(0, 0, 30, 40)); - artifact.Chunk(*t2, c0(), *e1).Bounds(IntRect(0, 0, 50, 60)); - auto chunks = artifact.Build()->Chunks(); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState(*t1, c0(), *e1); + chunk1.bounds = IntRect(0, 0, 30, 40); + + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = PropertyTreeState(*t2, c0(), *e1); + chunk2.bounds = IntRect(0, 0, 50, 60); + + PendingLayer pending_layer(nullptr, chunk1, 0); + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); EXPECT_EQ(FloatRect(20, 25, 1030, 1035), pending_layer.bounds); EXPECT_EQ(PropertyTreeState(t0(), c0(), *e1), pending_layer.property_tree_state); - EXPECT_THAT(pending_layer.paint_chunk_indices, - ElementsAre(PaintChunkIndex{0, 0}, PaintChunkIndex{0, 1})); + EXPECT_EQ((Vector<wtf_size_t>{0, 1}), pending_layer.paint_chunk_indices); } TEST_P(PaintArtifactCompositorTest, PendingLayerKnownOpaque) { - TestPaintArtifact artifact; - artifact.Chunk().Bounds(IntRect(0, 0, 30, 40)); - artifact.Chunk().Bounds(IntRect(0, 0, 25, 35)).KnownToBeOpaque(); - artifact.Chunk().Bounds(IntRect(0, 0, 50, 60)).KnownToBeOpaque(); - auto chunks = artifact.Build()->Chunks(); + PaintChunk chunk1 = DefaultChunk(); + chunk1.properties = PropertyTreeState::Root(); + chunk1.bounds = IntRect(0, 0, 30, 40); + chunk1.known_to_be_opaque = false; + PendingLayer pending_layer(nullptr, chunk1, 0); - PendingLayer pending_layer(chunks, PaintChunkIndex{0, 0}); EXPECT_TRUE(pending_layer.rect_known_to_be_opaque.IsEmpty()); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 1}))); + PaintChunk chunk2 = DefaultChunk(); + chunk2.properties = chunk1.properties; + chunk2.bounds = IntRect(0, 0, 25, 35); + chunk2.known_to_be_opaque = true; + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk2, 1))); + // Chunk 2 doesn't cover the entire layer, so not opaque. - EXPECT_EQ(FloatRect(0, 0, 25, 35), pending_layer.rect_known_to_be_opaque); + EXPECT_EQ(FloatRect(chunk2.bounds), pending_layer.rect_known_to_be_opaque); EXPECT_NE(pending_layer.bounds, pending_layer.rect_known_to_be_opaque); - ASSERT_TRUE(pending_layer.Merge(PendingLayer(chunks, PaintChunkIndex{0, 2}))); + PaintChunk chunk3 = DefaultChunk(); + chunk3.properties = chunk1.properties; + chunk3.bounds = IntRect(0, 0, 50, 60); + chunk3.known_to_be_opaque = true; + ASSERT_TRUE(pending_layer.Merge(PendingLayer(nullptr, chunk3, 2))); + // Chunk 3 covers the entire layer, so now it's opaque. - EXPECT_EQ(FloatRect(0, 0, 50, 60), pending_layer.bounds); + EXPECT_EQ(FloatRect(chunk3.bounds), pending_layer.bounds); EXPECT_EQ(pending_layer.bounds, pending_layer.rect_known_to_be_opaque); }
diff --git a/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.cc b/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.cc index 1dd13da3..2dee9c3 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.cc +++ b/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.cc
@@ -5,7 +5,6 @@ #include "third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.h" #include "base/numerics/safe_conversions.h" -#include "cc/layers/layer.h" #include "cc/paint/display_item_list.h" #include "cc/paint/paint_op_buffer.h" #include "cc/paint/render_surface_filters.h" @@ -87,7 +86,7 @@ // At last, close all pushed states to balance pairs (this happens when the // context object is destructed): // Output: End_C4 End_C3 End_C2 End_C1 - void Convert(const PaintChunkSubset&); + void Convert(const PaintChunkSubset&, const DisplayItemList&); private: // Adjust the translation of the whole display list relative to layer offset. @@ -703,13 +702,13 @@ previous_transform_ = nullptr; } -void ConversionContext::Convert(const PaintChunkSubset& chunks) { - for (auto it = chunks.begin(); it != chunks.end(); ++it) { - const auto& chunk = *it; +void ConversionContext::Convert(const PaintChunkSubset& paint_chunks, + const DisplayItemList& display_items) { + for (const auto& chunk : paint_chunks) { const auto& chunk_state = chunk.properties; bool switched_to_chunk_state = false; - for (const auto& item : it.DisplayItems()) { + for (const auto& item : display_items.ItemsInPaintChunk(chunk)) { sk_sp<const PaintRecord> record; if (item.IsScrollbar()) record = static_cast<const ScrollbarDisplayItem&>(item).Paint(); @@ -756,21 +755,25 @@ } // unnamed namespace -void PaintChunksToCcLayer::ConvertInto(const PaintChunkSubset& chunks, - const PropertyTreeState& layer_state, - const gfx::Vector2dF& layer_offset, - cc::DisplayItemList& cc_list) { - ConversionContext(layer_state, layer_offset, cc_list).Convert(chunks); +void PaintChunksToCcLayer::ConvertInto( + const PaintChunkSubset& paint_chunks, + const PropertyTreeState& layer_state, + const gfx::Vector2dF& layer_offset, + const DisplayItemList& display_items, + cc::DisplayItemList& cc_list) { + ConversionContext(layer_state, layer_offset, cc_list) + .Convert(paint_chunks, display_items); } scoped_refptr<cc::DisplayItemList> PaintChunksToCcLayer::Convert( const PaintChunkSubset& paint_chunks, const PropertyTreeState& layer_state, const gfx::Vector2dF& layer_offset, + const DisplayItemList& display_items, cc::DisplayItemList::UsageHint hint, RasterUnderInvalidationCheckingParams* under_invalidation_checking_params) { auto cc_list = base::MakeRefCounted<cc::DisplayItemList>(hint); - ConvertInto(paint_chunks, layer_state, layer_offset, *cc_list); + ConvertInto(paint_chunks, layer_state, layer_offset, display_items, *cc_list); if (under_invalidation_checking_params) { auto& params = *under_invalidation_checking_params; @@ -780,7 +783,8 @@ // use cc_list because it is not finalized yet. auto list_clone = base::MakeRefCounted<cc::DisplayItemList>( cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer); - ConvertInto(paint_chunks, layer_state, layer_offset, *list_clone); + ConvertInto(paint_chunks, layer_state, layer_offset, display_items, + *list_clone); recorder.getRecordingCanvas()->drawPicture(list_clone->ReleaseAsRecord()); params.tracking.CheckUnderInvalidations(params.debug_name, recorder.finishRecordingAsPicture(), @@ -796,39 +800,4 @@ return cc_list; } -// The heuristic for picking a checkerboarding color works as follows: -// - During paint, PaintChunker will look for background color display items, -// and annotates the chunk with the index of the display item that paints -// the largest area background color (ties are broken by selecting the -// display item that paints last). -// - After layer allocation, the paint chunks assigned to a layer are -// examined for a background color annotation. The chunk with the largest -// background color annotation is selected. -// - If the area of the selected background color is at least half the size -// of the layer, then it is set as the layer's background color. -// - The same color is used for the layer's safe opaque background color, but -// without the size requirement, as safe opaque background color should -// always get a value if possible. -void PaintChunksToCcLayer::UpdateBackgroundColor( - cc::Layer& layer, - const PaintChunkSubset& paint_chunks) { - SkColor color = SK_ColorTRANSPARENT; - uint64_t area = 0; - for (const auto& chunk : paint_chunks) { - if (chunk.background_color != Color::kTransparent && - chunk.background_color_area >= area) { - color = chunk.background_color.Rgb(); - area = chunk.background_color_area; - } - } - - layer.SetSafeOpaqueBackgroundColor(color); - - uint64_t layer_area = - static_cast<uint64_t>(layer.bounds().width()) * layer.bounds().height(); - if (area < layer_area / 2) - color = SK_ColorTRANSPARENT; - layer.SetBackgroundColor(color); -} - } // namespace blink
diff --git a/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.h b/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.h index c549b21..738d36a8 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.h +++ b/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.h
@@ -15,7 +15,6 @@ namespace cc { class DisplayItemList; -class Layer; } // namespace cc namespace gfx { @@ -24,6 +23,7 @@ namespace blink { +class DisplayItemList; class PaintChunkSubset; class PropertyTreeState; class RasterInvalidationTracking; @@ -60,6 +60,7 @@ static void ConvertInto(const PaintChunkSubset&, const PropertyTreeState& layer_state, const gfx::Vector2dF& layer_offset, + const DisplayItemList&, cc::DisplayItemList&); // Similar to ConvertInto(), but returns a finalized new list instead of @@ -68,11 +69,9 @@ const PaintChunkSubset&, const PropertyTreeState& layer_state, const gfx::Vector2dF& layer_offset, + const DisplayItemList&, cc::DisplayItemList::UsageHint, RasterUnderInvalidationCheckingParams* = nullptr); - - static void UpdateBackgroundColor(cc::Layer& layer, - const PaintChunkSubset& paint_chunks); }; } // namespace blink
diff --git a/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer_test.cc b/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer_test.cc index bf061ed1..d193ead 100644 --- a/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer_test.cc +++ b/third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer_test.cc
@@ -156,8 +156,10 @@ return PaintChunk::Id(fake_client, DisplayItem::kDrawingFirst); } -class TestChunks { - public: +struct TestChunks { + Vector<PaintChunk> chunks; + DisplayItemList items = DisplayItemList(0); + // Add a paint chunk with a non-empty paint record and given property nodes. void AddChunk( const TransformPaintPropertyNodeOrAlias& t, @@ -197,16 +199,6 @@ chunks.emplace_back(i, i, DefaultId(), PropertyTreeState(t, c, e)); chunks.back().bounds = bounds; } - - PaintChunkSubset Build() { - auto artifact = base::MakeRefCounted<PaintArtifact>(); - artifact->AddSegment(std::move(chunks), std::move(items)); - return artifact->Chunks(); - } - - private: - Vector<PaintChunk> chunks; - DisplayItemList items = DisplayItemList(0); }; TEST_P(PaintChunksToCcLayerTest, EffectGroupingSimple) { @@ -218,8 +210,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( *output, @@ -241,8 +233,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( *output, @@ -274,8 +266,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( *output, @@ -321,8 +313,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make( {cc::PaintOpType::Save, @@ -366,8 +358,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make( @@ -395,8 +387,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make( @@ -428,10 +420,11 @@ TestChunks chunks; chunks.AddChunk(t0(), c0(), *e1); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT( *output, PaintRecordMatcher::Make( @@ -458,8 +451,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState(*t1, *c1, *e1), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState(*t1, *c1, *e1), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({cc::PaintOpType::DrawRecord})); } @@ -475,8 +468,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState(*t1, *c1, *e1), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState(*t1, *c1, *e1), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make( @@ -496,8 +489,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState(t0(), *c1, e0()), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState(t0(), *c1, e0()), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( *output, @@ -521,8 +514,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( *output, @@ -549,8 +542,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState(t0(), c0(), *e1), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState(t0(), c0(), *e1), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( *output, @@ -574,8 +567,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState(t0(), *c1, *e1), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState(t0(), *c1, *e1), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( *output, @@ -596,8 +589,8 @@ auto cc_list = base::MakeRefCounted<cc::DisplayItemList>( cc::DisplayItemList::kTopLevelDisplayItemList); PaintChunksToCcLayer::ConvertInto( - chunks.Build(), PropertyTreeState(*layer_transform, c0(), e0()), - gfx::Vector2dF(100, 200), *cc_list); + chunks.chunks, PropertyTreeState(*layer_transform, c0(), e0()), + gfx::Vector2dF(100, 200), chunks.items, *cc_list); EXPECT_EQ(gfx::Rect(-50, -100, 100, 100), cc_list->VisualRectForTesting(4)); EXPECT_THAT(*cc_list->ReleaseAsRecord(), @@ -618,8 +611,8 @@ auto cc_list = base::MakeRefCounted<cc::DisplayItemList>( cc::DisplayItemList::kTopLevelDisplayItemList); - PaintChunksToCcLayer::ConvertInto(chunks.Build(), PropertyTreeState::Root(), - gfx::Vector2dF(), *cc_list); + PaintChunksToCcLayer::ConvertInto(chunks.chunks, PropertyTreeState::Root(), + gfx::Vector2dF(), chunks.items, *cc_list); EXPECT_THAT( *cc_list->ReleaseAsRecord(), @@ -646,8 +639,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); // Note that c1 and c1c2 are elided. @@ -676,8 +669,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, @@ -700,8 +693,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ @@ -727,8 +720,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( @@ -766,8 +759,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); // We combine c1/c2 across |identity|, but not c2/c3 across |non_identity| @@ -813,8 +806,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT( @@ -855,8 +848,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); EXPECT_THAT(*output, @@ -892,10 +885,11 @@ chunks.AddChunk(*t1, c0(), e0()); chunks.AddChunk(*t1, *c2, e0()); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make( @@ -920,10 +914,11 @@ chunks.AddChunk(*t1, c0(), *e1); chunks.AddChunk(*t1, c0(), *e2); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make( @@ -948,10 +943,11 @@ chunks.AddChunk(*t1, c0(), *e1); chunks.AddChunk(*t1, c0(), *e2); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make( @@ -982,10 +978,11 @@ chunks.AddChunk(*noop_t5, c0(), e0()); chunks.AddChunk(*t4, c0(), e0()); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ @@ -1013,10 +1010,11 @@ chunks.AddChunk(*noop_t1, c0(), e0()); chunks.AddChunk(*noop_t2, c0(), e0()); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({cc::PaintOpType::DrawRecord, cc::PaintOpType::DrawRecord, @@ -1032,10 +1030,11 @@ chunks.AddChunk(*noop_t2, c0(), e0()); chunks.AddChunk(*t1, c0(), e0()); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ cc::PaintOpType::DrawRecord, // t0 @@ -1058,10 +1057,11 @@ // The clip's local transform is t1, which is the parent of noop_t2. chunks.AddChunk(*noop_t2, *c1, e0()); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ cc::PaintOpType::DrawRecord, // t0 @@ -1086,10 +1086,11 @@ // The effects's local transform is t1, which is the parent of noop_t2. chunks.AddChunk(*noop_t2, c0(), *e1); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ cc::PaintOpType::DrawRecord, // t0 @@ -1119,10 +1120,11 @@ chunks.AddChunk(t0(), *noop_c2, e0()); chunks.AddChunk(t0(), *c1, e0()); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ @@ -1150,10 +1152,11 @@ chunks.AddChunk(t0(), *noop_c2, e0()); chunks.AddChunk(t0(), *noop_c2, *e1); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ @@ -1182,8 +1185,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState(t0(), *c1, e0()), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState(t0(), *c1, e0()), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); // We don't care about the exact output as long as it didn't crash. } @@ -1205,8 +1208,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); // We don't care about the exact output as long as it didn't crash. } @@ -1226,8 +1229,8 @@ sk_sp<PaintRecord> output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState(t0(), *c1, e0()), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + chunks.chunks, PropertyTreeState(t0(), *c1, e0()), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); // We don't care about the exact output as long as it didn't crash. } @@ -1248,10 +1251,11 @@ chunks.AddChunk(t0(), c0(), *noop_e2); chunks.AddChunk(t0(), c0(), *e1); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({ @@ -1285,7 +1289,7 @@ chunks.AddChunk(t0(), c0(), *e4); auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), layer_state, gfx::Vector2dF(), + chunks.chunks, layer_state, gfx::Vector2dF(), chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); @@ -1304,10 +1308,11 @@ TestChunks chunks; chunks.AddChunk(nullptr, t0(), c0(), *e1, {0, 0, 0, 0}); - auto output = PaintChunksToCcLayer::Convert( - chunks.Build(), PropertyTreeState::Root(), gfx::Vector2dF(), - cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) - ->ReleaseAsRecord(); + auto output = + PaintChunksToCcLayer::Convert( + chunks.chunks, PropertyTreeState::Root(), gfx::Vector2dF(), + chunks.items, cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) + ->ReleaseAsRecord(); EXPECT_THAT(*output, PaintRecordMatcher::Make({cc::PaintOpType::SaveLayer, // <e1> cc::PaintOpType::Restore})); // </e1> @@ -1331,8 +1336,9 @@ auto cc_list = base::MakeRefCounted<cc::DisplayItemList>( cc::DisplayItemList::kTopLevelDisplayItemList); - PaintChunksToCcLayer::ConvertInto(chunks.Build(), PropertyTreeState::Root(), - gfx::Vector2dF(5, 10), *cc_list); + PaintChunksToCcLayer::ConvertInto(chunks.chunks, PropertyTreeState::Root(), + gfx::Vector2dF(5, 10), chunks.items, + *cc_list); ASSERT_EQ(5u, cc_list->TotalOpCount()); // (7 16) is (12, 26) - layer_offset. gfx::Rect expected_visual_rect(7, 16, 93, 84); @@ -1363,8 +1369,9 @@ auto cc_list = base::MakeRefCounted<cc::DisplayItemList>( cc::DisplayItemList::kTopLevelDisplayItemList); - PaintChunksToCcLayer::ConvertInto(chunks.Build(), PropertyTreeState::Root(), - gfx::Vector2dF(5, 10), *cc_list); + PaintChunksToCcLayer::ConvertInto(chunks.chunks, PropertyTreeState::Root(), + gfx::Vector2dF(5, 10), chunks.items, + *cc_list); ASSERT_EQ(7u, cc_list->TotalOpCount()); // This is the visual rect for all filter related paint operations, which is // the union of the draw record and the output bounds of the filter with empty
diff --git a/third_party/blink/renderer/platform/graphics/contiguous_container.h b/third_party/blink/renderer/platform/graphics/contiguous_container.h index 2a50986..c81241eb 100644 --- a/third_party/blink/renderer/platform/graphics/contiguous_container.h +++ b/third_party/blink/renderer/platform/graphics/contiguous_container.h
@@ -102,9 +102,6 @@ bool operator!=(const IteratorWrapper& other) const { return it_ != other.it_; } - bool operator<(const IteratorWrapper& other) const { - return it_ < other.it_; - } ValueType& operator*() const { return *static_cast<ValueType*>(*it_); } ValueType* operator->() const { return &operator*(); } IteratorWrapper operator+(std::ptrdiff_t n) const {
diff --git a/third_party/blink/renderer/platform/graphics/graphics_layer.cc b/third_party/blink/renderer/platform/graphics/graphics_layer.cc index c2e0261..f252bcd 100644 --- a/third_party/blink/renderer/platform/graphics/graphics_layer.cc +++ b/third_party/blink/renderer/platform/graphics/graphics_layer.cc
@@ -310,8 +310,9 @@ if (!ShouldCreateLayersAfterPaint()) { IntRect layer_bounds(layer_state_->offset, IntSize(Size())); EnsureRasterInvalidator().Generate( - raster_invalidation_function_, GetPaintController().PaintChunks(), - layer_bounds, layer_state_->state.Unalias(), this); + raster_invalidation_function_, + GetPaintController().GetPaintArtifactShared(), layer_bounds, + layer_state_->state.Unalias(), this); } needs_check_raster_invalidation_ = false; @@ -328,7 +329,9 @@ // has a GraphicsLayer. if (!client_.IsSVGRoot()) return; - for (const auto& paint_chunk : GetPaintController().PaintChunks()) { + const PaintChunkSubset paint_chunks = + PaintChunkSubset(GetPaintController().PaintChunks()); + for (const auto& paint_chunk : paint_chunks) { const auto& chunk_state = paint_chunk.properties; if (chunk_state.GetPropertyTreeState() == GetPropertyTreeState()) continue; @@ -730,6 +733,7 @@ return PaintChunksToCcLayer::Convert( GetPaintController().PaintChunks(), layer_state_->state.Unalias(), gfx::Vector2dF(layer_state_->offset.X(), layer_state_->offset.Y()), + paint_controller.GetPaintArtifact().GetDisplayItemList(), cc::DisplayItemList::kTopLevelDisplayItemList, base::OptionalOrNullptr(raster_under_invalidation_params)); }
diff --git a/third_party/blink/renderer/platform/graphics/mailbox_ref.cc b/third_party/blink/renderer/platform/graphics/mailbox_ref.cc new file mode 100644 index 0000000..c926ce1 --- /dev/null +++ b/third_party/blink/renderer/platform/graphics/mailbox_ref.cc
@@ -0,0 +1,48 @@ +// Copyright 2020 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/graphics/mailbox_ref.h" + +#include "components/viz/common/resources/single_release_callback.h" +#include "gpu/command_buffer/client/raster_interface.h" +#include "third_party/blink/public/platform/platform.h" +#include "third_party/blink/public/platform/web_graphics_context_3d_provider.h" +#include "third_party/blink/renderer/platform/graphics/web_graphics_context_3d_provider_wrapper.h" +#include "third_party/blink/renderer/platform/scheduler/public/post_cross_thread_task.h" +#include "third_party/blink/renderer/platform/wtf/cross_thread_functional.h" + +namespace blink { +namespace { + +void ReleaseCallbackOnContextThread( + std::unique_ptr<viz::SingleReleaseCallback> callback, + const gpu::SyncToken sync_token) { + callback->Run(sync_token, /* is_lost = */ false); +} + +} // namespace + +MailboxRef::MailboxRef( + const gpu::SyncToken& sync_token, + base::PlatformThreadRef context_thread_ref, + scoped_refptr<base::SingleThreadTaskRunner> context_task_runner, + std::unique_ptr<viz::SingleReleaseCallback> release_callback) + : sync_token_(sync_token), + context_thread_ref_(context_thread_ref), + context_task_runner_(std::move(context_task_runner)), + release_callback_(std::move(release_callback)) { + DCHECK(sync_token.HasData()); +} + +MailboxRef::~MailboxRef() { + if (context_thread_ref_ == base::PlatformThread::CurrentRef()) { + ReleaseCallbackOnContextThread(std::move(release_callback_), sync_token_); + } else { + context_task_runner_->PostTask( + FROM_HERE, base::BindOnce(&ReleaseCallbackOnContextThread, + std::move(release_callback_), sync_token_)); + } +} + +} // namespace blink
diff --git a/third_party/blink/renderer/platform/graphics/mailbox_ref.h b/third_party/blink/renderer/platform/graphics/mailbox_ref.h new file mode 100644 index 0000000..ef9e2996 --- /dev/null +++ b/third_party/blink/renderer/platform/graphics/mailbox_ref.h
@@ -0,0 +1,51 @@ +// Copyright 2020 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_RENDERER_PLATFORM_GRAPHICS_MAILBOX_REF_H_ +#define THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_MAILBOX_REF_H_ + +#include <memory> + +#include "base/memory/weak_ptr.h" +#include "base/single_thread_task_runner.h" +#include "base/threading/thread_checker.h" +#include "gpu/command_buffer/common/sync_token.h" +#include "third_party/blink/renderer/platform/scheduler/public/thread.h" +#include "third_party/blink/renderer/platform/wtf/thread_safe_ref_counted.h" + +namespace viz { +class SingleReleaseCallback; +} // namespace viz + +namespace blink { +class WebGraphicsContext3DProviderWrapper; + +class MailboxRef : public ThreadSafeRefCounted<MailboxRef> { + public: + MailboxRef(const gpu::SyncToken& sync_token, + base::PlatformThreadRef context_thread_ref, + scoped_refptr<base::SingleThreadTaskRunner> context_task_runner, + std::unique_ptr<viz::SingleReleaseCallback> release_callback); + ~MailboxRef(); + + bool is_cross_thread() const { + return base::PlatformThread::CurrentRef() != context_thread_ref_; + } + void set_sync_token(gpu::SyncToken token) { + DCHECK(sync_token_.HasData()); + sync_token_ = token; + } + const gpu::SyncToken& sync_token() const { return sync_token_; } + bool verified_flush() { return sync_token_.verified_flush(); } + + private: + gpu::SyncToken sync_token_; + const base::PlatformThreadRef context_thread_ref_; + const scoped_refptr<base::SingleThreadTaskRunner> context_task_runner_; + std::unique_ptr<viz::SingleReleaseCallback> release_callback_; +}; + +} // namespace blink + +#endif
diff --git a/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.cc b/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.cc index 8f5a427..e13ebbc6 100644 --- a/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.cc +++ b/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.cc
@@ -4,6 +4,8 @@ #include "third_party/blink/renderer/platform/graphics/mailbox_texture_backing.h" +#include "third_party/blink/renderer/platform/graphics/accelerated_static_bitmap_image.h" +#include "third_party/blink/renderer/platform/graphics/mailbox_ref.h" #include "third_party/blink/renderer/platform/graphics/skia/skia_utils.h" #include "third_party/blink/renderer/platform/graphics/web_graphics_context_3d_provider_wrapper.h" @@ -11,20 +13,36 @@ MailboxTextureBacking::MailboxTextureBacking( sk_sp<SkImage> sk_image, + scoped_refptr<MailboxRef> mailbox_ref, const SkImageInfo& info, base::WeakPtr<WebGraphicsContext3DProviderWrapper> context_provider_wrapper) : sk_image_(std::move(sk_image)), + mailbox_ref_(std::move(mailbox_ref)), sk_image_info_(info), context_provider_wrapper_(std::move(context_provider_wrapper)) {} MailboxTextureBacking::MailboxTextureBacking( const gpu::Mailbox& mailbox, + scoped_refptr<MailboxRef> mailbox_ref, const SkImageInfo& info, base::WeakPtr<WebGraphicsContext3DProviderWrapper> context_provider_wrapper) : mailbox_(mailbox), + mailbox_ref_(std::move(mailbox_ref)), sk_image_info_(info), context_provider_wrapper_(std::move(context_provider_wrapper)) {} +MailboxTextureBacking::~MailboxTextureBacking() { + if (context_provider_wrapper_) { + gpu::raster::RasterInterface* ri = + context_provider_wrapper_->ContextProvider()->RasterInterface(); + // Update the sync token for MailboxRef. + ri->WaitSyncTokenCHROMIUM(mailbox_ref_->sync_token().GetConstData()); + gpu::SyncToken sync_token; + ri->GenUnverifiedSyncTokenCHROMIUM(sync_token.GetData()); + mailbox_ref_->set_sync_token(sync_token); + } +} + const SkImageInfo& MailboxTextureBacking::GetSkImageInfo() { return sk_image_info_; }
diff --git a/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.h b/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.h index 33c5f68..7ba3b6d 100644 --- a/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.h +++ b/third_party/blink/renderer/platform/graphics/mailbox_texture_backing.h
@@ -13,19 +13,23 @@ namespace blink { class WebGraphicsContext3DProviderWrapper; +class MailboxRef; class MailboxTextureBacking : public TextureBacking { public: explicit MailboxTextureBacking( sk_sp<SkImage> sk_image, + scoped_refptr<MailboxRef> mailbox_ref, const SkImageInfo& info, base::WeakPtr<WebGraphicsContext3DProviderWrapper> context_provider_wrapper); explicit MailboxTextureBacking( const gpu::Mailbox& mailbox, + scoped_refptr<MailboxRef> mailbox_ref, const SkImageInfo& info, base::WeakPtr<WebGraphicsContext3DProviderWrapper> context_provider_wrapper); + ~MailboxTextureBacking() override; const SkImageInfo& GetSkImageInfo() override; gpu::Mailbox GetMailbox() const override; sk_sp<SkImage> GetAcceleratedSkImage() override; @@ -40,6 +44,7 @@ private: const sk_sp<SkImage> sk_image_; const gpu::Mailbox mailbox_; + scoped_refptr<MailboxRef> mailbox_ref_; const SkImageInfo sk_image_info_; base::WeakPtr<WebGraphicsContext3DProviderWrapper> context_provider_wrapper_; };
diff --git a/third_party/blink/renderer/platform/graphics/paint/display_item_list.cc b/third_party/blink/renderer/platform/graphics/paint/display_item_list.cc index 825a6ef..d2f0578 100644 --- a/third_party/blink/renderer/platform/graphics/paint/display_item_list.cc +++ b/third_party/blink/renderer/platform/graphics/paint/display_item_list.cc
@@ -6,28 +6,52 @@ #include "third_party/blink/renderer/platform/graphics/logging_canvas.h" #include "third_party/blink/renderer/platform/graphics/paint/drawing_display_item.h" +#include "third_party/blink/renderer/platform/graphics/paint/paint_chunk.h" namespace blink { +DisplayItemList::Range<DisplayItemList::iterator> +DisplayItemList::ItemsInPaintChunk(const PaintChunk& paint_chunk) { + return Range<iterator>(begin() + paint_chunk.begin_index, + begin() + paint_chunk.end_index); +} + +DisplayItemList::Range<DisplayItemList::const_iterator> +DisplayItemList::ItemsInPaintChunk(const PaintChunk& paint_chunk) const { + return Range<const_iterator>(begin() + paint_chunk.begin_index, + begin() + paint_chunk.end_index); +} + #if DCHECK_IS_ON() std::unique_ptr<JSONArray> DisplayItemList::DisplayItemsAsJSON( - const DisplayItemRange& display_items, - JsonFlags flags) { + wtf_size_t begin_index, + wtf_size_t end_index, + JsonFlags flags) const { auto json_array = std::make_unique<JSONArray>(); + AppendSubsequenceAsJSON(begin_index, end_index, flags, *json_array); + return json_array; +} + +void DisplayItemList::AppendSubsequenceAsJSON(wtf_size_t begin_index, + wtf_size_t end_index, + JsonFlags flags, + JSONArray& json_array) const { if (flags & kCompact) { DCHECK(!(flags & kShowPaintRecords)) << "kCompact cannot show paint records"; DCHECK(!(flags & kShowOnlyDisplayItemTypes)) << "kCompact cannot show display item types"; - for (auto& item : display_items) - json_array->PushString(item.GetId().ToString()); + for (auto i = begin_index; i < end_index; ++i) { + const auto& item = (*this)[i]; + json_array.PushString(item.GetId().ToString()); + } } else { - int i = 0; - for (auto& item : display_items) { + for (auto i = begin_index; i < end_index; ++i) { auto json = std::make_unique<JSONObject>(); - json->SetInteger("index", i++); + const auto& item = (*this)[i]; + json->SetInteger("index", i); if (flags & kShowOnlyDisplayItemTypes) { json->SetString("type", DisplayItem::TypeAsDebugString(item.GetType())); @@ -48,10 +72,9 @@ json->SetArray("record", RecordAsJSON(*record)); } - json_array->PushObject(std::move(json)); + json_array.PushObject(std::move(json)); } } - return json_array; } #endif // DCHECK_IS_ON()
diff --git a/third_party/blink/renderer/platform/graphics/paint/display_item_list.h b/third_party/blink/renderer/platform/graphics/paint/display_item_list.h index b70243c..c6b83e17 100644 --- a/third_party/blink/renderer/platform/graphics/paint/display_item_list.h +++ b/third_party/blink/renderer/platform/graphics/paint/display_item_list.h
@@ -13,6 +13,7 @@ namespace blink { class JSONArray; +struct PaintChunk; // kDisplayItemAlignment must be a multiple of alignof(derived display item) for // each derived display item; the ideal value is the least common multiple. @@ -70,22 +71,13 @@ : begin_(begin), end_(end) {} Iterator begin() const { return begin_; } Iterator end() const { return end_; } - wtf_size_t size() const { return end_ - begin_; } private: Iterator begin_; Iterator end_; }; - - // In most cases, we should use PaintChunkSubset::Iterator::DisplayItems() - // instead of these. - Range<iterator> ItemsInRange(wtf_size_t begin_index, wtf_size_t end_index) { - return Range<iterator>(begin() + begin_index, begin() + end_index); - } - Range<const_iterator> ItemsInRange(wtf_size_t begin_index, - wtf_size_t end_index) const { - return Range<const_iterator>(begin() + begin_index, begin() + end_index); - } + Range<iterator> ItemsInPaintChunk(const PaintChunk&); + Range<const_iterator> ItemsInPaintChunk(const PaintChunk&) const; #if DCHECK_IS_ON() enum JsonOptions { @@ -99,15 +91,16 @@ }; typedef unsigned JsonFlags; - static std::unique_ptr<JSONArray> DisplayItemsAsJSON( - const Range<const_iterator>& display_items, - JsonFlags); + std::unique_ptr<JSONArray> DisplayItemsAsJSON(wtf_size_t begin_index, + wtf_size_t end_index, + JsonFlags) const; + void AppendSubsequenceAsJSON(wtf_size_t begin_index, + wtf_size_t end_index, + JsonFlags, + JSONArray&) const; #endif // DCHECK_IS_ON() }; -using DisplayItemIterator = DisplayItemList::const_iterator; -using DisplayItemRange = DisplayItemList::Range<DisplayItemIterator>; - } // namespace blink #endif // THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_DISPLAY_ITEM_LIST_H_
diff --git a/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.cc b/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.cc index 040362d..6d2e1f1 100644 --- a/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.cc +++ b/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.cc
@@ -20,14 +20,15 @@ clients_to_invalidate; Vector<bool> old_display_items_matched; - old_display_items_matched.resize(old_display_items_.size()); - auto next_old_item_to_match = old_display_items_.begin(); - auto latest_cached_old_item = next_old_item_to_match; + old_display_items_matched.resize(old_chunk_.size()); + auto next_old_item_to_match = old_chunk_.begin_index; + auto max_cached_old_index = next_old_item_to_match; - for (const auto& new_item : new_display_items_) { - auto matched_old_item = + for (const auto& new_item : + new_paint_artifact_.GetDisplayItemList().ItemsInPaintChunk(new_chunk_)) { + auto matched_old_index = MatchNewDisplayItemInOldChunk(new_item, next_old_item_to_match); - if (matched_old_item == old_display_items_.end()) { + if (matched_old_index == kNotFound) { if (new_item.DrawsContent()) { // Will invalidate for the new display item which doesn't match any old // display item. @@ -46,12 +47,13 @@ auto reason = new_item.Client().GetPaintInvalidationReason(); if (!IsFullPaintInvalidationReason(reason) && - matched_old_item < latest_cached_old_item) { + matched_old_index < max_cached_old_index) { // |new_item| has been moved above other cached items. reason = PaintInvalidationReason::kReordered; } - const auto& old_item = *matched_old_item; + const auto& old_item = + old_paint_artifact_.GetDisplayItemList()[matched_old_index]; if (reason != PaintInvalidationReason::kNone && (old_item.DrawsContent() || new_item.DrawsContent())) { // The display item reordered, skipped cache or changed. Will invalidate @@ -66,25 +68,22 @@ value.reason = reason; } - wtf_size_t offset = matched_old_item - old_display_items_.begin(); + wtf_size_t offset = matched_old_index - old_chunk_.begin_index; DCHECK(!old_display_items_matched[offset]); old_display_items_matched[offset] = true; // |old_item.IsTombstone()| is true means that |new_item| was copied from // cached |old_item|. - if (old_item.IsTombstone()) { - latest_cached_old_item = - std::max(latest_cached_old_item, matched_old_item); - } + if (old_item.IsTombstone()) + max_cached_old_index = std::max(max_cached_old_index, matched_old_index); } // Invalidate remaining unmatched (disappeared or uncacheable) old items. - for (auto it = old_display_items_.begin(); it != old_display_items_.end(); - ++it) { - if (old_display_items_matched[it - old_display_items_.begin()]) + for (auto i = old_chunk_.begin_index; i < old_chunk_.end_index; ++i) { + if (old_display_items_matched[i - old_chunk_.begin_index]) continue; - const auto& old_item = *it; + const auto& old_item = old_paint_artifact_.GetDisplayItemList()[i]; if (old_item.DrawsContent() || old_item.IsTombstone()) { clients_to_invalidate.insert(&old_item.Client(), OldAndNewDisplayItems()) .stored_value->value.old_visual_rect.Unite(old_item.VisualRect()); @@ -97,33 +96,34 @@ } } -DisplayItemIterator DisplayItemRasterInvalidator::MatchNewDisplayItemInOldChunk( +wtf_size_t DisplayItemRasterInvalidator::MatchNewDisplayItemInOldChunk( const DisplayItem& new_item, - DisplayItemIterator& next_old_item_to_match) { + wtf_size_t& next_old_item_to_match) { if (!new_item.IsCacheable()) - return old_display_items_.end(); - for (; next_old_item_to_match != old_display_items_.end(); + return kNotFound; + for (; next_old_item_to_match < old_chunk_.end_index; next_old_item_to_match++) { - const auto& old_item = *next_old_item_to_match; + const auto& old_item = + old_paint_artifact_.GetDisplayItemList()[next_old_item_to_match]; if (!old_item.IsCacheable()) continue; if (old_item.GetId() == new_item.GetId()) return next_old_item_to_match++; // Add the skipped old item into index. - old_display_items_index_ - .insert(&old_item.Client(), Vector<DisplayItemIterator>()) + old_display_items_index_.insert(&old_item.Client(), Vector<wtf_size_t>()) .stored_value->value.push_back(next_old_item_to_match); } // Didn't find matching old item in sequential matching. Look up the index. auto it = old_display_items_index_.find(&new_item.Client()); if (it == old_display_items_index_.end()) - return old_display_items_.end(); + return kNotFound; for (auto i : it->value) { - if (i->GetId() == new_item.GetId()) + const auto& old_item = old_paint_artifact_.GetDisplayItemList()[i]; + if (old_item.GetId() == new_item.GetId()) return i; } - return old_display_items_.end(); + return kNotFound; } void DisplayItemRasterInvalidator::AddRasterInvalidation(
diff --git a/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.h b/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.h index 03d4b7c..b17ceb11 100644 --- a/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.h +++ b/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator.h
@@ -5,7 +5,6 @@ #ifndef THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_DISPLAY_ITEM_RASTER_INVALIDATOR_H_ #define THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_DISPLAY_ITEM_RASTER_INVALIDATOR_H_ -#include "third_party/blink/renderer/platform/graphics/paint/display_item_list.h" #include "third_party/blink/renderer/platform/graphics/paint/raster_invalidator.h" #include "third_party/blink/renderer/platform/wtf/allocator/allocator.h" @@ -19,14 +18,20 @@ DisplayItemRasterInvalidator( RasterInvalidator& invalidator, RasterInvalidator::RasterInvalidationFunction function, - const DisplayItemRange& old_display_items, - const DisplayItemRange& new_display_items, + const PaintArtifact& old_paint_artifact, + const PaintArtifact& new_paint_artifact, + const PaintChunk& old_chunk, + const PaintChunk& new_chunk, const ChunkToLayerMapper& mapper) : invalidator_(invalidator), raster_invalidation_function_(function), - old_display_items_(old_display_items), - new_display_items_(new_display_items), - mapper_(mapper) {} + old_paint_artifact_(old_paint_artifact), + new_paint_artifact_(new_paint_artifact), + old_chunk_(old_chunk), + new_chunk_(new_chunk), + mapper_(mapper) { + DCHECK(old_chunk_.Matches(new_chunk_)); + } void Generate(); @@ -38,9 +43,9 @@ const IntRect&, PaintInvalidationReason, RasterInvalidator::ClientIsOldOrNew); - ALWAYS_INLINE DisplayItemIterator + ALWAYS_INLINE wtf_size_t MatchNewDisplayItemInOldChunk(const DisplayItem& new_item, - DisplayItemIterator& next_old_item_to_match); + wtf_size_t& next_old_item_to_match); ALWAYS_INLINE void GenerateRasterInvalidation(const DisplayItemClient&, const IntRect& old_visual_rect, const IntRect& new_visual_rect, @@ -57,11 +62,13 @@ RasterInvalidator& invalidator_; RasterInvalidator::RasterInvalidationFunction raster_invalidation_function_; - const DisplayItemRange& old_display_items_; - const DisplayItemRange& new_display_items_; + const PaintArtifact& old_paint_artifact_; + const PaintArtifact& new_paint_artifact_; + const PaintChunk& old_chunk_; + const PaintChunk& new_chunk_; const ChunkToLayerMapper& mapper_; - // Maps clients to indices of display items in old_display_items_. - HashMap<const DisplayItemClient*, Vector<DisplayItemIterator>> + // Maps clients to indices of display items in old_chunk_. + HashMap<const DisplayItemClient*, Vector<wtf_size_t>> old_display_items_index_; };
diff --git a/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator_test.cc b/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator_test.cc index 14a102f5..0cfb49b 100644 --- a/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator_test.cc +++ b/third_party/blink/renderer/platform/graphics/paint/display_item_raster_invalidator_test.cc
@@ -23,11 +23,11 @@ Vector<RasterInvalidationInfo> GenerateRasterInvalidations() { GetPaintController().CommitNewDisplayItems(); - invalidator_.Generate(base::DoNothing(), GetPaintController().PaintChunks(), - // The layer rect is big enough not to clip display - // item raster invalidation rects. - IntRect(0, 0, 20000, 20000), - PropertyTreeState::Root()); + invalidator_.Generate( + base::DoNothing(), GetPaintController().GetPaintArtifactShared(), + // The layer rect is big enough not to clip display item raster + // invalidation rects. + IntRect(0, 0, 20000, 20000), PropertyTreeState::Root()); GetPaintController().FinishCycle(); GetPaintController().ClearPropertyTreeChangedStateTo( PropertyTreeState::Root());
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_artifact.cc b/third_party/blink/renderer/platform/graphics/paint/paint_artifact.cc index 519ae539..56e5366 100644 --- a/third_party/blink/renderer/platform/graphics/paint/paint_artifact.cc +++ b/third_party/blink/renderer/platform/graphics/paint/paint_artifact.cc
@@ -4,51 +4,42 @@ #include "third_party/blink/renderer/platform/graphics/paint/paint_artifact.h" -#include <ostream> - +#include "cc/layers/layer.h" #include "cc/paint/display_item_list.h" #include "third_party/blink/renderer/platform/geometry/int_rect.h" #include "third_party/blink/renderer/platform/graphics/compositing/paint_chunks_to_cc_layer.h" #include "third_party/blink/renderer/platform/graphics/graphics_context.h" #include "third_party/blink/renderer/platform/graphics/paint/drawing_display_item.h" -#include "third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h" #include "third_party/blink/renderer/platform/instrumentation/tracing/trace_event.h" namespace blink { -String PaintChunkIndex::ToString() const { - return String::Format("{%i, %i}", segment_index, chunk_index); +PaintArtifact::PaintArtifact() : display_item_list_(0) {} + +PaintArtifact::PaintArtifact(DisplayItemList display_items, + Vector<PaintChunk> chunks) + : display_item_list_(std::move(display_items)), chunks_(std::move(chunks)) { } -std::ostream& operator<<(std::ostream& os, PaintChunkIndex i) { - return os << i.ToString(); -} - -String DisplayItemIndex::ToString() const { - return String::Format("{%i, %i}", segment_index, item_index); -} - -std::ostream& operator<<(std::ostream& os, DisplayItemIndex i) { - return os << i.ToString(); -} - -PaintArtifact::PaintArtifact() = default; PaintArtifact::~PaintArtifact() = default; -PaintChunkSubset PaintArtifact::Chunks() const { - return PaintChunkSubset(this, 0, segments_.size()); +scoped_refptr<PaintArtifact> PaintArtifact::Create( + DisplayItemList display_items, + Vector<PaintChunk> chunks) { + return base::AdoptRef( + new PaintArtifact(std::move(display_items), std::move(chunks))); +} + +scoped_refptr<PaintArtifact> PaintArtifact::Empty() { + DEFINE_STATIC_REF(PaintArtifact, empty, base::AdoptRef(new PaintArtifact())); + return empty; } size_t PaintArtifact::ApproximateUnsharedMemoryUsage() const { - size_t total_size = - sizeof(*this) + segments_.capacity() * sizeof(segments_[0]); - for (const auto& segment : segments_) { - total_size += segment.display_item_list.MemoryUsageInBytes(); - total_size += (segment.chunks.capacity() - segment.chunks.size()) * - sizeof(segment.chunks[0]); - for (const auto& chunk : segment.chunks) - total_size += chunk.MemoryUsageInBytes(); - } + size_t total_size = sizeof(*this) + display_item_list_.MemoryUsageInBytes() + + chunks_.capacity() * sizeof(chunks_[0]); + for (const auto& chunk : chunks_) + total_size += chunk.MemoryUsageInBytes(); return total_size; } @@ -69,16 +60,50 @@ const PropertyTreeState& replay_state, const IntPoint& offset) const { return PaintChunksToCcLayer::Convert( - Chunks(), replay_state, gfx::Vector2dF(offset.X(), offset.Y()), + PaintChunks(), replay_state, + gfx::Vector2dF(offset.X(), offset.Y()), GetDisplayItemList(), cc::DisplayItemList::kToBeReleasedAsPaintOpBuffer) ->ReleaseAsRecord(); } -void PaintArtifact::FinishCycle() { - for (auto& segment : segments_) { - for (auto& chunk : segment.chunks) - chunk.client_is_just_created = false; +// The heuristic for picking a checkerboarding color works as follows: +// - During paint, PaintChunker will look for background color display items, +// and annotates the chunk with the index of the display item that paints +// the largest area background color (ties are broken by selecting the +// display item that paints last). +// - After layer allocation, the paint chunks assigned to a layer are +// examined for a background color annotation. The chunk with the largest +// background color annotation is selected. +// - If the area of the selected background color is at least half the size +// of the layer, then it is set as the layer's background color. +// - The same color is used for the layer's safe opaque background color, but +// without the size requirement, as safe opaque background color should +// always get a value if possible. +void PaintArtifact::UpdateBackgroundColor( + cc::Layer* layer, + const PaintChunkSubset& paint_chunks) const { + SkColor color = SK_ColorTRANSPARENT; + uint64_t area = 0; + for (const auto& chunk : paint_chunks) { + if (chunk.background_color != Color::kTransparent && + chunk.background_color_area >= area) { + color = chunk.background_color.Rgb(); + area = chunk.background_color_area; + } } + + layer->SetSafeOpaqueBackgroundColor(color); + + base::ClampedNumeric<uint64_t> layer_area = layer->bounds().width(); + layer_area *= layer->bounds().height(); + if (area < static_cast<uint64_t>(layer_area) / 2) + color = SK_ColorTRANSPARENT; + layer->SetBackgroundColor(color); +} + +void PaintArtifact::FinishCycle() { + for (auto& chunk : chunks_) + chunk.client_is_just_created = false; } } // namespace blink
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_artifact.h b/third_party/blink/renderer/platform/graphics/paint/paint_artifact.h index 81794566..83daf93 100644 --- a/third_party/blink/renderer/platform/graphics/paint/paint_artifact.h +++ b/third_party/blink/renderer/platform/graphics/paint/paint_artifact.h
@@ -5,165 +5,61 @@ #ifndef THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_PAINT_ARTIFACT_H_ #define THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_PAINT_ARTIFACT_H_ -#include <iosfwd> - +#include "base/macros.h" #include "third_party/blink/renderer/platform/graphics/paint/display_item_list.h" #include "third_party/blink/renderer/platform/graphics/paint/paint_chunk.h" +#include "third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h" #include "third_party/blink/renderer/platform/platform_export.h" #include "third_party/blink/renderer/platform/wtf/allocator/allocator.h" #include "third_party/blink/renderer/platform/wtf/vector.h" #include "third_party/skia/include/core/SkColor.h" namespace cc { +class Layer; class PaintCanvas; } namespace blink { - class GraphicsContext; class PaintChunkSubset; -// Contains the indices to locate a paint chunk in a paint artifact. See the -// comments for PaintArtifact below for the reason why we need two indices. -// Most users of this struct should treat it as an opaque data structure. -struct PLATFORM_EXPORT PaintChunkIndex { - wtf_size_t segment_index = 0; - wtf_size_t chunk_index = 0; - - bool operator==(PaintChunkIndex other) const { - return segment_index == other.segment_index && - chunk_index == other.chunk_index; - } - bool operator!=(PaintChunkIndex other) const { return !(*this == other); } - - String ToString() const; -}; - -// Similar to PaintChunkIndex, but for display items. -struct PLATFORM_EXPORT DisplayItemIndex { - wtf_size_t segment_index = 0; - wtf_size_t item_index = 0; - - bool operator==(DisplayItemIndex other) const { - return segment_index == other.segment_index && - item_index == other.item_index; - } - bool operator!=(DisplayItemIndex other) const { return !(*this == other); } - - String ToString() const; -}; - -PLATFORM_EXPORT std::ostream& operator<<(std::ostream&, PaintChunkIndex); -PLATFORM_EXPORT std::ostream& operator<<(std::ostream&, DisplayItemIndex); - -// A PaintArtifact represents the output of painting, consisting of paint chunks -// and display items which are stored in a two-level vector: -// - The first level vector contains the second level vectors which are -// called "segments". Segments are the unit of subsequence caching. -// - For paint chunks, the second level vectors are Vector<PaintChunk>. -// - For display items, the second level vectors are DisplayItemList. +// The output of painting, consisting of display item list (in DisplayItemList) +// and paint chunks. // -// A PaintArtifact not only represent the output of the current painting, but -// also serve as cache of individual display items and paint chunks for later -// paintings as long as the display items and paint chunks are valid. +// Display item list and paint chunks not only represent the output of the +// current painting, but also serve as cache of individual display items and +// paint chunks for later paintings as long as the display items and chunks are +// valid. // -// It represents a particular state of the world, and is immutable (const) and -// promises to be in a reasonable state (e.g. chunk bounding boxes computed) to -// all users, except for PaintController and unit tests. +// It represents a particular state of the world, and should be immutable +// (const) to most of its users. // -// Empty segments are not allowed except the following cases: -// TODO(wangxianzhu): the cases don't exist yet. -// -// A segment containing empty |display_item_list| is valid because we can have -// paint chunks without any display items, e.g. for hit testing. -// +// Unless its dangerous accessors are used, it promises to be in a reasonable +// state (e.g. chunk bounding boxes computed). class PLATFORM_EXPORT PaintArtifact final : public RefCounted<PaintArtifact> { USING_FAST_MALLOC(PaintArtifact); public: - PaintArtifact(); + static scoped_refptr<PaintArtifact> Create(DisplayItemList, + Vector<PaintChunk>); + + static scoped_refptr<PaintArtifact> Empty(); + ~PaintArtifact(); - PaintArtifact(const PaintArtifact& other) = delete; - PaintArtifact& operator=(const PaintArtifact& other) = delete; - PaintArtifact(PaintArtifact&& other) = delete; - PaintArtifact& operator=(PaintArtifact&& other) = delete; + bool IsEmpty() const { return display_item_list_.IsEmpty(); } - // See class comment for details about emptiness. - bool IsEmpty() const { return segments_.IsEmpty(); } - - void AddSegment(Vector<PaintChunk> chunks, DisplayItemList list) { - // We don't allow empty segments. - DCHECK(!chunks.IsEmpty()); - // |list| can be empty. - segments_.push_back(Segment{std::move(chunks), std::move(list)}); - } - - const PaintChunk& GetChunk(PaintChunkIndex i) const { - CheckChunkIndex(i); - return segments_[i.segment_index].chunks[i.chunk_index]; - } - - void IncrementChunkIndex(PaintChunkIndex& i) const { - CheckChunkIndex(i); - DCHECK(!segments_[i.segment_index].chunks.IsEmpty()); - if (i.chunk_index < segments_[i.segment_index].chunks.size() - 1) { - i.chunk_index++; - return; - } - i.chunk_index = 0; - i.segment_index++; - } - - const DisplayItem& GetDisplayItem(DisplayItemIndex i) const { - CheckDisplayItemIndex(i); - return segments_[i.segment_index].display_item_list[i.item_index]; - } - - void IncrementDisplayItemIndex(DisplayItemIndex& i) const { - CheckDisplayItemIndex(i); - DCHECK(!segments_[i.segment_index].display_item_list.IsEmpty()); - if (i.item_index < - segments_[i.segment_index].display_item_list.size() - 1) { - i.item_index++; - return; - } - i.item_index = 0; - do { - i.segment_index++; - } while (i.segment_index < segments_.size() && - segments_[i.segment_index].display_item_list.IsEmpty()); - } - - DisplayItemRange DisplayItemsInChunk(PaintChunkIndex i) const { - CheckChunkIndex(i); - auto& chunk = GetChunk(i); - return segments_[i.segment_index].display_item_list.ItemsInRange( - chunk.begin_index, chunk.end_index); - } - - // The returned PaintChunkSubset holds a reference to this PaintArtifact. - // It can be used to iterate all paint chunks (and display items through - // paint chunk iterators) in this PaintArtifact. - PaintChunkSubset Chunks() const; - - // TODO(wangxianzhu): These temporarily adapt for the existing callers. - // Remove when callers support multiple segments. - DisplayItemList& GetDisplayItemList() { - DCHECK_EQ(1u, segments_.size()); - return segments_[0].display_item_list; - } + DisplayItemList& GetDisplayItemList() { return display_item_list_; } const DisplayItemList& GetDisplayItemList() const { - DCHECK_EQ(1u, segments_.size()); - return segments_[0].display_item_list; + return display_item_list_; } - Vector<PaintChunk>& DeprecatedChunks() { - DCHECK_EQ(1u, segments_.size()); - return segments_[0].chunks; - } - const Vector<PaintChunk>& DeprecatedChunks() const { - DCHECK_EQ(1u, segments_.size()); - return segments_[0].chunks; + + Vector<PaintChunk>& PaintChunks() { return chunks_; } + const Vector<PaintChunk>& PaintChunks() const { return chunks_; } + + PaintChunkSubset GetPaintChunkSubset( + const Vector<wtf_size_t>& subset_indices) const { + return PaintChunkSubset(PaintChunks(), subset_indices); } // Returns the approximate memory usage, excluding memory likely to be @@ -190,28 +86,19 @@ // for the next cycle, and update status to be ready for the next cycle. void FinishCycle(); + void UpdateBackgroundColor(cc::Layer* layer, + const PaintChunkSubset& paint_chunks) const; + private: - void CheckChunkIndex(PaintChunkIndex i) const { - DCHECK_LT(i.segment_index, segments_.size()); - DCHECK_LT(i.chunk_index, segments_[i.segment_index].chunks.size()); - } + PaintArtifact(); + PaintArtifact(DisplayItemList, Vector<PaintChunk>); - void CheckDisplayItemIndex(DisplayItemIndex i) const { - DCHECK_LT(i.segment_index, segments_.size()); - DCHECK_LT(i.item_index, - segments_[i.segment_index].display_item_list.size()); - } + DisplayItemList display_item_list_; + Vector<PaintChunk> chunks_; - struct Segment { - Vector<PaintChunk> chunks; - DisplayItemList display_item_list; - }; - Vector<Segment> segments_; + DISALLOW_COPY_AND_ASSIGN(PaintArtifact); }; -PLATFORM_EXPORT std::ostream& operator<<(std::ostream&, PaintChunkIndex); -PLATFORM_EXPORT std::ostream& operator<<(std::ostream&, DisplayItemIndex); - } // namespace blink #endif // THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_PAINT_ARTIFACT_H_
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.cc b/third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.cc deleted file mode 100644 index 1d40bb0..0000000 --- a/third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.cc +++ /dev/null
@@ -1,15 +0,0 @@ -// Copyright 2020 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/graphics/paint/paint_chunk_subset.h" - -#include <ostream> - -namespace blink { - -std::ostream& operator<<(std::ostream& os, PaintChunkIterator it) { - return os << it.ToString(); -} - -} // namespace blink
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h b/third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h index 2dd6e147..c28b7285 100644 --- a/third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h +++ b/third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h
@@ -5,132 +5,78 @@ #ifndef THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_PAINT_CHUNK_SUBSET_H_ #define THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_PAINT_CHUNK_SUBSET_H_ -#include <iosfwd> - -#include "third_party/blink/renderer/platform/graphics/paint/paint_artifact.h" #include "third_party/blink/renderer/platform/wtf/allocator/allocator.h" #include "third_party/blink/renderer/platform/wtf/vector.h" namespace blink { -// Provides access to a subset of paint chunks in a PaintArtifact. -// TODO(wangxianzhu): When we remove pre-CAP, we can split this class for the -// two use cases (corresponding to the two constructors respectively): One for -// iterating paint chunks in a paint artifact within a segment range, and the -// other for PaintArtifactCompositor PendingLayer to create a subset of paint -// chunks from indices. For now we still need this class to provide a common API -// for the two use cases for RasterInvalidator and PaintChunksToCcLayer, etc. +struct PaintChunk; + +// Provides access to a subset of a Vector<PaintChunk>. class PaintChunkSubset { - STACK_ALLOCATED(); + DISALLOW_NEW(); public: - // A subset defined by a vector of paint chunk indices. It references - // |subset_indices| provided by the caller, so it should not live longer than - // |subset_indices|. - PaintChunkSubset(scoped_refptr<const PaintArtifact> paint_artifact, - const Vector<PaintChunkIndex>& subset_indices) - : paint_artifact_(std::move(paint_artifact)), - subset_indices_(&subset_indices) {} + PaintChunkSubset(const Vector<PaintChunk>& chunks, + const Vector<wtf_size_t>& subset_indices) + : chunks_(chunks), subset_indices_(&subset_indices) {} - // A subset defined by a range of segments. |end_segment_index| is not - // inclusive. - PaintChunkSubset(scoped_refptr<const PaintArtifact> paint_artifact, - wtf_size_t begin_segment_index, - wtf_size_t end_segment_index) - : paint_artifact_(std::move(paint_artifact)), - begin_segment_index_(begin_segment_index), - end_segment_index_(end_segment_index) { - DCHECK_LE(begin_segment_index_, end_segment_index_); - } + // For convenience, this allows using a Vector<PaintChunk> in place of + // PaintChunkSubset to include all paint chunks. + PaintChunkSubset(const Vector<PaintChunk>& chunks) + : chunks_(chunks), subset_indices_(nullptr) {} class Iterator { STACK_ALLOCATED(); public: - const PaintChunk& operator*() const { return subset_[Index()]; } - const PaintChunk* operator->() const { return &subset_[Index()]; } - bool operator==(const Iterator& other) const { + const PaintChunk& operator*() const { return subset_[offset_]; } + const PaintChunk* operator->() const { return &subset_[offset_]; } + bool operator!=(const Iterator& other) const { DCHECK_EQ(&subset_, &other.subset_); - if (subset_.subset_indices_) - return subset_index_ == other.subset_index_; - return chunk_index_ == other.chunk_index_; + return offset_ != other.offset_; } - bool operator!=(const Iterator& other) const { return !(*this == other); } const Iterator& operator++() { - if (subset_.subset_indices_) - subset_index_++; - else - subset_.paint_artifact_->IncrementChunkIndex(chunk_index_); + ++offset_; return *this; } - // Returns the index of the current PaintChunk in the PaintArtifact. - PaintChunkIndex Index() const { - if (subset_.subset_indices_) - return (*subset_.subset_indices_)[subset_index_]; - return chunk_index_; - } - - DisplayItemRange DisplayItems() const { - return subset_.paint_artifact_->DisplayItemsInChunk(Index()); - } - - String ToString() const { return Index().ToString(); } + // The index in the whole paint chunks set. + wtf_size_t OriginalIndex() const { return subset_.OriginalIndex(offset_); } private: friend class PaintChunkSubset; - - Iterator(const PaintChunkSubset& subset, PaintChunkIndex chunk_index) - : subset_(subset), chunk_index_(chunk_index) {} - Iterator(const PaintChunkSubset& subset, wtf_size_t subset_index) - : subset_(subset), subset_index_(subset_index) {} + Iterator(const PaintChunkSubset& subset, wtf_size_t offset) + : subset_(subset), offset_(offset) {} const PaintChunkSubset& subset_; - union { - PaintChunkIndex chunk_index_; // If subset_.subset_indices_ is nullptr. - wtf_size_t subset_index_; // If subset_.subset_indices_ is not nullptr. - }; + wtf_size_t offset_; }; - using value_type = PaintChunk; - using const_iterator = Iterator; + Iterator begin() const { return Iterator(*this, 0); } - Iterator begin() const { - if (subset_indices_) - return Iterator(*this, 0); - return Iterator(*this, {begin_segment_index_, 0}); + Iterator end() const { return Iterator(*this, size()); } + + wtf_size_t size() const { + return subset_indices_ ? subset_indices_->size() : chunks_.size(); } - Iterator end() const { - if (subset_indices_) - return Iterator(*this, subset_indices_->size()); - return Iterator(*this, {end_segment_index_, 0}); + // |i| is an index in the subset. + const PaintChunk& operator[](wtf_size_t i) const { + return chunks_[OriginalIndex(i)]; } - bool IsEmpty() const { - if (subset_indices_) - return subset_indices_->IsEmpty(); - return begin_segment_index_ == end_segment_index_; + // |i| is an index in the subset. + // Returns the index in the whole paint chunks set. + wtf_size_t OriginalIndex(wtf_size_t i) const { + return subset_indices_ ? (*subset_indices_)[i] : i; } - const PaintChunk& operator[](PaintChunkIndex i) const { - return paint_artifact_->GetChunk(i); - } - - const PaintArtifact& GetPaintArtifact() const { return *paint_artifact_; } - private: - scoped_refptr<const PaintArtifact> paint_artifact_; - const Vector<PaintChunkIndex>* subset_indices_ = nullptr; - // These are used when subset_indices is nullptr. - wtf_size_t begin_segment_index_ = kNotFound; - wtf_size_t end_segment_index_ = kNotFound; + const Vector<PaintChunk>& chunks_; + const Vector<wtf_size_t>* subset_indices_; }; -using PaintChunkIterator = PaintChunkSubset::Iterator; - -PLATFORM_EXPORT std::ostream& operator<<(std::ostream&, PaintChunkIterator); - } // namespace blink #endif // THIRD_PARTY_BLINK_RENDERER_PLATFORM_GRAPHICS_PAINT_PAINT_CHUNK_SUBSET_H_
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_controller.cc b/third_party/blink/renderer/platform/graphics/paint/paint_controller.cc index d712ddf..353434f 100644 --- a/third_party/blink/renderer/platform/graphics/paint/paint_controller.cc +++ b/third_party/blink/renderer/platform/graphics/paint/paint_controller.cc
@@ -10,22 +10,13 @@ #include "third_party/blink/renderer/platform/graphics/logging_canvas.h" #include "third_party/blink/renderer/platform/graphics/paint/drawing_display_item.h" #include "third_party/blink/renderer/platform/graphics/paint/ignore_paint_timing_scope.h" -#include "third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h" #include "third_party/blink/renderer/platform/instrumentation/tracing/trace_event.h" namespace blink { -// This is just for initializing current_paint_artifact_ to avoid allocation of -// a PaintArtifacts that might not be used. -static scoped_refptr<PaintArtifact> EmptyPaintArtifact() { - DEFINE_STATIC_REF(PaintArtifact, empty, base::AdoptRef(new PaintArtifact())); - DCHECK(empty->IsEmpty()); - return empty; -} - PaintController::PaintController(Usage usage) : usage_(usage), - current_paint_artifact_(EmptyPaintArtifact()), + current_paint_artifact_(PaintArtifact::Empty()), new_display_item_list_(0) { // frame_first_paints_ should have one null frame since the beginning, so // that PaintController is robust even if it paints outside of BeginFrame @@ -164,9 +155,12 @@ return false; } - const auto& chunks = current_paint_artifact_->DeprecatedChunks(); - wtf_size_t start_item_index = chunks[markers->start_chunk_index].begin_index; - wtf_size_t end_item_index = chunks[markers->end_chunk_index - 1].end_index; + wtf_size_t start_item_index = + current_paint_artifact_->PaintChunks()[markers->start_chunk_index] + .begin_index; + wtf_size_t end_item_index = + current_paint_artifact_->PaintChunks()[markers->end_chunk_index - 1] + .end_index; if (end_item_index > start_item_index && current_paint_artifact_->GetDisplayItemList()[start_item_index] .IsTombstone()) { @@ -249,7 +243,7 @@ new_chunk_index < end_chunk_index; ++new_chunk_index, ++old_chunk_index) { const auto& old_chunk = - current_paint_artifact_->DeprecatedChunks()[old_chunk_index]; + current_paint_artifact_->PaintChunks()[old_chunk_index]; const auto& new_chunk = new_paint_chunks_.PaintChunks()[new_chunk_index]; if (!old_chunk.EqualsForUnderInvalidationChecking(new_chunk)) { @@ -351,7 +345,7 @@ // TODO(wangxianzhu): Rename this to InvalidateAllForTesting() for CAP. // Can only be called during layout/paintInvalidation, not during painting. DCHECK(new_display_item_list_.IsEmpty()); - current_paint_artifact_ = EmptyPaintArtifact(); + current_paint_artifact_ = PaintArtifact::Empty(); current_cached_subsequences_.clear(); cache_is_all_invalid_ = true; } @@ -417,9 +411,6 @@ wtf_size_t PaintController::FindCachedItem(const DisplayItem::Id& id) { DCHECK(ClientCacheIsValid(id.client)); - if (current_paint_artifact_->IsEmpty()) - return kNotFound; - if (next_item_to_match_ < current_paint_artifact_->GetDisplayItemList().size()) { // If current_list[next_item_to_match_] matches the new item, we don't need @@ -504,15 +495,15 @@ for (auto chunk_index = start_chunk_index; chunk_index < end_chunk_index; ++chunk_index) { - auto& cached_chunk = - current_paint_artifact_->DeprecatedChunks()[chunk_index]; + auto& cached_chunk = current_paint_artifact_->PaintChunks()[chunk_index]; auto cached_item_index = cached_chunk.begin_index; for (auto& cached_item : - current_paint_artifact_->GetDisplayItemList().ItemsInRange( - cached_chunk.begin_index, cached_chunk.end_index)) { + current_paint_artifact_->GetDisplayItemList().ItemsInPaintChunk( + cached_chunk)) { SECURITY_CHECK(!cached_item.IsTombstone()); - DCHECK(!cached_item.IsCacheable() || - ClientCacheIsValid(cached_item.Client())); +#if DCHECK_IS_ON() + DCHECK(cached_item.Client().IsAlive()); +#endif auto& item = MoveItemFromCurrentListToNewList(cached_item_index++); item.SetMovedFromCachedSubsequence(true); DidAppendItem(item); @@ -540,9 +531,7 @@ void PaintController::CommitNewDisplayItems() { TRACE_EVENT2("blink,benchmark", "PaintController::commitNewDisplayItems", "current_display_list_size", - current_paint_artifact_->IsEmpty() - ? 0 - : (int)current_paint_artifact_->GetDisplayItemList().size(), + (int)current_paint_artifact_->GetDisplayItemList().size(), "num_non_cached_new_items", (int)new_display_item_list_.size() - num_cached_new_items_); @@ -565,14 +554,9 @@ // The new list will not be appended to again so we can release unused memory. new_display_item_list_.ShrinkToFit(); - current_paint_artifact_ = base::AdoptRef(new PaintArtifact()); - if (new_paint_chunks_.size()) { - current_paint_artifact_->AddSegment(new_paint_chunks_.ReleasePaintChunks(), - std::move(new_display_item_list_)); - } else { - new_paint_chunks_.ReleasePaintChunks(); - DCHECK(new_display_item_list_.IsEmpty()); - } + current_paint_artifact_ = + PaintArtifact::Create(std::move(new_display_item_list_), + new_paint_chunks_.ReleasePaintChunks()); ResetCurrentListIndices(); out_of_order_item_id_index_map_.clear(); @@ -604,29 +588,33 @@ if (item.key->IsCacheable()) item.key->Validate(); } - auto chunks = current_paint_artifact_->Chunks(); - for (auto it = chunks.begin(); it != chunks.end(); ++it) { - auto& chunk = *it; + for (const auto& item : current_paint_artifact_->GetDisplayItemList()) { + const auto& client = item.Client(); + if (item.IsMovedFromCachedSubsequence()) { + // We don't need to validate the clients of a display item that is + // copied from a cached subsequence, because it should be already + // valid. See http://crbug.com/1050090 for more details. +#if DCHECK_IS_ON() + DCHECK(client.IsAlive()); + DCHECK(client.IsValid() || !client.IsCacheable()); +#endif + continue; + } + client.ClearPartialInvalidationVisualRect(); + if (client.IsCacheable()) + client.Validate(); + } + for (const auto& chunk : current_paint_artifact_->PaintChunks()) { const auto& client = chunk.id.client; if (chunk.is_moved_from_cached_subsequence) { - DCHECK(!chunk.is_cacheable || ClientCacheIsValid(client)); +#if DCHECK_IS_ON() + DCHECK(client.IsAlive()); + DCHECK(client.IsValid() || !client.IsCacheable()); +#endif continue; } if (client.IsCacheable()) client.Validate(); - - for (const auto& item : it.DisplayItems()) { - if (item.IsMovedFromCachedSubsequence()) { - // We don't need to validate the clients of a display item that is - // copied from a cached subsequence, because it should be already - // valid. See http://crbug.com/1050090 for more details. - DCHECK(!item.IsCacheable() || ClientCacheIsValid(item.Client())); - continue; - } - item.Client().ClearPartialInvalidationVisualRect(); - if (item.Client().IsCacheable()) - item.Client().Validate(); - } } current_paint_artifact_->FinishCycle(); @@ -648,7 +636,7 @@ const PropertyTreeStateOrAlias& to) { // Calling |ClearChangedTo| for every chunk is O(|property nodes|^2) and // could be optimized by caching which nodes that have already been cleared. - for (const auto& chunk : PaintChunks()) { + for (const auto& chunk : current_paint_artifact_->PaintChunks()) { chunk.properties.Transform().ClearChangedTo(&to.Transform()); chunk.properties.Clip().ClearChangedTo(&to.Clip()); chunk.properties.Effect().ClearChangedTo(&to.Effect()); @@ -834,8 +822,7 @@ void PaintController::UpdateUMACountsOnFullyCached() { DCHECK_EQ(usage_, kMultiplePaints); - int num_items = - GetPaintArtifact().IsEmpty() ? 0 : GetDisplayItemList().size(); + int num_items = GetDisplayItemList().size(); sum_num_items_ += num_items; sum_num_cached_items_ += num_items;
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_controller.h b/third_party/blink/renderer/platform/graphics/paint/paint_controller.h index 00468403..5a80c63 100644 --- a/third_party/blink/renderer/platform/graphics/paint/paint_controller.h +++ b/third_party/blink/renderer/platform/graphics/paint/paint_controller.h
@@ -17,7 +17,6 @@ #include "third_party/blink/renderer/platform/graphics/paint/display_item_list.h" #include "third_party/blink/renderer/platform/graphics/paint/paint_artifact.h" #include "third_party/blink/renderer/platform/graphics/paint/paint_chunk.h" -#include "third_party/blink/renderer/platform/graphics/paint/paint_chunk_subset.h" #include "third_party/blink/renderer/platform/graphics/paint/paint_chunker.h" #include "third_party/blink/renderer/platform/platform_export.h" #include "third_party/blink/renderer/platform/runtime_enabled_features.h" @@ -215,7 +214,9 @@ const DisplayItemList& GetDisplayItemList() const { return GetPaintArtifact().GetDisplayItemList(); } - PaintChunkSubset PaintChunks() const { return GetPaintArtifact().Chunks(); } + const Vector<PaintChunk>& PaintChunks() const { + return GetPaintArtifact().PaintChunks(); + } // For micro benchmarks of record time. static void SetSubsequenceCachingDisabledForBenchmark(); @@ -273,9 +274,13 @@ void InvalidateAllInternal(); void EnsureNewDisplayItemListInitialCapacity() { - if (new_display_item_list_.CapacityInBytes() == 0) { - new_display_item_list_ = - DisplayItemList(kInitialDisplayItemListCapacityBytes); + if (new_display_item_list_.IsEmpty()) { + // TODO(wangxianzhu): Consider revisiting this heuristic. + new_display_item_list_ = DisplayItemList( + current_paint_artifact_->GetDisplayItemList().IsEmpty() + ? kInitialDisplayItemListCapacityBytes + : current_paint_artifact_->GetDisplayItemList() + .UsedCapacityInBytes()); } }
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_controller_debug_data.cc b/third_party/blink/renderer/platform/graphics/paint/paint_controller_debug_data.cc index c0891fd..ef94b6f 100644 --- a/third_party/blink/renderer/platform/graphics/paint/paint_controller_debug_data.cc +++ b/third_party/blink/renderer/platform/graphics/paint/paint_controller_debug_data.cc
@@ -123,10 +123,8 @@ json_object->SetString("chunkData", chunk.ToString()); json_object->SetArray( - "displayItems", DisplayItemList::DisplayItemsAsJSON( - DisplayItemRange(list_.begin() + chunk.begin_index, - list_.begin() + chunk.end_index), - flags_)); + "displayItems", + list_.DisplayItemsAsJSON(chunk.begin_index, chunk.end_index, flags_)); json_array.PushObject(std::move(json_object)); } @@ -147,8 +145,7 @@ << DisplayItemListAsJSON( current_paint_artifact_->GetDisplayItemList(), current_cached_subsequences_, - current_paint_artifact_->DeprecatedChunks(), - current_list_flags) + current_paint_artifact_->PaintChunks(), current_list_flags) .ToString() .Utf8();
diff --git a/third_party/blink/renderer/platform/graphics/paint/paint_controller_test.cc b/third_party/blink/renderer/platform/graphics/paint/paint_controller_test.cc index d16829aa..a392dee9 100644 --- a/third_party/blink/renderer/platform/graphics/paint/paint_controller_test.cc +++ b/third_party/blink/renderer/platform/graphics/paint/paint_controller_test.cc
@@ -1344,8 +1344,10 @@ DrawRect(context, client, kBackgroundType, IntRect(0, 0, 100, 100)); CommitAndFinishCycle(); - EXPECT_THAT(GetPaintController().PaintChunks(), - ElementsAre(IsPaintChunk(0, 1))); + const auto& paint_chunks = GetPaintController().PaintChunks(); + ASSERT_EQ(1u, paint_chunks.size()); + EXPECT_EQ(0u, paint_chunks[0].begin_index); + EXPECT_EQ(1u, paint_chunks[0].end_index); } void DrawPath(GraphicsContext& context,
diff --git a/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.cc b/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.cc index 5e016ee..ebfd05e 100644 --- a/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.cc +++ b/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.cc
@@ -15,17 +15,16 @@ namespace blink { -void RasterInvalidator::UpdateClientDebugNames() { +void RasterInvalidator::UpdateClientDebugNames( + const PaintArtifact& paint_artifact, + const PaintChunkSubset& paint_chunks) { DCHECK(tracking_info_); auto& debug_names = tracking_info_->old_client_debug_names; debug_names.clear(); - // This is called just after a full document cycle update, so all clients in - // old_paint_artifact_ should be still alive. - for (const auto& chunk_info : old_chunks_info_) { - const auto& chunk = old_paint_artifact_->GetChunk(chunk_info.index); + for (const auto& chunk : paint_chunks) { debug_names.insert(&chunk.id.client, chunk.id.client.DebugName()); for (const auto& item : - old_paint_artifact_->DisplayItemsInChunk(chunk_info.index)) + paint_artifact.GetDisplayItemList().ItemsInPaintChunk(chunk)) debug_names.insert(&item.Client(), item.Client().DebugName()); } } @@ -35,7 +34,13 @@ if (!tracking_info_) tracking_info_ = std::make_unique<RasterInvalidationTrackingInfo>(); tracking_info_->tracking.ClearInvalidations(); - UpdateClientDebugNames(); + + // This is called just after a full document cycle update, so all clients in + // old_paint_artifact_ should be still alive. + if (old_paint_artifact_) { + UpdateClientDebugNames(*old_paint_artifact_, + old_paint_artifact_->PaintChunks()); + } } else if (!RasterInvalidationTracking::ShouldAlwaysTrack()) { tracking_info_ = nullptr; } else if (tracking_info_) { @@ -45,10 +50,12 @@ const PaintChunk& RasterInvalidator::GetOldChunk(wtf_size_t index) const { DCHECK(old_paint_artifact_); - const auto& old_chunk_info = old_chunks_info_[index]; - const auto& old_chunk = old_paint_artifact_->GetChunk(old_chunk_info.index); + const auto& old_chunk_info = old_paint_chunks_info_[index]; + const auto& old_chunk = + old_paint_artifact_ + ->PaintChunks()[old_chunk_info.index_in_paint_artifact]; #if DCHECK_IS_ON() - DCHECK_EQ(old_chunk.id, old_chunk_info.id); + DCHECK(old_chunk.id == old_chunk_info.id); #endif return old_chunk; } @@ -56,7 +63,7 @@ wtf_size_t RasterInvalidator::MatchNewChunkToOldChunk( const PaintChunk& new_chunk, wtf_size_t old_index) const { - for (wtf_size_t i = old_index; i < old_chunks_info_.size(); i++) { + for (wtf_size_t i = old_index; i < old_paint_chunks_info_.size(); i++) { if (new_chunk.Matches(GetOldChunk(i))) return i; } @@ -146,10 +153,11 @@ // Skip the chunk for raster invalidation if it contains only one non-drawing // display item. We could also skip chunks containing all non-drawing display // items, but single non-drawing item is more common, e.g. scroll hit test. -static bool ShouldSkipForRasterInvalidation( - const PaintChunkSubset::Iterator& chunk_it) { - return chunk_it->size() == 1 && - !chunk_it.DisplayItems().begin()->DrawsContent(); +bool ShouldSkipForRasterInvalidation(const PaintArtifact& paint_artifact, + const PaintChunk& paint_chunk) { + return paint_chunk.size() == 1 && + !paint_artifact.GetDisplayItemList()[paint_chunk.begin_index] + .DrawsContent(); } // Generates raster invalidations by checking changes (appearing, disappearing, @@ -164,19 +172,20 @@ // is slightly larger than O(n). void RasterInvalidator::GenerateRasterInvalidations( RasterInvalidationFunction function, + const PaintArtifact& new_paint_artifact, const PaintChunkSubset& new_chunks, const PropertyTreeState& layer_state, Vector<PaintChunkInfo>& new_chunks_info) { ChunkToLayerMapper mapper(layer_state, layer_bounds_.OffsetFromOrigin()); Vector<bool> old_chunks_matched; - old_chunks_matched.resize(old_chunks_info_.size()); + old_chunks_matched.resize(old_paint_chunks_info_.size()); wtf_size_t old_index = 0; wtf_size_t max_matched_old_index = 0; for (auto it = new_chunks.begin(); it != new_chunks.end(); ++it) { - if (ShouldSkipForRasterInvalidation(it)) + const auto& new_chunk = *it; + if (ShouldSkipForRasterInvalidation(new_paint_artifact, new_chunk)) continue; - const auto& new_chunk = *it; mapper.SwitchToChunk(new_chunk); auto& new_chunk_info = new_chunks_info.emplace_back(*this, mapper, it); @@ -206,7 +215,7 @@ DCHECK(!old_chunks_matched[matched_old_index]); old_chunks_matched[matched_old_index] = true; - auto& old_chunk_info = old_chunks_info_[matched_old_index]; + auto& old_chunk_info = old_paint_chunks_info_[matched_old_index]; const auto& old_chunk = GetOldChunk(matched_old_index); // Clip the old chunk bounds by the new layer bounds. old_chunk_info.bounds_in_layer = @@ -244,24 +253,23 @@ new_chunk.id.client); } - if (&new_chunks.GetPaintArtifact() != old_paint_artifact_.get() && + if (&new_paint_artifact != old_paint_artifact_ && !new_chunk.is_moved_from_cached_subsequence) { - DisplayItemRasterInvalidator( - *this, function, - old_paint_artifact_->DisplayItemsInChunk(old_chunk_info.index), - it.DisplayItems(), mapper) + DisplayItemRasterInvalidator(*this, function, *old_paint_artifact_, + new_paint_artifact, old_chunk, new_chunk, + mapper) .Generate(); } } old_index = matched_old_index + 1; - if (old_index == old_chunks_info_.size()) + if (old_index == old_paint_chunks_info_.size()) old_index = 0; max_matched_old_index = std::max(max_matched_old_index, matched_old_index); } // Invalidate remaining unmatched (disappeared or uncacheable) old chunks. - for (wtf_size_t i = 0; i < old_chunks_info_.size(); ++i) { + for (wtf_size_t i = 0; i < old_paint_chunks_info_.size(); ++i) { if (old_chunks_matched[i]) continue; @@ -269,7 +277,7 @@ auto reason = old_chunk.is_cacheable ? PaintInvalidationReason::kChunkDisappeared : PaintInvalidationReason::kChunkUncacheable; - AddRasterInvalidation(function, old_chunks_info_[i].bounds_in_layer, + AddRasterInvalidation(function, old_paint_chunks_info_[i].bounds_in_layer, old_chunk.id.client, reason, kClientIsOld); } } @@ -306,7 +314,19 @@ void RasterInvalidator::Generate( RasterInvalidationFunction raster_invalidation_function, - const PaintChunkSubset& new_chunks, + scoped_refptr<const PaintArtifact> new_paint_artifact, + const gfx::Rect& layer_bounds, + const PropertyTreeState& layer_state, + const DisplayItemClient* layer_client) { + Generate(raster_invalidation_function, new_paint_artifact, + new_paint_artifact->PaintChunks(), layer_bounds, layer_state, + layer_client); +} + +void RasterInvalidator::Generate( + RasterInvalidationFunction raster_invalidation_function, + scoped_refptr<const PaintArtifact> new_paint_artifact, + const PaintChunkSubset& paint_chunks, const gfx::Rect& layer_bounds, const PropertyTreeState& layer_state, const DisplayItemClient* layer_client) { @@ -317,34 +337,36 @@ layer_bounds_ = layer_bounds; Vector<PaintChunkInfo> new_chunks_info; + new_chunks_info.ReserveCapacity(paint_chunks.size()); if (layer_bounds_was_empty || layer_bounds_.IsEmpty()) { // No raster invalidation is needed if either the old bounds or the new // bounds is empty, but we still need to update new_chunks_info for the // next cycle. ChunkToLayerMapper mapper(layer_state, layer_bounds.OffsetFromOrigin()); - for (auto it = new_chunks.begin(); it != new_chunks.end(); ++it) { - if (ShouldSkipForRasterInvalidation(it)) + for (auto it = paint_chunks.begin(); it != paint_chunks.end(); ++it) { + if (ShouldSkipForRasterInvalidation(*new_paint_artifact, *it)) continue; mapper.SwitchToChunk(*it); new_chunks_info.emplace_back(*this, mapper, it); } if (tracking_info_ && layer_bounds_was_empty && !layer_bounds.IsEmpty() && - !new_chunks.IsEmpty()) { + paint_chunks.size()) { TrackImplicitFullLayerInvalidation( - layer_client ? *layer_client : new_chunks.begin()->id.client); + layer_client ? *layer_client : paint_chunks[0].id.client); } } else { - GenerateRasterInvalidations(raster_invalidation_function, new_chunks, - layer_state, new_chunks_info); + GenerateRasterInvalidations(raster_invalidation_function, + *new_paint_artifact, paint_chunks, layer_state, + new_chunks_info); } - old_chunks_info_ = std::move(new_chunks_info); - old_paint_artifact_ = &new_chunks.GetPaintArtifact(); - if (tracking_info_) - UpdateClientDebugNames(); + UpdateClientDebugNames(*new_paint_artifact, paint_chunks); + + old_paint_chunks_info_ = std::move(new_chunks_info); + old_paint_artifact_ = std::move(new_paint_artifact); } void RasterInvalidator::TrackImplicitFullLayerInvalidation( @@ -364,12 +386,13 @@ } size_t RasterInvalidator::ApproximateUnsharedMemoryUsage() const { - return sizeof(*this) + old_chunks_info_.capacity() * sizeof(PaintChunkInfo); + return sizeof(*this) + + old_paint_chunks_info_.capacity() * sizeof(PaintChunkInfo); } void RasterInvalidator::ClearOldStates() { old_paint_artifact_ = nullptr; - old_chunks_info_.clear(); + old_paint_chunks_info_.clear(); layer_bounds_ = gfx::Rect(); }
diff --git a/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.h b/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.h index 80a4b555..2aa33f3 100644 --- a/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.h +++ b/third_party/blink/renderer/platform/graphics/paint/raster_invalidator.h
@@ -36,9 +36,18 @@ RasterInvalidationTracking& EnsureTracking(); + // Generate raster invalidations for all of the changed paint chunks and + // display items in the paint artifact. + void Generate(RasterInvalidationFunction, + scoped_refptr<const PaintArtifact>, + const gfx::Rect& layer_bounds, + const PropertyTreeState& layer_state, + const DisplayItemClient* layer_client = nullptr); + // Generate raster invalidations for a subset of the paint chunks in the // paint artifact. void Generate(RasterInvalidationFunction, + scoped_refptr<const PaintArtifact>, const PaintChunkSubset&, const gfx::Rect& layer_bounds, const PropertyTreeState& layer_state, @@ -54,13 +63,13 @@ friend class DisplayItemRasterInvalidator; friend class RasterInvalidatorTest; - void UpdateClientDebugNames(); + void UpdateClientDebugNames(const PaintArtifact&, const PaintChunkSubset&); struct PaintChunkInfo { PaintChunkInfo(const RasterInvalidator& invalidator, const ChunkToLayerMapper& mapper, PaintChunkSubset::Iterator chunk_it) - : index(chunk_it.Index()), + : index_in_paint_artifact(chunk_it.OriginalIndex()), #if DCHECK_IS_ON() id(chunk_it->id), #endif @@ -70,7 +79,10 @@ chunk_to_layer_transform(mapper.Transform()) { } - PaintChunkIndex index; + // The index of the chunk in the PaintArtifact. It may be different from + // the index of this PaintChunkInfo in paint_chunks_info_ when a subset of + // the paint chunks is handled by the RasterInvalidator. + wtf_size_t index_in_paint_artifact; #if DCHECK_IS_ON() PaintChunk::Id id; @@ -82,6 +94,7 @@ }; void GenerateRasterInvalidations(RasterInvalidationFunction, + const PaintArtifact&, const PaintChunkSubset&, const PropertyTreeState& layer_state, Vector<PaintChunkInfo>& new_chunks_info); @@ -133,7 +146,7 @@ void TrackImplicitFullLayerInvalidation(const DisplayItemClient&); gfx::Rect layer_bounds_; - Vector<PaintChunkInfo> old_chunks_info_; + Vector<PaintChunkInfo> old_paint_chunks_info_; scoped_refptr<const PaintArtifact> old_paint_artifact_; struct RasterInvalidationTrackingInfo {
diff --git a/third_party/blink/renderer/platform/graphics/paint/raster_invalidator_test.cc b/third_party/blink/renderer/platform/graphics/paint/raster_invalidator_test.cc index 535ecc9..28eea88 100644 --- a/third_party/blink/renderer/platform/graphics/paint/raster_invalidator_test.cc +++ b/third_party/blink/renderer/platform/graphics/paint/raster_invalidator_test.cc
@@ -40,7 +40,7 @@ void FinishCycle(PaintArtifact& artifact) { artifact.FinishCycle(); ClearGeometryMapperCache(); - for (auto& chunk : artifact.Chunks()) + for (auto& chunk : artifact.PaintChunks()) chunk.properties.ClearChangedToRoot(); } @@ -95,9 +95,9 @@ auto artifact = TestPaintArtifact().Chunk(0).Build(); invalidator_.SetTracksRasterInvalidations(true); - invalidator_.Generate(base::DoNothing(), artifact->Chunks(), - kDefaultLayerBounds, DefaultPropertyTreeState()); - const auto& client = artifact->Chunks().begin()->id.client; + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, + DefaultPropertyTreeState()); + const auto& client = artifact->PaintChunks()[0].id.client; EXPECT_THAT(TrackedRasterInvalidations(), ElementsAre(RasterInvalidationInfo{ &client, client.DebugName(), @@ -109,37 +109,36 @@ TEST_P(RasterInvalidatorTest, LayerBounds) { auto artifact = TestPaintArtifact().Chunk(0).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); FinishCycle(*artifact); invalidator_.SetTracksRasterInvalidations(true); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); // No raster invalidations needed if layer origin doesn't change. EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); auto new_layer_bounds = kDefaultLayerBounds; new_layer_bounds.Move(66, 77); - invalidator_.Generate(base::DoNothing(), chunks, new_layer_bounds, + invalidator_.Generate(base::DoNothing(), artifact, new_layer_bounds, DefaultPropertyTreeState()); // Change of layer origin causes change of chunk0's transform to layer. EXPECT_THAT( TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation(chunks.begin(), - PaintInvalidationReason::kPaintProperty), - ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty, - -new_layer_bounds.Location(), base::DoNothing()))); + ElementsAre( + ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty), + ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty, + -new_layer_bounds.Location(), base::DoNothing()))); FinishCycle(*artifact); } TEST_P(RasterInvalidatorTest, ReorderChunks) { auto artifact = TestPaintArtifact().Chunk(0).Chunk(1).Chunk(2).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); FinishCycle(*artifact); @@ -151,16 +150,15 @@ .Chunk(1) .Bounds(IntRect(11, 22, 33, 44)) .Build(); - auto new_chunks = new_artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), new_chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), new_artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); - // Invalidated new chunk 2's old (as chunks[{0, 1]) and new - // (as new_chunks[{0, 2]) bounds. + // Invalidated new chunk 2's old (as artifact->PaintChunks()[1]) and new + // (as new_artifact->PaintChunks()[2]) bounds. EXPECT_THAT( TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation(&chunks[{0, 1}], + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[1], PaintInvalidationReason::kChunkReordered), - ChunkInvalidation(&new_chunks[{0, 2}], + ChunkInvalidation(&new_artifact->PaintChunks()[2], PaintInvalidationReason::kChunkReordered))); FinishCycle(*new_artifact); } @@ -168,8 +166,7 @@ TEST_P(RasterInvalidatorTest, ReorderChunkSubsequences) { auto artifact = TestPaintArtifact().Chunk(0).Chunk(1).Chunk(2).Chunk(3).Chunk(4).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); FinishCycle(*artifact); @@ -183,47 +180,44 @@ .Bounds(IntRect(11, 22, 33, 44)) .Chunk(2) .Build(); - auto new_chunks = new_artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), new_chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), new_artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); - // Invalidated new chunk 3's old (as chunks[{0, 1] and new - // (as new_chunks[{0, 3]) bounds. + // Invalidated new chunk 3's old (as artifact->PaintChunks()[1] and new + // (as new_artifact->PaintChunks()[3]) bounds. // Invalidated new chunk 4's new bounds. Didn't invalidate old bounds because // it's the same as the new bounds. EXPECT_THAT( TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation(&chunks[{0, 1}], + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[1], PaintInvalidationReason::kChunkReordered), - ChunkInvalidation(&new_chunks[{0, 3}], + ChunkInvalidation(&new_artifact->PaintChunks()[3], PaintInvalidationReason::kChunkReordered), - ChunkInvalidation(&new_chunks[{0, 4}], + ChunkInvalidation(&new_artifact->PaintChunks()[4], PaintInvalidationReason::kChunkReordered))); FinishCycle(*new_artifact); } TEST_P(RasterInvalidatorTest, ChunkAppearAndDisappear) { auto artifact = TestPaintArtifact().Chunk(0).Chunk(1).Chunk(2).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); FinishCycle(*artifact); // Chunk 1 and 2 disappeared, 3 and 4 appeared. invalidator_.SetTracksRasterInvalidations(true); auto new_artifact = TestPaintArtifact().Chunk(0).Chunk(3).Chunk(4).Build(); - auto new_chunks = new_artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), new_chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), new_artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); EXPECT_THAT( TrackedRasterInvalidations(), ElementsAre( - ChunkInvalidation(&new_chunks[{0, 1}], + ChunkInvalidation(&new_artifact->PaintChunks()[1], PaintInvalidationReason::kChunkAppeared), - ChunkInvalidation(&new_chunks[{0, 2}], + ChunkInvalidation(&new_artifact->PaintChunks()[2], PaintInvalidationReason::kChunkAppeared), - ChunkInvalidation(&chunks[{0, 1}], + ChunkInvalidation(&artifact->PaintChunks()[1], PaintInvalidationReason::kChunkDisappeared), - ChunkInvalidation(&chunks[{0, 2}], + ChunkInvalidation(&artifact->PaintChunks()[2], PaintInvalidationReason::kChunkDisappeared))); FinishCycle(*new_artifact); } @@ -237,8 +231,7 @@ .Bounds(bounds) .DrawableBounds(drawable_bounds) .Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); FinishCycle(*artifact); @@ -249,38 +242,35 @@ .Bounds(bounds) .DrawableBounds(drawable_bounds) .Build(); - auto new_chunks = new_artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), new_chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), new_artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); // ChunkInvalidation uses the drawable_bounds. We expect raster invalidations // based on drawable_bounds instead of bounds. EXPECT_THAT( TrackedRasterInvalidations(), ElementsAre( - ChunkInvalidation(&new_chunks[{0, 1}], + ChunkInvalidation(&new_artifact->PaintChunks()[1], PaintInvalidationReason::kChunkAppeared), - ChunkInvalidation(&chunks[{0, 1}], + ChunkInvalidation(&artifact->PaintChunks()[1], PaintInvalidationReason::kChunkDisappeared))); FinishCycle(*new_artifact); } TEST_P(RasterInvalidatorTest, ChunkAppearAtEnd) { auto artifact = TestPaintArtifact().Chunk(0).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); FinishCycle(*artifact); invalidator_.SetTracksRasterInvalidations(true); auto new_artifact = TestPaintArtifact().Chunk(0).Chunk(1).Chunk(2).Build(); - auto new_chunks = new_artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), new_chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), new_artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); EXPECT_THAT( TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation(&new_chunks[{0, 1}], + ElementsAre(ChunkInvalidation(&new_artifact->PaintChunks()[1], PaintInvalidationReason::kChunkAppeared), - ChunkInvalidation(&new_chunks[{0, 2}], + ChunkInvalidation(&new_artifact->PaintChunks()[2], PaintInvalidationReason::kChunkAppeared))); FinishCycle(*new_artifact); } @@ -288,24 +278,22 @@ TEST_P(RasterInvalidatorTest, UncacheableChunks) { auto artifact = TestPaintArtifact().Chunk(0).Chunk(1).Uncacheable().Chunk(2).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); FinishCycle(*artifact); invalidator_.SetTracksRasterInvalidations(true); auto new_artifact = TestPaintArtifact().Chunk(0).Chunk(2).Chunk(1).Uncacheable().Build(); - auto new_chunks = new_artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), new_chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), new_artifact, kDefaultLayerBounds, DefaultPropertyTreeState()); EXPECT_THAT( TrackedRasterInvalidations(), ElementsAre( - ChunkInvalidation(&new_chunks[{0, 2}], + ChunkInvalidation(&new_artifact->PaintChunks()[2], PaintInvalidationReason::kChunkUncacheable), - ChunkInvalidation(&chunks[{0, 1}], + ChunkInvalidation(&artifact->PaintChunks()[1], PaintInvalidationReason::kChunkUncacheable))); FinishCycle(*new_artifact); } @@ -327,9 +315,8 @@ .Chunk(2) .Properties(t0(), *clip2, e0()) .Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -343,33 +330,33 @@ ClipPaintPropertyNode::State{&clip2->LocalTransformSpace(), new_clip_rect}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); // Property change in the layer state should not trigger raster invalidation. // |clip2| change should trigger raster invalidation. - EXPECT_THAT(TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation( - &chunks[{0, 2}], PaintInvalidationReason::kPaintProperty))); + EXPECT_THAT( + TrackedRasterInvalidations(), + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[2], + PaintInvalidationReason::kPaintProperty))); invalidator_.SetTracksRasterInvalidations(false); FinishCycle(*artifact); // Change chunk1's properties to use a different property tree state. auto new_artifact1 = TestPaintArtifact() .Chunk(0) - .Properties(chunks[{0, 0}].properties) + .Properties(artifact->PaintChunks()[0].properties) .Chunk(1) - .Properties(chunks[{0, 2}].properties) + .Properties(artifact->PaintChunks()[2].properties) .Chunk(2) - .Properties(chunks[{0, 2}].properties) + .Properties(artifact->PaintChunks()[2].properties) .Build(); - auto new_chunks1 = new_artifact1->Chunks(); invalidator_.SetTracksRasterInvalidations(true); - invalidator_.Generate(base::DoNothing(), new_chunks1, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), new_artifact1, kDefaultLayerBounds, layer_state); EXPECT_THAT( TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation(&new_chunks1[{0, 1}], + ElementsAre(ChunkInvalidation(&new_artifact1->PaintChunks()[1], PaintInvalidationReason::kPaintProperty))); invalidator_.SetTracksRasterInvalidations(false); FinishCycle(*new_artifact1); @@ -390,9 +377,8 @@ .Properties(t0(), *clip1, e0()) .Bounds(EnclosingIntRect(clip_rect.Rect())) .Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -404,7 +390,7 @@ ClipPaintPropertyNode::State{&clip1->LocalTransformSpace(), new_clip_rect1}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); FinishCycle(*artifact); @@ -415,18 +401,18 @@ ClipPaintPropertyNode::State{&clip1->LocalTransformSpace(), new_clip_rect2}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); // |clip1| change should trigger incremental raster invalidation. EXPECT_THAT( TrackedRasterInvalidations(), - ElementsAre(IncrementalInvalidation(&chunks[{0, 1}], + ElementsAre(IncrementalInvalidation(&artifact->PaintChunks()[1], IntRect(-1000, -1000, 2000, 500)), - IncrementalInvalidation(&chunks[{0, 1}], + IncrementalInvalidation(&artifact->PaintChunks()[1], IntRect(-1000, -500, 500, 1000)), - IncrementalInvalidation(&chunks[{0, 1}], + IncrementalInvalidation(&artifact->PaintChunks()[1], IntRect(500, -500, 500, 1000)), - IncrementalInvalidation(&chunks[{0, 1}], + IncrementalInvalidation(&artifact->PaintChunks()[1], IntRect(-1000, 500, 2000, 500)))); invalidator_.SetTracksRasterInvalidations(false); FinishCycle(*artifact); @@ -438,12 +424,12 @@ new_clip_rect3}); invalidator_.SetTracksRasterInvalidations(true); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); // |clip1| change should trigger incremental raster invalidation. EXPECT_THAT(TrackedRasterInvalidations(), ElementsAre(IncrementalInvalidation( - &chunks[{0, 1}], IntRect(500, -500, 500, 1000)))); + &artifact->PaintChunks()[1], IntRect(500, -500, 500, 1000)))); invalidator_.SetTracksRasterInvalidations(false); FinishCycle(*artifact); } @@ -462,9 +448,8 @@ .Bounds(EnclosingIntRect(clip_rect.Rect())) .SetRasterEffectOutset(RasterEffectOutset::kWholePixel) .Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -472,13 +457,13 @@ FloatRoundedRect new_clip_rect(-2000, -2000, 4000, 4000); clip->Update(c0(), ClipPaintPropertyNode::State{&t0(), new_clip_rect}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); auto mapper = [](IntRect& r) { r.Inflate(1); }; EXPECT_THAT( TrackedRasterInvalidations(), ElementsAre(ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty, + &artifact->PaintChunks()[0], PaintInvalidationReason::kPaintProperty, -kDefaultLayerBounds.Location(), base::BindRepeating(mapper)))); invalidator_.SetTracksRasterInvalidations(false); FinishCycle(*artifact); @@ -496,9 +481,8 @@ PropertyTreeState layer_state = DefaultPropertyTreeState(); auto artifact = TestPaintArtifact().Chunk(0).Properties(*t2, *c1, e0()).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -508,11 +492,12 @@ t1->Update(t0(), TransformPaintPropertyNode::State{FloatSize(-10, -20)}); t2->Update(*t1, TransformPaintPropertyNode::State{FloatSize(10, 20)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); - EXPECT_THAT(TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty))); + EXPECT_THAT( + TrackedRasterInvalidations(), + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty))); invalidator_.SetTracksRasterInvalidations(false); } @@ -532,9 +517,8 @@ PropertyTreeState layer_state = DefaultPropertyTreeState(); auto artifact = TestPaintArtifact().Chunk(0).Properties(*t2, *c1, e0()).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -543,7 +527,7 @@ t1->Update(t0(), TransformPaintPropertyNode::State{FloatSize(-10, -20)}); t2->Update(*t1, TransformPaintPropertyNode::State{FloatSize(10, 20)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); FinishCycle(*artifact); @@ -561,9 +545,8 @@ .Chunk(1) .Properties(*transform1, c0(), e0()) .Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -573,7 +556,7 @@ *layer_transform->Parent(), TransformPaintPropertyNode::State{TransformationMatrix().Scale(10)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); FinishCycle(*artifact); @@ -587,7 +570,7 @@ transform0->Update(*new_layer_transform, TransformPaintPropertyNode::State{ transform0->Translation2D()}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); FinishCycle(*artifact); @@ -598,7 +581,7 @@ transform0->Update(layer_state.Transform(), TransformPaintPropertyNode::State{ transform0->Translation2D()}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); FinishCycle(*artifact); @@ -613,19 +596,20 @@ TransformPaintPropertyNode::State{ transform1->Translation2D() + FloatSize(-20, -30)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); auto mapper0 = [](IntRect& r) { r.Move(10, 20); }; auto mapper1 = [](IntRect& r) { r.Move(30, 50); }; EXPECT_THAT( TrackedRasterInvalidations(), - ElementsAre( - ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty, - -kDefaultLayerBounds.Location(), base::BindRepeating(mapper0)), - ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty, - -kDefaultLayerBounds.Location(), base::BindRepeating(mapper1)))); + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty, + -kDefaultLayerBounds.Location(), + base::BindRepeating(mapper0)), + ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty, + -kDefaultLayerBounds.Location(), + base::BindRepeating(mapper1)))); invalidator_.SetTracksRasterInvalidations(false); FinishCycle(*artifact); } @@ -639,9 +623,8 @@ .Chunk(0) .Properties(*chunk_transform, c0(), e0()) .Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -654,7 +637,7 @@ .Scale(1.0000001) .Rotate(0.0000001)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); FinishCycle(*artifact); @@ -669,7 +652,7 @@ .Translate(0.0000001, -0.0000001) .Scale(1.0000001) .Rotate(0.0000001)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); invalidated = !TrackedRasterInvalidations().IsEmpty(); FinishCycle(*artifact); @@ -689,9 +672,8 @@ .Properties(*chunk_transform, c0(), e0()) .Bounds(chunk_bounds) .Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -701,7 +683,7 @@ layer_state.Transform(), TransformPaintPropertyNode::State{TransformationMatrix().Scale(2e-6)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_FALSE(TrackedRasterInvalidations().IsEmpty()); invalidator_.SetTracksRasterInvalidations(false); @@ -713,7 +695,7 @@ TransformPaintPropertyNode::State{ TransformationMatrix().Scale(2e-6 + 1e-15)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); invalidator_.SetTracksRasterInvalidations(false); @@ -730,9 +712,8 @@ PropertyTreeState layer_state = DefaultPropertyTreeState(); auto artifact = TestPaintArtifact().Chunk(0).Properties(*t2, c0(), *e1).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -742,13 +723,13 @@ t1->Update(t0(), TransformPaintPropertyNode::State{FloatSize(-10, -20)}); t2->Update(*t1, TransformPaintPropertyNode::State{FloatSize(10, 20)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); auto mapper = [](IntRect& r) { r.Inflate(60); }; EXPECT_THAT( TrackedRasterInvalidations(), ElementsAre(ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty, + &artifact->PaintChunks()[0], PaintInvalidationReason::kPaintProperty, -kDefaultLayerBounds.Location(), base::BindRepeating(mapper)))); invalidator_.SetTracksRasterInvalidations(false); FinishCycle(*artifact); @@ -768,9 +749,8 @@ PropertyTreeState layer_state = DefaultPropertyTreeState(); auto artifact = TestPaintArtifact().Chunk(0).Properties(*t2, c0(), *e1).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -779,7 +759,7 @@ t1->Update(t0(), TransformPaintPropertyNode::State{FloatSize(-10, -20)}); t2->Update(*t1, TransformPaintPropertyNode::State{FloatSize(10, 20)}); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); EXPECT_TRUE(TrackedRasterInvalidations().IsEmpty()); FinishCycle(*artifact); @@ -796,9 +776,8 @@ PropertyTreeState layer_state = DefaultPropertyTreeState(); PropertyTreeStateOrAlias chunk_state(t0(), c0(), *alias_effect); auto artifact = TestPaintArtifact().Chunk(0).Properties(chunk_state).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -809,11 +788,12 @@ // We expect to get invalidations since the effect unaliased effect is // actually different now. - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); - EXPECT_THAT(TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty))); + EXPECT_THAT( + TrackedRasterInvalidations(), + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty))); FinishCycle(*artifact); } @@ -829,9 +809,8 @@ PropertyTreeState layer_state = DefaultPropertyTreeState(); PropertyTreeStateOrAlias chunk_state(t0(), c0(), *alias_effect_2); auto artifact = TestPaintArtifact().Chunk(0).Properties(chunk_state).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -843,11 +822,12 @@ // We expect to get invalidations since the effect unaliased effect is // actually different now. - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); - EXPECT_THAT(TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty))); + EXPECT_THAT( + TrackedRasterInvalidations(), + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty))); FinishCycle(*artifact); } @@ -864,9 +844,8 @@ PropertyTreeState layer_state = PropertyTreeState::Root(); PropertyTreeState chunk_state(t0(), c0(), *e1); auto artifact = TestPaintArtifact().Chunk(0).Properties(chunk_state).Build(); - auto chunks = artifact->Chunks(); - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); FinishCycle(*artifact); @@ -877,11 +856,12 @@ // We expect to get invalidations since the effect unaliased effect is // actually different now. - invalidator_.Generate(base::DoNothing(), chunks, kDefaultLayerBounds, + invalidator_.Generate(base::DoNothing(), artifact, kDefaultLayerBounds, layer_state); - EXPECT_THAT(TrackedRasterInvalidations(), - ElementsAre(ChunkInvalidation( - chunks.begin(), PaintInvalidationReason::kPaintProperty))); + EXPECT_THAT( + TrackedRasterInvalidations(), + ElementsAre(ChunkInvalidation(&artifact->PaintChunks()[0], + PaintInvalidationReason::kPaintProperty))); FinishCycle(*artifact); }
diff --git a/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.cc b/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.cc index 2794082..ce7e7d6a 100644 --- a/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.cc +++ b/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.cc
@@ -471,13 +471,13 @@ } } -void RTCVideoDecoderAdapter::OnDecodeDone(media::DecodeStatus status) { - DVLOG(3) << __func__ << "(" << status << ")"; +void RTCVideoDecoderAdapter::OnDecodeDone(media::Status status) { + DVLOG(3) << __func__ << "(" << status.code() << ")"; DCHECK(media_task_runner_->BelongsToCurrentThread()); outstanding_decode_requests_--; - if (status == media::DecodeStatus::DECODE_ERROR) { + if (!status.is_ok() && status.code() != media::StatusCode::kAborted) { DVLOG(2) << "Entering permanent error state"; UMA_HISTOGRAM_ENUMERATION("Media.RTCVideoDecoderError", media::VideoDecodeAccelerator::PLATFORM_FAILURE, @@ -583,8 +583,8 @@ media::DecoderBuffer::CreateEOSBuffer(), WTF::BindRepeating( [](FlushDoneCB flush_success, FlushDoneCB flush_fail, - media::DecodeStatus status) { - if (status == media::DecodeStatus::OK) + media::Status status) { + if (status.is_ok()) std::move(flush_success).Run(); else std::move(flush_fail).Run();
diff --git a/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.h b/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.h index ded3110..82ab3ae 100644 --- a/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.h +++ b/third_party/blink/renderer/platform/peerconnection/rtc_video_decoder_adapter.h
@@ -104,7 +104,7 @@ static void OnInitializeDone(base::OnceCallback<void(bool)> cb, media::Status status); void DecodeOnMediaThread(); - void OnDecodeDone(media::DecodeStatus status); + void OnDecodeDone(media::Status status); void OnOutput(scoped_refptr<media::VideoFrame> frame); bool ShouldReinitializeForSettingHDRColorSpace(
diff --git a/third_party/blink/renderer/platform/runtime_enabled_features.json5 b/third_party/blink/renderer/platform/runtime_enabled_features.json5 index 8825f43..7421c2f 100644 --- a/third_party/blink/renderer/platform/runtime_enabled_features.json5 +++ b/third_party/blink/renderer/platform/runtime_enabled_features.json5
@@ -2150,6 +2150,12 @@ status: "experimental", }, { + name: "WebXRMultiGpu", + depends_on: ["WebXR"], + // Enabled when blink::features::kWebXrMultiGpu is enabled. + status: "experimental", + }, + { name: "WebXRPlaneDetection", depends_on: ["WebXRARModule"], status: "experimental",
diff --git a/third_party/blink/renderer/platform/testing/test_paint_artifact.cc b/third_party/blink/renderer/platform/testing/test_paint_artifact.cc index f9263c3a..29353d7 100644 --- a/third_party/blink/renderer/platform/testing/test_paint_artifact.cc +++ b/third_party/blink/renderer/platform/testing/test_paint_artifact.cc
@@ -131,14 +131,8 @@ } scoped_refptr<PaintArtifact> TestPaintArtifact::Build() { - auto artifact = base::AdoptRef(new PaintArtifact()); - if (paint_chunks_.IsEmpty()) { - DCHECK(display_item_list_.IsEmpty()); - } else { - artifact->AddSegment(std::move(paint_chunks_), - std::move(display_item_list_)); - } - return artifact; + return PaintArtifact::Create(std::move(display_item_list_), + std::move(paint_chunks_)); } FakeDisplayItemClient& TestPaintArtifact::NewClient() {
diff --git a/third_party/blink/renderer/platform/wtf/allocator/partitions.cc b/third_party/blink/renderer/platform/wtf/allocator/partitions.cc index 03d05534d..ca2b037 100644 --- a/third_party/blink/renderer/platform/wtf/allocator/partitions.cc +++ b/third_party/blink/renderer/platform/wtf/allocator/partitions.cc
@@ -75,8 +75,8 @@ // - BUILDFLAG(USE_PARTITION_ALLOC_AS_MALLOC): Only one thread cache at a time // is supported, in this case it is already claimed by malloc(). #if DCHECK_IS_ON() && !BUILDFLAG(USE_PARTITION_ALLOC_AS_MALLOC) - fast_malloc_allocator.init(base::PartitionAllocatorAlignment::kRegular, - true /* with_thread_cache */); + fast_malloc_allocator.init({base::PartitionOptions::Alignment::kRegular, + base::PartitionOptions::ThreadCache::kEnabled}); #else fast_malloc_allocator.init(); #endif
diff --git a/third_party/blink/tools/blinkpy/web_tests/controllers/manager_unittest.py b/third_party/blink/tools/blinkpy/web_tests/controllers/manager_unittest.py index 9cacb9e..02a9a77 100644 --- a/third_party/blink/tools/blinkpy/web_tests/controllers/manager_unittest.py +++ b/third_party/blink/tools/blinkpy/web_tests/controllers/manager_unittest.py
@@ -136,7 +136,7 @@ port = host.port_factory.get('test-mac-mac10.10') tests = ['failures/expected/crash.html'] expectations = test_expectations.TestExpectations(port) - run_results = TestRunResults(expectations, len(tests)) + run_results = TestRunResults(expectations, len(tests), None) manager = get_manager() manager._look_for_new_crash_logs(run_results, time.time())
diff --git a/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink.py b/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink.py index 8953705..0b00a77 100644 --- a/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink.py +++ b/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink.py
@@ -168,5 +168,13 @@ # 'startTime': result.start_time 'tags': self._tags(result), 'testId': result.test_name, + + # testLocation is where the test is defined. It is used to find + # the associated component/team/os information in flakiness and + # disabled-test dashboards. + 'testLocation': { + 'fileName': + '//third_party/blink/web_tests/' + result.test_name, + }, } self._send({'testResults': [r]})
diff --git a/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink_unittest.py b/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink_unittest.py index 881b4340..74e5a8d 100644 --- a/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink_unittest.py +++ b/third_party/blink/tools/blinkpy/web_tests/controllers/test_result_sink_unittest.py
@@ -84,6 +84,16 @@ self.assertEqual(sent_data['status'], 'CRASH') self.assertEqual(sent_data['duration'], '123.456s') + def test_test_location(self): + tr = test_results.TestResult('') + prefix = '//third_party/blink/web_tests/' + sink = lambda tr: self.sink(True, tr)['testLocation']['fileName'] + + tr.test_name = "test-name" + self.assertEqual(sink(tr), prefix + 'test-name') + tr.test_name = "///test-name" + self.assertEqual(sink(tr), prefix + '///test-name') + def test_device_failure(self): tr = test_results.TestResult(test_name='test-name') tr.type = ResultType.Failure
diff --git a/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner.py b/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner.py index caad148..b76bc91 100644 --- a/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner.py +++ b/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner.py
@@ -91,7 +91,9 @@ test_run_results = TestRunResults( self._expectations, - len(test_inputs) + len(tests_to_skip)) + len(test_inputs) + len(tests_to_skip), + self._test_result_sink, + ) self._current_run_results = test_run_results self._printer.num_tests = len(test_inputs) self._printer.num_completed = 0 @@ -225,8 +227,6 @@ result.test_name, result.type) expectation_string = ' '.join( self._expectations.get_expectations(result.test_name).results) - if self._test_result_sink: - self._test_result_sink.sink(expected, result) if result.device_failed: self._printer.print_finished_test(self._port, result, False,
diff --git a/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner_unittest.py b/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner_unittest.py index bc8567be..a849ec2a 100644 --- a/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner_unittest.py +++ b/third_party/blink/tools/blinkpy/web_tests/controllers/web_test_runner_unittest.py
@@ -27,6 +27,7 @@ # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +import mock import sys import unittest @@ -120,8 +121,8 @@ TestInput(test_name, timeout_ms=6000) for test_name in test_names ] - run_results = TestRunResults( - TestExpectations(runner._port), len(test_names)) + run_results = TestRunResults(TestExpectations(runner._port), + len(test_names), None) run_results.unexpected_failures = 100 run_results.unexpected_crashes = 50 run_results.unexpected_timeouts = 50 @@ -153,7 +154,7 @@ expectations = TestExpectations(runner._port) runner._expectations = expectations - run_results = TestRunResults(expectations, 1) + run_results = TestRunResults(expectations, 1, None) result = TestResult( test_name=test, failures=[ @@ -165,12 +166,48 @@ self.assertEqual(1, run_results.expected) self.assertEqual(0, run_results.unexpected) - run_results = TestRunResults(expectations, 1) + run_results = TestRunResults(expectations, 1, None) result = TestResult(test_name=test, failures=[], reftest_type=['==']) runner._update_summary_with_result(run_results, result) self.assertEqual(0, run_results.expected) self.assertEqual(1, run_results.unexpected) + def test_skipped_tests_are_sinked(self): + runner = self._runner() + runner._options.derived_batch_size = 1 + runner._options.must_use_derived_batch_size = True + with mock.patch.object(runner, "_test_result_sink") as rdb: + runner.run_tests( + TestExpectations(runner._port), + [], + tests_to_skip=['skips/image.html'], + num_workers=1, + retry_attempt=0, + ) + rdb.sink.assert_called_with( + True, TestResult(test_name='skips/image.html')) + + def test_results_are_sinked(self): + runner = self._runner() + runner._options.derived_batch_size = 1 + runner._options.must_use_derived_batch_size = True + test_names = ['passes/text.html', 'passes/image.html'] + test_inputs = [ + TestInput(test_name, timeout_ms=6000) for test_name in test_names + ] + with mock.patch.object(runner, "_test_result_sink") as rdb: + runner.run_tests( + TestExpectations(runner._port), + test_inputs, + tests_to_skip=[], + num_workers=1, + retry_attempt=0, + ) + rdb.sink.assert_has_calls( + '', [True, TestResult(test_name='passes/text.html')]) + rdb.sink.assert_has_calls( + '', [True, TestResult(test_name='passes/images.html')]) + class SharderTests(unittest.TestCase):
diff --git a/third_party/blink/tools/blinkpy/web_tests/models/test_run_results.py b/third_party/blink/tools/blinkpy/web_tests/models/test_run_results.py index 666db5e..9a9b8827 100644 --- a/third_party/blink/tools/blinkpy/web_tests/models/test_run_results.py +++ b/third_party/blink/tools/blinkpy/web_tests/models/test_run_results.py
@@ -45,10 +45,11 @@ class TestRunResults(object): - def __init__(self, expectations, num_tests): + def __init__(self, expectations, num_tests, result_sink): self.total = num_tests self.remaining = self.total self.expectations = expectations + self.result_sink = result_sink # Various counters: self.expected = 0 @@ -88,6 +89,8 @@ result_type_for_stats = test_result.type self.tests_by_expectation[result_type_for_stats].add( test_result.test_name) + if self.result_sink: + self.result_sink.sink(expected, test_result) self.results_by_name[test_result.test_name] = test_result if test_result.type != ResultType.Skip:
diff --git a/third_party/blink/tools/blinkpy/web_tests/models/test_run_results_unittest.py b/third_party/blink/tools/blinkpy/web_tests/models/test_run_results_unittest.py index 86bffce1..64e7667 100644 --- a/third_party/blink/tools/blinkpy/web_tests/models/test_run_results_unittest.py +++ b/third_party/blink/tools/blinkpy/web_tests/models/test_run_results_unittest.py
@@ -26,6 +26,7 @@ # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +import mock import unittest from blinkpy.common.host_mock import MockHost @@ -64,7 +65,7 @@ for test in extra_skipped_tests: extra_expectations += '\n%s [ Skip ]' % test expectations.merge_raw_expectations(extra_expectations) - return test_run_results.TestRunResults(expectations, len(tests)) + return test_run_results.TestRunResults(expectations, len(tests), None) def summarized_results(port, @@ -207,6 +208,25 @@ only_include_failing=only_include_failing) +class RunResultsWithSinkTest(unittest.TestCase): + def setUp(self): + expectations = test_expectations.TestExpectations( + MockHost().port_factory.get(port_name='test')) + self.results = test_run_results.TestRunResults(expectations, 1, None) + self.test = get_result('failures/expected/text.html', + ResultType.Timeout, + run_time=1) + + def testAddWithSink(self): + self.results.result_sink = mock.Mock() + self.results.add(self.test, False, False) + self.results.result_sink.sink.assert_called_with(False, self.test) + + def testAddWithoutSink(self): + self.results.result_sink = None + self.results.add(self.test, False, False) + + class InterpretTestFailuresTest(unittest.TestCase): def setUp(self): host = MockHost() @@ -392,14 +412,15 @@ def test_timeout_then_unexpected_pass(self): test_name = 'failures/expected/text.html' expectations = test_expectations.TestExpectations(self.port) - initial_results = test_run_results.TestRunResults(expectations, 1) + initial_results = test_run_results.TestRunResults( + expectations, 1, None) initial_results.add( get_result(test_name, ResultType.Timeout, run_time=1), False, False) all_retry_results = [ - test_run_results.TestRunResults(expectations, 1), - test_run_results.TestRunResults(expectations, 1), - test_run_results.TestRunResults(expectations, 1) + test_run_results.TestRunResults(expectations, 1, None), + test_run_results.TestRunResults(expectations, 1, None), + test_run_results.TestRunResults(expectations, 1, None) ] all_retry_results[0].add( get_result(test_name, ResultType.Failure, run_time=0.1), False, @@ -480,13 +501,14 @@ def test_summarized_results_flaky_pass_after_first_retry(self): test_name = 'passes/text.html' expectations = test_expectations.TestExpectations(self.port) - initial_results = test_run_results.TestRunResults(expectations, 1) + initial_results = test_run_results.TestRunResults( + expectations, 1, None) initial_results.add( get_result(test_name, ResultType.Crash), False, False) all_retry_results = [ - test_run_results.TestRunResults(expectations, 1), - test_run_results.TestRunResults(expectations, 1), - test_run_results.TestRunResults(expectations, 1) + test_run_results.TestRunResults(expectations, 1, None), + test_run_results.TestRunResults(expectations, 1, None), + test_run_results.TestRunResults(expectations, 1, None) ] all_retry_results[0].add( get_result(test_name, ResultType.Timeout), False, False) @@ -509,14 +531,17 @@ def test_summarized_results_with_iterations(self): test_name = 'passes/text.html' expectations = test_expectations.TestExpectations(self.port) - initial_results = test_run_results.TestRunResults(expectations, 3) + initial_results = test_run_results.TestRunResults( + expectations, 3, None) initial_results.add( get_result(test_name, ResultType.Crash), False, False) initial_results.add( get_result(test_name, ResultType.Failure), False, False) initial_results.add( get_result(test_name, ResultType.Timeout), False, False) - all_retry_results = [test_run_results.TestRunResults(expectations, 2)] + all_retry_results = [ + test_run_results.TestRunResults(expectations, 2, None) + ] all_retry_results[0].add( get_result(test_name, ResultType.Failure), False, False) all_retry_results[0].add(
diff --git a/third_party/blink/web_tests/TestExpectations b/third_party/blink/web_tests/TestExpectations index 82623e5..2a7ef50 100644 --- a/third_party/blink/web_tests/TestExpectations +++ b/third_party/blink/web_tests/TestExpectations
@@ -288,7 +288,6 @@ crbug.com/1045668 external/wpt/css/css-sizing/aspect-ratio/abspos-013.tentative.html [ Failure ] crbug.com/1045668 external/wpt/css/css-sizing/aspect-ratio/flex-aspect-ratio-013.tentative.html [ Failure ] crbug.com/1045668 external/wpt/css/css-sizing/aspect-ratio/flex-aspect-ratio-014.tentative.html [ Failure ] -crbug.com/1045668 external/wpt/css/css-sizing/aspect-ratio/flex-aspect-ratio-024.tentative.html [ Failure ] crbug.com/1045668 external/wpt/css/css-sizing/aspect-ratio/replaced-element-016.tentative.html [ Failure ] crbug.com/1045668 external/wpt/css/css-sizing/aspect-ratio/replaced-element-021.tentative.html [ Failure ] @@ -1047,7 +1046,6 @@ crbug.com/1058792 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/composited-under-clip-under-multicol.html [ Failure Crash ] crbug.com/996655 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/going-out-of-flow-after-spanner.html [ Crash Failure Pass ] crbug.com/829028 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/multicol-clip-002.xht [ Failure ] -crbug.com/1079031 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/multicol-contained-absolute.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/multicol-containing-002.xht [ Crash Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/multicol-fill-auto-002.xht [ Crash Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/multicol-fill-balance-001.xht [ Crash Failure ] @@ -1075,7 +1073,6 @@ crbug.com/829028 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/multicol-width-004.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/external/wpt/css/css-multicol/multicol-width-small-001.xht [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/abspos-after-break-after.html [ Failure ] -crbug.com/1066616 virtual/layout_ng_block_frag/fast/multicol/abspos-in-overflow-hidden-in-2nd-column.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/abspos-new-width-rebalance.html [ Crash Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/border-radius-clipped-layer.html [ Failure ] crbug.com/1066616 virtual/layout_ng_block_frag/fast/multicol/border-radius-clipped-layer-second-column.html [ Failure ] @@ -1107,7 +1104,6 @@ crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/float-margin-at-row-boundary-fixed-multicol-height.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/float-moved-by-child-line-and-unbreakable.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/float-paginate-empty-lines.html [ Failure ] -crbug.com/1061423 virtual/layout_ng_block_frag/fast/multicol/float-truncation.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/float-with-margin-moved-by-child-block-and-unbreakable.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/float-with-margin-moved-by-child-block.html [ Failure Timeout ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/float-with-margin-moved-by-child-line-and-unbreakable.html [ Failure ] @@ -1143,7 +1139,6 @@ crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/out-of-flow/abspos-auto-position.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/out-of-flow/abspos-auto-position-on-line.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/out-of-flow/abspos-auto-position-on-line-rtl.html [ Failure ] -crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/out-of-flow/abspos-auto-position-small-on-line-at-boundary.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/out-of-flow/nested-multicol.html [ Failure ] crbug.com/1066616 virtual/layout_ng_block_frag/fast/multicol/overflow-content.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fast/multicol/positioned-outside-of-columns.html [ Crash Failure ] @@ -1181,7 +1176,6 @@ crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/vertical-rl/client-rects-crossing-boundaries-nested.html [ Failure ] crbug.com/1058792 virtual/layout_ng_block_frag/fast/multicol/vertical-rl/composited-relpos-overlapping-will-change.html [ Failure ] crbug.com/1061423 virtual/layout_ng_block_frag/fast/multicol/vertical-rl/float-truncation.html [ Failure ] -crbug.com/1061423 virtual/layout_ng_block_frag/fast/multicol/vertical-lr/float-truncation.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/vertical-rl/nested-columns.html [ Crash Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/vertical-rl/offset-top-and-left-at-boundaries-nested.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/vertical-rl/offset-top-and-left-nested.html [ Failure ] @@ -1189,12 +1183,10 @@ crbug.com/829028 virtual/layout_ng_block_frag/fast/multicol/widows.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fragmentation/abspos-after-forced-break.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fragmentation/auto-scrollbar-shrink-to-fit.html [ Failure ] -crbug.com/829028 virtual/layout_ng_block_frag/fragmentation/change-fragmentainer-height-inline-float.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fragmentation/content-preceding-first-fragmentainer.html [ Crash Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fragmentation/float-after-forced-break.html [ Failure ] crbug.com/829028 virtual/layout_ng_block_frag/fragmentation/overflow-crossing-boundary.html [ Failure ] crbug.com/1079031 virtual/layout_ng_block_frag/fragmentation/relayout-abspos.html [ Failure ] -crbug.com/829028 virtual/layout_ng_block_frag/fragmentation/remove-unbreakable-block-in-line-float.html [ Failure ] ### With LayoutNGFragmentTraversal (and LayoutNGFragmentItem) enabled: @@ -6373,6 +6365,7 @@ crbug.com/1057822 http/tests/misc/synthetic-gesture-initiated-in-cross-origin-frame.html [ Pass Failure Crash ] crbug.com/1057807 http/tests/misc/destroy-middle-click-locked-target-crash.html [ Pass Timeout ] +crbug.com/1131977 [ Mac ] http/tests/misc/hover-state-recomputed-on-main-frame.html [ Timeout ] crbug.com/1057351 virtual/threaded-no-composited-antialiasing/animations/responsive/interpolation/offset-rotate-responsive.html [ Pass Failure ] crbug.com/1057351 virtual/threaded-no-composited-antialiasing/animations/stability/empty-keyframes.html [ Pass Failure ]
diff --git a/third_party/blink/web_tests/external/wpt/css/css-break/out-of-flow-in-multicolum-001-ref.html b/third_party/blink/web_tests/external/wpt/css/css-break/out-of-flow-in-multicolum-001-ref.html new file mode 100644 index 0000000..7b6a3c5 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-break/out-of-flow-in-multicolum-001-ref.html
@@ -0,0 +1,5 @@ +<!DOCTYPE html> +<link rel="author" title="Benjamin Beaudry" href="mailto:bebeaudr@microsoft.com"> +<p>The abs element should be split equally into the two columns - no red!</p> +<div style="float:left; border-bottom:10px solid green; width:42px; height: 30px; background:gray;"></div> +<div style="float:left; margin-left: 16px; border-top:10px solid green; width:42px; height: 30px; background:gray;"></div>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-break/out-of-flow-in-multicolumn-001.html b/third_party/blink/web_tests/external/wpt/css/css-break/out-of-flow-in-multicolumn-001.html new file mode 100644 index 0000000..148f3946 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-break/out-of-flow-in-multicolumn-001.html
@@ -0,0 +1,39 @@ +<!DOCTYPE html> +<link rel="author" title="Benjamin Beaudry" href="mailto:bebeaudr@microsoft.com"> +<link rel="help" href="href=https://www.w3.org/TR/css-break-3/#break-decoration"> +<link rel="match" href="out-of-flow-in-multicolum-001-ref.html"> + +<p>The abs element should be split equally into the two columns - no red!</p> +<style> + #multicol { + column-count: 2; + column-fill: auto; + column-gap: 16px; + column-rule:16px white solid; + width: 100px; + height: 40px; + background: gray; + } + + .abs { + position: absolute; + top: 0px; + width: 100%; + height: 20px; + background: green; + } + + .below-abs { + height: 20px; + background: red; + } +</style> +<div id="container"> + <div id="multicol"> + <div style="width:100px; height:30px;"></div> + <div style="position: relative;"> + <div class="below-abs"></div> + <div class="abs"></div> + </div> + </div> +</div> \ No newline at end of file
diff --git a/third_party/blink/web_tests/external/wpt/css/css-sizing/aspect-ratio/flex-aspect-ratio-024.tentative.html b/third_party/blink/web_tests/external/wpt/css/css-sizing/aspect-ratio/flex-aspect-ratio-024.tentative.html index b0cefd57..ebac88c 100644 --- a/third_party/blink/web_tests/external/wpt/css/css-sizing/aspect-ratio/flex-aspect-ratio-024.tentative.html +++ b/third_party/blink/web_tests/external/wpt/css/css-sizing/aspect-ratio/flex-aspect-ratio-024.tentative.html
@@ -7,6 +7,6 @@ <p>Test passes if there is a filled green square and <strong>no red</strong>.</p> -<div style="display: inline-flex; flex-direction: column; height: 100px;"> +<div style="display: inline-flex; flex-direction: column; flex-wrap: wrap; height: 100px;"> <img src="support/20x50-green.png" style="aspect-ratio: 1/1; min-height: 0; height: 50px; flex: 1;"> </div>
diff --git a/third_party/blink/web_tests/external/wpt/html/browsers/browsing-the-web/read-text/load-text-plain-expected.txt b/third_party/blink/web_tests/external/wpt/html/browsers/browsing-the-web/read-text/load-text-plain-expected.txt new file mode 100644 index 0000000..aecbfdd --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/html/browsers/browsing-the-web/read-text/load-text-plain-expected.txt
@@ -0,0 +1,6 @@ +This is a testharness.js-based test. +FAIL Checking document metadata for text file assert_equals: expected "BackCompat" but got "CSS1Compat" +PASS Checking DOM for text file +PASS Checking contents for text file +Harness: the test ran to completion. +
diff --git a/third_party/blink/web_tests/external/wpt/resources/chromium/webxr-test.js b/third_party/blink/web_tests/external/wpt/resources/chromium/webxr-test.js index a1f57ac0..800c0a4 100644 --- a/third_party/blink/web_tests/external/wpt/resources/chromium/webxr-test.js +++ b/third_party/blink/web_tests/external/wpt/resources/chromium/webxr-test.js
@@ -217,8 +217,13 @@ // Only handles asynchronous calls to makeXrCompatible. Synchronous calls are // not supported in Javascript. makeXrCompatible() { + if (this.runtimes_.length == 0) { + return Promise.resolve({ + xrCompatibleResult: device.mojom.XrCompatibleResult.kNoDeviceAvailable + }); + } return Promise.resolve({ - xr_compatible_result: device.mojom.XrCompatibleResult.kAlreadyCompatible + xrCompatibleResult: device.mojom.XrCompatibleResult.kAlreadyCompatible }); } }
diff --git a/third_party/blink/web_tests/external/wpt/webxr/webGLCanvasContext_create_xrcompatible.https.html b/third_party/blink/web_tests/external/wpt/webxr/webGLCanvasContext_create_xrcompatible.https.html index 33e54865..2b3a1fcc 100644 --- a/third_party/blink/web_tests/external/wpt/webxr/webGLCanvasContext_create_xrcompatible.https.html +++ b/third_party/blink/web_tests/external/wpt/webxr/webGLCanvasContext_create_xrcompatible.https.html
@@ -6,6 +6,15 @@ <script src="resources/webxr_test_constants.js"></script> <canvas id="webgl-canvas"></canvas> <script> + xr_promise_test("Creating a webglCanvasContext with no device", + (t) => { + let webglCanvas = document.createElement('canvas'); + let gl = webglCanvas.getContext('webgl'); + + assert_false(gl.getContextAttributes().xrCompatible); + return promise_rejects_dom(t, "InvalidStateError", gl.makeXRCompatible()); + }); + xr_promise_test("An XR-compatible webglCanvasContext can be created", (t) => { let gl = null; @@ -26,6 +35,5 @@ assert_true(offscreenGl.getContextAttributes().xrCompatible); }); }); - </script> </body>
diff --git a/third_party/blink/web_tests/external/wpt/webxr/webxr_feature_policy.https.html b/third_party/blink/web_tests/external/wpt/webxr/webxr_feature_policy.https.html index 7f3d03b..b493ec7 100644 --- a/third_party/blink/web_tests/external/wpt/webxr/webxr_feature_policy.https.html +++ b/third_party/blink/web_tests/external/wpt/webxr/webxr_feature_policy.https.html
@@ -78,4 +78,20 @@ }); }); + +xr_promise_test( +"Validate xr compatibility requests without xr-spatial-tracking policy", +(t) => { + let canvas = document.createElement('canvas'); + let gl = canvas.getContext('webgl', {xrCompatible: true}); + + t.step(() => { + assert_false(gl.getContextAttributes().xrCompatible, + "xrCompatibility shouldn't be set when requested without feature policy"); + }); + + return promise_rejects_dom(t, "SecurityError", + gl.makeXRCompatible(), + "makeXRCompatible should reject without feature policy"); +}); </script>
diff --git a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-display-none.html b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-display-none.html index b23e2c352..9e48e93 100644 --- a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-display-none.html +++ b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-display-none.html
@@ -13,7 +13,7 @@ select { width: 200px; font: 10px Ahem; - -webkit-appearance: none; + appearance: none; background-color: white; } select::-webkit-scrollbar {
diff --git a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-hover-expected.png b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-hover-expected.png new file mode 100644 index 0000000..1310bea --- /dev/null +++ b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-hover-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-hover.html b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-hover.html new file mode 100644 index 0000000..95eae899 --- /dev/null +++ b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-thumb-hover.html
@@ -0,0 +1,98 @@ +<!DOCTYPE html> +<html> +<head> +<script> + window.enablePixelTesting = true; +</script> +<script src="../resources/picker-common.js"></script> +<script src="../resources/common.js"></script> +<style> + select:focus { + outline-width: 0; + } + select { + width: 200px; + font: 10px Ahem; + -webkit-appearance: none; + background-color: white; + } + select::-webkit-scrollbar { + width: 200px; + } + select::-webkit-scrollbar-track { + background: orange; + } + select::-webkit-scrollbar-corner { + background: yellow; + } + + select::-webkit-scrollbar-thumb { + background: gray; + } + select::-webkit-scrollbar-thumb:hover { + background: green; + } + option:hover{ + background-color: green; + } +</style> +</head> +<body> +<select id='menu'> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> +</select> +<script> +let menu = document.getElementById('menu'); +function mouseMoveToScrollbar() { + return new Promise(function(resolve, reject) { + if (window.chrome && chrome.gpuBenchmarking) { + let selectElement = internals.pagePopupWindow.global.picker._selectElement; + let innerSelectRect = selectElement.getBoundingClientRect(); + let scrollbarX = innerSelectRect.x + innerSelectRect.width - 10; + let scrollbarY = innerSelectRect.y + 50; + chrome.gpuBenchmarking.pointerActionSequence( + [{ + source: 'mouse', + actions: [{name: 'pointerMove', x: scrollbarX, y: scrollbarY}] + }], + resolve); + } else { + reject(); + } + }); +} +openPicker(menu, ()=>{ + mouseMoveToScrollbar().then(()=>{ + testRunner.notifyDone() + }) +}) +testRunner.waitUntilDone() +</script> +</body> +</html> \ No newline at end of file
diff --git a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-display-none.html b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-display-none.html index 89e18c04..d4294991 100644 --- a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-display-none.html +++ b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-display-none.html
@@ -13,7 +13,7 @@ select { width: 200px; font: 10px Ahem; - -webkit-appearance: none; + appearance: none; background-color: white; } select::-webkit-scrollbar {
diff --git a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-hover-expected.png b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-hover-expected.png new file mode 100644 index 0000000..bbcc520 --- /dev/null +++ b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-hover-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-hover.html b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-hover.html new file mode 100644 index 0000000..daa4cbd0 --- /dev/null +++ b/third_party/blink/web_tests/fast/forms/select-popup/popup-menu-appearance-custom-scrollbar-track-hover.html
@@ -0,0 +1,96 @@ +<!DOCTYPE html> +<html> +<head> +<script> + window.enablePixelTesting = true; +</script> +<script src="../resources/picker-common.js"></script> +<script src="../resources/common.js"></script> +<style> + select:focus { + outline-width: 0; + } + select { + width: 200px; + font: 10px Ahem; + -webkit-appearance: none; + background-color: white; + } + select::-webkit-scrollbar { + width: 200px; + } + select::-webkit-scrollbar-track { + background: orange; + } + select::-webkit-scrollbar-corner { + background: yellow; + } + + select::-webkit-scrollbar-thumb { + background: gray; + } + select::-webkit-scrollbar-track:hover { + background: green; + } + option:hover{ + background-color: green; + } +</style> +</head> +<body> +<select id='menu'> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> + <option>This is an option</option> +</select> +<script> +let menu = document.getElementById('menu'); +function mouseMoveToScrollbar() { + return new Promise(function(resolve, reject) { + if (window.chrome && chrome.gpuBenchmarking) { + let selectElement = internals.pagePopupWindow.global.picker._selectElement; + let innerSelectRect = selectElement.getBoundingClientRect(); + let scrollbarX = innerSelectRect.x + innerSelectRect.width - 5; + let scrollbarY = innerSelectRect.y + innerSelectRect.height - 10; + chrome.gpuBenchmarking.pointerActionSequence( + [{ + source: 'mouse', + actions: [{name: 'pointerMove', x: scrollbarX, y: scrollbarY}] + }], + resolve); + } else { + reject(); + } + }); +} +openPicker(menu, ()=>{ + mouseMoveToScrollbar().then(()=>{testRunner.notifyDone()}) +}) +testRunner.waitUntilDone() +</script> +</body> +</html> \ No newline at end of file
diff --git a/third_party/blink/web_tests/http/tests/misc/hover-state-recomputed-on-main-frame.html b/third_party/blink/web_tests/http/tests/misc/hover-state-recomputed-on-main-frame.html new file mode 100644 index 0000000..69e1bbd --- /dev/null +++ b/third_party/blink/web_tests/http/tests/misc/hover-state-recomputed-on-main-frame.html
@@ -0,0 +1,43 @@ +<!DOCTYPE html> +<script src="../../resources/testharness.js"></script> +<script src="../../resources/testharnessreport.js"></script> + +<style> + .oop-iframe { + width: 300px; + height: 300px; + } +</style> +<iframe id="target-iframe" class="oop-iframe" + src="http://localhost:8080/misc/resources/cross-origin-iframe-for-hover-state-refresh.html"> +</iframe> +<script> +// Check that cursor hover state is updated after changes to layout or scroll +// in OOPIFs. + +var hover_test = async_test("Verify that cursor/hover updates after" + + " scroll/layout changes in OOPIF"); +var iframe = document.getElementById("target-iframe"); +iframe.onload = startTest; +let state = 0; +function startTest() { + if (!internals.isSiteIsolated(iframe)) { + hover_test.name = "No site isolation - test skipped" + hover_test.done(); + return; + } + else { + window.addEventListener("message", handleMessage); + iframe.contentWindow.postMessage("clickiframe", "*"); + } +} +function handleMessage(event) { + if (state == 0) { + assert_equals("mouseover", event.data); + state++; + } else if (state == 1) { + assert_equals("mouseout", event.data); + hover_test.done(); + } +} +</script>
diff --git a/third_party/blink/web_tests/http/tests/misc/resources/cross-origin-iframe-for-hover-state-refresh.html b/third_party/blink/web_tests/http/tests/misc/resources/cross-origin-iframe-for-hover-state-refresh.html new file mode 100644 index 0000000..a1100e2 --- /dev/null +++ b/third_party/blink/web_tests/http/tests/misc/resources/cross-origin-iframe-for-hover-state-refresh.html
@@ -0,0 +1,48 @@ +<html> + <script src='/js-test-resources/gesture-util.js'></script> + <style> + .cursor_holder { + cursor: pointer; + height: 150px; + width: 150px; + background-color: green; + } + </style> + + <body onclick="changeCursor()"> + <div class="cursor_holder" id="cursor_holder" style="margin-left: 0px;"> + I am iframe + </div> + <script> + var element = document.getElementById("cursor_holder"); + var port; + element.addEventListener('mouseover', function (e) { + if (port) { + port.postMessage("mouseover", "*"); + } else{ + parent.postMessage("mouseover", "*"); + } + }); + element.addEventListener('mouseout', function (e) { + if (port) { + port.postMessage("mouseout", "*"); + } else{ + parent.postMessage("mouseout", "*"); + } + }); + function changeCursor() { + document.getElementById("cursor_holder").style.marginLeft = "200px"; + } + + window.addEventListener("message", async (event) => { + port = event.source; + if (event.data == "clickiframe") { + await mouseMoveTo(30, 30); + await mouseClickOn(30, 30); + } + }); + </script> + + + </body> +</html>
diff --git a/third_party/blink/web_tests/platform/linux/external/wpt/entries-api/idlharness-manual.window-expected.png b/third_party/blink/web_tests/platform/linux/external/wpt/entries-api/idlharness-manual.window-expected.png index 79f3d4f..257dfc4 100644 --- a/third_party/blink/web_tests/platform/linux/external/wpt/entries-api/idlharness-manual.window-expected.png +++ b/third_party/blink/web_tests/platform/linux/external/wpt/entries-api/idlharness-manual.window-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/linux/fast/forms/targeted-frame-submission-expected.png b/third_party/blink/web_tests/platform/linux/fast/forms/targeted-frame-submission-expected.png index 8b65a1d..d04e4f0 100644 --- a/third_party/blink/web_tests/platform/linux/fast/forms/targeted-frame-submission-expected.png +++ b/third_party/blink/web_tests/platform/linux/fast/forms/targeted-frame-submission-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/linux/fast/loader/text-document-wrapping-expected.png b/third_party/blink/web_tests/platform/linux/fast/loader/text-document-wrapping-expected.png index 1afacdca..4a902b2 100644 --- a/third_party/blink/web_tests/platform/linux/fast/loader/text-document-wrapping-expected.png +++ b/third_party/blink/web_tests/platform/linux/fast/loader/text-document-wrapping-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/mac/external/wpt/entries-api/idlharness-manual.window-expected.png b/third_party/blink/web_tests/platform/mac/external/wpt/entries-api/idlharness-manual.window-expected.png index dc6a40e..edf0ec9 100644 --- a/third_party/blink/web_tests/platform/mac/external/wpt/entries-api/idlharness-manual.window-expected.png +++ b/third_party/blink/web_tests/platform/mac/external/wpt/entries-api/idlharness-manual.window-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/mac/fast/forms/targeted-frame-submission-expected.png b/third_party/blink/web_tests/platform/mac/fast/forms/targeted-frame-submission-expected.png index 8aad8419..77e77f4 100644 --- a/third_party/blink/web_tests/platform/mac/fast/forms/targeted-frame-submission-expected.png +++ b/third_party/blink/web_tests/platform/mac/fast/forms/targeted-frame-submission-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/mac/fast/loader/text-document-wrapping-expected.png b/third_party/blink/web_tests/platform/mac/fast/loader/text-document-wrapping-expected.png index 1bd9e10..6da4031 100644 --- a/third_party/blink/web_tests/platform/mac/fast/loader/text-document-wrapping-expected.png +++ b/third_party/blink/web_tests/platform/mac/fast/loader/text-document-wrapping-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/win/external/wpt/entries-api/idlharness-manual.window-expected.png b/third_party/blink/web_tests/platform/win/external/wpt/entries-api/idlharness-manual.window-expected.png index 17ea64f..12d5238 100644 --- a/third_party/blink/web_tests/platform/win/external/wpt/entries-api/idlharness-manual.window-expected.png +++ b/third_party/blink/web_tests/platform/win/external/wpt/entries-api/idlharness-manual.window-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/win/fast/forms/targeted-frame-submission-expected.png b/third_party/blink/web_tests/platform/win/fast/forms/targeted-frame-submission-expected.png index ff22883..029313ea 100644 --- a/third_party/blink/web_tests/platform/win/fast/forms/targeted-frame-submission-expected.png +++ b/third_party/blink/web_tests/platform/win/fast/forms/targeted-frame-submission-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/platform/win/fast/loader/text-document-wrapping-expected.png b/third_party/blink/web_tests/platform/win/fast/loader/text-document-wrapping-expected.png index 0af4b09c..0a44db4 100644 --- a/third_party/blink/web_tests/platform/win/fast/loader/text-document-wrapping-expected.png +++ b/third_party/blink/web_tests/platform/win/fast/loader/text-document-wrapping-expected.png Binary files differ
diff --git a/third_party/blink/web_tests/webaudio/AudioBufferSource/audiobuffersource-loop-points.html b/third_party/blink/web_tests/webaudio/AudioBufferSource/audiobuffersource-loop-points.html index 07d3cf7a..58c850b8 100644 --- a/third_party/blink/web_tests/webaudio/AudioBufferSource/audiobuffersource-loop-points.html +++ b/third_party/blink/web_tests/webaudio/AudioBufferSource/audiobuffersource-loop-points.html
@@ -137,7 +137,7 @@ // in ULP. This is experimentally determined. Assuming that // the reference file is a 16-bit wav file, the max values in // the wave file are +/- 32768. - let maxUlp = 1.9532e-3; + let maxUlp = 0; let threshold = maxUlp / 32768; for (let k = 0; k < renderedAudio.numberOfChannels; ++k) {
diff --git a/third_party/blink/web_tests/wpt_internal/webxr/ar/ar_light_estimation.https.html b/third_party/blink/web_tests/wpt_internal/webxr/ar/ar_light_estimation.https.html index ae364ce..e0dd7a6f 100644 --- a/third_party/blink/web_tests/wpt_internal/webxr/ar/ar_light_estimation.https.html +++ b/third_party/blink/web_tests/wpt_internal/webxr/ar/ar_light_estimation.https.html
@@ -40,37 +40,39 @@ function verifyReflectionCubeMap(session, lightProbe) { // Currently reflection cube maps only work on WebGL 2. const gl2Canvas = document.createElement('canvas'); - const gl = gl2Canvas.getContext('webgl2', { xrCompatible: true }); + const gl = gl2Canvas.getContext('webgl2'); if (!gl) { return; } - const glBinding = new XRWebGLBinding(session, gl); + return gl.makeXRCompatible().then(() => { + const glBinding = new XRWebGLBinding(session, gl); - assert_true(glBinding instanceof XRWebGLBinding); + assert_true(glBinding instanceof XRWebGLBinding); - assert_defined(glBinding.getReflectionCubeMap, "getReflectionCubeMap was not defined on XRWebGLBinding"); + assert_defined(glBinding.getReflectionCubeMap, "getReflectionCubeMap was not defined on XRWebGLBinding"); - // Bind a different cube map prior to fetching the reflection cube map so we - // can ensure the binding is preserved. - const tmpCubeMap = gl.createTexture(); - gl.bindTexture(gl.TEXTURE_CUBE_MAP, tmpCubeMap); + // Bind a different cube map prior to fetching the reflection cube map so we + // can ensure the binding is preserved. + const tmpCubeMap = gl.createTexture(); + gl.bindTexture(gl.TEXTURE_CUBE_MAP, tmpCubeMap); - // Make sure we get back a valid cube map - const cubeMap = glBinding.getReflectionCubeMap(lightProbe); - assert_true(cubeMap instanceof WebGLTexture); + // Make sure we get back a valid cube map + const cubeMap = glBinding.getReflectionCubeMap(lightProbe); + assert_true(cubeMap instanceof WebGLTexture); - const boundCubeMap = gl.getParameter(gl.TEXTURE_BINDING_CUBE_MAP); - assert_equals(boundCubeMap, tmpCubeMap); + const boundCubeMap = gl.getParameter(gl.TEXTURE_BINDING_CUBE_MAP); + assert_equals(boundCubeMap, tmpCubeMap); - // Ensure that we can't bind the returned cube map to the TEXTURE_2D bind - // target but can bind it to the TEXTURE_CUBE_MAP bind point. This effectively - // tests that the texture was created as a cube map. - gl.bindTexture(gl.TEXTURE_2D, cubeMap); - assert_equals(gl.getError(), gl.INVALID_OPERATION); + // Ensure that we can't bind the returned cube map to the TEXTURE_2D bind + // target but can bind it to the TEXTURE_CUBE_MAP bind point. This effectively + // tests that the texture was created as a cube map. + gl.bindTexture(gl.TEXTURE_2D, cubeMap); + assert_equals(gl.getError(), gl.INVALID_OPERATION); - gl.bindTexture(gl.TEXTURE_CUBE_MAP, cubeMap); - assert_equals(gl.getError(), gl.NO_ERROR); + gl.bindTexture(gl.TEXTURE_CUBE_MAP, cubeMap); + assert_equals(gl.getError(), gl.NO_ERROR); + }); } // Verifies the structure of |XRFrame| (as it relates to light estimation) @@ -94,14 +96,18 @@ // Reflection cube maps may be enabled separately from the other lighting values. if ('XRWebGLBinding' in window) { - verifyReflectionCubeMap(session, lightProbe); + verifyReflectionCubeMap(session, lightProbe).then(() => { + // If the light probe is providing valid results it should also have a + // valid space. + assert_not_equals(lightProbePose, null); + resolve(); + }); + } else { + // If the light probe is providing valid results it should also have a + // valid space. + assert_not_equals(lightProbePose, null); + resolve(); } - - // If the light probe is providing valid results it should also have a - // valid space. - assert_not_equals(lightProbePose, null); - - resolve(); } }); }
diff --git a/tools/binary_size/libsupersize/archive.py b/tools/binary_size/libsupersize/archive.py index 077451f..98b457b 100644 --- a/tools/binary_size/libsupersize/archive.py +++ b/tools/binary_size/libsupersize/archive.py
@@ -852,7 +852,7 @@ key += '-' + name metadata[key] = size - return metadata or None + return metadata def _ResolveThinArchivePaths(raw_symbols, thin_archives): @@ -1262,9 +1262,15 @@ zip_info_total = 0 zipalign_total = 0 with zipfile.ZipFile(apk_path) as z: + signing_block_size = zip_util.MeasureApkSignatureBlock(z) for zip_info in z.infolist(): zip_info_total += zip_info.compress_size + # Account for zipalign overhead that exists in local file header. zipalign_total += zip_util.ReadZipInfoExtraFieldLength(z, zip_info) + # Account for zipalign overhead that exists in central directory header. + # Happens when python aligns entries in apkbuilder.py, but does not + # exist when using Android's zipalign. E.g. for bundle .apks files. + zipalign_total += len(zip_info.extra) # Skip main shared library, pak, and dex files as they are accounted for. if (zip_info.filename == apk_so_path or zip_info.filename.endswith('.pak')): @@ -1284,7 +1290,18 @@ zip_info.compress_size, source_path=source_path, full_name=resource_filename)) # Full name must disambiguate - overhead_size = os.path.getsize(apk_path) - zip_info_total - zipalign_total + + if signing_block_size > 0: + signing_symbol = models.Symbol(models.SECTION_OTHER, + signing_block_size, + full_name='APK Signature Block') + apk_symbols.append(signing_symbol) + + # Overhead includes: + # * Size of all local zip headers (minus zipalign padding). + # * Size of central directory & end of central directory. + overhead_size = (os.path.getsize(apk_path) - zip_info_total - zipalign_total - + signing_block_size) assert overhead_size >= 0, 'Apk overhead must be non-negative' zip_overhead_symbol = models.Symbol( models.SECTION_OTHER, overhead_size, full_name='Overhead: APK file')
diff --git a/tools/binary_size/libsupersize/testdata/Archive_Apk.golden b/tools/binary_size/libsupersize/testdata/Archive_Apk.golden index 2bf73e1..c101d25 100644 --- a/tools/binary_size/libsupersize/testdata/Archive_Apk.golden +++ b/tools/binary_size/libsupersize/testdata/Archive_Apk.golden
@@ -10,7 +10,7 @@ linker_name=gold map_file_name=../../../test.map tool_prefix=tools/binary_size/libsupersize/testdata/mock_toolchain/ -zipalign_padding=16 +zipalign_padding=32 Section .text: has 100.0% of 35982248 bytes accounted for from 22 symbols. 0 bytes are unaccounted for. * Padding accounts for 13808 bytes (0.0%) * 16 have source paths. Accounts for 73986 bytes (0.2%). @@ -75,8 +75,8 @@ * 0 have source paths. Accounts for 0 bytes (0.0%). * 0 have a component assigned. Accounts for 0 bytes (0.0%). * 0 symbols have shared ownership. -Section .other: has 100.0% of 95595813 bytes accounted for from 27 symbols. 0 bytes are unaccounted for. -* Padding accounts for 33903415 bytes (35.5%) +Section .other: has 100.0% of 95595797 bytes accounted for from 27 symbols. 0 bytes are unaccounted for. +* Padding accounts for 33903399 bytes (35.5%) * 3 have source paths. Accounts for 5243904 bytes (5.5%). * 1 have a component assigned. Accounts for 1048576 bytes (1.1%). * 22 placeholders exist (symbols that start with **). Accounts for 56448494 bytes (59.0%). @@ -306,7 +306,7 @@ .other@0(size_without_padding=436,padding=0,full_name=** ELF Section: .shstrtab,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=34841854,padding=0,full_name=** ELF Section: .strtab,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=17166112,padding=0,full_name=** ELF Section: .symtab,object_path=,source_path=,flags={},num_aliases=1,component=) -.other@0(size_without_padding=0,padding=780,full_name=Overhead: APK file,object_path=,source_path=,flags={},num_aliases=1,component=) +.other@0(size_without_padding=0,padding=764,full_name=Overhead: APK file,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=0,padding=33902635,full_name=Overhead: ELF file,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=1048576,padding=0,full_name=assets/icudtl.dat,object_path=,source_path=third_party/icu/android/icudtl.dat,flags={},num_aliases=1,component=Internal>Android) .other@0(size_without_padding=1024,padding=0,full_name=res/drawable-v13/test.xml,object_path=,source_path=chrome/android/res/drawable/test.xml,flags={},num_aliases=1,component=)
diff --git a/tools/binary_size/libsupersize/testdata/Archive_MinimalApks.golden b/tools/binary_size/libsupersize/testdata/Archive_MinimalApks.golden index 107ddf6..2f828517 100644 --- a/tools/binary_size/libsupersize/testdata/Archive_MinimalApks.golden +++ b/tools/binary_size/libsupersize/testdata/Archive_MinimalApks.golden
@@ -11,7 +11,7 @@ linker_name=gold map_file_name=../../../test.map tool_prefix=tools/binary_size/libsupersize/testdata/mock_toolchain/ -zipalign_padding=16 +zipalign_padding=32 Section .text: has 100.0% of 35982248 bytes accounted for from 22 symbols. 0 bytes are unaccounted for. * Padding accounts for 13808 bytes (0.0%) * 16 have source paths. Accounts for 73986 bytes (0.2%). @@ -76,8 +76,8 @@ * 0 have source paths. Accounts for 0 bytes (0.0%). * 0 have a component assigned. Accounts for 0 bytes (0.0%). * 0 symbols have shared ownership. -Section .other: has 100.0% of 95595813 bytes accounted for from 27 symbols. 0 bytes are unaccounted for. -* Padding accounts for 33903415 bytes (35.5%) +Section .other: has 100.0% of 95595797 bytes accounted for from 27 symbols. 0 bytes are unaccounted for. +* Padding accounts for 33903399 bytes (35.5%) * 3 have source paths. Accounts for 5243904 bytes (5.5%). * 1 have a component assigned. Accounts for 1048576 bytes (1.1%). * 22 placeholders exist (symbols that start with **). Accounts for 56448494 bytes (59.0%). @@ -307,7 +307,7 @@ .other@0(size_without_padding=436,padding=0,full_name=** ELF Section: .shstrtab,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=34841854,padding=0,full_name=** ELF Section: .strtab,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=17166112,padding=0,full_name=** ELF Section: .symtab,object_path=,source_path=,flags={},num_aliases=1,component=) -.other@0(size_without_padding=0,padding=780,full_name=Overhead: APK file,object_path=,source_path=,flags={},num_aliases=1,component=) +.other@0(size_without_padding=0,padding=764,full_name=Overhead: APK file,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=0,padding=33902635,full_name=Overhead: ELF file,object_path=,source_path=,flags={},num_aliases=1,component=) .other@0(size_without_padding=1048576,padding=0,full_name=assets/icudtl.dat,object_path=,source_path=third_party/icu/android/icudtl.dat,flags={},num_aliases=1,component=Internal>Android) .other@0(size_without_padding=1024,padding=0,full_name=res/drawable-v13/test.xml,object_path=,source_path=chrome/android/res/drawable/test.xml,flags={},num_aliases=1,component=)
diff --git a/tools/binary_size/libsupersize/zip_util.py b/tools/binary_size/libsupersize/zip_util.py index a52d5a8..73d591ff 100644 --- a/tools/binary_size/libsupersize/zip_util.py +++ b/tools/binary_size/libsupersize/zip_util.py
@@ -46,3 +46,27 @@ # Refer to https://en.wikipedia.org/wiki/Zip_(file_format)#File_headers zip_file.fp.seek(zip_info.header_offset + 28) return struct.unpack('<H', zip_file.fp.read(2))[0] + + +def MeasureApkSignatureBlock(zip_file): + """Measures the size of the v2 / v3 signing block. + + Refer to: https://source.android.com/security/apksigning/v2 + """ + # Seek to "end of central directory" struct. + eocd_offset_from_end = -22 - len(zip_file.comment) + zip_file.fp.seek(eocd_offset_from_end, os.SEEK_END) + assert zip_file.fp.read(4) == b'PK\005\006', ( + 'failed to find end-of-central-directory') + + # Read out the "start of central directory" offset. + zip_file.fp.seek(eocd_offset_from_end + 16, os.SEEK_END) + start_of_central_directory = struct.unpack('<I', zip_file.fp.read(4))[0] + + # Compute the offset after the last zip entry. + last_info = zip_file.infolist()[-1] + last_header_size = (30 + len(last_info.filename) + + ReadZipInfoExtraFieldLength(zip_file, last_info)) + end_of_last_file = (last_info.header_offset + last_header_size + + last_info.compress_size) + return start_of_central_directory - end_of_last_file
diff --git a/tools/binary_size/libsupersize/zip_util_test.py b/tools/binary_size/libsupersize/zip_util_test.py new file mode 100755 index 0000000..b7d1853 --- /dev/null +++ b/tools/binary_size/libsupersize/zip_util_test.py
@@ -0,0 +1,58 @@ +#!/usr/bin/env python3 +# Copyright 2020 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 glob +import subprocess +import tempfile +import unittest +import zipfile + +import path_util +import zip_util + + +def _FindZipAlign(): + # SDK does not exist on presubmit CQ bot. + candidates = glob.glob( + path_util.FromToolsSrcRootRelative( + 'third_party/android_sdk/public/build-tools/*/zipalign')) + # Any version will do. + return candidates[0] if candidates else None + + +class ZipUtilTest(unittest.TestCase): + def testReadZipInfoExtraFieldLength(self): + zipalign = _FindZipAlign() + if not zipalign: + return + + with tempfile.NamedTemporaryFile() as f: + with zipfile.ZipFile(f, 'w') as z: + z.writestr('a', 'a') + z.writestr('b', 'bb') + z.writestr('c', 'ccc') + f.flush() + with tempfile.NamedTemporaryFile() as f2: + subprocess.run([zipalign, '-f', '4', f.name, f2.name], check=True) + with zipfile.ZipFile(f2) as z: + alignments = [ + zip_util.ReadZipInfoExtraFieldLength(z, i) for i in z.infolist() + ] + + self.assertEqual([1, 0, 3], alignments) + + def testMeasureApkSignatureBlock(self): + with tempfile.NamedTemporaryFile() as f: + with zipfile.ZipFile(f, 'w') as z: + z.writestr('a', 'a') + f.flush() + with zipfile.ZipFile(f) as z: + # It's non-trivial to sign an apk, so at least make sure the logic + # reports 0 for an unsigned .zip. + self.assertEqual(0, zip_util.MeasureApkSignatureBlock(z)) + + +if __name__ == '__main__': + unittest.main()
diff --git a/tools/mb/mb_config.pyl b/tools/mb/mb_config.pyl index 36234ef8..2e23312 100644 --- a/tools/mb/mb_config.pyl +++ b/tools/mb/mb_config.pyl
@@ -261,12 +261,6 @@ 'Mac Builder Next': 'gpu_tests_release_bot_minimal_symbols', 'Mac deterministic': 'release_bot_mac_strip_minimal_symbols_deterministic', 'Mac deterministic (dbg)': 'debug_bot_deterministic', - # TODO(https://crbug.com/1131163) Remove the mojo entries once the - # builders have started reading from the correct spec file - 'Mojo Android': 'android_release_bot_minimal_symbols_arm64', - 'Mojo ChromiumOS': 'chromeos_with_codecs_release_trybot', - 'Mojo Linux': 'release_trybot', - 'Mojo Windows': 'release_bot_x86_minimal_symbols', 'Site Isolation Android': 'android_release_bot_minimal_symbols_arm64', 'VR Linux': 'vr_release_bot', @@ -274,9 +268,6 @@ 'Win10 Tests x64 1909': 'release_trybot', 'android-code-coverage': 'gpu_tests_android_release_bot_minimal_symbols_arm64_fastbuild_java_coverage', 'android-code-coverage-native': 'gpu_tests_android_release_bot_minimal_symbols_arm64_fastbuild_native_coverage', - # TODO(https://crbug.com/1131163) Remove the mojo entries once the - # builders have started reading from the correct spec file - 'android-mojo-webview-rel': 'android_release_bot_minimal_symbols_arm64', 'chromeos-amd64-generic-lacros-rel': 'chromeos_amd64-generic_lacros_rel', 'fuchsia-fyi-arm64-dbg': 'debug_bot_fuchsia_arm64', 'fuchsia-fyi-arm64-rel': 'release_bot_fuchsia_arm64', @@ -313,9 +304,6 @@ 'linux-wpt-payments-fyi-rel': 'release_bot_minimal_symbols', 'mac-code-coverage': 'clang_code_coverage', 'mac-hermetic-upgrade-rel': 'release_bot', - # TODO(https://crbug.com/1131163) Remove the mojo entries once the - # builders have started reading from the correct spec file - 'mac-mojo-rel': 'release_trybot', 'mac-omaha-builder-rel': 'updater_release_bot', 'mac-upload-perfetto': 'release_bot', 'win-annotator-rel': 'release_bot',
diff --git a/tools/metrics/histograms/enums.xml b/tools/metrics/histograms/enums.xml index 45ca1f3d..8b4b0516 100644 --- a/tools/metrics/histograms/enums.xml +++ b/tools/metrics/histograms/enums.xml
@@ -17418,6 +17418,7 @@ <int value="6" label="DNS_SB"/> <int value="7" label="CZ_NIC"/> <int value="8" label="NEXT_DNS"/> + <int value="9" label="OPEN_DNS"/> </enum> <enum name="DomainBoundCerts.DBLoadStatus"> @@ -29314,7 +29315,8 @@ <int value="3543" label="V8HIDDevice_ProductId_AttributeGetter"/> <int value="3544" label="V8HIDDevice_ProductName_AttributeGetter"/> <int value="3545" label="V8HIDDevice_VendorId_AttributeGetter"/> - <int value="3546" label="IdentifiabilityStudyReserved3546"/> + <int value="3546" + label="V8BeforeInstallPromptEvent_Platforms_AttributeGetter"/> <int value="3547" label="V8HIDReportItem_HasNull_AttributeGetter"/> <int value="3548" label="V8HIDReportItem_IsAbsolute_AttributeGetter"/> <int value="3549" label="V8HIDReportItem_IsArray_AttributeGetter"/> @@ -42202,6 +42204,7 @@ <int value="-747919789" label="VideoToolboxVp9Decoding:enabled"/> <int value="-747463111" label="ContentSuggestionsNotifications:disabled"/> <int value="-747072690" label="NtpRepeatableQueries:disabled"/> + <int value="-746482855" label="GuestOsExternalProtocol:disabled"/> <int value="-746328467" label="ExpensiveBackgroundTimerThrottling:disabled"/> <int value="-745082968" label="SyncDeviceInfoInTransportMode:disabled"/> <int value="-744159181" label="disable-spdy-proxy-dev-auth-origin"/> @@ -43235,6 +43238,7 @@ <int value="351005753" label="enable-experimental-accessibility-autoclick"/> <int value="352191859" label="disabled-new-style-notification"/> <int value="352937987" label="OverflowIconsForMediaControls:disabled"/> + <int value="354523543" label="GuestOsExternalProtocol:enabled"/> <int value="354631905" label="RecoverFromNeverSaveAndroid:disabled"/> <int value="357138275" label="enable-floating-virtual-keyboard:disabled"/> <int value="358399482" label="enable-high-dpi-fixed-position-compositing"/>
diff --git a/tools/metrics/histograms/find_unmapped_histograms.py b/tools/metrics/histograms/find_unmapped_histograms.py index 478cdb8b..5219242 100644 --- a/tools/metrics/histograms/find_unmapped_histograms.py +++ b/tools/metrics/histograms/find_unmapped_histograms.py
@@ -24,6 +24,8 @@ import path_util import extract_histograms +import histogram_paths +import merge_xml C_FILENAME = re.compile(r""" @@ -289,11 +291,25 @@ return histograms, location_map -def readXmlHistograms(histograms_file_location): - """Parses all histogram names from histograms.xml. +def readAllXmlHistograms(): + """Parses all histogram names defined in |histogram_paths.ALL_XMLS|. Returns: - A set cotaining the parsed histogram names. + A set containing the parsed histogram names. + """ + merged = merge_xml.MergeFiles(histogram_paths.ALL_XMLS) + histograms, _ = extract_histograms.ExtractHistogramsFromDom(merged) + return set(extract_histograms.ExtractNames(histograms)) + + +def readXmlHistograms(histograms_file_location): + """Parses all histogram names from |histograms_file_location|. + + Args: + histograms_file_location: The given histograms.xml file path. + + Returns: + A set containing the parsed histogram names. """ logging.info('Reading histograms from %s...' % histograms_file_location) histograms = extract_histograms.ExtractHistograms(histograms_file_location) @@ -340,8 +356,6 @@ def main(): # Find default paths. default_root = path_util.GetInputFile('/') - default_histograms_path = path_util.GetInputFile( - 'tools/metrics/histograms/histograms.xml') default_extra_histograms_path = path_util.GetInputFile( 'tools/histograms/histograms.xml') @@ -353,12 +367,6 @@ default_root, metavar='DIRECTORY') parser.add_option( - '--histograms-file', dest='histograms_file_location', - default=default_histograms_path, - help='read histogram definitions from FILE (relative to --root-directory) ' - '[optional, defaults to "%s"]' % default_histograms_path, - metavar='FILE') - parser.add_option( '--extra_histograms-file', dest='extra_histograms_file_location', default=default_extra_histograms_path, help='read additional histogram definitions from FILE (relative to ' @@ -389,7 +397,7 @@ logging.error("Could not change to root directory: %s", e) sys.exit(1) chromium_histograms, location_map = readChromiumHistograms() - xml_histograms = readXmlHistograms(options.histograms_file_location) + xml_histograms = readAllXmlHistograms() unmapped_histograms = chromium_histograms - xml_histograms if os.path.isfile(options.extra_histograms_file_location):
diff --git a/tools/metrics/histograms/histograms.xml b/tools/metrics/histograms/histograms.xml index 1d1c45c3..abc615c 100644 --- a/tools/metrics/histograms/histograms.xml +++ b/tools/metrics/histograms/histograms.xml
@@ -30926,28 +30926,28 @@ </histogram> <histogram name="Crashpad.ExceptionCaptureResult" - enum="CrashpadExceptionCaptureResult" expires_after="M85"> + enum="CrashpadExceptionCaptureResult" expires_after="M90"> <owner>jperaza@chromium.org</owner> <owner>crashpad-dev@chromium.org</owner> <summary>The outcome of execution of the Crashpad exception handler.</summary> </histogram> <histogram name="Crashpad.ExceptionCode.Mac" enum="CrashpadMacExceptionCodes" - expires_after="M85"> + expires_after="M90"> <owner>mark@chromium.org</owner> <owner>crashpad-dev@chromium.org</owner> <summary>The exception code encountered in a crash on Mac OS X.</summary> </histogram> <histogram name="Crashpad.ExceptionCode.Win" enum="CrashpadWinExceptionCodes" - expires_after="M85"> + expires_after="M90"> <owner>jperaza@chromium.org</owner> <owner>crashpad-dev@chromium.org</owner> <summary>The exception code encountered in a crash on Windows.</summary> </histogram> <histogram name="Crashpad.ExceptionEncountered" - enum="CrashpadExceptionProcessingState" expires_after="M85"> + enum="CrashpadExceptionProcessingState" expires_after="M90"> <owner>jperaza@chromium.org</owner> <owner>crashpad-dev@chromium.org</owner> <summary> @@ -30957,7 +30957,7 @@ </histogram> <histogram name="Crashpad.HandlerCrash.ExceptionCode.Mac" - enum="CrashpadMacExceptionCodes" expires_after="M85"> + enum="CrashpadMacExceptionCodes" expires_after="M90"> <owner>mark@chromium.org</owner> <owner>crashpad-dev@chromium.org</owner> <summary> @@ -30967,7 +30967,7 @@ </histogram> <histogram name="Crashpad.HandlerCrash.ExceptionCode.Win" - enum="CrashpadWinExceptionCodes" expires_after="M85"> + enum="CrashpadWinExceptionCodes" expires_after="M90"> <owner>jperaza@chromium.org</owner> <owner>crashpad-dev@chromium.org</owner> <summary> @@ -30977,7 +30977,7 @@ </histogram> <histogram name="Crashpad.HandlerLifetimeMilestone" - enum="CrashpadLifetimeMilestone" expires_after="M85"> + enum="CrashpadLifetimeMilestone" expires_after="M90"> <owner>jperaza@chromium.org</owner> <owner>crashpad-dev@chromium.org</owner> <summary>Handler start/crash/exit events.</summary> @@ -78563,6 +78563,16 @@ </summary> </histogram> +<histogram name="Media.Kaleidoscope.NewTabPage.ServerFetchTime" units="ms" + expires_after="2021-08-19"> + <owner>beccahughes@chromium.org</owner> + <owner>media-dev@chromium.org</owner> + <summary> + Recorded each time the Kaleidoscope module is loaded on the New Tab Page + with the time it takes to fetch the data from the server. + </summary> +</histogram> + <histogram base="true" name="Media.Learning.BinaryThreshold.Aggregate" enum="ConfusionMatrix" expires_after="2019-10-30"> <!-- Name completed by histogram_suffixes
diff --git a/tools/metrics/histograms/histograms_xml/Blink/histograms.xml b/tools/metrics/histograms/histograms_xml/Blink/histograms.xml index 75a39aa..8421cb0 100644 --- a/tools/metrics/histograms/histograms_xml/Blink/histograms.xml +++ b/tools/metrics/histograms/histograms_xml/Blink/histograms.xml
@@ -1664,20 +1664,22 @@ </histogram> <histogram name="Blink.Sms.Receive.DestroyedReason" - enum="SmsReceiverDestroyedReason" expires_after="M88"> + enum="SmsReceiverDestroyedReason" expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records the reason an SMS Service is destroyed before request completion. </summary> </histogram> <histogram name="Blink.Sms.Receive.Infobar" enum="SMSReceiverInfobarAction" - expires_after="M88"> + expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records how many times the infobar was called and how many times the infobar replaced a keyboard. @@ -1685,17 +1687,19 @@ </histogram> <histogram name="Blink.Sms.Receive.Outcome" enum="SMSReceiverOutcome" - expires_after="M88"> + expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary>Records the result of a call to the SmsReceiver API.</summary> </histogram> -<histogram name="Blink.Sms.Receive.TimeCancel" units="ms" expires_after="M88"> +<histogram name="Blink.Sms.Receive.TimeCancel" units="ms" expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records the duration from when the API is called to when the user presses the cancel button to abort SMS retrieval. @@ -1703,11 +1707,12 @@ </histogram> <histogram name="Blink.Sms.Receive.TimeCancelOnKeyboardDismissal" units="ms" - expires_after="M88"> + expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> <owner>juncai@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records the duration from when the keyboard was replaced with an infobar until when the user clicked the cancel button. @@ -1715,10 +1720,11 @@ </histogram> <histogram name="Blink.Sms.Receive.TimeCancelOnSuccess" units="ms" - expires_after="M88"> + expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records the time from when a successful SMS was retrieved to when the user presses the Cancel button. @@ -1726,10 +1732,11 @@ </histogram> <histogram name="Blink.Sms.Receive.TimeContinueOnSuccess" units="ms" - expires_after="M88"> + expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records the time from when a successful SMS was retrieved to when the user presses the Continue button. @@ -1737,20 +1744,22 @@ </histogram> <histogram name="Blink.Sms.Receive.TimeSmsReceive" units="ms" - expires_after="M88"> + expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records the duration from when the API is called to when an SMS has been successfully received. </summary> </histogram> -<histogram name="Blink.Sms.Receive.TimeSuccess" units="ms" expires_after="M88"> +<histogram name="Blink.Sms.Receive.TimeSuccess" units="ms" expires_after="M92"> <owner>goto@chromium.org</owner> <owner>reillyg@chromium.org</owner> - <owner>ayui@chromium.org</owner> + <owner>yigu@chromium.org</owner> + <owner>web-identity@google.com</owner> <summary> Records the duration from when the API is called to when the user successfully receives the SMS and presses continue to pass the incoming SMS
diff --git a/tools/metrics/histograms/print_histogram_names.py b/tools/metrics/histograms/print_histogram_names.py index d8da9b2b..eaefd1b 100755 --- a/tools/metrics/histograms/print_histogram_names.py +++ b/tools/metrics/histograms/print_histogram_names.py
@@ -31,7 +31,7 @@ histograms, had_errors = extract_histograms.ExtractHistogramsFromDom(doc) if had_errors: raise ValueError("Error parsing inputs.") - return extract_histograms.ExtractNames(histograms) + return set(extract_histograms.ExtractNames(histograms)) def histogram_xml_files(): @@ -59,12 +59,16 @@ # _that_ big. return StringIO(contents) - current_histogram_names = set(get_names(histogram_xml_files())) - prev_histogram_names = set( - get_names([ - get_file_at_revision(os.path.normpath(p)) - for p in histogram_paths.ALL_XMLS_RELATIVE - ])) + prev_files = [] + for p in histogram_paths.ALL_XMLS_RELATIVE: + try: + prev_files.append(get_file_at_revision(os.path.normpath(p))) + except subprocess.CalledProcessError: + # Paths might not exist in the provided revision. + continue + + current_histogram_names = get_names(histogram_xml_files()) + prev_histogram_names = get_names(prev_files) added_names = sorted(list(current_histogram_names - prev_histogram_names)) removed_names = sorted(list(prev_histogram_names - current_histogram_names))
diff --git a/tools/metrics/histograms/split_xml.py b/tools/metrics/histograms/split_xml.py index a591873c..e4e9fa6 100644 --- a/tools/metrics/histograms/split_xml.py +++ b/tools/metrics/histograms/split_xml.py
@@ -8,6 +8,7 @@ """ import os +import re from xml.dom import minidom import histogram_configuration_model @@ -23,15 +24,12 @@ found in the LICENSE file. """ SECOND_TOP_LEVEL_COMMENT_TEMPLATE = """ -This file is used to generate a comprehensive list of %s along -with a detailed description for each histogram. +This file is used to generate a comprehensive list of %s +along with a detailed description for each histogram. For best practices on writing histogram descriptions, see https://chromium.googlesource.com/chromium/src.git/+/HEAD/tools/metrics/histograms/README.md -For brief details on how to modify this file to add your description, see -https://chromium.googlesource.com/chromium/src.git/+/HEAD/tools/metrics/histograms/one-pager.md - Please send CLs to chromium-metrics-reviews@google.com rather than to specific individuals. These CLs will be automatically reassigned to a reviewer within about 5 minutes. This approach helps the metrics team to load-balance incoming @@ -42,6 +40,39 @@ # The number of histograms below which they will be aggregated into # the histograms.xml in 'others'. AGGREGATE_THRESHOLD = 20 +# A map from the histogram name to the folder name these histograms should be +# put in. +_PREDEFINED_NAMES_MAPPING = { + 'BackForwardCache': 'BackForwardCache', + 'CustomTabs': 'CustomTabs', + 'CustomTab': 'CustomTabs', + 'DataReductionProxy': 'DataReductionProxy', + 'DataUse': 'DataUse', + 'MultiDevice': 'MultiDevice', + 'NaCl': 'NaCl', + 'SafeBrowsing': 'SafeBrowsing', + 'SafeBrowsingBinaryUploadRequest': 'SafeBrowsing', + 'SafeBrowsingFCMService': 'SafeBrowsing', + 'NewTabPage': 'NewTabPage', + 'SiteEngagementService': 'SiteEngagementService', + 'SiteIsolation': 'SiteIsolation', + 'Tabs': 'Tab', + 'TextFragmentAnchor': 'TextFragmentAnchor', + 'TextToSpeech': 'TextToSpeech', + 'UpdateEngine': 'UpdateEngine', + 'WebApk': 'WebApk', + 'WebApp': 'WebApp', + 'WebAudio': 'WebAudio', + 'WebAuthentication': 'WebAuthentication', + 'WebCore': 'WebCore', + 'WebFont': 'WebFont', + 'WebHistory': 'WebHistory', + 'WebRTC': 'WebRTC', + 'WebRtcEventLogging': 'WebRTC', + 'WebRtcTextLogging': 'WebRTC', + 'WebUI': 'WebUI', + 'WebUITabStrip': 'WebUI', +} def _ParseMergedXML(): @@ -98,7 +129,7 @@ output_file.write(pretty_xml_string) -def _GetCamelName(node, depth=0): +def _GetCamelCaseName(node, depth=0): """Returns the first camelcase name part of the given |node|. Args: @@ -121,6 +152,8 @@ split_string_list = name.split('.') if len(split_string_list) <= depth: return 'others' + elif split_string_list[depth] in _PREDEFINED_NAMES_MAPPING: + return _PREDEFINED_NAMES_MAPPING[split_string_list[depth]] else: name_part = split_string_list[depth] start_index = 0 @@ -142,7 +175,7 @@ def GetDirForNode(node): """Returns the correct directory that the given |node| should be placed in.""" - camel_name = _GetCamelName(node) + camel_name = _GetCamelCaseName(node) # Check if the directory of its prefix exists. Return the |camel_name| if the # folder exists. Otherwise, this |node| should be placed in 'others' folder. if camel_name in histogram_paths.HISTOGRAMS_PREFIX_LIST: @@ -150,6 +183,12 @@ return 'others' +def _CamelCaseToSnakeCase(name): + """Converts CamelCase |name| to snake_case.""" + name = re.sub('(.)([A-Z][a-z]+)', r'\1_\2', name) + return re.sub('([a-z0-9])([A-Z])', r'\1_\2', name).lower() + + def _OutputToFolderAndXML(nodes, output_dir, key): """Creates new folder and XML file for separated histograms. @@ -158,7 +197,8 @@ output_dir: The output directory. key: The prefix of the histograms, also the name of the new folder. """ - output_dir = os.path.join(output_dir, key) + # Convert CamelCase name to snake_case when creating a directory. + output_dir = os.path.join(output_dir, _CamelCaseToSnakeCase(key)) if not os.path.exists(output_dir): os.makedirs(output_dir) _CreateXMLFile(key + ' histograms', 'histograms', nodes, output_dir, @@ -220,7 +260,7 @@ temp_dict = document_dict = {} for node in nodes: - name_part = _GetCamelName(node, depth) + name_part = _GetCamelCaseName(node, depth) if name_part not in temp_dict: temp_dict[name_part] = [] temp_dict[name_part].append(node)
diff --git a/tools/metrics/histograms/split_xml_unittest.py b/tools/metrics/histograms/split_xml_unittest.py new file mode 100644 index 0000000..c71ddcd --- /dev/null +++ b/tools/metrics/histograms/split_xml_unittest.py
@@ -0,0 +1,37 @@ +# Copyright 2020 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 parameterized import parameterized +from xml.dom import minidom +import unittest + +import split_xml + +class SplitXmlTest(unittest.TestCase): + + @parameterized.expand([ + ('Camel case', 'MyHistogram.ThisHistogram', 'My'), + ('All upper case', 'UMA', 'UMA'), + ('In the predefined map', 'SafeBrowsing.TestHist', 'SafeBrowsing'), + ]) + def testGetCamelCaseName(self, _, name, expected_name): + doc = minidom.Document() + node = doc.createElement('histogram') + node.setAttribute('name', name) + result = split_xml._GetCamelCaseName(node) + self.assertEqual(expected_name, result) + + @parameterized.expand([ + ('Camel case', 'MyHistogram', 'my_histogram'), + ('All upper case', 'UMA', 'uma'), + ('mixed case', 'MYHistogram', 'my_histogram'), + ('usual case followed by all upper case', 'MyHISTOGRAM', 'my_histogram') + ]) + def testCamelCaseToSnakeCase(self, _, name, expected_name): + result = split_xml._CamelCaseToSnakeCase(name) + self.assertEqual(expected_name, result) + + +if __name__ == "__main__": + unittest.main() \ No newline at end of file
diff --git a/tools/perf/core/test_data/benchmarks_to_shard.json b/tools/perf/core/test_data/benchmarks_to_shard.json index 017275d..a9ccfbd9 100644 --- a/tools/perf/core/test_data/benchmarks_to_shard.json +++ b/tools/perf/core/test_data/benchmarks_to_shard.json
@@ -236,6 +236,7 @@ "repeat": 1, "stories": [ "css-parser-yui.html", + "declarative-shadow-dom.html", "html-parser-threaded.html", "html-parser.html", "html5-full-render.html",
diff --git a/tools/traffic_annotation/summary/annotations.xml b/tools/traffic_annotation/summary/annotations.xml index 3315cc4..3432558 100644 --- a/tools/traffic_annotation/summary/annotations.xml +++ b/tools/traffic_annotation/summary/annotations.xml
@@ -306,6 +306,7 @@ <item id="service_worker_navigation_preload" added_in_milestone="63" hash_code="129872904" type="0" content_hash_code="79473248" os_list="linux,windows" file_path="content/browser/service_worker/service_worker_fetch_dispatcher.cc"/> <item id="service_worker_update_checker" added_in_milestone="71" hash_code="130931413" type="0" content_hash_code="46608086" os_list="linux,windows" file_path="content/browser/service_worker/service_worker_single_script_update_checker.cc"/> <item id="services_http_server_error_response" added_in_milestone="68" hash_code="59302801" type="0" content_hash_code="127774041" os_list="linux,windows" file_path="services/network/public/cpp/server/http_server.cc"/> + <item id="shopping_tasks_service" added_in_milestone="87" hash_code="90297622" type="0" content_hash_code="133566501" os_list="linux,windows" file_path="chrome/browser/search/shopping_tasks/shopping_tasks_service.cc"/> <item id="sigined_exchange_cert_fetcher" added_in_milestone="66" hash_code="79442849" type="0" content_hash_code="8138156" os_list="linux,windows" file_path="content/browser/web_package/signed_exchange_cert_fetcher.cc"/> <item id="sigined_exchange_validity_pinger" added_in_milestone="75" hash_code="57114284" type="0" content_hash_code="119482488" os_list="linux,windows" file_path="content/browser/web_package/signed_exchange_validity_pinger.cc"/> <item id="signed_in_profile_avatar" added_in_milestone="62" hash_code="108903331" type="0" content_hash_code="72850619" os_list="linux,windows" file_path="chrome/browser/profiles/profile_downloader.cc"/>
diff --git a/tools/traffic_annotation/summary/grouping.xml b/tools/traffic_annotation/summary/grouping.xml index 98be6f78..e71c29e6 100644 --- a/tools/traffic_annotation/summary/grouping.xml +++ b/tools/traffic_annotation/summary/grouping.xml
@@ -390,6 +390,7 @@ <traffic_annotation unique_id="search_suggest_service"/> <traffic_annotation unique_id="remote_suggestions_provider"/> <traffic_annotation unique_id="promo_service"/> + <traffic_annotation unique_id="shopping_tasks_service"/> </sender> <sender name="Speech Recognition"> <traffic_annotation unique_id="speech_recognition_downstream"/>
diff --git a/ui/aura/BUILD.gn b/ui/aura/BUILD.gn index ef7a3da6..eba8f05 100644 --- a/ui/aura/BUILD.gn +++ b/ui/aura/BUILD.gn
@@ -5,6 +5,13 @@ import("//build/config/ui.gni") import("//testing/test.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + component("aura") { public = [ "client/aura_constants.h",
diff --git a/ui/aura_extra/BUILD.gn b/ui/aura_extra/BUILD.gn index cd3bf2d..b46ef76 100644 --- a/ui/aura_extra/BUILD.gn +++ b/ui/aura_extra/BUILD.gn
@@ -4,6 +4,13 @@ import("//build/config/ui.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + component("aura_extra") { sources = [ "aura_extra_export.h",
diff --git a/ui/base/ime/win/tsf_bridge.cc b/ui/base/ime/win/tsf_bridge.cc index 8c40f203..982d5c1 100644 --- a/ui/base/ime/win/tsf_bridge.cc +++ b/ui/base/ime/win/tsf_bridge.cc
@@ -112,10 +112,6 @@ // An ITfThreadMgr object to be used in focus and document management. Microsoft::WRL::ComPtr<ITfThreadMgr> thread_manager_; - // An ITfInputProcessorProfiles object to be used to get current language - // locale profile. - Microsoft::WRL::ComPtr<ITfInputProcessorProfiles> input_processor_profiles_; - // A map from TextInputType to an editable document for TSF. We use multiple // TSF documents that have different InputScopes and TSF attributes based on // the TextInputType associated with the target document. For a TextInputType @@ -133,15 +129,15 @@ // Current focused text input client. Do not free |client_|. TextInputClient* client_ = nullptr; + // Input Type of current focused text input client. + TextInputType input_type_ = TEXT_INPUT_TYPE_NONE; + // Represents the window that is currently owns text input focus. HWND attached_window_handle_ = nullptr; // Handle to ITfKeyTraceEventSink. DWORD key_trace_sink_cookie_ = 0; - // Handle to ITfLanguageProfileNotifySink - DWORD language_profile_cookie_ = 0; - DISALLOW_COPY_AND_ASSIGN(TSFBridgeImpl); }; @@ -157,11 +153,6 @@ if (SUCCEEDED(thread_manager_->QueryInterface(IID_PPV_ARGS(&source)))) { source->UnadviseSink(key_trace_sink_cookie_); } - Microsoft::WRL::ComPtr<ITfSource> language_source; - if (SUCCEEDED(input_processor_profiles_->QueryInterface( - IID_PPV_ARGS(&language_source)))) { - language_source->UnadviseSink(language_profile_cookie_); - } } for (TSFDocumentMap::iterator it = tsf_document_map_.begin(); @@ -186,16 +177,8 @@ return S_OK; // shouldn't return error code in this case. } - HRESULT hr = - ::CoCreateInstance(CLSID_TF_InputProcessorProfiles, nullptr, CLSCTX_ALL, - IID_PPV_ARGS(&input_processor_profiles_)); - if (FAILED(hr)) { - DVLOG(1) << "Failed to create InputProcessorProfiles instance."; - return hr; - } - - hr = ::CoCreateInstance(CLSID_TF_ThreadMgr, nullptr, CLSCTX_ALL, - IID_PPV_ARGS(&thread_manager_)); + HRESULT hr = ::CoCreateInstance(CLSID_TF_ThreadMgr, nullptr, CLSCTX_ALL, + IID_PPV_ARGS(&thread_manager_)); if (FAILED(hr)) { DVLOG(1) << "Failed to create ThreadManager instance."; return hr; @@ -250,6 +233,10 @@ return; } + TextInputType new_input_type = client_->GetTextInputType(); + if (new_input_type == input_type_) + return; + input_type_ = new_input_type; TSFDocument* document = GetAssociatedDocument(); if (!document) return; @@ -258,7 +245,7 @@ // focus notifications for the same text input type so we don't // call AssociateFocus and SetFocus together. Just calling SetFocus // should be sufficient for setting focus on a textstore. - if (client_->GetTextInputType() != TEXT_INPUT_TYPE_NONE) + if (new_input_type != TEXT_INPUT_TYPE_NONE) thread_manager_->SetFocus(document->document_manager.Get()); else UpdateAssociateFocus(); @@ -450,22 +437,6 @@ return hr; } - Microsoft::WRL::ComPtr<ITfSource> language_source; - hr = - input_processor_profiles_->QueryInterface(IID_PPV_ARGS(&language_source)); - if (FAILED(hr)) { - DVLOG(1) << "Failed to get source_ITfInputProcessorProfiles."; - return hr; - } - - hr = language_source->AdviseSink(IID_ITfLanguageProfileNotifySink, - static_cast<ITfTextEditSink*>(text_store), - &language_profile_cookie_); - if (FAILED(hr)) { - DVLOG(1) << "AdviseSink for language profile notify sink failed."; - return hr; - } - if (*source_cookie == TF_INVALID_COOKIE) { DVLOG(1) << "The result of cookie is invalid."; return E_FAIL; @@ -609,8 +580,7 @@ TSFBridgeImpl::TSFDocument* TSFBridgeImpl::GetAssociatedDocument() { if (!client_) return nullptr; - TSFDocumentMap::iterator it = - tsf_document_map_.find(client_->GetTextInputType()); + TSFDocumentMap::iterator it = tsf_document_map_.find(input_type_); if (it == tsf_document_map_.end()) { it = tsf_document_map_.find(TEXT_INPUT_TYPE_TEXT); // This check is necessary because it's possible that we failed to
diff --git a/ui/base/ime/win/tsf_text_store.cc b/ui/base/ime/win/tsf_text_store.cc index 0ff57b5..6006717 100644 --- a/ui/base/ime/win/tsf_text_store.cc +++ b/ui/base/ime/win/tsf_text_store.cc
@@ -87,8 +87,6 @@ *result = static_cast<ITextStoreACP*>(this); } else if (iid == IID_ITfContextOwnerCompositionSink) { *result = static_cast<ITfContextOwnerCompositionSink*>(this); - } else if (iid == IID_ITfLanguageProfileNotifySink) { - *result = static_cast<ITfLanguageProfileNotifySink*>(this); } else if (iid == IID_ITfTextEditSink) { *result = static_cast<ITfTextEditSink*>(this); } else if (iid == IID_ITfKeyTraceEventSink) { @@ -855,15 +853,6 @@ return S_OK; } -HRESULT TSFTextStore::OnLanguageChange(LANGID langid, BOOL* pfAccept) { - return S_OK; -} -HRESULT TSFTextStore::OnLanguageChanged() { - if (text_input_client_) - text_input_client_->OnInputMethodChanged(); - return S_OK; -} - HRESULT TSFTextStore::OnKeyTraceDown(WPARAM wParam, LPARAM lParam) { // fire the event right away if we're in composition if (has_composition_range_) {
diff --git a/ui/base/ime/win/tsf_text_store.h b/ui/base/ime/win/tsf_text_store.h index 63b6091..efcc912 100644 --- a/ui/base/ime/win/tsf_text_store.h +++ b/ui/base/ime/win/tsf_text_store.h
@@ -102,7 +102,6 @@ class COMPONENT_EXPORT(UI_BASE_IME_WIN) TSFTextStore : public ITextStoreACP, public ITfContextOwnerCompositionSink, - public ITfLanguageProfileNotifySink, public ITfKeyTraceEventSink, public ITfTextEditSink { public: @@ -218,10 +217,6 @@ IFACEMETHODIMP OnEndComposition( ITfCompositionView* composition_view) override; - // ITfLanguageProfileNotifySink: - IFACEMETHODIMP OnLanguageChange(LANGID langid, BOOL* pfAccept) override; - IFACEMETHODIMP OnLanguageChanged() override; - // ITfTextEditSink: IFACEMETHODIMP OnEndEdit(ITfContext* context, TfEditCookie read_only_edit_cookie,
diff --git a/ui/chromeos/search_box/DEPS b/ui/chromeos/search_box/DEPS deleted file mode 100644 index 446935f..0000000 --- a/ui/chromeos/search_box/DEPS +++ /dev/null
@@ -1,3 +0,0 @@ -include_rules = [ - "+ui/strings/grit/ui_strings.h", -]
diff --git a/ui/display/manager/display_manager.cc b/ui/display/manager/display_manager.cc index 7d909ddd..5fb0a934 100644 --- a/ui/display/manager/display_manager.cc +++ b/ui/display/manager/display_manager.cc
@@ -1414,11 +1414,13 @@ const int kVerticalOffsetPx = 100; // Layout the 2nd display below the primary as with the real device. - ManagedDisplayInfo display = ManagedDisplayInfo::CreateFromSpec( + ManagedDisplayInfo display = ManagedDisplayInfo::CreateFromSpecWithID( base::StringPrintf("%d+%d-%dx%d", host_bounds.x(), host_bounds.bottom() + kVerticalOffsetPx, native_display_mode->size().width(), - native_display_mode->size().height())); + native_display_mode->size().height()), + first_display.id() + 1); + display.SetManagedDisplayModes(std::move(display_modes)); new_display_info_list.push_back(std::move(display)); }
diff --git a/ui/events/ozone/BUILD.gn b/ui/events/ozone/BUILD.gn index 3f08cf23..313dfdc 100644 --- a/ui/events/ozone/BUILD.gn +++ b/ui/events/ozone/BUILD.gn
@@ -5,6 +5,13 @@ import("//build/config/features.gni") import("//build/config/ui.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + assert(use_ozone) component("ozone") {
diff --git a/ui/message_center/BUILD.gn b/ui/message_center/BUILD.gn index 7104a5f..f1ea064 100644 --- a/ui/message_center/BUILD.gn +++ b/ui/message_center/BUILD.gn
@@ -8,6 +8,13 @@ import("//testing/test.gni") import("//ui/base/ui_features.gni") +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + aggregate_vector_icons("message_center_vector_icons") { icon_directory = "vector_icons"
diff --git a/ui/ozone/platform/wayland/BUILD.gn b/ui/ozone/platform/wayland/BUILD.gn index 95ed45ea..203e295 100644 --- a/ui/ozone/platform/wayland/BUILD.gn +++ b/ui/ozone/platform/wayland/BUILD.gn
@@ -4,6 +4,7 @@ visibility = [ "//ui/ozone/*" ] +import("//build/config/chromeos/ui_mode.gni") import("//build/config/linux/gtk/gtk.gni") import("//build/config/linux/pkg_config.gni") import("//gpu/vulkan/features.gni") @@ -157,6 +158,7 @@ "//third_party/wayland-protocols:linux_explicit_synchronization_protocol", "//third_party/wayland-protocols:presentation_time_protocol", "//third_party/wayland-protocols:text_input_protocol", + "//third_party/wayland-protocols:viewporter_protocol", "//third_party/wayland-protocols:wayland_drm_protocol", "//third_party/wayland-protocols:xdg_decoration_protocol", "//third_party/wayland-protocols:xdg_foreign", @@ -211,6 +213,11 @@ ] } + # TODO(crbug.com/1052397): Rename chromeos_is_browser_only to is_lacros. + if (chromeos_is_browser_only) { + deps += [ "//chromeos/crosapi/cpp" ] + } + defines = [ "OZONE_IMPLEMENTATION" ] if (use_wayland_gbm) { @@ -298,6 +305,10 @@ "test/test_subsurface.h", "test/test_touch.cc", "test/test_touch.h", + "test/test_viewport.cc", + "test/test_viewport.h", + "test/test_viewporter.cc", + "test/test_viewporter.h", "test/test_wayland_server_thread.cc", "test/test_wayland_server_thread.h", "test/test_xdg_popup.cc", @@ -320,6 +331,7 @@ "//third_party/wayland-protocols:linux_dmabuf_protocol", "//third_party/wayland-protocols:presentation_time_protocol", "//third_party/wayland-protocols:text_input_protocol", + "//third_party/wayland-protocols:viewporter_protocol", "//third_party/wayland-protocols:xdg_shell_protocol", "//ui/gfx/geometry:geometry", ]
diff --git a/ui/ozone/platform/wayland/common/wayland_object.cc b/ui/ozone/platform/wayland/common/wayland_object.cc index 0bb3df4..6d9c7536 100644 --- a/ui/ozone/platform/wayland/common/wayland_object.cc +++ b/ui/ozone/platform/wayland/common/wayland_object.cc
@@ -11,6 +11,7 @@ #include <linux-explicit-synchronization-unstable-v1-client-protocol.h> #include <presentation-time-client-protocol.h> #include <text-input-unstable-v1-client-protocol.h> +#include <viewporter-client-protocol.h> #include <wayland-drm-client-protocol.h> #include <xdg-decoration-unstable-v1-client-protocol.h> #include <xdg-foreign-unstable-v1-client-protocol.h> @@ -182,6 +183,15 @@ void (*ObjectTraits<struct wp_presentation_feedback>::deleter)( struct wp_presentation_feedback*) = &wp_presentation_feedback_destroy; +const wl_interface* ObjectTraits<wp_viewport>::interface = + &wp_viewport_interface; +void (*ObjectTraits<wp_viewport>::deleter)(wp_viewport*) = &wp_viewport_destroy; + +const wl_interface* ObjectTraits<wp_viewporter>::interface = + &wp_viewporter_interface; +void (*ObjectTraits<wp_viewporter>::deleter)(wp_viewporter*) = + &wp_viewporter_destroy; + const wl_interface* ObjectTraits<xdg_wm_base>::interface = &xdg_wm_base_interface; void (*ObjectTraits<xdg_wm_base>::deleter)(xdg_wm_base*) = &xdg_wm_base_destroy;
diff --git a/ui/ozone/platform/wayland/common/wayland_object.h b/ui/ozone/platform/wayland/common/wayland_object.h index a48997cd7..bfc61f88 100644 --- a/ui/ozone/platform/wayland/common/wayland_object.h +++ b/ui/ozone/platform/wayland/common/wayland_object.h
@@ -35,6 +35,8 @@ struct wl_touch; struct wp_presentation; struct wp_presentation_feedback; +struct wp_viewport; +struct wp_viewporter; struct xdg_wm_base; struct xdg_surface; struct xdg_toplevel; @@ -240,6 +242,18 @@ }; template <> +struct ObjectTraits<wp_viewport> { + static const wl_interface* interface; + static void (*deleter)(wp_viewport*); +}; + +template <> +struct ObjectTraits<wp_viewporter> { + static const wl_interface* interface; + static void (*deleter)(wp_viewporter*); +}; + +template <> struct ObjectTraits<xdg_wm_base> { static const wl_interface* interface; static void (*deleter)(xdg_wm_base*);
diff --git a/ui/ozone/platform/wayland/common/wayland_util.cc b/ui/ozone/platform/wayland/common/wayland_util.cc index 3b0b8829..042cfc8e 100644 --- a/ui/ozone/platform/wayland/common/wayland_util.cc +++ b/ui/ozone/platform/wayland/common/wayland_util.cc
@@ -157,6 +157,98 @@ child_bounds.size()); } +wl_output_transform ToWaylandTransform(gfx::OverlayTransform transform) { + switch (transform) { + case gfx::OVERLAY_TRANSFORM_NONE: + return WL_OUTPUT_TRANSFORM_NORMAL; + case gfx::OVERLAY_TRANSFORM_FLIP_HORIZONTAL: + return WL_OUTPUT_TRANSFORM_FLIPPED; + case gfx::OVERLAY_TRANSFORM_FLIP_VERTICAL: + return WL_OUTPUT_TRANSFORM_FLIPPED_180; + case gfx::OVERLAY_TRANSFORM_ROTATE_90: + return WL_OUTPUT_TRANSFORM_90; + case gfx::OVERLAY_TRANSFORM_ROTATE_180: + return WL_OUTPUT_TRANSFORM_180; + case gfx::OVERLAY_TRANSFORM_ROTATE_270: + return WL_OUTPUT_TRANSFORM_270; + default: + break; + } + NOTREACHED(); + return WL_OUTPUT_TRANSFORM_NORMAL; +} + +gfx::Rect ApplyWaylandTransform(const gfx::Rect& rect, + const gfx::Size& bounds, + wl_output_transform transform) { + gfx::Rect result = rect; + switch (transform) { + case WL_OUTPUT_TRANSFORM_NORMAL: + break; + case WL_OUTPUT_TRANSFORM_FLIPPED: + result.set_x(bounds.width() - rect.x() - rect.width()); + break; + case WL_OUTPUT_TRANSFORM_FLIPPED_90: + result.set_x(rect.y()); + result.set_y(rect.x()); + result.set_width(rect.height()); + result.set_height(rect.width()); + break; + case WL_OUTPUT_TRANSFORM_FLIPPED_180: + result.set_y(bounds.height() - rect.y() - rect.height()); + break; + case WL_OUTPUT_TRANSFORM_FLIPPED_270: + result.set_x(bounds.height() - rect.y() - rect.height()); + result.set_y(bounds.width() - rect.x() - rect.width()); + result.set_width(rect.height()); + result.set_height(rect.width()); + break; + case WL_OUTPUT_TRANSFORM_90: + result.set_x(rect.y()); + result.set_y(bounds.width() - rect.x() - rect.width()); + result.set_width(rect.height()); + result.set_height(rect.width()); + break; + case WL_OUTPUT_TRANSFORM_180: + result.set_x(bounds.width() - rect.x() - rect.width()); + result.set_y(bounds.height() - rect.y() - rect.height()); + break; + case WL_OUTPUT_TRANSFORM_270: + result.set_x(bounds.height() - rect.y() - rect.height()); + result.set_y(rect.x()); + result.set_width(rect.height()); + result.set_height(rect.width()); + break; + default: + NOTREACHED(); + break; + } + return result; +} + +gfx::Size ApplyWaylandTransform(const gfx::Size& size, + wl_output_transform transform) { + gfx::Size result = size; + switch (transform) { + case WL_OUTPUT_TRANSFORM_NORMAL: + case WL_OUTPUT_TRANSFORM_FLIPPED: + case WL_OUTPUT_TRANSFORM_FLIPPED_180: + case WL_OUTPUT_TRANSFORM_180: + break; + case WL_OUTPUT_TRANSFORM_FLIPPED_90: + case WL_OUTPUT_TRANSFORM_FLIPPED_270: + case WL_OUTPUT_TRANSFORM_90: + case WL_OUTPUT_TRANSFORM_270: + result.set_width(size.height()); + result.set_height(size.width()); + break; + default: + NOTREACHED(); + break; + } + return result; +} + bool IsMenuType(ui::PlatformWindowType type) { return type == ui::PlatformWindowType::kMenu || type == ui::PlatformWindowType::kPopup;
diff --git a/ui/ozone/platform/wayland/common/wayland_util.h b/ui/ozone/platform/wayland/common/wayland_util.h index 4452251..d755de9 100644 --- a/ui/ozone/platform/wayland/common/wayland_util.h +++ b/ui/ozone/platform/wayland/common/wayland_util.h
@@ -12,6 +12,7 @@ #include "base/files/scoped_file.h" #include "base/macros.h" #include "ui/gfx/geometry/rect.h" +#include "ui/gfx/overlay_transform.h" #include "ui/ozone/platform/wayland/common/wayland_object.h" #include "ui/platform_window/platform_window_init_properties.h" @@ -58,6 +59,21 @@ gfx::Rect TranslateBoundsToTopLevelCoordinates(const gfx::Rect& child_bounds, const gfx::Rect& parent_bounds); +// Returns wl_output_transform corresponding |transform|. |transform| is an +// enumeration of a fixed selection of transformations. +wl_output_transform ToWaylandTransform(gfx::OverlayTransform transform); + +// |bounds| contains |rect|. ApplyWaylandTransform() returns the resulted +// |rect| after transformation is applied to |bounds| containing |rect| as a +// whole. +gfx::Rect ApplyWaylandTransform(const gfx::Rect& rect, + const gfx::Size& bounds, + wl_output_transform transform); + +// Applies transformation to |size|. +gfx::Size ApplyWaylandTransform(const gfx::Size& size, + wl_output_transform transform); + // Says if the type is kPopup or kMenu. bool IsMenuType(ui::PlatformWindowType type);
diff --git a/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.cc b/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.cc index 8ee69e5b..b77c13b5 100644 --- a/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.cc +++ b/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.cc
@@ -46,8 +46,10 @@ } void GbmSurfacelessWayland::QueueOverlayPlane(OverlayPlane plane, - uint32_t buffer_id) { - unsubmitted_frames_.back()->planes.push_back({std::move(plane), buffer_id}); + BufferId buffer_id) { + auto result = + unsubmitted_frames_.back()->planes.emplace(buffer_id, std::move(plane)); + DCHECK(result.second); } bool GbmSurfacelessWayland::ScheduleOverlayPlane( @@ -100,7 +102,7 @@ return; } - // TODO(dcastagna): remove glFlush since eglImageFlushExternalEXT called on + // TODO(fangzhoug): remove glFlush since eglImageFlushExternalEXT called on // the image should be enough (https://crbug.com/720045). if (!no_gl_flush_for_tests_) glFlush(); @@ -123,16 +125,16 @@ // Uset in-fences provided in the overlays. If there are none, we insert our // own fence and wait. for (auto& plane : frame->planes) { - if (plane.plane.gpu_fence) - fences.push_back(std::move(plane.plane.gpu_fence)); + if (plane.second.gpu_fence) + fences.push_back(std::move(plane.second.gpu_fence)); } base::OnceClosure fence_wait_task; if (!fences.empty()) { fence_wait_task = base::BindOnce(&WaitForGpuFences, std::move(fences)); } else { - // TODO: the following should be replaced by a per surface flush as it gets - // implemented in GL drivers. + // TODO(fangzhoug): the following should be replaced by a per surface flush + // as it gets implemented in GL drivers. EGLSyncKHR fence = InsertFence(has_implicit_external_sync_); CHECK_NE(fence, EGL_NO_SYNC_KHR) << "eglCreateSyncKHR failed"; @@ -238,18 +240,14 @@ std::vector<ui::ozone::mojom::WaylandOverlayConfigPtr> overlay_configs; for (const auto& plane : submitted_frame->planes) { overlay_configs.push_back( - ui::ozone::mojom::WaylandOverlayConfig::From(plane.plane)); - overlay_configs.back()->buffer_id = plane.buffer_id; - if (plane.plane.z_order == 0) { + ui::ozone::mojom::WaylandOverlayConfig::From(plane.second)); + overlay_configs.back()->buffer_id = plane.first; + if (plane.second.z_order == 0) { overlay_configs.back()->damage_region = submitted_frame->damage_region_; - submitted_frame->buffer_id = plane.buffer_id; + submitted_frame->buffer_id = plane.first; } } buffer_manager_->CommitOverlays(widget_, std::move(overlay_configs)); - - submitted_frame->unacked_submissions = submitted_frame->planes.size(); - submitted_frame->unacked_presentations = submitted_frame->planes.size(); - submitted_frame->planes.clear(); submitted_frames_.push_back(std::move(submitted_frame)); } } @@ -271,22 +269,46 @@ no_gl_flush_for_tests_ = true; } -void GbmSurfacelessWayland::OnSubmission(uint32_t buffer_id, +void GbmSurfacelessWayland::OnSubmission(BufferId buffer_id, const gfx::SwapResult& swap_result) { // submitted_frames_ may temporarily have more than one buffer in it if // buffers are released out of order by the Wayland server. DCHECK(!submitted_frames_.empty()); - if (--submitted_frames_.front()->unacked_submissions) - return; - auto submitted_frame = std::move(submitted_frames_.front()); - submitted_frames_.erase(submitted_frames_.begin()); - submitted_frame->overlays.clear(); + size_t erased = 0; + for (auto& submitted_frame : submitted_frames_) { + if ((erased = submitted_frame->planes.erase(buffer_id)) > 0) { + // |completion_callback| only takes 1 SwapResult. It's possible that only + // one of the buffers in a frame gets a SWAP_FAILED or + // SWAP_NAK_RECREATE_BUFFERS. Don't replace a failed swap_result with + // SWAP_ACK. If both SWAP_FAILED and SWAP_NAK_RECREATE_BUFFERS happens, + // this swap is treated as SWAP_FAILED. + if (submitted_frame->swap_result == gfx::SwapResult::SWAP_ACK || + swap_result == gfx::SwapResult::SWAP_FAILED) { + submitted_frame->swap_result = swap_result; + } + submitted_frame->pending_presentation_buffers.insert(buffer_id); + break; + } + } + DCHECK(erased); - std::move(submitted_frame->completion_callback) - .Run(gfx::SwapCompletionResult(swap_result)); + // Following while loop covers below scenario: + // frame_1 submitted a buffer_1 for overlay; frame_2 submitted a buffer_2 + // for primary plane. This can happen at the end of a single-on-top overlay. + // buffer_1 is not attached immediately due to unack'ed wl_frame_callback. + // buffer_2 is attached immediately Onsubmission() of buffer_2 runs. + while (!submitted_frames_.empty() && + submitted_frames_.front()->planes.empty()) { + auto submitted_frame = std::move(submitted_frames_.front()); + submitted_frames_.erase(submitted_frames_.begin()); + submitted_frame->overlays.clear(); - pending_presentation_frames_.push_back(std::move(submitted_frame)); + std::move(submitted_frame->completion_callback) + .Run(gfx::SwapCompletionResult(submitted_frame->swap_result)); + + pending_presentation_frames_.push_back(std::move(submitted_frame)); + } if (swap_result != gfx::SwapResult::SWAP_ACK) { last_swap_buffers_result_ = false; @@ -297,10 +319,20 @@ } void GbmSurfacelessWayland::OnPresentation( - uint32_t buffer_id, + BufferId buffer_id, const gfx::PresentationFeedback& feedback) { + DCHECK(!submitted_frames_.empty() || !pending_presentation_frames_.empty()); + + size_t erased = 0; + for (auto& frame : pending_presentation_frames_) { + if ((erased = frame->pending_presentation_buffers.erase(buffer_id)) > 0) { + frame->feedback = feedback; + break; + } + } + // Items in |submitted_frames_| will not be moved to - // |pending_presentation_frames_| until |unacked_submissions| decrements to 0. + // |pending_presentation_frames_| until |planes| is empty. // Example: // A SwapBuffers that submitted 2 buffers (buffer_1 and buffer_2) will push // a submitted_frame expecting 2 submission feedbacks and 2 presentation @@ -312,24 +344,26 @@ // buffer_1:submission > buffer_1:presentation > buffer_2:submission > // buffer_2:presentation // In this case, we have to find the item in |submitted_frames_| and - // decrement |unacked_presentations| there. - // TODO(fangzhoug): This solution is sub-optimal and confusing. It increases - // the number of IPCs from browser to gpu. The barrier logic should be in the - // browser process. - if (pending_presentation_frames_.empty()) { - auto it = submitted_frames_.begin(); - for (; !(*it)->unacked_presentations; ++it) - ; - --(*it)->unacked_presentations; - return; + // remove from |pending_presentation_buffers| there. + if (!erased) { + for (auto& frame : submitted_frames_) { + if ((erased = frame->pending_presentation_buffers.erase(buffer_id)) > 0) { + frame->feedback = feedback; + break; + } + } } - auto* frame = pending_presentation_frames_.front().get(); - if (--frame->unacked_presentations) - return; + DCHECK(erased); - std::move(frame->presentation_callback).Run(feedback); - pending_presentation_frames_.erase(pending_presentation_frames_.begin()); + while (!pending_presentation_frames_.empty() && + pending_presentation_frames_.front() + ->pending_presentation_buffers.empty()) { + auto* frame = pending_presentation_frames_.front().get(); + DCHECK(frame->planes.empty()); + std::move(frame->presentation_callback).Run(frame->feedback); + pending_presentation_frames_.erase(pending_presentation_frames_.begin()); + } } } // namespace ui
diff --git a/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.h b/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.h index 13dbd84..910b9a70 100644 --- a/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.h +++ b/ui/ozone/platform/wayland/gpu/gbm_surfaceless_wayland.h
@@ -7,6 +7,7 @@ #include <memory> +#include "base/containers/small_map.h" #include "base/macros.h" #include "base/memory/weak_ptr.h" #include "ui/gfx/native_widget_types.h" @@ -19,6 +20,8 @@ class WaylandBufferManagerGpu; +using BufferId = uint32_t; + // A GLSurface for Wayland Ozone platform that uses surfaceless drawing. Drawing // and displaying happens directly through NativePixmap buffers. CC would call // into SurfaceFactoryOzone to allocate the buffers and then call @@ -29,7 +32,7 @@ GbmSurfacelessWayland(WaylandBufferManagerGpu* buffer_manager, gfx::AcceleratedWidget widget); - void QueueOverlayPlane(OverlayPlane plane, uint32_t buffer_id); + void QueueOverlayPlane(OverlayPlane plane, BufferId buffer_id); // gl::GLSurface: bool ScheduleOverlayPlane(int z_order, @@ -62,22 +65,19 @@ private: FRIEND_TEST_ALL_PREFIXES(WaylandSurfaceFactoryTest, GbmSurfacelessWaylandCheckOrderOfCallbacksTest); + FRIEND_TEST_ALL_PREFIXES(WaylandSurfaceFactoryTest, + GbmSurfacelessWaylandCommitOverlaysCallbacksTest); + FRIEND_TEST_ALL_PREFIXES(WaylandSurfaceFactoryTest, + GbmSurfacelessWaylandGroupOnSubmissionCallbacksTest); ~GbmSurfacelessWayland() override; // WaylandSurfaceGpu overrides: - void OnSubmission(uint32_t buffer_id, + void OnSubmission(BufferId buffer_id, const gfx::SwapResult& swap_result) override; - void OnPresentation(uint32_t buffer_id, + void OnPresentation(BufferId buffer_id, const gfx::PresentationFeedback& feedback) override; - struct PlaneData { - OverlayPlane plane; - // The id of the buffer, which represents buffer that backs this overlay - // plane. - const uint32_t buffer_id; - }; - struct PendingFrame { PendingFrame(); ~PendingFrame(); @@ -89,24 +89,25 @@ bool ready = false; // The id of the buffer, which represents this frame. - uint32_t buffer_id = 0; + BufferId buffer_id = 0; // A region of the updated content in a corresponding frame. It's used to // advice Wayland which part of a buffer is going to be updated. Passing {0, // 0, 0, 0} results in a whole buffer update on the Wayland compositor side. gfx::Rect damage_region_ = gfx::Rect(); + // TODO(fangzhoug): This should be changed to support Vulkan. std::vector<gl::GLSurfaceOverlay> overlays; SwapCompletionCallback completion_callback; PresentationCallback presentation_callback; bool schedule_planes_succeeded = false; - std::vector<PlaneData> planes; - // TODO(fangzhoug): This is a temporary solution to barrier swap/present - // acks of a frame that contains multiple buffer commits. Next step is to - // barrier in browser process to avoid extra IPC hops. - size_t unacked_submissions; - size_t unacked_presentations; + // Maps |buffer_id| to an OverlayPlane, used for committing overlays and + // wait for OnSubmission's. + base::small_map<std::map<BufferId, OverlayPlane>> planes; + base::flat_set<BufferId> pending_presentation_buffers; + gfx::SwapResult swap_result = gfx::SwapResult::SWAP_ACK; + gfx::PresentationFeedback feedback; }; void MaybeSubmitFrames();
diff --git a/ui/ozone/platform/wayland/gpu/wayland_surface_factory_unittest.cc b/ui/ozone/platform/wayland/gpu/wayland_surface_factory_unittest.cc index ebec5b4..1c5062651 100644 --- a/ui/ozone/platform/wayland/gpu/wayland_surface_factory_unittest.cc +++ b/ui/ozone/platform/wayland/gpu/wayland_surface_factory_unittest.cc
@@ -19,6 +19,7 @@ #include "ui/ozone/platform/wayland/gpu/wayland_buffer_manager_gpu.h" #include "ui/ozone/platform/wayland/gpu/wayland_surface_factory.h" #include "ui/ozone/platform/wayland/host/wayland_buffer_manager_host.h" +#include "ui/ozone/platform/wayland/host/wayland_subsurface.h" #include "ui/ozone/platform/wayland/host/wayland_window.h" #include "ui/ozone/platform/wayland/test/mock_surface.h" #include "ui/ozone/platform/wayland/test/scoped_wl_array.h" @@ -125,19 +126,23 @@ // that 1) the image has been sent to be shown after being scheduled 2) the // image is displayed. This sort of mimics a buffer queue, but in a simpliear // way. - void FinishSwapBuffersAsync(uint32_t local_swap_id, - scoped_refptr<FakeGLImageNativePixmap> gl_image, - gfx::SwapCompletionResult result) { + void FinishSwapBuffersAsync( + uint32_t local_swap_id, + std::vector<scoped_refptr<FakeGLImageNativePixmap>> gl_images, + gfx::SwapCompletionResult result) { last_finish_swap_id_ = pending_local_swap_ids_.front(); pending_local_swap_ids_.pop(); - EXPECT_EQ(gl_image->GetAssociateWithSwapId(), last_finish_swap_id_); - EXPECT_TRUE(gl_image->busy() && !gl_image->displayed()); - if (displayed_image_) - displayed_image_->SetDisplayed(false); - displayed_image_ = gl_image; - displayed_image_->SetBusy(false); - displayed_image_->SetDisplayed(true); + for (auto& gl_image : gl_images) { + EXPECT_EQ(gl_image->GetAssociateWithSwapId(), last_finish_swap_id_); + EXPECT_TRUE(gl_image->busy() && !gl_image->displayed()); + gl_image->SetBusy(false); + gl_image->SetDisplayed(true); + } + + for (auto& displayed_image : displayed_images_) + displayed_image->SetDisplayed(false); + displayed_images_ = std::move(gl_images); } void BufferPresented(uint64_t local_swap_id, @@ -156,7 +161,7 @@ base::queue<uint64_t> pending_local_swap_ids_; // Keeps track of a displayed image. - scoped_refptr<FakeGLImageNativePixmap> displayed_image_; + std::vector<scoped_refptr<FakeGLImageNativePixmap>> displayed_images_; }; } // namespace @@ -253,10 +258,13 @@ 0, gfx::OverlayTransform::OVERLAY_TRANSFORM_FLIP_VERTICAL, gl_image.get(), window_->GetBounds(), {}, false, nullptr); + std::vector<scoped_refptr<FakeGLImageNativePixmap>> gl_images; + gl_images.push_back(gl_image); + // And submit each image. They will be executed in FIFO manner. gl_surface->SwapBuffersAsync( base::BindOnce(&CallbacksHelper::FinishSwapBuffersAsync, - base::Unretained(&cbs_helper), swap_id, gl_image), + base::Unretained(&cbs_helper), swap_id, gl_images), base::BindOnce(&CallbacksHelper::BufferPresented, base::Unretained(&cbs_helper), swap_id)); } @@ -402,6 +410,473 @@ mock_surface->SendFrameCallback(); } +TEST_P(WaylandSurfaceFactoryTest, + GbmSurfacelessWaylandCommitOverlaysCallbacksTest) { + // GbmSurfacelessWaylandCheckOrderOfCallbacksTest tests with one buffer per + // frame. This tests multiple buffers per-frame and order of + // SwapCompletionCallbacks. Even when all OnSubmission from later frames are + // called, their SwapCompletionCallbacks should not run until previous frames' + // SwapCompletionCallbacks run. + gl::SetGLImplementation(gl::kGLImplementationEGLGLES2); + + buffer_manager_gpu_->set_gbm_device(std::make_unique<MockGbmDevice>()); + + auto* gl_ozone = surface_factory_->GetGLOzone(gl::kGLImplementationEGLGLES2); + auto gl_surface = gl_ozone->CreateSurfacelessViewGLSurface(widget_); + EXPECT_TRUE(gl_surface); + gl_surface->SetRelyOnImplicitSync(); + static_cast<ui::GbmSurfacelessWayland*>(gl_surface.get()) + ->SetNoGLFlushForTests(); + + // Expect to create 4 buffers. + EXPECT_CALL(*server_.zwp_linux_dmabuf_v1(), CreateParams(_, _, _)).Times(4); + + // Create buffers and FakeGlImageNativePixmap. + std::vector<scoped_refptr<FakeGLImageNativePixmap>> fake_gl_image; + for (int i = 0; i < 4; ++i) { + auto native_pixmap = surface_factory_->CreateNativePixmap( + widget_, nullptr, window_->GetBounds().size(), + gfx::BufferFormat::BGRA_8888, gfx::BufferUsage::SCANOUT); + fake_gl_image.push_back(base::MakeRefCounted<FakeGLImageNativePixmap>( + native_pixmap, window_->GetBounds().size())); + + Sync(); + + // Create one buffer at a time. + auto params_vector = server_.zwp_linux_dmabuf_v1()->buffer_params(); + DCHECK_EQ(params_vector.size(), 1u); + zwp_linux_buffer_params_v1_send_created( + params_vector.front()->resource(), + params_vector.front()->buffer_resource()); + + Sync(); + } + + auto* mock_primary_surface = server_.GetObject<wl::MockSurface>( + window_->root_surface()->GetSurfaceId()); + + CallbacksHelper cbs_helper; + // Submit a frame with only primary plane + { + // Associate each image with swap id so that we could track released + // buffers. + auto swap_id = cbs_helper.GetNextLocalSwapId(); + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[0]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[0]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + 0, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[0].get(), window_->GetBounds(), {}, false, nullptr); + + std::vector<scoped_refptr<FakeGLImageNativePixmap>> gl_images; + gl_images.push_back(fake_gl_image[0]); + + // And submit each image. They will be executed in FIFO manner. + gl_surface->SwapBuffersAsync( + base::BindOnce(&CallbacksHelper::FinishSwapBuffersAsync, + base::Unretained(&cbs_helper), swap_id, gl_images), + base::BindOnce(&CallbacksHelper::BufferPresented, + base::Unretained(&cbs_helper), swap_id)); + } + + // Let's sync so that 1) GbmSurfacelessWayland submits the buffer according to + // internal queue and fake server processes the request. + + // Also, we expect only one buffer to be committed. + EXPECT_CALL(*mock_primary_surface, Attach(_, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Frame(_)).Times(1); + EXPECT_CALL(*mock_primary_surface, DamageBuffer(_, _, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Commit()).Times(1); + + Sync(); + + testing::Mock::VerifyAndClearExpectations(&mock_primary_surface); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // We have just received Attach/DamageBuffer/Commit for buffer with swap + // id=0u. The SwapCompletionCallback must be executed automatically as long as + // we didn't have any buffers attached to the surface before. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), 0u); + + cbs_helper.ResetLastFinishedSwapId(); + + for (const auto& gl_image : fake_gl_image) { + // All the images except the first one, which was associated with swap + // id=0u, must be busy and not displayed. The first one must be displayed. + if (gl_image->GetAssociateWithSwapId() == 0u) { + EXPECT_FALSE(gl_image->busy()); + EXPECT_TRUE(gl_image->displayed()); + } else { + EXPECT_FALSE(gl_image->displayed()); + } + } + + // Submit another frame with only primary plane + { + // Associate each image with swap id so that we could track released + // buffers. + auto swap_id = cbs_helper.GetNextLocalSwapId(); + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[1]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[1]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + 0, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[1].get(), window_->GetBounds(), {}, false, nullptr); + + std::vector<scoped_refptr<FakeGLImageNativePixmap>> gl_images; + gl_images.push_back(fake_gl_image[1]); + + // And submit each image. They will be executed in FIFO manner. + gl_surface->SwapBuffersAsync( + base::BindOnce(&CallbacksHelper::FinishSwapBuffersAsync, + base::Unretained(&cbs_helper), swap_id, gl_images), + base::BindOnce(&CallbacksHelper::BufferPresented, + base::Unretained(&cbs_helper), swap_id)); + } + + // Expect one buffer to be committed. + EXPECT_CALL(*mock_primary_surface, Attach(_, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Frame(_)).Times(1); + EXPECT_CALL(*mock_primary_surface, DamageBuffer(_, _, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Commit()).Times(1); + + // Send the frame callback so that pending buffer for swap id=1u is processed + // and swapped. + mock_primary_surface->SendFrameCallback(); + + Sync(); + + testing::Mock::VerifyAndClearExpectations(&mock_primary_surface); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // Even though the second buffer was submitted, we mustn't receive + // SwapCompletionCallback until the previous buffer is released. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), + std::numeric_limits<uint32_t>::max()); + + // Submit another frame with 2 overlays, 0 primary plane. + { + // Associate each image with swap id so that we could track released + // buffers. + auto swap_id = cbs_helper.GetNextLocalSwapId(); + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[2]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[2]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + -1, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[2].get(), window_->GetBounds(), {}, false, nullptr); + + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[3]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[3]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + 1, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[3].get(), window_->GetBounds(), {}, false, nullptr); + + std::vector<scoped_refptr<FakeGLImageNativePixmap>> gl_images; + gl_images.push_back(fake_gl_image[2]); + gl_images.push_back(fake_gl_image[3]); + + // And submit each image. They will be executed in FIFO manner. + gl_surface->SwapBuffersAsync( + base::BindOnce(&CallbacksHelper::FinishSwapBuffersAsync, + base::Unretained(&cbs_helper), swap_id, gl_images), + base::BindOnce(&CallbacksHelper::BufferPresented, + base::Unretained(&cbs_helper), swap_id)); + } + // Expect parent surface to be committed without a buffer. + EXPECT_CALL(*mock_primary_surface, Attach(_, _, _)).Times(0); + EXPECT_CALL(*mock_primary_surface, Frame(_)).Times(1); + EXPECT_CALL(*mock_primary_surface, DamageBuffer(_, _, _, _)).Times(0); + EXPECT_CALL(*mock_primary_surface, Commit()).Times(1); + + // Send the frame callback so that pending buffer for swap id=2u is processed + // and swapped. + mock_primary_surface->SendFrameCallback(); + + Sync(); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // Even though OnSubmission can come back because 2 overlays are submitted to + // new wl_surfaces so OnSubmission for third frame has already run, + // GbmSurfacelessWayland should not run SwapCompletionCallback out of order. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), + std::numeric_limits<uint32_t>::max()); + + // This will result in Wayland server releasing previously attached buffer for + // swap id=1u and calling OnSubmission for buffer with swap id=1u. + mock_primary_surface->ReleaseBuffer( + mock_primary_surface->prev_attached_buffer()); + + Sync(); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // We should expect next 2 SwapCompletionCallbacks for the next 2 swap ids + // consecutively. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), 2u); + + cbs_helper.ResetLastFinishedSwapId(); + + for (const auto& gl_image : fake_gl_image) { + if (gl_image->GetAssociateWithSwapId() == 2u) { + EXPECT_TRUE(gl_image->displayed()); + EXPECT_FALSE(gl_image->busy()); + } else { + EXPECT_FALSE(gl_image->displayed()); + } + } +} + +TEST_P(WaylandSurfaceFactoryTest, + GbmSurfacelessWaylandGroupOnSubmissionCallbacksTest) { + // This tests multiple buffers per-frame. GbmSurfacelessWayland should wait + // for all OnSubmission calls targeting the same frame before running + // SwapCompletionCallbacks. + gl::SetGLImplementation(gl::kGLImplementationEGLGLES2); + + buffer_manager_gpu_->set_gbm_device(std::make_unique<MockGbmDevice>()); + + auto* gl_ozone = surface_factory_->GetGLOzone(gl::kGLImplementationEGLGLES2); + auto gl_surface = gl_ozone->CreateSurfacelessViewGLSurface(widget_); + EXPECT_TRUE(gl_surface); + gl_surface->SetRelyOnImplicitSync(); + static_cast<ui::GbmSurfacelessWayland*>(gl_surface.get()) + ->SetNoGLFlushForTests(); + + // Expect to create 4 buffers. + EXPECT_CALL(*server_.zwp_linux_dmabuf_v1(), CreateParams(_, _, _)).Times(4); + + // Create buffers and FakeGlImageNativePixmap. + std::vector<scoped_refptr<FakeGLImageNativePixmap>> fake_gl_image; + for (int i = 0; i < 4; ++i) { + auto native_pixmap = surface_factory_->CreateNativePixmap( + widget_, nullptr, window_->GetBounds().size(), + gfx::BufferFormat::BGRA_8888, gfx::BufferUsage::SCANOUT); + fake_gl_image.push_back(base::MakeRefCounted<FakeGLImageNativePixmap>( + native_pixmap, window_->GetBounds().size())); + + Sync(); + + // Create one buffer at a time. + auto params_vector = server_.zwp_linux_dmabuf_v1()->buffer_params(); + DCHECK_EQ(params_vector.size(), 1u); + zwp_linux_buffer_params_v1_send_created( + params_vector.front()->resource(), + params_vector.front()->buffer_resource()); + + Sync(); + } + + auto* mock_primary_surface = server_.GetObject<wl::MockSurface>( + window_->root_surface()->GetSurfaceId()); + + CallbacksHelper cbs_helper; + // Submit a frame with 1 primary plane and 1 overlay + { + // Associate each image with swap id so that we could track released + // buffers. + auto swap_id = cbs_helper.GetNextLocalSwapId(); + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[0]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[0]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + 0, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[0].get(), window_->GetBounds(), {}, false, nullptr); + + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[1]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[1]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + 1, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[1].get(), window_->GetBounds(), {}, false, nullptr); + + std::vector<scoped_refptr<FakeGLImageNativePixmap>> gl_images; + gl_images.push_back(fake_gl_image[0]); + gl_images.push_back(fake_gl_image[1]); + + // And submit each image. They will be executed in FIFO manner. + gl_surface->SwapBuffersAsync( + base::BindOnce(&CallbacksHelper::FinishSwapBuffersAsync, + base::Unretained(&cbs_helper), swap_id, gl_images), + base::BindOnce(&CallbacksHelper::BufferPresented, + base::Unretained(&cbs_helper), swap_id)); + } + + // Let's sync so that 1) GbmSurfacelessWayland submits the buffer according to + // internal queue and fake server processes the request. + + // Also, we expect only one buffer to be committed. + EXPECT_CALL(*mock_primary_surface, Attach(_, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Frame(_)).Times(1); + EXPECT_CALL(*mock_primary_surface, DamageBuffer(_, _, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Commit()).Times(1); + + Sync(); + + testing::Mock::VerifyAndClearExpectations(&mock_primary_surface); + auto* subsurface = window_->wayland_subsurfaces().begin()->get(); + auto* mock_overlay_surface = server_.GetObject<wl::MockSurface>( + subsurface->wayland_surface()->GetSurfaceId()); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // We have just received Attach/DamageBuffer/Commit for buffer with swap + // id=0u. The SwapCompletionCallback must be executed automatically as long as + // we didn't have any buffers attached to the surface before. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), 0u); + + cbs_helper.ResetLastFinishedSwapId(); + + for (const auto& gl_image : fake_gl_image) { + // All the images except the first one, which was associated with swap + // id=0u, must be busy and not displayed. The first one must be displayed. + if (gl_image->GetAssociateWithSwapId() == 0u) { + EXPECT_FALSE(gl_image->busy()); + EXPECT_TRUE(gl_image->displayed()); + } else { + EXPECT_FALSE(gl_image->displayed()); + } + } + + // Submit another frame with 1 primary plane and 1 overlay + { + // Associate each image with swap id so that we could track released + // buffers. + auto swap_id = cbs_helper.GetNextLocalSwapId(); + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[2]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[2]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + 0, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[2].get(), window_->GetBounds(), {}, false, nullptr); + + // Associate the image with the next swap id so that we can easily track if + // it became free to reuse. + fake_gl_image[3]->AssociateWithSwapId(swap_id); + // And set it to be busy... + fake_gl_image[3]->SetBusy(true); + + // Prepare overlay plane. + gl_surface->ScheduleOverlayPlane( + 1, gfx::OverlayTransform::OVERLAY_TRANSFORM_NONE, + fake_gl_image[3].get(), window_->GetBounds(), {}, false, nullptr); + + std::vector<scoped_refptr<FakeGLImageNativePixmap>> gl_images; + gl_images.push_back(fake_gl_image[2]); + gl_images.push_back(fake_gl_image[3]); + + // And submit each image. They will be executed in FIFO manner. + gl_surface->SwapBuffersAsync( + base::BindOnce(&CallbacksHelper::FinishSwapBuffersAsync, + base::Unretained(&cbs_helper), swap_id, gl_images), + base::BindOnce(&CallbacksHelper::BufferPresented, + base::Unretained(&cbs_helper), swap_id)); + } + + // Expect one buffer to be committed. + EXPECT_CALL(*mock_primary_surface, Attach(_, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Frame(_)).Times(1); + EXPECT_CALL(*mock_primary_surface, DamageBuffer(_, _, _, _)).Times(1); + EXPECT_CALL(*mock_primary_surface, Commit()).Times(1); + + // Expect one buffer to be committed. + EXPECT_CALL(*mock_overlay_surface, Attach(_, _, _)).Times(1); + EXPECT_CALL(*mock_overlay_surface, Frame(_)).Times(0); + EXPECT_CALL(*mock_overlay_surface, DamageBuffer(_, _, _, _)).Times(1); + EXPECT_CALL(*mock_overlay_surface, Commit()).Times(1); + + // Send the frame callback so that pending buffer for swap id=1u is processed + // and swapped. + mock_primary_surface->SendFrameCallback(); + + Sync(); + + testing::Mock::VerifyAndClearExpectations(&mock_primary_surface); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // Even though the second frame was submitted, we mustn't receive + // SwapCompletionCallback until the previous frame's buffers are released. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), + std::numeric_limits<uint32_t>::max()); + + // This will result in Wayland server releasing one of the previously attached + // buffers for swap id=0u and calling OnSubmission for a buffer with swap + // id=1u attached to the primary surface. + mock_primary_surface->ReleaseBuffer( + mock_primary_surface->prev_attached_buffer()); + + Sync(); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // OnSubmission was only called for one of the buffers with swap id=1u, so + // SwapCompletionCallback should not run. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), + std::numeric_limits<uint32_t>::max()); + + // Release the another buffer. + mock_overlay_surface->ReleaseBuffer( + mock_overlay_surface->prev_attached_buffer()); + + Sync(); + + // Give mojo the chance to pass the callbacks. + base::RunLoop().RunUntilIdle(); + + // OnSubmission was called for both of the buffers with swap id=1u, so + // SwapCompletionCallback should run. + EXPECT_EQ(cbs_helper.GetLastFinishedSwapId(), 1u); + + for (const auto& gl_image : fake_gl_image) { + if (gl_image->GetAssociateWithSwapId() == 1u) { + EXPECT_TRUE(gl_image->displayed()); + EXPECT_FALSE(gl_image->busy()); + } else { + EXPECT_FALSE(gl_image->displayed()); + } + } +} + TEST_P(WaylandSurfaceFactoryTest, Canvas) { auto canvas = CreateCanvas(widget_); ASSERT_TRUE(canvas);
diff --git a/ui/ozone/platform/wayland/host/DEPS b/ui/ozone/platform/wayland/host/DEPS new file mode 100644 index 0000000..1741810 --- /dev/null +++ b/ui/ozone/platform/wayland/host/DEPS
@@ -0,0 +1,4 @@ +include_rules = [ + # For Lacros. + "+chromeos/crosapi/cpp/crosapi_constants.h", +]
diff --git a/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.cc b/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.cc index 82ebb3a9..5fa747f3 100644 --- a/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.cc +++ b/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.cc
@@ -25,6 +25,9 @@ namespace { +// Use |kInvalidBufferId| to commit surface state without updating wl_buffer. +constexpr uint32_t kInvalidBufferId = 0u; + uint32_t GetPresentationKindFlags(uint32_t flags) { // Wayland spec has different meaning of VSync. In Chromium, VSync means to // update the begin frame vsync timing based on presentation feedback. @@ -65,11 +68,20 @@ buffer_manager_(buffer_manager) {} ~Surface() = default; - bool CommitBuffer(uint32_t buffer_id, const gfx::Rect& damage_region) { + bool CommitBuffer(uint32_t buffer_id, + const gfx::Rect& damage_region, + bool wait_for_frame_callback) { // The window has already been destroyed. if (!wayland_surface_) return true; + // This is a buffer-less commit, do not lookup buffers. + if (buffer_id == kInvalidBufferId) { + pending_commits_.push_back({nullptr, wait_for_frame_callback}); + MaybeProcessPendingBuffer(); + return true; + } + WaylandBuffer* buffer = GetBuffer(buffer_id); if (!buffer) { // Get the anonymous_wl_buffer aka the buffer that has not been attached @@ -95,7 +107,7 @@ if (buffer->attached && !buffer->wl_buffer) return false; - pending_buffers_.push_back(buffer); + pending_commits_.push_back({buffer, wait_for_frame_callback}); MaybeProcessPendingBuffer(); return true; } @@ -108,7 +120,11 @@ if (buffer) { buffer->released = true; MaybeProcessSubmittedBuffers(); - base::Erase(pending_buffers_, buffer); + for (auto it = pending_commits_.begin(); it != pending_commits_.end(); + ++it) { + if (it->buffer == buffer) + pending_commits_.erase(it++); + } } return buffers_.erase(buffer_id); @@ -139,7 +155,7 @@ ResetSurfaceContents(); submitted_buffers_.clear(); - pending_buffers_.clear(); + pending_commits_.clear(); connection_->ScheduleFlush(); } @@ -204,7 +220,16 @@ bool acked; }; - bool CommitBufferInternal(WaylandBuffer* buffer) { + // Represents a pending surface commit. + struct PendingCommit { + // If null, means this commit will not attach buffer. + WaylandBuffer* buffer = nullptr; + // Whether this commit must wait for a wl_frame_callback and setup another + // wl_frame_callback. + bool wait_for_callback = false; + }; + + bool CommitBufferInternal(WaylandBuffer* buffer, bool wait_for_callback) { DCHECK(buffer && wayland_surface_); // If the same buffer has been submitted again right after the client @@ -225,7 +250,8 @@ DamageBuffer(buffer); - SetupFrameCallback(); + if (wait_for_callback) + SetupFrameCallback(); SetupPresentationFeedback(buffer->buffer_id); CommitSurface(); @@ -246,7 +272,8 @@ pending_damage_region.set_size(buffer->size); DCHECK(!pending_damage_region.size().IsEmpty()); - wayland_surface_->Damage(pending_damage_region); + wayland_surface_->UpdateBufferDamageRegion(pending_damage_region, + buffer->size); } void AttachBuffer(WaylandBuffer* buffer) { @@ -503,10 +530,10 @@ } void MaybeProcessPendingBuffer() { - DCHECK_LE(pending_buffers_.size(), 6u); + DCHECK_LE(pending_commits_.size(), 6u); // There is nothing to process if there is no pending buffer or the window // has been destroyed. - if (pending_buffers_.empty() || !wayland_surface_) + if (pending_commits_.empty() || !wayland_surface_) return; // This request may come earlier than the Wayland compositor has imported a @@ -523,12 +550,27 @@ // // The third case happens if the window hasn't been configured until a // request to attach a buffer to its surface is sent. - auto* pending_buffer = pending_buffers_.front(); - if (!pending_buffer->wl_buffer || wl_frame_callback_ || !configured_) + auto pending_commit = std::move(pending_commits_.front()); + if ((pending_commit.buffer && !pending_commit.buffer->wl_buffer) || + (wl_frame_callback_ && pending_commit.wait_for_callback) || + !configured_) { return; + } - pending_buffers_.erase(pending_buffers_.begin()); - CommitBufferInternal(pending_buffer); + // A Commit without attaching buffers only needs to setup wl_frame_callback. + if (!pending_commit.buffer) { + pending_commits_.erase(pending_commits_.begin()); + if (pending_commit.wait_for_callback) + SetupFrameCallback(); + CommitSurface(); + connection_->ScheduleFlush(); + MaybeProcessSubmittedBuffers(); + return; + } + + pending_commits_.erase(pending_commits_.begin()); + CommitBufferInternal(pending_commit.buffer, + pending_commit.wait_for_callback); } // Widget this helper surface backs and has 1:1 relationship with the @@ -551,9 +593,9 @@ // operation. wl::Object<wl_callback> wl_frame_callback_; - // Queue of buffers which are pending to be submitted (look the comment + // Queue of commits which are pending to be submitted (look the comment // in the CommitBuffer method). - std::vector<WaylandBuffer*> pending_buffers_; + std::list<PendingCommit> pending_commits_; // Queue of buffers which have been submitted and are waiting to be // acked (send OnSubmission) @@ -633,6 +675,13 @@ surfaces_.erase(it); } +void WaylandBufferManagerHost::SetSurfaceConfigured(WaylandSurface* surface) { + DCHECK(surface); + auto it = surfaces_.find(surface); + DCHECK(it != surfaces_.end()); + it->second->OnSurfaceConfigured(); +} + void WaylandBufferManagerHost::SetTerminateGpuCallback( base::OnceCallback<void(std::string)> terminate_callback) { terminate_gpu_cb_ = std::move(terminate_callback); @@ -755,14 +804,16 @@ bool WaylandBufferManagerHost::CommitBufferInternal( WaylandSurface* wayland_surface, uint32_t buffer_id, - const gfx::Rect& damage_region) { + const gfx::Rect& damage_region, + bool wait_for_frame_callback) { DCHECK(base::CurrentUIThread::IsSet()); Surface* surface = GetSurface(wayland_surface); if (!surface || !ValidateBufferIdFromGpu(buffer_id)) return false; - if (!surface->CommitBuffer(buffer_id, damage_region)) { + if (!surface->CommitBuffer(buffer_id, damage_region, + wait_for_frame_callback)) { error_message_ = base::StrCat({"Buffer with ", NumberToString(buffer_id), " id does not exist or failed to be created."}); @@ -773,6 +824,24 @@ return true; } +bool WaylandBufferManagerHost::CommitWithoutBufferInternal( + WaylandSurface* wayland_surface, + bool wait_for_frame_callback) { + DCHECK(base::CurrentUIThread::IsSet()); + + Surface* surface = GetSurface(wayland_surface); + if (!surface) + return false; + + bool result = surface->CommitBuffer(kInvalidBufferId, gfx::Rect(), + wait_for_frame_callback); + DCHECK(result); + + if (!error_message_.empty()) + TerminateGpuProcess(); + return true; +} + void WaylandBufferManagerHost::CommitBuffer(gfx::AcceleratedWidget widget, uint32_t buffer_id, const gfx::Rect& damage_region) {
diff --git a/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.h b/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.h index 20a974e..28dc77dc 100644 --- a/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.h +++ b/ui/ozone/platform/wayland/host/wayland_buffer_manager_host.h
@@ -89,6 +89,9 @@ void OnSubsurfaceRemoved(WaylandWindow* window, WaylandSubsurface* subsurface) override; + // Start allowing attaching buffers to |surface|, same as + // OnWindowConfigured(), but for WaylandSurface. + void SetSurfaceConfigured(WaylandSurface* surface); void SetTerminateGpuCallback( base::OnceCallback<void(std::string)> terminate_gpu_cb); @@ -154,9 +157,22 @@ // |buffer_id| to a WaylandSurface. // Calls OnSubmission and OnPresentation on successful swap and pixels // presented. + // |wait_for_frame_callback| instructs that a surface should wait for previous + // wl_frame_callback. This is primarily used for sync wl_subsurfaces case + // where buffer updates within a frame should be seen together. A root_surface + // commit will move an entire wl_surface tree from pending state to ready + // state. This root_surface commit must wait for wl_frame_callback, such that + // in effect all other surface updates wait for this wl_frame_callback, too. bool CommitBufferInternal(WaylandSurface* wayland_surface, uint32_t buffer_id, - const gfx::Rect& damage_region); + const gfx::Rect& damage_region, + bool wait_for_frame_callback = true); + + // Does a wl_surface commit without attaching any buffers. This commit will + // still wait for previous wl_frame_callback. Similar to above but for + // commits that do not change the root_surface. + bool CommitWithoutBufferInternal(WaylandSurface* wayland_surface, + bool wait_for_frame_callback = true); // When a surface is hidden, the client may want to detach the buffer attached // to the surface to ensure Wayland does not present those contents and do not @@ -236,8 +252,13 @@ base::OnceCallback<void(std::string)> terminate_gpu_cb_; // Contains anonymous buffers aka buffers that are not attached to any of the - // existing surfaces and that will be mapped to surfaces later. Typically - // created when CreateAnonymousImage is called on the gpu process side. + // existing surfaces and that will be mapped to surfaces later. + // Typically created when CreateAnonymousImage is called on the gpu process + // side. + // We assume that a buffer_id/wl_buffer will never be used on multiple + // wl_surfaces so we never re-map buffers to surfaces. If we ever need to use + // the same buffer for 2 surfaces at the same time, create multiple wl_buffers + // referencing the same dmabuf or underlying storage. base::flat_map<uint32_t, std::unique_ptr<WaylandBuffer>> anonymous_buffers_; base::WeakPtrFactory<WaylandBufferManagerHost> weak_factory_;
diff --git a/ui/ozone/platform/wayland/host/wayland_connection.cc b/ui/ozone/platform/wayland/host/wayland_connection.cc index 3c0caa4..40717570 100644 --- a/ui/ozone/platform/wayland/host/wayland_connection.cc +++ b/ui/ozone/platform/wayland/host/wayland_connection.cc
@@ -52,6 +52,7 @@ constexpr uint32_t kMaxXdgShellVersion = 1; constexpr uint32_t kMaxDeviceManagerVersion = 3; constexpr uint32_t kMaxWpPresentationVersion = 1; +constexpr uint32_t kMaxWpViewporterVersion = 1; constexpr uint32_t kMaxTextInputManagerVersion = 1; constexpr uint32_t kMaxExplicitSyncVersion = 2; constexpr uint32_t kMinAuraShellVersion = 10; @@ -354,6 +355,10 @@ (strcmp(interface, "wp_presentation") == 0)) { connection->presentation_ = wl::Bind<wp_presentation>(registry, name, kMaxWpPresentationVersion); + } else if (!connection->viewporter_ && + (strcmp(interface, "wp_viewporter") == 0)) { + connection->viewporter_ = + wl::Bind<wp_viewporter>(registry, name, kMaxWpViewporterVersion); } else if (!connection->keyboard_extension_v1_ && strcmp(interface, "zcr_keyboard_extension_v1") == 0) { connection->keyboard_extension_v1_ = wl::Bind<zcr_keyboard_extension_v1>(
diff --git a/ui/ozone/platform/wayland/host/wayland_connection.h b/ui/ozone/platform/wayland/host/wayland_connection.h index 98e9e76..ec7beb9 100644 --- a/ui/ozone/platform/wayland/host/wayland_connection.h +++ b/ui/ozone/platform/wayland/host/wayland_connection.h
@@ -64,6 +64,7 @@ wl_compositor* compositor() const { return compositor_.get(); } uint32_t compositor_version() const { return compositor_version_; } wl_subcompositor* subcompositor() const { return subcompositor_.get(); } + wp_viewporter* viewporter() const { return viewporter_.get(); } xdg_wm_base* shell() const { return shell_.get(); } zxdg_shell_v6* shell_v6() const { return shell_v6_.get(); } zaura_shell* aura_shell() const { return aura_shell_.get(); } @@ -188,6 +189,7 @@ wl::Object<xdg_wm_base> shell_; wl::Object<zxdg_shell_v6> shell_v6_; wl::Object<wp_presentation> presentation_; + wl::Object<wp_viewporter> viewporter_; wl::Object<zcr_keyboard_extension_v1> keyboard_extension_v1_; wl::Object<zwp_text_input_manager_v1> text_input_manager_v1_; wl::Object<zaura_shell> aura_shell_;
diff --git a/ui/ozone/platform/wayland/host/wayland_subsurface.cc b/ui/ozone/platform/wayland/host/wayland_subsurface.cc index 24b48e41..9b27f617 100644 --- a/ui/ozone/platform/wayland/host/wayland_subsurface.cc +++ b/ui/ozone/platform/wayland/host/wayland_subsurface.cc
@@ -43,6 +43,7 @@ LOG(ERROR) << "Failed to create wl_surface"; return; } + wayland_surface_.Initialize(); } WaylandSubsurface::~WaylandSubsurface() = default; @@ -69,11 +70,9 @@ } void WaylandSubsurface::UpdateOpaqueRegion() { - gfx::Size region_size = enable_blend_ ? gfx::Size() : bounds_px_.size(); - wl::Object<wl_region> region( - wl_compositor_create_region(connection_->compositor())); - wl_region_add(region.get(), 0, 0, region_size.width(), region_size.height()); - wl_surface_set_opaque_region(surface(), region.get()); + gfx::Rect region_px = + enable_blend_ ? gfx::Rect() : gfx::Rect(bounds_px_.size()); + wayland_surface()->SetOpaqueRegion(region_px); } void WaylandSubsurface::SetBounds(const gfx::Rect& bounds) { @@ -115,21 +114,22 @@ wl_compositor_create_region(connection_->compositor())); wl_region_add(region.get(), 0, 0, 0, 0); wl_surface_set_input_region(surface(), region.get()); + + connection_->buffer_manager_host()->SetSurfaceConfigured(wayland_surface()); } void WaylandSubsurface::ConfigureAndShowSurface( gfx::OverlayTransform transform, + const gfx::RectF& src_rect, const gfx::Rect& bounds_rect, bool enable_blend, const WaylandSurface* reference_below, const WaylandSurface* reference_above) { + wayland_surface()->SetBufferTransform(transform); wayland_surface()->SetBufferScale(parent_->buffer_scale(), false); - gfx::Rect bounds_px{ - bounds_rect.origin() + parent_->GetBounds().origin().OffsetFromOrigin(), - bounds_rect.size()}; auto old_bounds = bounds_px_; - SetBounds(bounds_px); + SetBounds(bounds_rect); if (old_bounds != bounds_px_ || enable_blend_ != enable_blend) { enable_blend_ = enable_blend; @@ -144,6 +144,9 @@ } else if (reference_above) { wl_subsurface_place_below(subsurface_.get(), reference_above->surface()); } + + wayland_surface()->SetViewportSource(src_rect); + wayland_surface()->SetViewportDestination(bounds_rect.size()); } } // namespace ui
diff --git a/ui/ozone/platform/wayland/host/wayland_subsurface.h b/ui/ozone/platform/wayland/host/wayland_subsurface.h index 50098b2..26a4c58 100644 --- a/ui/ozone/platform/wayland/host/wayland_subsurface.h +++ b/ui/ozone/platform/wayland/host/wayland_subsurface.h
@@ -34,7 +34,23 @@ // Sets up wl_surface and wl_subsurface. Allows an overlay to be shown // correctly once a wl_buffer is attached. + // |transform|: specifies the wl_surface buffer_transform. + // |src_rect|: specifies the displayable content (wp_viewport.src) of + // upcoming attached buffers. + // |bounds_rect|: The contents of the source rectangle are scaled to the + // destination size (wp_viewport.dst). + // |enable_blend|: whether the wl_surface will be transluscent. + // |reference_below| & |reference_above|: this subsurface is taken from the + // subsurface stack and inserted back to be immediately below/above the + // reference subsurface. + // + // The coordinate transformations from buffer pixel coordinates up to the + // surface-local coordinates happen in the following order: + // 1. buffer_transform + // 2. buffer_scale + // 3. crop and scale of viewport void ConfigureAndShowSurface(gfx::OverlayTransform transform, + const gfx::RectF& src_rect, const gfx::Rect& bounds_rect, bool enable_blend, const WaylandSurface* reference_below,
diff --git a/ui/ozone/platform/wayland/host/wayland_surface.cc b/ui/ozone/platform/wayland/host/wayland_surface.cc index 2a6467b..3cfccaa 100644 --- a/ui/ozone/platform/wayland/host/wayland_surface.cc +++ b/ui/ozone/platform/wayland/host/wayland_surface.cc
@@ -4,7 +4,11 @@ #include "ui/ozone/platform/wayland/host/wayland_surface.h" +#include <viewporter-client-protocol.h> + +#include "ui/gfx/geometry/rect_conversions.h" #include "ui/gfx/native_widget_types.h" +#include "ui/ozone/platform/wayland/common/wayland_util.h" #include "ui/ozone/platform/wayland/host/wayland_connection.h" #include "ui/ozone/platform/wayland/host/wayland_window.h" @@ -38,6 +42,15 @@ }; wl_surface_add_listener(surface_.get(), &surface_listener, this); + if (connection_->viewporter()) { + viewport_.reset( + wp_viewporter_get_viewport(connection_->viewporter(), surface())); + if (!viewport_) { + LOG(ERROR) << "Failed to create wp_viewport"; + return false; + } + } + return true; } @@ -54,7 +67,39 @@ connection_->ScheduleFlush(); } -void WaylandSurface::Damage(const gfx::Rect& pending_damage_region) { +void WaylandSurface::UpdateBufferDamageRegion( + const gfx::Rect& pending_damage_region, + const gfx::Size& buffer_size) { + // Buffer-local coordinates are in pixels, surface coordinates are in DIP. + // The coordinate transformations from buffer pixel coordinates up to + // the surface-local coordinates happen in the following order: + // 1. buffer_transform (wl_surface.set_buffer_transform) + // 2. buffer_scale (wl_surface.set_buffer_scale) + // 3. crop and scale (wp_viewport.set*) + // Apply buffer_transform (wl_surface.set_buffer_transform). + gfx::Size bounds = wl::ApplyWaylandTransform( + buffer_size, wl::ToWaylandTransform(buffer_transform_)); + // Apply buffer_scale (wl_surface.set_buffer_scale). + bounds = gfx::ScaleToCeiledSize(bounds, 1.f / buffer_scale_); + // Apply crop (wp_viewport.set_source). + gfx::Rect viewport_src = gfx::Rect(bounds); + if (!crop_rect_.IsEmpty()) { + viewport_src = gfx::ToEnclosedRect( + gfx::ScaleRect(crop_rect_, bounds.width(), bounds.height())); + wp_viewport_set_source(viewport(), wl_fixed_from_int(viewport_src.x()), + wl_fixed_from_int(viewport_src.y()), + wl_fixed_from_int(viewport_src.width()), + wl_fixed_from_int(viewport_src.height())); + } + // Apply viewport scale (wp_viewport.set_destination). + gfx::Size viewport_dst = bounds; + if (!display_size_px_.IsEmpty()) { + viewport_dst = + gfx::ScaleToCeiledSize(display_size_px_, 1.f / buffer_scale_); + wp_viewport_set_destination(viewport(), viewport_dst.width(), + viewport_dst.height()); + } + if (connection_->compositor_version() >= WL_SURFACE_DAMAGE_BUFFER_SINCE_VERSION) { // wl_surface_damage_buffer relies on compositor API version 4. See @@ -65,20 +110,29 @@ surface_.get(), pending_damage_region.x(), pending_damage_region.y(), pending_damage_region.width(), pending_damage_region.height()); } else { - // The calculation for damage region relies on two assumptions: - // 1) The buffer is always attached at surface location (0, 0) - // 2) The API wl_surface::set_buffer_transform is not used. - // It's possible to write logic that accounts for both cases above, but - // it's currently unnecessary. - // - // Note: The damage region may not be an integer multiple of scale. To - // keep the implementation simple, the x() and y() coordinates round down, - // and the width() and height() calculations always add an extra pixel. - wl_surface_damage(surface_.get(), pending_damage_region.x() / buffer_scale_, - pending_damage_region.y() / buffer_scale_, - pending_damage_region.width() / buffer_scale_ + 1, - pending_damage_region.height() / buffer_scale_ + 1); + // Calculate the damage region in surface coordinates. + // The calculation for damage region relies on the assumption: The buffer is + // always attached at surface location (0, 0). + // It's possible to write logic that accounts for attaching buffer at other + // locations, but it's currently unnecessary. + + // Apply buffer_transform (wl_surface.set_buffer_transform). + gfx::Rect damage = + wl::ApplyWaylandTransform(pending_damage_region, buffer_size, + wl::ToWaylandTransform(buffer_transform_)); + // Apply buffer_scale (wl_surface.set_buffer_scale). + damage = gfx::ScaleToEnclosingRect(damage, 1.f / buffer_scale_); + // Adjust coordinates to |viewport_src| (wp_viewport.set_source). + damage = wl::TranslateBoundsToParentCoordinates(damage, viewport_src); + // Apply viewport scale (wp_viewport.set_destination). + damage = gfx::ScaleToEnclosingRect( + damage, static_cast<float>(viewport_dst.width()) / viewport_src.width(), + static_cast<float>(viewport_dst.height()) / viewport_src.height()); + + wl_surface_damage(surface_.get(), damage.x(), damage.y(), damage.width(), + damage.height()); } + connection_->ScheduleFlush(); } @@ -87,6 +141,16 @@ connection_->ScheduleFlush(); } +void WaylandSurface::SetBufferTransform(gfx::OverlayTransform transform) { + DCHECK(transform != gfx::OVERLAY_TRANSFORM_INVALID); + if (buffer_transform_ == transform) + return; + + buffer_transform_ = transform; + wl_output_transform wl_transform = wl::ToWaylandTransform(buffer_transform_); + wl_surface_set_buffer_transform(surface_.get(), wl_transform); +} + void WaylandSurface::SetBufferScale(int32_t new_scale, bool update_bounds) { DCHECK_GT(new_scale, 0); @@ -98,7 +162,7 @@ connection_->ScheduleFlush(); } -void WaylandSurface::SetBounds(const gfx::Rect& bounds_px) { +void WaylandSurface::SetOpaqueRegion(const gfx::Rect& region_px) { // It's important to set opaque region for opaque windows (provides // optimization hint for the Wayland compositor). if (!root_window_ || !root_window_->IsOpaqueWindow()) @@ -106,13 +170,38 @@ wl::Object<wl_region> region( wl_compositor_create_region(connection_->compositor())); - wl_region_add(region.get(), 0, 0, bounds_px.width(), bounds_px.height()); + gfx::Rect region_dip = + gfx::ScaleToEnclosingRect(region_px, 1.f / buffer_scale_); + wl_region_add(region.get(), region_dip.x(), region_dip.y(), + region_dip.width(), region_dip.height()); wl_surface_set_opaque_region(surface_.get(), region.get()); connection_->ScheduleFlush(); } +void WaylandSurface::SetViewportSource(const gfx::RectF& src_rect) { + if (src_rect == crop_rect_) { + return; + } else if (src_rect.IsEmpty() || src_rect == gfx::RectF{0.f, 0.f, 1.f, 1.f}) { + wp_viewport_set_source(viewport(), wl_fixed_from_int(-1), + wl_fixed_from_int(-1), wl_fixed_from_int(-1), + wl_fixed_from_int(-1)); + return; + } + + crop_rect_ = src_rect; +} + +void WaylandSurface::SetViewportDestination(const gfx::Size& dest_size_px) { + if (dest_size_px == display_size_px_) { + return; + } else if (dest_size_px.IsEmpty()) { + wp_viewport_set_destination(viewport(), -1, -1); + } + display_size_px_ = dest_size_px; +} + wl::Object<wl_subsurface> WaylandSurface::CreateSubsurface( WaylandSurface* parent) { DCHECK(parent);
diff --git a/ui/ozone/platform/wayland/host/wayland_surface.h b/ui/ozone/platform/wayland/host/wayland_surface.h index ef86bc6..7747c6e 100644 --- a/ui/ozone/platform/wayland/host/wayland_surface.h +++ b/ui/ozone/platform/wayland/host/wayland_surface.h
@@ -8,7 +8,9 @@ #include <cstdint> #include "ui/gfx/geometry/rect.h" +#include "ui/gfx/geometry/rect_f.h" #include "ui/gfx/native_widget_types.h" +#include "ui/gfx/overlay_transform.h" #include "ui/ozone/platform/wayland/common/wayland_object.h" namespace ui { @@ -26,6 +28,7 @@ WaylandWindow* root_window() const { return root_window_; } wl_surface* surface() const { return surface_.get(); } + wp_viewport* viewport() const { return viewport_.get(); } int32_t buffer_scale() const { return buffer_scale_; } void set_buffer_scale(int32_t scale) { buffer_scale_ = scale; } @@ -47,19 +50,35 @@ // Attaches the given wl_buffer to the underlying wl_surface at (0, 0). void AttachBuffer(wl_buffer* buffer); - // Damages the surface according to |pending_damage_region|, which should be - // in surface coordinates (dp). - void Damage(const gfx::Rect& pending_damage_region); + // Describes where the surface needs to be repainted according to + // |buffer_pending_damage_region|, which should be in buffer coordinates (px). + void UpdateBufferDamageRegion(const gfx::Rect& buffer_pending_damage_region, + const gfx::Size& buffer_size); // Commits the underlying wl_surface. void Commit(); + // Sets an optional transformation for how the Wayland compositor interprets + // the contents of the buffer attached to this surface. + void SetBufferTransform(gfx::OverlayTransform transform); + // Sets the buffer scale for this surface. void SetBufferScale(int32_t scale, bool update_bounds); - // Sets the bounds on this surface. This is used for determining the opaque - // region. - void SetBounds(const gfx::Rect& bounds_px); + // Sets the region that is opaque on this surface in physical pixels. This is + // expected to be called whenever the region that the surface span changes or + // the opacity changes. + void SetOpaqueRegion(const gfx::Rect& bounds_px); + + // Set the source rectangle of the associated wl_surface. + // See: + // https://cgit.freedesktop.org/wayland/wayland-protocols/tree/stable/viewporter/viewporter.xml + // If |src_rect| is empty, the source rectangle is unset. + void SetViewportSource(const gfx::RectF& src_rect); + + // Set the destination size of the associated wl_surface according to + // |dest_size_px|, which should be in physical pixels. + void SetViewportDestination(const gfx::Size& dest_size_px); // Creates a wl_subsurface relating this surface and a parent surface, // |parent|. Callers take ownership of the wl_subsurface. @@ -69,11 +88,28 @@ WaylandConnection* const connection_; WaylandWindow* root_window_ = nullptr; wl::Object<wl_surface> surface_; + wl::Object<wp_viewport> viewport_; - // Wayland's scale factor for the output that this window currently belongs + // Transformation for how the compositor interprets the contents of the + // buffer. + gfx::OverlayTransform buffer_transform_ = gfx::OVERLAY_TRANSFORM_NONE; + + // Wayland's scale factor for the output that this surface currently belongs // to. int32_t buffer_scale_ = 1; + // Following fields are used to help determine the damage_region in + // surface-local coordinates if wl_surface_damage_buffer() is not available. + // Normalized bounds of the buffer to be displayed in |display_size_px_|. + // If empty, no cropping is applied. + gfx::RectF crop_rect_ = gfx::RectF(); + + // Current size of the destination of the viewport in physical pixels. Wayland + // compositor will scale the (cropped) buffer content to fit the + // |display_size_px_|. + // If empty, no scaling is applied. + gfx::Size display_size_px_ = gfx::Size(); + // wl_surface_listener static void Enter(void* data, struct wl_surface* wl_surface,
diff --git a/ui/ozone/platform/wayland/host/wayland_toplevel_window.cc b/ui/ozone/platform/wayland/host/wayland_toplevel_window.cc index b76b2375..ba33bbd 100644 --- a/ui/ozone/platform/wayland/host/wayland_toplevel_window.cc +++ b/ui/ozone/platform/wayland/host/wayland_toplevel_window.cc
@@ -24,6 +24,10 @@ #include "ui/platform_window/extensions/wayland_extension.h" #include "ui/platform_window/wm/wm_drop_handler.h" +#if BUILDFLAG(IS_LACROS) +#include "chromeos/crosapi/cpp/crosapi_constants.h" +#endif + namespace ui { WaylandToplevelWindow::WaylandToplevelWindow(PlatformWindowDelegate* delegate, @@ -338,7 +342,8 @@ PlatformWindowInitProperties properties) { #if BUILDFLAG(IS_LACROS) auto token = base::UnguessableToken::Create(); - window_unique_id_ = "org.chromium.lacros." + token.ToString(); + window_unique_id_ = + std::string(crosapi::kLacrosAppIdPrefix) + token.ToString(); #else wm_class_class_ = properties.wm_class_class; #endif
diff --git a/ui/ozone/platform/wayland/host/wayland_window.cc b/ui/ozone/platform/wayland/host/wayland_window.cc index bb313b2..567ff7f 100644 --- a/ui/ozone/platform/wayland/host/wayland_window.cc +++ b/ui/ozone/platform/wayland/host/wayland_window.cc
@@ -134,7 +134,7 @@ return; bounds_px_ = bounds_px; - root_surface_->SetBounds(bounds_px); + root_surface_->SetOpaqueRegion(bounds_px); delegate_->OnBoundsChanged(bounds_px_); } @@ -358,7 +358,7 @@ // Will do nothing for menus because they have got their scale above. UpdateBufferScale(false); - root_surface_->SetBounds(bounds_px_); + root_surface_->SetOpaqueRegion(bounds_px_); return true; } @@ -541,8 +541,9 @@ ozone::mojom::WaylandOverlayConfig::New(); auto split = std::lower_bound(overlays.begin(), overlays.end(), value, OverlayStackOrderCompare); - CHECK((*split)->z_order >= 0); - size_t num_primary_planes = (*split)->z_order == 0 ? 1 : 0; + CHECK(split == overlays.end() || (*split)->z_order >= 0); + size_t num_primary_planes = + (split != overlays.end() && (*split)->z_order == 0) ? 1 : 0; size_t above = (overlays.end() - split) - num_primary_planes; size_t below = split - overlays.begin(); @@ -568,11 +569,12 @@ reference_above = (*std::next(iter))->wayland_surface(); } (*iter)->ConfigureAndShowSurface( - (*overlay_iter)->transform, (*overlay_iter)->bounds_rect, - (*overlay_iter)->enable_blend, nullptr, reference_above); + (*overlay_iter)->transform, (*overlay_iter)->crop_rect, + (*overlay_iter)->bounds_rect, (*overlay_iter)->enable_blend, + nullptr, reference_above); connection_->buffer_manager_host()->CommitBufferInternal( - (*iter)->wayland_surface(), (*overlay_iter)->buffer_id, - gfx::Rect()); + (*iter)->wayland_surface(), (*overlay_iter)->buffer_id, gfx::Rect(), + /*wait_for_frame_callback=*/false); } else { // If there're more subsurfaces requested that we don't need at the // moment, hide them. @@ -596,11 +598,12 @@ reference_below = (*std::prev(iter))->wayland_surface(); } (*iter)->ConfigureAndShowSurface( - (*overlay_iter)->transform, (*overlay_iter)->bounds_rect, - (*overlay_iter)->enable_blend, reference_below, nullptr); + (*overlay_iter)->transform, (*overlay_iter)->crop_rect, + (*overlay_iter)->bounds_rect, (*overlay_iter)->enable_blend, + reference_below, nullptr); connection_->buffer_manager_host()->CommitBufferInternal( - (*iter)->wayland_surface(), (*overlay_iter)->buffer_id, - gfx::Rect()); + (*iter)->wayland_surface(), (*overlay_iter)->buffer_id, gfx::Rect(), + /*wait_for_frame_callback=*/false); } else { // If there're more subsurfaces requested that we don't need at the // moment, hide them. @@ -610,16 +613,16 @@ } if (num_primary_planes) { - // TODO: forward fence. connection_->buffer_manager_host()->CommitBufferInternal( - root_surface(), (*split)->buffer_id, (*split)->damage_region); + root_surface(), (*split)->buffer_id, (*split)->damage_region, + /*wait_for_frame_callback=*/true); } else { - // Subsurfaces are set to desync, above operations will only take effects + // Subsurfaces are set to sync, above operations will only take effects // when root_surface is committed. - root_surface()->Commit(); + connection_->buffer_manager_host()->CommitWithoutBufferInternal( + root_surface(), /*wait_for_frame_callback=*/true); } - // commit all; return true; }
diff --git a/ui/ozone/platform/wayland/host/wayland_window_unittest.cc b/ui/ozone/platform/wayland/host/wayland_window_unittest.cc index 0e87762d..7d0bce7 100644 --- a/ui/ozone/platform/wayland/host/wayland_window_unittest.cc +++ b/ui/ozone/platform/wayland/host/wayland_window_unittest.cc
@@ -2128,8 +2128,9 @@ auto* mock_surface_subsurface = server_.GetObject<wl::MockSurface>( wayland_subsurface->wayland_surface()->GetSurfaceId()); EXPECT_TRUE(mock_surface_subsurface); - wayland_subsurface->ConfigureAndShowSurface( - gfx::OVERLAY_TRANSFORM_NONE, subsurface_bounds, true, nullptr, nullptr); + wayland_subsurface->ConfigureAndShowSurface(gfx::OVERLAY_TRANSFORM_NONE, + gfx::RectF(), subsurface_bounds, + true, nullptr, nullptr); connection_->ScheduleFlush(); Sync();
diff --git a/ui/ozone/platform/wayland/test/mock_surface.cc b/ui/ozone/platform/wayland/test/mock_surface.cc index f6cda055..d7ec1ec 100644 --- a/ui/ozone/platform/wayland/test/mock_surface.cc +++ b/ui/ozone/platform/wayland/test/mock_surface.cc
@@ -89,6 +89,8 @@ wl_resource_destroy(xdg_surface_->resource()); if (sub_surface_ && sub_surface_->resource()) wl_resource_destroy(sub_surface_->resource()); + if (viewport_ && viewport_->resource()) + wl_resource_destroy(viewport_->resource()); } MockSurface* MockSurface::FromResource(wl_resource* resource) {
diff --git a/ui/ozone/platform/wayland/test/mock_surface.h b/ui/ozone/platform/wayland/test/mock_surface.h index e562a20..5c4e5cf 100644 --- a/ui/ozone/platform/wayland/test/mock_surface.h +++ b/ui/ozone/platform/wayland/test/mock_surface.h
@@ -15,6 +15,7 @@ #include "ui/ozone/platform/wayland/test/mock_xdg_surface.h" #include "ui/ozone/platform/wayland/test/server_object.h" #include "ui/ozone/platform/wayland/test/test_subsurface.h" +#include "ui/ozone/platform/wayland/test/test_viewport.h" #include "ui/ozone/platform/wayland/test/test_xdg_popup.h" struct wl_resource; @@ -52,6 +53,9 @@ } TestSubSurface* sub_surface() const { return sub_surface_; } + void set_viewport(TestViewport* viewport) { viewport_ = viewport; } + TestViewport* viewport() { return viewport_; } + void set_frame_callback(wl_resource* callback_resource) { DCHECK(!frame_callback_); frame_callback_ = callback_resource; @@ -70,6 +74,7 @@ private: MockXdgSurface* xdg_surface_ = nullptr; TestSubSurface* sub_surface_ = nullptr; + TestViewport* viewport_ = nullptr; wl_resource* frame_callback_ = nullptr;
diff --git a/ui/ozone/platform/wayland/test/test_viewport.cc b/ui/ozone/platform/wayland/test/test_viewport.cc new file mode 100644 index 0000000..b82e86f --- /dev/null +++ b/ui/ozone/platform/wayland/test/test_viewport.cc
@@ -0,0 +1,49 @@ +// Copyright 2020 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "ui/ozone/platform/wayland/test/test_viewport.h" + +#include "base/notreached.h" +#include "ui/ozone/platform/wayland/test/mock_surface.h" + +namespace wl { + +namespace { + +void SetSource(wl_client* client, + wl_resource* resource, + wl_fixed_t x, + wl_fixed_t y, + wl_fixed_t width, + wl_fixed_t height) { + NOTIMPLEMENTED_LOG_ONCE(); +} + +void SetDestination(wl_client* client, + wl_resource* resource, + int32_t x, + int32_t y) { + NOTIMPLEMENTED_LOG_ONCE(); +} + +} // namespace + +const struct wp_viewport_interface kTestViewportImpl = { + DestroyResource, + SetSource, + SetDestination, +}; + +TestViewport::TestViewport(wl_resource* resource, wl_resource* surface) + : ServerObject(resource), surface_(surface) { + DCHECK(surface_); +} + +TestViewport::~TestViewport() { + auto* mock_surface = GetUserDataAs<MockSurface>(surface_); + if (mock_surface) + mock_surface->set_viewport(nullptr); +} + +} // namespace wl
diff --git a/ui/ozone/platform/wayland/test/test_viewport.h b/ui/ozone/platform/wayland/test/test_viewport.h new file mode 100644 index 0000000..0cea33c --- /dev/null +++ b/ui/ozone/platform/wayland/test/test_viewport.h
@@ -0,0 +1,32 @@ +// Copyright 2020 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef UI_OZONE_PLATFORM_WAYLAND_TEST_TEST_VIEWPORT_H_ +#define UI_OZONE_PLATFORM_WAYLAND_TEST_TEST_VIEWPORT_H_ + +#include <viewporter-server-protocol.h> + +#include "ui/ozone/platform/wayland/test/server_object.h" + +struct wl_resource; + +namespace wl { + +extern const struct wp_viewport_interface kTestViewportImpl; + +class TestViewport : public ServerObject { + public: + explicit TestViewport(wl_resource* resource, wl_resource* surface); + ~TestViewport() override; + TestViewport(const TestViewport& rhs) = delete; + TestViewport& operator=(const TestViewport& rhs) = delete; + + private: + // Surface resource that is the ground for this Viewport. + wl_resource* surface_ = nullptr; +}; + +} // namespace wl + +#endif // UI_OZONE_PLATFORM_WAYLAND_TEST_TEST_VIEWPORT_H_
diff --git a/ui/ozone/platform/wayland/test/test_viewporter.cc b/ui/ozone/platform/wayland/test/test_viewporter.cc new file mode 100644 index 0000000..1b44f81 --- /dev/null +++ b/ui/ozone/platform/wayland/test/test_viewporter.cc
@@ -0,0 +1,53 @@ +// Copyright 2020 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "ui/ozone/platform/wayland/test/test_viewporter.h" + +#include <viewporter-server-protocol.h> +#include <wayland-server-core.h> + +#include "base/check.h" +#include "ui/ozone/platform/wayland/test/mock_surface.h" +#include "ui/ozone/platform/wayland/test/test_viewport.h" + +namespace wl { + +namespace { + +constexpr uint32_t kViewporterVersion = 1; + +void GetViewport(struct wl_client* client, + struct wl_resource* resource, + uint32_t id, + struct wl_resource* surface) { + auto* mock_surface = GetUserDataAs<MockSurface>(surface); + if (mock_surface->viewport()) { + wl_resource_post_error(resource, WP_VIEWPORTER_ERROR_VIEWPORT_EXISTS, + "viewport exists"); + return; + } + + wl_resource* viewport_resource = + CreateResourceWithImpl<::testing::NiceMock<TestViewport>>( + client, &wp_viewport_interface, wl_resource_get_version(resource), + &kTestViewportImpl, id, surface); + DCHECK(viewport_resource); + mock_surface->set_viewport(GetUserDataAs<TestViewport>(viewport_resource)); +} + +} // namespace + +const struct wp_viewporter_interface kTestViewporterImpl = { + DestroyResource, + GetViewport, +}; + +TestViewporter::TestViewporter() + : GlobalObject(&wp_viewporter_interface, + &kTestViewporterImpl, + kViewporterVersion) {} + +TestViewporter::~TestViewporter() = default; + +} // namespace wl
diff --git a/ui/ozone/platform/wayland/test/test_viewporter.h b/ui/ozone/platform/wayland/test/test_viewporter.h new file mode 100644 index 0000000..6f8281a5 --- /dev/null +++ b/ui/ozone/platform/wayland/test/test_viewporter.h
@@ -0,0 +1,23 @@ +// Copyright 2020 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef UI_OZONE_PLATFORM_WAYLAND_TEST_TEST_VIEWPORTER_H_ +#define UI_OZONE_PLATFORM_WAYLAND_TEST_TEST_VIEWPORTER_H_ + +#include "ui/ozone/platform/wayland/test/global_object.h" + +namespace wl { + +// Manage wl_viewporter object. +class TestViewporter : public GlobalObject { + public: + TestViewporter(); + ~TestViewporter() override; + TestViewporter(const TestViewporter& rhs) = delete; + TestViewporter& operator=(const TestViewporter& rhs) = delete; +}; + +} // namespace wl + +#endif // UI_OZONE_PLATFORM_WAYLAND_TEST_TEST_VIEWPORTER_H_
diff --git a/ui/ozone/platform/wayland/test/test_wayland_server_thread.cc b/ui/ozone/platform/wayland/test/test_wayland_server_thread.cc index c6f0fe7c..6cf79816 100644 --- a/ui/ozone/platform/wayland/test/test_wayland_server_thread.cc +++ b/ui/ozone/platform/wayland/test/test_wayland_server_thread.cc
@@ -58,6 +58,8 @@ return false; if (!sub_compositor_.Initialize(display_.get())) return false; + if (!viewporter_.Initialize(display_.get())) + return false; if (!output_.Initialize(display_.get())) return false; SetupOutputs();
diff --git a/ui/ozone/platform/wayland/test/test_wayland_server_thread.h b/ui/ozone/platform/wayland/test/test_wayland_server_thread.h index e3d4d48..712ce602 100644 --- a/ui/ozone/platform/wayland/test/test_wayland_server_thread.h +++ b/ui/ozone/platform/wayland/test/test_wayland_server_thread.h
@@ -22,6 +22,7 @@ #include "ui/ozone/platform/wayland/test/test_output.h" #include "ui/ozone/platform/wayland/test/test_seat.h" #include "ui/ozone/platform/wayland/test/test_subcompositor.h" +#include "ui/ozone/platform/wayland/test/test_viewporter.h" #include "ui/ozone/platform/wayland/test/test_zwp_text_input_manager.h" struct wl_client; @@ -111,6 +112,7 @@ // Represent Wayland global objects TestCompositor compositor_; TestSubCompositor sub_compositor_; + TestViewporter viewporter_; TestDataDeviceManager data_device_manager_; TestOutput output_; TestSeat seat_;
diff --git a/ui/views/controls/scrollbar/scroll_bar_views.h b/ui/views/controls/scrollbar/scroll_bar_views.h index d8f0084..e30f08f8 100644 --- a/ui/views/controls/scrollbar/scroll_bar_views.h +++ b/ui/views/controls/scrollbar/scroll_bar_views.h
@@ -25,7 +25,7 @@ METADATA_HEADER(ScrollBarViews); // Creates new scrollbar, either horizontal or vertical. - explicit ScrollBarViews(bool horizontal); + explicit ScrollBarViews(bool horizontal = true); ~ScrollBarViews() override; static int GetVerticalScrollBarWidth(const ui::NativeTheme* theme);
diff --git a/ui/views/controls/scrollbar/scrollbar_unittest.cc b/ui/views/controls/scrollbar/scrollbar_unittest.cc index 12e55b83..2d74d2a 100644 --- a/ui/views/controls/scrollbar/scrollbar_unittest.cc +++ b/ui/views/controls/scrollbar/scrollbar_unittest.cc
@@ -86,8 +86,7 @@ auto* container = widget_->SetContentsView(std::make_unique<TestScrollbarContainer>()); - scrollbar_ = - container->AddChildView(std::make_unique<ScrollBarViews>(true)); + scrollbar_ = container->AddChildView(std::make_unique<ScrollBarViews>()); scrollbar_->SetBounds(0, 0, 100, 100); scrollbar_->Update(100, 1000, 0); scrollbar_->set_controller(controller_.get());
diff --git a/ui/views/layout/flex_layout.cc b/ui/views/layout/flex_layout.cc index f56c490..6989bd7 100644 --- a/ui/views/layout/flex_layout.cc +++ b/ui/views/layout/flex_layout.cc
@@ -1118,7 +1118,8 @@ } ChildLayout& child_layout = data.layout.child_layouts[child_index]; - DCHECK(is_first_pass || child_layout.visible); + DCHECK(is_first_pass || child_layout.visible || + flex_child.preferred_size.main() == 0); const int old_size = child_layout.visible ? flex_child.current_size.main() : 0;
diff --git a/url/gurl_fuzzer.cc b/url/gurl_fuzzer.cc index cb6041fa..c5c22a6 100644 --- a/url/gurl_fuzzer.cc +++ b/url/gurl_fuzzer.cc
@@ -3,7 +3,9 @@ // found in the LICENSE file. #include "base/at_exit.h" +#include "base/check_op.h" #include "base/i18n/icu_util.h" +#include "base/no_destructor.h" #include "url/gurl.h" struct TestCase { @@ -15,9 +17,6 @@ TestCase* test_case = new TestCase(); -// Empty replacements cause no change when applied. -GURL::Replacements* no_op = new GURL::Replacements(); - // Checks that GURL's canonicalization is idempotent. This can help discover // issues like https://crbug.com/1128999. void CheckIdempotency(const GURL& url) { @@ -29,52 +28,62 @@ CHECK_EQ(spec, recanonicalized.spec()); } +// Checks that |url.spec()| is preserved across a call to ReplaceComponents with +// zero replacements, which is effectively a copy. This can help discover issues +// like https://crbug.com/1075515. +void CheckReplaceComponentsPreservesSpec(const GURL& url) { + static const base::NoDestructor<GURL::Replacements> no_op; + GURL copy = url.ReplaceComponents(*no_op); + CHECK_EQ(url.is_valid(), copy.is_valid()); + if (url.is_valid()) { + CHECK_EQ(url.spec(), copy.spec()); + } +} + // Entry point for LibFuzzer. extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) { if (size < 1) return 0; - - base::StringPiece string_piece_input(reinterpret_cast<const char*>(data), - size); - GURL url_from_string_piece(string_piece_input); - CheckIdempotency(url_from_string_piece); - // Copying by applying empty replacements exercises interesting code paths. - // This can help discover issues like https://crbug.com/1075515. - GURL copy = url_from_string_piece.ReplaceComponents(*no_op); - CHECK_EQ(url_from_string_piece.is_valid(), copy.is_valid()); - if (url_from_string_piece.is_valid()) { - CHECK_EQ(url_from_string_piece.spec(), copy.spec()); + { + base::StringPiece string_piece_input(reinterpret_cast<const char*>(data), + size); + const GURL url_from_string_piece(string_piece_input); + CheckIdempotency(url_from_string_piece); + CheckReplaceComponentsPreservesSpec(url_from_string_piece); } - // Test for StringPiece16 if size is even. if (size % 2 == 0) { base::StringPiece16 string_piece_input16( reinterpret_cast<const base::char16*>(data), size / 2); - - GURL url_from_string_piece16(string_piece_input16); + const GURL url_from_string_piece16(string_piece_input16); CheckIdempotency(url_from_string_piece16); + CheckReplaceComponentsPreservesSpec(url_from_string_piece16); } - // Resolve relative url tests. - size_t size_t_bytes = sizeof(size_t); - if (size < size_t_bytes + 1) { - return 0; - } - size_t relative_size = - *reinterpret_cast<const size_t*>(data) % (size - size_t_bytes); - std::string relative_string( - reinterpret_cast<const char*>(data + size_t_bytes), relative_size); - base::StringPiece string_piece_part_input( - reinterpret_cast<const char*>(data + size_t_bytes + relative_size), - size - relative_size - size_t_bytes); - GURL url_from_string_piece_part(string_piece_part_input); - url_from_string_piece_part.Resolve(relative_string); + { + size_t size_t_bytes = sizeof(size_t); + if (size < size_t_bytes + 1) { + return 0; + } + size_t relative_size = + *reinterpret_cast<const size_t*>(data) % (size - size_t_bytes); + std::string relative_string( + reinterpret_cast<const char*>(data + size_t_bytes), relative_size); + base::StringPiece string_piece_part_input( + reinterpret_cast<const char*>(data + size_t_bytes + relative_size), + size - relative_size - size_t_bytes); + const GURL url_from_string_piece_part(string_piece_part_input); + CheckIdempotency(url_from_string_piece_part); + CheckReplaceComponentsPreservesSpec(url_from_string_piece_part); - if (relative_size % 2 == 0) { - base::string16 relative_string16( - reinterpret_cast<const base::char16*>(data + size_t_bytes), - relative_size / 2); - url_from_string_piece_part.Resolve(relative_string16); + url_from_string_piece_part.Resolve(relative_string); + + if (relative_size % 2 == 0) { + base::string16 relative_string16( + reinterpret_cast<const base::char16*>(data + size_t_bytes), + relative_size / 2); + url_from_string_piece_part.Resolve(relative_string16); + } } return 0; }
diff --git a/weblayer/BUILD.gn b/weblayer/BUILD.gn index dc39a3b..c56ceb2f 100644 --- a/weblayer/BUILD.gn +++ b/weblayer/BUILD.gn
@@ -28,6 +28,13 @@ import("//v8/gni/v8.gni") } +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + source_set("android_descriptors") { sources = [ "browser/android_descriptors.h" ] public_deps = [ "//content/public/common:content_descriptors" ]
diff --git a/weblayer/shell/BUILD.gn b/weblayer/shell/BUILD.gn index 1ed0831c..66984a7 100644 --- a/weblayer/shell/BUILD.gn +++ b/weblayer/shell/BUILD.gn
@@ -14,6 +14,13 @@ import("//build/config/android/config.gni") } +# This file depends on the legacy global sources assignment filter. It should +# be converted to check target platform before assigning source files to the +# sources variable. Remove this import and set_sources_assignment_filter call +# when the file has been converted. See https://crbug.com/1018739 for details. +import("//build/config/deprecated_default_sources_assignment_filter.gni") +set_sources_assignment_filter(deprecated_default_sources_assignment_filter) + static_library("weblayer_shell_lib") { testonly = true sources = [