diff --git a/DEPS b/DEPS index c2105aa4..dc62341 100644 --- a/DEPS +++ b/DEPS
@@ -205,10 +205,12 @@ # 1 Choose a version that's not newer than the Ash side so it's thoroughly # tested: # https://chromium-review.googlesource.com/q/%2522Automated+Commit:+LKGM%2522+status:merged - # 2 Run additional a few optional tryjobs: - # lacros-amd64-generic-chrome-skylab - # lacros-arm-generic-chrome-skylab - 'lacros_sdk_version': '14803.0.0', + # 2 CL description: + # Lacros SDK: Update version <version> + # + # CQ_INCLUDE_TRYBOTS=luci.chrome.try:lacros-amd64-generic-chrome-skylab + # CQ_INCLUDE_TRYBOTS=luci.chrome.try:lacros-arm-generic-chrome-skylab + 'lacros_sdk_version': '14844.0.0', # Generate location tag metadata to include in tests result data uploaded # to ResultDB. This isn't needed on some configs and the tool that generates @@ -269,7 +271,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling Skia # and whatever else without interference from each other. - 'skia_revision': 'fb7f03aeac6eddfea329c91ceb1bce1a71e9f902', + 'skia_revision': 'd3cbea4114aabd84958d6ec9662c2f80c405dc59', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling V8 # and whatever else without interference from each other. @@ -277,7 +279,7 @@ # 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': 'e4a517c923d5b4809e1a8f7c75be5e593c40790f', + 'angle_revision': '2db4297ad0fb70cfa1f18ac86b3548448ccf14b0', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling SwiftShader # and whatever else without interference from each other. @@ -296,7 +298,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling Fuchsia sdk # and whatever else without interference from each other. - 'fuchsia_version': 'version:8.20220522.3.1', + 'fuchsia_version': 'version:8.20220523.1.1', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling google-toolbox-for-mac # and whatever else without interference from each other. @@ -348,7 +350,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling devtools-frontend # and whatever else without interference from each other. - 'devtools_frontend_revision': 'a2e55b403896db8f13e82c583160b4dd5507789c', + 'devtools_frontend_revision': 'e2040405a1dcaf52613c0e8ad9d0fc330b276d43', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling libprotobuf-mutator # and whatever else without interference from each other. @@ -1133,7 +1135,7 @@ }, 'src/third_party/depot_tools': - Var('chromium_git') + '/chromium/tools/depot_tools.git' + '@' + '4e6aa2530fbfa4d8ae2c5d29678079c7e482eeca', + Var('chromium_git') + '/chromium/tools/depot_tools.git' + '@' + '964f8124b630dec44dae9dbd0a79bf468356578c', 'src/third_party/devtools-frontend/src': Var('chromium_git') + '/devtools/devtools-frontend' + '@' + Var('devtools_frontend_revision'), @@ -1530,7 +1532,7 @@ }, 'src/third_party/perfetto': - Var('android_git') + '/platform/external/perfetto.git' + '@' + '370def59dcc5b6423f805754160cab7c5b772c2d', + Var('android_git') + '/platform/external/perfetto.git' + '@' + '5a9d84436fccfcb0eaaad6f8c40c851b12c24420', 'src/third_party/perl': { 'url': Var('chromium_git') + '/chromium/deps/perl.git' + '@' + '6f3e5028eb65d0b4c5fdd792106ac4c84eee1eb3', @@ -1705,7 +1707,7 @@ Var('chromium_git') + '/external/github.com/gpuweb/cts.git' + '@' + '9618103c4aa25ea342ddad65848ff8bb0c1cee9a', 'src/third_party/webrtc': - Var('webrtc_git') + '/src.git' + '@' + 'd91996dd00e1daa060942d18be5a5e10f29a280b', + Var('webrtc_git') + '/src.git' + '@' + 'c3fa7c38b2b74cf7b5dd2cc323ccaa8473b50e80', 'src/third_party/libgifcodec': Var('skia_git') + '/libgifcodec' + '@'+ Var('libgifcodec_revision'), @@ -1778,7 +1780,7 @@ Var('chromium_git') + '/v8/v8.git' + '@' + Var('v8_revision'), 'src-internal': { - 'url': 'https://chrome-internal.googlesource.com/chrome/src-internal.git@ad19ab17a11480b1a6e0779728a67ac91a79eeaa', + 'url': 'https://chrome-internal.googlesource.com/chrome/src-internal.git@4169a9720b7c7aad9f7478c9c272a68749bca591', 'condition': 'checkout_src_internal', }, @@ -1819,7 +1821,7 @@ 'packages': [ { 'package': 'chromeos_internal/apps/media_app/app', - 'version': '6RkqT0Gy8h6rQBA8h1dG46N_7Iy_5L9CNNdsm7ps5KYC', + 'version': 'VW8OLMUzhVZlvxnnmL-162Mk66yVLTxDMIuFrZc2HjIC', }, ], 'condition': 'checkout_chromeos and checkout_src_internal', @@ -1830,7 +1832,7 @@ 'packages': [ { 'package': 'chromeos_internal/apps/projector_app/app', - 'version': 'qJq23XcKB1Y1d24mJ8I7L4SwVgxw6WhfhGFTn7FPx38C', + 'version': 'LmSSJqjR5Vm1KHfkGZFFVnw5ntNeKIU5LcxHqcFlF_YC', }, ], 'condition': 'checkout_chromeos and checkout_src_internal',
diff --git a/android_webview/java/src/org/chromium/android_webview/common/ProductionSupportedFlagList.java b/android_webview/java/src/org/chromium/android_webview/common/ProductionSupportedFlagList.java index a08990f..4c5b393 100644 --- a/android_webview/java/src/org/chromium/android_webview/common/ProductionSupportedFlagList.java +++ b/android_webview/java/src/org/chromium/android_webview/common/ProductionSupportedFlagList.java
@@ -195,6 +195,12 @@ Flag.baseFeature(AutofillFeatures.AUTOFILL_RATIONALIZE_STREET_ADDRESS_AND_ADDRESS_LINE, "Rationalizes (street address, address line 2) field sequences to " + "(address line1, address line 2)."), + Flag.baseFeature(AutofillFeatures.AUTOFILL_FILL_CREDIT_CARD_AS_PER_FORMAT_STRING, + "When enabled, Autofill tries to infer the credit card expiry date format " + + "from the label and placeholder."), + Flag.baseFeature(AutofillFeatures.AUTOFILL_CONSIDER_PLACEHOLDER_FOR_PARSING, + "When enabled, Autofill local heuristics consider the placeholder attribute " + + "for determining field types."), Flag.baseFeature(FeatureConstants.KEYBOARD_ACCESSORY_PAYMENT_VIRTUAL_CARD_FEATURE, "When enabled, merchant bound virtual cards will be offered in the keyboard " + "accessory."),
diff --git a/ash/components/arc/session/arc_container_client_adapter.cc b/ash/components/arc/session/arc_container_client_adapter.cc index 1d11471f..bd5b0c1 100644 --- a/ash/components/arc/session/arc_container_client_adapter.cc +++ b/ash/components/arc/session/arc_container_client_adapter.cc
@@ -122,8 +122,6 @@ request.set_dalvik_memory_profile( ToLoginManagerDalvikMemoryProfile(params.dalvik_memory_profile)); request.set_arc_custom_tabs_experiment(params.arc_custom_tabs_experiment); - request.set_disable_system_default_app( - params.arc_disable_system_default_app); request.set_disable_media_store_maintenance( params.disable_media_store_maintenance); request.set_disable_download_provider(params.disable_download_provider);
diff --git a/ash/components/arc/session/arc_session_impl.cc b/ash/components/arc/session/arc_session_impl.cc index 434c0f6..3756016 100644 --- a/ash/components/arc/session/arc_session_impl.cc +++ b/ash/components/arc/session/arc_session_impl.cc
@@ -489,12 +489,6 @@ } } - params.arc_disable_system_default_app = - base::CommandLine::ForCurrentProcess()->HasSwitch( - ash::switches::kArcDisableSystemDefaultApps); - if (params.arc_disable_system_default_app) - VLOG(1) << "System default app(s) are disabled"; - params.disable_media_store_maintenance = base::CommandLine::ForCurrentProcess()->HasSwitch( ash::switches::kArcDisableMediaStoreMaintenance);
diff --git a/ash/components/arc/session/arc_start_params.h b/ash/components/arc/session/arc_start_params.h index 9b083c1..e329370 100644 --- a/ash/components/arc/session/arc_start_params.h +++ b/ash/components/arc/session/arc_start_params.h
@@ -69,9 +69,6 @@ // Experiment flag for ARC Custom Tabs. bool arc_custom_tabs_experiment = false; - // Flag to disable system default apps. - bool arc_disable_system_default_app = false; - // Flag to disable scheduling of media store periodic maintenance tasks. bool disable_media_store_maintenance = false;
diff --git a/ash/components/arc/session/arc_vm_client_adapter.cc b/ash/components/arc/session/arc_vm_client_adapter.cc index a122e31..8005d1f 100644 --- a/ash/components/arc/session/arc_vm_client_adapter.cc +++ b/ash/components/arc/session/arc_vm_client_adapter.cc
@@ -115,21 +115,6 @@ return chromeos::DBusThreadManager::Get()->GetDebugDaemonClient(); } -std::string GetChromeOsChannelFromLsbRelease() { - constexpr const char kChromeOsReleaseTrack[] = "CHROMEOS_RELEASE_TRACK"; - constexpr const char kUnknown[] = "unknown"; - const std::string kChannelSuffix = "-channel"; - - std::string value; - base::SysInfo::GetLsbReleaseValue(kChromeOsReleaseTrack, &value); - - if (!base::EndsWith(value, kChannelSuffix, base::CompareCase::SENSITIVE)) { - LOG(ERROR) << "Unknown ChromeOS channel: \"" << value << "\""; - return kUnknown; - } - return value.erase(value.find(kChannelSuffix), kChannelSuffix.size()); -} - ArcBinaryTranslationType IdentifyBinaryTranslationType( const StartParams& start_params) { const auto* command_line = base::CommandLine::ForCurrentProcess(); @@ -195,9 +180,7 @@ std::vector<std::string> GenerateKernelCmdline( const StartParams& start_params, const FileSystemStatus& file_system_status, - bool is_dev_mode, - bool is_host_on_vm, - const std::string& channel) { + bool is_host_on_vm) { std::string native_bridge; switch (IdentifyBinaryTranslationType(start_params)) { case ArcBinaryTranslationType::NONE: @@ -216,8 +199,6 @@ std::vector<std::string> result = { base::StringPrintf("androidboot.native_bridge=%s", native_bridge.c_str()), - base::StringPrintf("androidboot.dev_mode=%d", is_dev_mode), - base::StringPrintf("androidboot.disable_runas=%d", !is_dev_mode), base::StringPrintf("androidboot.host_is_in_vm=%d", is_host_on_vm), base::StringPrintf("androidboot.lcd_density=%d", start_params.lcd_density), @@ -228,9 +209,6 @@ base::StringPrintf( "androidboot.keyboard_shortcut_helper_integration=%d", start_params.enable_keyboard_shortcut_helper_integration), - base::StringPrintf("androidboot.disable_system_default_app=%d", - start_params.arc_disable_system_default_app), - "androidboot.chromeos_channel=" + channel, base::StringPrintf("androidboot.iioservice_present=%d", BUILDFLAG(USE_IIOSERVICE)), base::StringPrintf("androidboot.enable_notifications_refresh=%d", @@ -254,11 +232,6 @@ break; } - // We run vshd under a restricted domain on non-test images. - // (go/arcvm-android-sh-restricted) - if (channel == "testimage") - result.push_back("androidboot.vshd_service_override=vshd_for_test"); - // Only add boot property if flag to disable media store maintenance is set. if (start_params.disable_media_store_maintenance) result.push_back("androidboot.disable_media_store_maintenance=1"); @@ -632,7 +605,7 @@ public ash::ConciergeClient::Observer, public ConnectionObserver<arc::mojom::AppInstance> { public: - // Initializing |is_host_on_vm_| and |is_dev_mode_| is not always very fast. + // Initializing |is_host_on_vm_| is not always very fast. // Try to initialize them in the constructor and in StartMiniArc respectively. // They usually run when the system is not busy. ArcVmClientAdapter() : ArcVmClientAdapter(FileSystemStatusRewriter{}) {} @@ -702,12 +675,26 @@ } start_params_ = std::move(params); - base::ThreadPool::PostTaskAndReplyWithResult( - FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE}, + std::vector<std::string> enviroment; + if (start_params_.disable_ureadahead) + enviroment.emplace_back("DISABLE_UREADAHEAD=1"); + std::deque<JobDesc> jobs{ + // Note: the first Upstart job is a task, and the callback for the start + // request won't be called until the task finishes. When the callback is + // called with true, it is ensured that the per-board features files + // exist. + JobDesc{kArcVmPerBoardFeaturesJobName, UpstartOperation::JOB_START, {}}, + JobDesc{ + kArcVmPostVmStartServicesJobName, UpstartOperation::JOB_STOP, {}}, + JobDesc{kArcVmPostLoginServicesJobName, UpstartOperation::JOB_STOP, {}}, + JobDesc{kArcVmPreLoginServicesJobName, + UpstartOperation::JOB_STOP_AND_START, std::move(enviroment)}, + }; + ConfigureUpstartJobs( + std::move(jobs), base::BindOnce( - []() { return GetSystemPropertyInt("cros_debug") == 1; }), - base::BindOnce(&ArcVmClientAdapter::OnIsDevMode, - weak_factory_.GetWeakPtr(), std::move(callback))); + &ArcVmClientAdapter::OnConfigureUpstartJobsOnStartMiniArc, + weak_factory_.GetWeakPtr(), std::move(callback))); } void UpgradeArc(UpgradeParams params, @@ -855,31 +842,6 @@ weak_factory_.GetWeakPtr())); } - void OnIsDevMode(chromeos::VoidDBusMethodCallback callback, - bool is_dev_mode) { - is_dev_mode_ = is_dev_mode; - std::vector<std::string> enviroment; - if (start_params_.disable_ureadahead) - enviroment.emplace_back("DISABLE_UREADAHEAD=1"); - std::deque<JobDesc> jobs{ - // Note: the first Upstart job is a task, and the callback for the start - // request won't be called until the task finishes. When the callback is - // called with true, it is ensured that the per-board features files - // exist. - JobDesc{kArcVmPerBoardFeaturesJobName, UpstartOperation::JOB_START, {}}, - JobDesc{ - kArcVmPostVmStartServicesJobName, UpstartOperation::JOB_STOP, {}}, - JobDesc{kArcVmPostLoginServicesJobName, UpstartOperation::JOB_STOP, {}}, - JobDesc{kArcVmPreLoginServicesJobName, - UpstartOperation::JOB_STOP_AND_START, std::move(enviroment)}, - }; - ConfigureUpstartJobs( - std::move(jobs), - base::BindOnce( - &ArcVmClientAdapter::OnConfigureUpstartJobsOnStartMiniArc, - weak_factory_.GetWeakPtr(), std::move(callback))); - } - void OnConfigureUpstartJobsOnStartMiniArc( chromeos::VoidDBusMethodCallback callback, bool result) { @@ -1055,8 +1017,7 @@ DCHECK_LT(0, cpus); std::vector<std::string> kernel_cmdline = GenerateKernelCmdline( - start_params_, file_system_status, *is_dev_mode_, is_host_on_vm_, - GetChromeOsChannelFromLsbRelease()); + start_params_, file_system_status, is_host_on_vm_); auto start_request = CreateStartArcVmRequest( user_id_hash_, cpus, demo_session_apps_path, data_image_path, file_system_status, use_per_vm_core_scheduling, @@ -1249,7 +1210,6 @@ std::unique_ptr<ArcVmClientAdapterDelegate> delegate_; - absl::optional<bool> is_dev_mode_; // True when the *host* is running on a VM. const bool is_host_on_vm_; // A cryptohome ID of the primary profile.
diff --git a/ash/components/arc/session/arc_vm_client_adapter_unittest.cc b/ash/components/arc/session/arc_vm_client_adapter_unittest.cc index 6aab62e7..51232448 100644 --- a/ash/components/arc/session/arc_vm_client_adapter_unittest.cc +++ b/ash/components/arc/session/arc_vm_client_adapter_unittest.cc
@@ -1313,17 +1313,6 @@ "ro.boot.arc_demo_mode=1")); } -TEST_F(ArcVmClientAdapterTest, StartMiniArc_DisableSystemDefaultApp) { - StartParams start_params(GetPopulatedStartParams()); - start_params.arc_disable_system_default_app = true; - StartMiniArcWithParams(true, std::move(start_params)); - EXPECT_GE(GetTestConciergeClient()->start_arc_vm_call_count(), 1); - EXPECT_FALSE(is_system_shutdown().has_value()); - EXPECT_TRUE( - base::Contains(GetTestConciergeClient()->start_arc_vm_request().params(), - "androidboot.disable_system_default_app=1")); -} - TEST_F(ArcVmClientAdapterTest, StartUpgradeArc_DisableMediaStoreMaintenance) { StartParams start_params(GetPopulatedStartParams()); start_params.disable_media_store_maintenance = true; @@ -1543,28 +1532,6 @@ CreateArcVmClientAdapter(); } -TEST_F(ArcVmClientAdapterTest, ChromeOsChannelStable) { - base::test::ScopedChromeOSVersionInfo info( - "CHROMEOS_RELEASE_TRACK=stable-channel", base::Time::Now()); - - StartParams start_params(GetPopulatedStartParams()); - StartMiniArcWithParams(true, std::move(start_params)); - EXPECT_TRUE( - base::Contains(GetTestConciergeClient()->start_arc_vm_request().params(), - "androidboot.chromeos_channel=stable")); -} - -TEST_F(ArcVmClientAdapterTest, ChromeOsChannelUnknown) { - base::test::ScopedChromeOSVersionInfo info("CHROMEOS_RELEASE_TRACK=invalid", - base::Time::Now()); - - StartParams start_params(GetPopulatedStartParams()); - StartMiniArcWithParams(true, std::move(start_params)); - EXPECT_TRUE( - base::Contains(GetTestConciergeClient()->start_arc_vm_request().params(), - "androidboot.chromeos_channel=unknown")); -} - TEST_F(ArcVmClientAdapterTest, DefaultBlockSize) { base::test::ScopedFeatureList feature_list; feature_list.InitWithFeatureState(arc::kUseDefaultBlockSize, true /* use */); @@ -1669,18 +1636,6 @@ base::Contains(req.params(), "androidboot.arcvm_virtio_blk_data=1")); } -TEST_F(ArcVmClientAdapterTest, VshdForTest) { - base::test::ScopedChromeOSVersionInfo info( - "CHROMEOS_RELEASE_TRACK=testimage-channel", base::Time::Now()); - - StartParams start_params(GetPopulatedStartParams()); - StartMiniArcWithParams(true, std::move(start_params)); - UpgradeArc(true); - EXPECT_TRUE( - base::Contains(GetTestConciergeClient()->start_arc_vm_request().params(), - "androidboot.vshd_service_override=vshd_for_test")); -} - TEST_F(ArcVmClientAdapterTest, VshdForRelease) { base::test::ScopedChromeOSVersionInfo info( "CHROMEOS_RELEASE_TRACK=stable-channel", base::Time::Now());
diff --git a/ash/constants/ash_switches.cc b/ash/constants/ash_switches.cc index 45f3ff3b..adaa940 100644 --- a/ash/constants/ash_switches.cc +++ b/ash/constants/ash_switches.cc
@@ -101,10 +101,6 @@ // apps silently. Used in autotests to resolve racy conditions. const char kArcDisablePlayAutoInstall[] = "arc-disable-play-auto-install"; -// Used for development of Android app that are included into ARC as system -// default apps in order to be able to install them via adb. -const char kArcDisableSystemDefaultApps[] = "arc-disable-system-default-apps"; - // Flag that disables ureadahead completely, including host and guest parts. // See also |kArcVmUreadaheadMode|. const char kArcDisableUreadahead[] = "arc-disable-ureadahead";
diff --git a/ash/constants/ash_switches.h b/ash/constants/ash_switches.h index b6c4037..9f2fd73 100644 --- a/ash/constants/ash_switches.h +++ b/ash/constants/ash_switches.h
@@ -40,8 +40,6 @@ COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kArcDisableMediaStoreMaintenance[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kArcDisablePlayAutoInstall[]; -COMPONENT_EXPORT(ASH_CONSTANTS) -extern const char kArcDisableSystemDefaultApps[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kArcDisableUreadahead[]; COMPONENT_EXPORT(ASH_CONSTANTS) extern const char kArcEnableNativeBridge64BitSupportExperiment[];
diff --git a/ash/login/login_screen_test_api.cc b/ash/login/login_screen_test_api.cc index 0d90056d..eec4b32 100644 --- a/ash/login/login_screen_test_api.cc +++ b/ash/login/login_screen_test_api.cc
@@ -276,6 +276,14 @@ } // static +bool LoginScreenTestApi::IsKioskInstructionBubbleShown() { + LoginShelfView* view = GetLoginShelfView(); + return view->GetKioskInstructionBubbleForTesting() && + view->GetKioskInstructionBubbleForTesting()->GetWidget() && + view->GetKioskInstructionBubbleForTesting()->GetWidget()->IsVisible(); +} + +// static bool LoginScreenTestApi::IsPasswordFieldShown(const AccountId& account_id) { if (GetFocusedUser() != account_id) { ADD_FAILURE() << "The user " << account_id.Serialize() << " is not focused";
diff --git a/ash/public/cpp/login_screen_test_api.h b/ash/public/cpp/login_screen_test_api.h index 2e02868..dd67910 100644 --- a/ash/public/cpp/login_screen_test_api.h +++ b/ash/public/cpp/login_screen_test_api.h
@@ -43,6 +43,7 @@ static bool IsWarningBubbleShown(); static bool IsUserAddingScreenIndicatorShown(); static bool IsSystemInfoShown(); + static bool IsKioskInstructionBubbleShown(); static bool IsPasswordFieldShown(const AccountId& account_id); static bool IsDisplayPasswordButtonShown(const AccountId& account_id); static bool IsManagedIconShown(const AccountId& account_id);
diff --git a/ash/webui/camera_app_ui/camera_app_ui.cc b/ash/webui/camera_app_ui/camera_app_ui.cc index f1c83c4..0827131 100644 --- a/ash/webui/camera_app_ui/camera_app_ui.cc +++ b/ash/webui/camera_app_ui/camera_app_ui.cc
@@ -10,6 +10,9 @@ #include "ash/webui/camera_app_ui/url_constants.h" #include "ash/webui/grit/ash_camera_app_resources_map.h" #include "base/bind.h" +#include "base/feature_list.h" +#include "base/files/file_util.h" +#include "base/memory/ref_counted_memory.h" #include "base/strings/string_util.h" #include "components/arc/intent_helper/arc_intent_helper_bridge.h" #include "components/content_settings/core/common/content_settings_types.h" @@ -35,6 +38,11 @@ namespace { +const base::Feature kCCALocalOverride{"CCALocalOverride", + base::FEATURE_DISABLED_BY_DEFAULT}; +const base::FilePath::CharType kCCALocalOverrideDirectoryPath[] = + FILE_PATH_LITERAL("/etc/camera/cca"); + content::WebUIDataSource* CreateCameraAppUIHTMLSource( CameraAppUIDelegate* delegate) { content::WebUIDataSource* source = @@ -54,6 +62,41 @@ source->UseStringsJs(); + if (base::FeatureList::IsEnabled(kCCALocalOverride)) { + source->SetRequestFilter( + base::BindRepeating([](const std::string& url) { + // Only override files that are copied locally with cca.py deploy. + if (!(base::StartsWith(url, "js/") || base::StartsWith(url, "css/") || + base::StartsWith(url, "images/") || + base::StartsWith(url, "views/") || + base::StartsWith(url, "sounds/"))) { + return false; + } + // This file is written by `cca.py deploy` and contains version + // information of deployed file. + base::FilePath version_path = + base::FilePath(kCCALocalOverrideDirectoryPath) + .Append("js/deployed_version.js"); + if (!base::PathExists(version_path)) { + return false; + } + return true; + }), + base::BindRepeating( + [](const std::string& url, + content::WebUIDataSource::GotDataCallback callback) { + base::FilePath path = + base::FilePath(kCCALocalOverrideDirectoryPath).Append(url); + std::string result; + if (base::ReadFileToString(path, &result)) { + std::move(callback).Run( + base::RefCountedString::TakeString(&result)); + } else { + std::move(callback).Run(nullptr); + } + })); + } + source->OverrideContentSecurityPolicy( network::mojom::CSPDirectiveName::WorkerSrc, std::string("worker-src 'self';"));
diff --git a/ash/webui/camera_app_ui/resources/css/focus_ring.css b/ash/webui/camera_app_ui/resources/css/focus_ring.css index 96c32f9..1b7ec5a0 100644 --- a/ash/webui/camera_app_ui/resources/css/focus_ring.css +++ b/ash/webui/camera_app_ui/resources/css/focus_ring.css
@@ -2,7 +2,7 @@ * Use of this source code is governed by a BSD-style license that can be * found in the LICENSE file. */ -body:not(.keyboard-navigation) #focus-ring { +body:not(.show-focus-ring) #focus-ring { visibility: hidden; }
diff --git a/ash/webui/camera_app_ui/resources/css/main.css b/ash/webui/camera_app_ui/resources/css/main.css index 23488606..471e505c 100644 --- a/ash/webui/camera_app_ui/resources/css/main.css +++ b/ash/webui/camera_app_ui/resources/css/main.css
@@ -596,7 +596,7 @@ --option-item-vpadding: 12px; --switch-device-gap: 32px; bottom: calc(var(--bottom-line) + (var(--big-icon) / 2) + var(--switch-device-gap) - var(--option-item-vpadding)); - flex-direction: column-reverse; + flex-direction: column; transition: bottom var(--fast1-duration); }
diff --git a/ash/webui/camera_app_ui/resources/js/focus_ring.ts b/ash/webui/camera_app_ui/resources/js/focus_ring.ts index 85f126a..60fe2328 100644 --- a/ash/webui/camera_app_ui/resources/js/focus_ring.ts +++ b/ash/webui/camera_app_ui/resources/js/focus_ring.ts
@@ -5,6 +5,7 @@ import {assert} from './assert.js'; import {cssStyle} from './css.js'; import * as dom from './dom.js'; +import * as state from './state.js'; import {getStyleValueInPx} from './util.js'; /** @@ -85,12 +86,24 @@ } /** + * Check visibility of the focus ring. + */ +export function checkFocusRingVisibility(): void { + const showFocusRing = + document.activeElement?.hasAttribute('tabindex') === true && + state.get(state.State.KEYBOARD_NAVIGATION); + state.set(state.State.SHOW_FOCUS_RING, showFocusRing); +} + +/** * Initializes DOM elements and observers used for focus ring. */ export function initialize(): void { ring = dom.get('#focus-ring', HTMLElement); ringCSSStyle = cssStyle('#focus-ring'); + window.addEventListener('focus', checkFocusRingVisibility, true); + for (const el of dom.getAll('[tabindex]', HTMLElement)) { setup(el); }
diff --git a/ash/webui/camera_app_ui/resources/js/nav.ts b/ash/webui/camera_app_ui/resources/js/nav.ts index 7d4ee361..865fa4c 100644 --- a/ash/webui/camera_app_ui/resources/js/nav.ts +++ b/ash/webui/camera_app_ui/resources/js/nav.ts
@@ -4,6 +4,7 @@ import {assert} from './assert.js'; import {toggleExpertMode} from './expert.js'; +import {checkFocusRingVisibility} from './focus_ring.js'; import * as state from './state.js'; import * as toast from './toast.js'; import {ViewName} from './type.js'; @@ -39,10 +40,14 @@ */ export function setup(views: View[]): void { allViews = views.flatMap((v) => [...getRecursiveViews(v)]); - document.addEventListener( - 'pointerdown', () => state.set(state.State.KEYBOARD_NAVIGATION, false)); - document.addEventListener( - 'keydown', () => state.set(state.State.KEYBOARD_NAVIGATION, true)); + document.addEventListener('pointerdown', () => { + state.set(state.State.KEYBOARD_NAVIGATION, false); + checkFocusRingVisibility(); + }); + document.addEventListener('keydown', () => { + state.set(state.State.KEYBOARD_NAVIGATION, true); + checkFocusRingVisibility(); + }); } /**
diff --git a/ash/webui/camera_app_ui/resources/js/state.ts b/ash/webui/camera_app_ui/resources/js/state.ts index f0c1abd8..55b5e6e 100644 --- a/ash/webui/camera_app_ui/resources/js/state.ts +++ b/ash/webui/camera_app_ui/resources/js/state.ts
@@ -56,6 +56,7 @@ SAVE_METADATA = 'save-metadata', SHOULD_HANDLE_INTENT_RESULT = 'should-handle-intent-result', SHOW_ALL_RESOLUTIONS = 'show-all-resolutions', + SHOW_FOCUS_RING = 'show-focus-ring', SHOW_GIF_RECORDING_OPTION = 'show-gif-recording-option', SHOW_METADATA = 'show-metadata', SHOW_SCAN_MODE = 'show-scan-mode',
diff --git a/ash/webui/camera_app_ui/resources/views/main.html b/ash/webui/camera_app_ui/resources/views/main.html index 46b76acc..2a1aac0 100644 --- a/ash/webui/camera_app_ui/resources/views/main.html +++ b/ash/webui/camera_app_ui/resources/views/main.html
@@ -118,70 +118,29 @@ </div> </div> </div> - <div id="video-snapshot-holder" class="buttons right-stripe circle"> - <button id="video-snapshot" tabindex="0" - i18n-label="take_video_snapshot_button"></button> + <div class="top-stripe left-stripe buttons circle"> + <button id="open-settings" tabindex="0" + i18n-label="settings_button" aria-haspopup="true"></button> </div> - <div id="shutters-group" class="buttons right-stripe circle"> - <button id="recordvideo" class="shutter" tabindex="0" - i18n-label="record_video_start_button"> - <div class="red-dot"></div> - <div class="white-square"></div> - <svg id="shutter-progress-bar"> - <circle></circle> - </svg> + <div class="top-stripe right-stripe circle buttons"> + <input id="toggle-mic" type="checkbox" tabindex="0" + i18n-label="toggle_mic_button" data-state="mic" + i18n-aria="aria_mute_off" data-key="toggleMic" checked> + </div> + <div class="top-stripe right-stripe circle buttons"> + <input id="toggle-barcode" type="checkbox" tabindex="0" + i18n-label="toggle_barcode_button"> + </div> + <div id="options-group" class="left-stripe buttons circle"> + <button id="open-mirror-panel" tabindex="0" aria-haspopup="true"> </button> - <button id="start-takephoto" class="shutter" tabindex="0" - i18n-label="take_photo_button"></button> - <button id="stop-takephoto" class="shutter" tabindex="0" - i18n-label="take_photo_cancel_button"></button> - </div> - <div id="pause-recordvideo-holder" class="buttons right-stripe circle"> - <button id="pause-recordvideo" tabindex="0" - i18n-label="record_video_pause_button"> - <div class="red-dot"></div> - <div class="two-bars"></div> + <button id="open-grid-panel" tabindex="0" aria-haspopup="true"></button> + <button id="open-timer-panel" tabindex="0" aria-haspopup="true"> + <button id="open-ptz-panel" tabindex="0" aria-haspopup="true" + i18n-label="open_ptz_panel_button" + i18n-new-feature="new_control_toast"></button> </button> </div> - <div class="bottom-stripe right-stripe buttons circle"> - <button id="gallery-enter" tabindex="0" - i18n-label="gallery_button" hidden> - <img> - </button> - </div> - <div id="mode-selector" class="bottom-stripe"> - <div id="modes-group" class="buttons" role="radiogroup" - i18n-aria="aria_camera_mode_group"> - <div class="mode-item"> - <input type="radio" name="mode" - data-mode="video" tabindex="0" - i18n-aria="switch_record_video_button"> - <span i18n-text="label_switch_record_video_button" - aria-hidden="true"></span> - </div> - <div class="mode-item"> - <input type="radio" name="mode" - data-mode="photo" tabindex="0" - i18n-aria="switch_take_photo_button"> - <span i18n-text="label_switch_take_photo_button" - aria-hidden="true"></span> - </div> - <div class="mode-item" i18n-new-feature="new_document_scan_toast"> - <input type="radio" name="mode" - data-mode="scan" tabindex="0" - i18n-aria="switch_scan_mode_button"> - <span i18n-text="label_switch_scan_mode_button" - aria-hidden="true"></span> - </div> - <div class="mode-item"> - <input type="radio" name="mode" - data-mode="portrait" tabindex="0" - i18n-aria="switch_take_portrait_bokeh_photo_button"> - <span i18n-text="label_switch_take_portrait_bokeh_photo_button" - aria-hidden="true"></span> - </div> - </div> - </div> <div id="scan-modes-group" class="mode-subgroup" role="radiogroup" i18n-aria="aria_scan_type_group"> <div id="scan-document-option" class="item"> @@ -216,39 +175,79 @@ aria-hidden="true"></div> </div> </div> + <div id="video-snapshot-holder" class="buttons right-stripe circle"> + <button id="video-snapshot" tabindex="0" + i18n-label="take_video_snapshot_button"></button> + </div> + <div id="shutters-group" class="buttons right-stripe circle"> + <button id="recordvideo" class="shutter" tabindex="0" + i18n-label="record_video_start_button"> + <div class="red-dot"></div> + <div class="white-square"></div> + <svg id="shutter-progress-bar"> + <circle></circle> + </svg> + </button> + <button id="start-takephoto" class="shutter" tabindex="0" + i18n-label="take_photo_button"></button> + <button id="stop-takephoto" class="shutter" tabindex="0" + i18n-label="take_photo_cancel_button"></button> + </div> + <div id="pause-recordvideo-holder" class="buttons right-stripe circle"> + <button id="pause-recordvideo" tabindex="0" + i18n-label="record_video_pause_button"> + <div class="red-dot"></div> + <div class="two-bars"></div> + </button> + </div> <div class="bottom-stripe left-stripe buttons circle"> <button id="switch-device" tabindex="0" i18n-label="switch_camera_button"></button> </div> - - <div id="options-group" class="left-stripe buttons circle"> - <button id="open-ptz-panel" tabindex="0" aria-haspopup="true" - i18n-label="open_ptz_panel_button" - i18n-new-feature="new_control_toast"></button> - <button id="open-timer-panel" tabindex="0" aria-haspopup="true"> - </button> - <button id="open-grid-panel" tabindex="0" aria-haspopup="true"></button> - <button id="open-mirror-panel" tabindex="0" aria-haspopup="true"> - </button> + <div id="mode-selector" class="bottom-stripe"> + <div id="modes-group" class="buttons" role="radiogroup" + i18n-aria="aria_camera_mode_group"> + <div class="mode-item"> + <input type="radio" name="mode" + data-mode="video" tabindex="0" + i18n-aria="switch_record_video_button"> + <span i18n-text="label_switch_record_video_button" + aria-hidden="true"></span> + </div> + <div class="mode-item"> + <input type="radio" name="mode" + data-mode="photo" tabindex="0" + i18n-aria="switch_take_photo_button"> + <span i18n-text="label_switch_take_photo_button" + aria-hidden="true"></span> + </div> + <div class="mode-item" i18n-new-feature="new_document_scan_toast"> + <input type="radio" name="mode" + data-mode="scan" tabindex="0" + i18n-aria="switch_scan_mode_button"> + <span i18n-text="label_switch_scan_mode_button" + aria-hidden="true"></span> + </div> + <div class="mode-item"> + <input type="radio" name="mode" + data-mode="portrait" tabindex="0" + i18n-aria="switch_take_portrait_bokeh_photo_button"> + <span i18n-text="label_switch_take_portrait_bokeh_photo_button" + aria-hidden="true"></span> + </div> + </div> </div> - <div class="top-stripe left-stripe buttons circle"> - <button id="open-settings" tabindex="0" - i18n-label="settings_button" aria-haspopup="true"></button> + <div class="bottom-stripe right-stripe buttons circle"> + <button id="gallery-enter" tabindex="0" + i18n-label="gallery_button" hidden> + <img> + </button> </div> <div id="record-time" class="top-stripe horizontal-center-stripe" hidden> <div class="icon"></div> <div id="paused-msg" i18n-text="record_video_paused_msg"></div> <div id="record-time-msg"></div> </div> - <div class="top-stripe right-stripe circle buttons"> - <input id="toggle-mic" type="checkbox" tabindex="0" - i18n-label="toggle_mic_button" data-state="mic" - i18n-aria="aria_mute_off" data-key="toggleMic" checked> - </div> - <div class="top-stripe right-stripe circle buttons"> - <input id="toggle-barcode" type="checkbox" tabindex="0" - i18n-label="toggle_barcode_button"> - </div> <div class="centered-overlay"> <div id="timer-tick-msg"></div> </div>
diff --git a/base/allocator/partition_allocator/BUILD.gn b/base/allocator/partition_allocator/BUILD.gn index 559a733..a9105b0f 100644 --- a/base/allocator/partition_allocator/BUILD.gn +++ b/base/allocator/partition_allocator/BUILD.gn
@@ -75,6 +75,8 @@ "partition_alloc_base/atomic_ref_count.h", "partition_alloc_base/bit_cast.h", "partition_alloc_base/bits.h", + "partition_alloc_base/check.cc", + "partition_alloc_base/check.h", "partition_alloc_base/compiler_specific.h", "partition_alloc_base/cpu.cc", "partition_alloc_base/cpu.h",
diff --git a/base/allocator/partition_allocator/DEPS b/base/allocator/partition_allocator/DEPS index 0f186c8..d05f961 100644 --- a/base/allocator/partition_allocator/DEPS +++ b/base/allocator/partition_allocator/DEPS
@@ -6,8 +6,6 @@ include_rules = [ "+base/allocator/buildflags.h", "+base/base_export.h", - "+base/check.h", - "+base/check_op.h", "+base/compiler_specific.h", "+base/dcheck_is_on.h", "+base/logging_buildflags.h",
diff --git a/base/allocator/partition_allocator/address_space_randomization_unittest.cc b/base/allocator/partition_allocator/address_space_randomization_unittest.cc index 6b221ef..88d91d3 100644 --- a/base/allocator/partition_allocator/address_space_randomization_unittest.cc +++ b/base/allocator/partition_allocator/address_space_randomization_unittest.cc
@@ -8,8 +8,8 @@ #include <vector> #include "base/allocator/partition_allocator/page_allocator.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "base/allocator/partition_allocator/random.h" -#include "base/check_op.h" #include "base/dcheck_is_on.h" #include "build/build_config.h" #include "testing/gtest/include/gtest/gtest.h" @@ -190,7 +190,7 @@ // For k=2 probability of Chi^2 < 35 is p=3.338e-9. This condition is // tested ~19000 times, so probability of it failing randomly per one // base_unittests run is (1 - (1 - p) ^ 19000) ~= 6e-5. - CHECK_LE(chi_squared, 35.0); + PA_CHECK(chi_squared <= 35.0); // If the predictor bit is a fixed 0 or 1 then it makes no sense to // repeat the test with a different age. if (predictor_bit < 0)
diff --git a/base/allocator/partition_allocator/partition_alloc_base/check.cc b/base/allocator/partition_allocator/partition_alloc_base/check.cc new file mode 100644 index 0000000..c687549 --- /dev/null +++ b/base/allocator/partition_allocator/partition_alloc_base/check.cc
@@ -0,0 +1,103 @@ +// 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 "base/allocator/partition_allocator/partition_alloc_base/check.h" + +#include "build/build_config.h" + +// check.h is a widely included header and its size has significant impact on +// build time. Try not to raise this limit unless absolutely necessary. See +// https://chromium.googlesource.com/chromium/src/+/HEAD/docs/wmax_tokens.md +#ifndef NACL_TC_REV +#pragma clang max_tokens_here 17000 +#endif + +#include "base/allocator/partition_allocator/partition_alloc_base/logging.h" +#include "build/build_config.h" + +namespace partition_alloc::internal::logging { + +// TODO(1151236): Make CheckError not to allocate memory. So we can use +// CHECK() inside PartitionAllocator when PartitionAllocator-Everywhere is +// enabled. (Also need to modify LogMessage). +CheckError CheckError::Check(const char* file, + int line, + const char* condition) { + CheckError check_error(new LogMessage(file, line, LOGGING_FATAL)); + check_error.stream() << "Check failed: " << condition << ". "; + return check_error; +} + +CheckError CheckError::DCheck(const char* file, + int line, + const char* condition) { + CheckError check_error(new LogMessage(file, line, LOGGING_DCHECK)); + check_error.stream() << "Check failed: " << condition << ". "; + return check_error; +} + +CheckError CheckError::PCheck(const char* file, + int line, + const char* condition) { + SystemErrorCode err_code = logging::GetLastSystemErrorCode(); +#if BUILDFLAG(IS_WIN) + CheckError check_error( + new Win32ErrorLogMessage(file, line, LOGGING_FATAL, err_code)); +#elif BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_FUCHSIA) + CheckError check_error( + new ErrnoLogMessage(file, line, LOGGING_FATAL, err_code)); +#endif + check_error.stream() << "Check failed: " << condition << ". "; + return check_error; +} + +CheckError CheckError::PCheck(const char* file, int line) { + return PCheck(file, line, ""); +} + +CheckError CheckError::DPCheck(const char* file, + int line, + const char* condition) { + SystemErrorCode err_code = logging::GetLastSystemErrorCode(); +#if BUILDFLAG(IS_WIN) + CheckError check_error( + new Win32ErrorLogMessage(file, line, LOGGING_DCHECK, err_code)); +#elif BUILDFLAG(IS_POSIX) || BUILDFLAG(IS_FUCHSIA) + CheckError check_error( + new ErrnoLogMessage(file, line, LOGGING_DCHECK, err_code)); +#endif + check_error.stream() << "Check failed: " << condition << ". "; + return check_error; +} + +CheckError CheckError::NotImplemented(const char* file, + int line, + const char* function) { + CheckError check_error(new LogMessage(file, line, LOGGING_ERROR)); + check_error.stream() << "Not implemented reached in " << function; + return check_error; +} + +std::ostream& CheckError::stream() { + return log_message_->stream(); +} + +CheckError::~CheckError() { + // Note: This function ends up in crash stack traces. If its full name + // changes, the crash server's magic signature logic needs to be updated. + // See cl/306632920. + delete log_message_; +} + +CheckError::CheckError(LogMessage* log_message) : log_message_(log_message) {} + +void RawCheck(const char* message) { + RawLog(LOGGING_FATAL, message); +} + +void RawError(const char* message) { + RawLog(LOGGING_ERROR, message); +} + +} // namespace partition_alloc::internal::logging
diff --git a/base/allocator/partition_allocator/partition_alloc_base/check.h b/base/allocator/partition_allocator/partition_alloc_base/check.h new file mode 100644 index 0000000..50f46e71 --- /dev/null +++ b/base/allocator/partition_allocator/partition_alloc_base/check.h
@@ -0,0 +1,178 @@ +// 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 BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_BASE_CHECK_H_ +#define BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_BASE_CHECK_H_ + +#include <iosfwd> + +#include "base/allocator/partition_allocator/partition_alloc_base/immediate_crash.h" +#include "base/base_export.h" +#include "base/compiler_specific.h" +#include "base/dcheck_is_on.h" + +// This header defines the CHECK, DCHECK, and DPCHECK macros. +// +// CHECK dies with a fatal error if its condition is not true. It is not +// controlled by NDEBUG, so the check will be executed regardless of compilation +// mode. +// +// DCHECK, the "debug mode" check, is enabled depending on NDEBUG and +// DCHECK_ALWAYS_ON, and its severity depends on DCHECK_IS_CONFIGURABLE. +// +// (D)PCHECK is like (D)CHECK, but includes the system error code (c.f. +// perror(3)). +// +// Additional information can be streamed to these macros and will be included +// in the log output if the condition doesn't hold (you may need to include +// <ostream>): +// +// CHECK(condition) << "Additional info."; +// +// The condition is evaluated exactly once. Even in build modes where e.g. +// DCHECK is disabled, the condition and any stream arguments are still +// referenced to avoid warnings about unused variables and functions. +// +// For the (D)CHECK_EQ, etc. macros, see base/check_op.h. However, that header +// is *significantly* larger than check.h, so try to avoid including it in +// header files. + +namespace partition_alloc::internal::logging { + +// Class used to explicitly ignore an ostream, and optionally a boolean value. +class VoidifyStream { + public: + VoidifyStream() = default; + explicit VoidifyStream(bool ignored) {} + + // This operator has lower precedence than << but higher than ?: + void operator&(std::ostream&) {} +}; + +// Helper macro which avoids evaluating the arguments to a stream if the +// condition is false. +#define PA_LAZY_CHECK_STREAM(stream, condition) \ + !(condition) \ + ? (void)0 \ + : ::partition_alloc::internal::logging::VoidifyStream() & (stream) + +// Macro which uses but does not evaluate expr and any stream parameters. +#define PA_EAT_CHECK_STREAM_PARAMS(expr) \ + true ? (void)0 \ + : ::partition_alloc::internal::logging::VoidifyStream(expr) & \ + (*::partition_alloc::internal::logging::g_swallow_stream) +BASE_EXPORT extern std::ostream* g_swallow_stream; + +class LogMessage; + +// Class used for raising a check error upon destruction. +class BASE_EXPORT CheckError { + public: + static CheckError Check(const char* file, int line, const char* condition); + + static CheckError DCheck(const char* file, int line, const char* condition); + + static CheckError PCheck(const char* file, int line, const char* condition); + static CheckError PCheck(const char* file, int line); + + static CheckError DPCheck(const char* file, int line, const char* condition); + + static CheckError NotImplemented(const char* file, + int line, + const char* function); + + // Stream for adding optional details to the error message. + std::ostream& stream(); + + NOMERGE ~CheckError(); + + CheckError(const CheckError& other) = delete; + CheckError& operator=(const CheckError& other) = delete; + CheckError(CheckError&& other) = default; + CheckError& operator=(CheckError&& other) = default; + + private: + explicit CheckError(LogMessage* log_message); + + LogMessage* log_message_; +}; + +#if defined(OFFICIAL_BUILD) && defined(NDEBUG) + +// Discard log strings to reduce code bloat. +// +// This is not calling BreakDebugger since this is called frequently, and +// calling an out-of-line function instead of a noreturn inline macro prevents +// compiler optimizations. +#define PA_BASE_CHECK(condition) \ + UNLIKELY(!(condition)) ? PA_IMMEDIATE_CRASH() : PA_EAT_CHECK_STREAM_PARAMS() + +// TODO(1151236): base/test/gtest_util.h uses CHECK_WILL_STREAM(). After +// copying (or removing) gtest_util.h and removing gtest_uti.h from partition +// allocator's DEPS, rename or remove CHECK_WILL_STREAM(). +#define CHECK_WILL_STREAM() false + +#define PA_BASE_PCHECK(condition) \ + PA_LAZY_CHECK_STREAM( \ + ::partition_alloc::internal::logging::CheckError::PCheck(__FILE__, \ + __LINE__) \ + .stream(), \ + UNLIKELY(!(condition))) + +#else + +#define PA_BASE_CHECK(condition) \ + PA_LAZY_CHECK_STREAM( \ + ::partition_alloc::internal::logging::CheckError::Check( \ + __FILE__, __LINE__, #condition) \ + .stream(), \ + !ANALYZER_ASSUME_TRUE(condition)) + +#define CHECK_WILL_STREAM() true + +#define PA_BASE_PCHECK(condition) \ + PA_LAZY_CHECK_STREAM( \ + ::partition_alloc::internal::logging::CheckError::PCheck( \ + __FILE__, __LINE__, #condition) \ + .stream(), \ + !ANALYZER_ASSUME_TRUE(condition)) + +#endif + +#if DCHECK_IS_ON() + +#define PA_BASE_DCHECK(condition) \ + PA_LAZY_CHECK_STREAM( \ + ::partition_alloc::internal::logging::CheckError::DCheck( \ + __FILE__, __LINE__, #condition) \ + .stream(), \ + !ANALYZER_ASSUME_TRUE(condition)) + +#define PA_BASE_DPCHECK(condition) \ + PA_LAZY_CHECK_STREAM( \ + ::partition_alloc::internal::logging::CheckError::DPCheck( \ + __FILE__, __LINE__, #condition) \ + .stream(), \ + !ANALYZER_ASSUME_TRUE(condition)) + +#else + +#define PA_BASE_DCHECK(condition) PA_EAT_CHECK_STREAM_PARAMS(!(condition)) +#define PA_BASE_DPCHECK(condition) PA_EAT_CHECK_STREAM_PARAMS(!(condition)) + +#endif + +// Async signal safe checking mechanism. +BASE_EXPORT void RawCheck(const char* message); +BASE_EXPORT void RawError(const char* message); +#define PA_RAW_CHECK(condition) \ + do { \ + if (!(condition)) \ + ::partition_alloc::internal::logging::RawCheck( \ + "Check failed: " #condition "\n"); \ + } while (0) + +} // namespace partition_alloc::internal::logging + +#endif // BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_BASE_CHECK_H_
diff --git a/base/allocator/partition_allocator/partition_alloc_base/files/file_path.cc b/base/allocator/partition_allocator/partition_alloc_base/files/file_path.cc index 17233aba..3a1560d 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/files/file_path.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/files/file_path.cc
@@ -16,7 +16,7 @@ #include <string.h> #include <algorithm> -#include "base/check_op.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "build/build_config.h" #if BUILDFLAG(IS_WIN) @@ -103,7 +103,7 @@ appended = without_nuls; } - DCHECK(!IsPathAbsolute(appended)); + PA_DCHECK(!IsPathAbsolute(appended)); if (path_.compare(kCurrentDirectory) == 0 && !appended.empty()) { // Append normally doesn't do any normalization, but as a special case,
diff --git a/base/allocator/partition_allocator/partition_alloc_base/logging.cc b/base/allocator/partition_allocator/partition_alloc_base/logging.cc index b4e73086..cbf408a 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/logging.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/logging.cc
@@ -4,7 +4,12 @@ #include "base/allocator/partition_allocator/partition_alloc_base/logging.h" -#ifdef BASE_CHECK_H_ +// TODO(1151236): After finishing copying //base files to PA library, remove +// defined(BASE_CHECK_H_) from here. +#if defined( \ + BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_BASE_CHECK_H_) || \ + defined(BASE_CHECK_H_) || \ + defined(BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_CHECK_H_) #error "logging.h should not include check.h" #endif
diff --git a/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.cc b/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.cc index c935ce41..3b7a5c1 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.cc
@@ -20,8 +20,8 @@ #if DCHECK_IS_ON() RefCountedThreadSafeBase::~RefCountedThreadSafeBase() { - DCHECK(in_dtor_) << "RefCountedThreadSafe object deleted without " - "calling Release()"; + PA_DCHECK(in_dtor_) << "RefCountedThreadSafe object deleted without " + "calling Release()"; } #endif
diff --git a/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.h b/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.h index 630ede2..7ff63087 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.h +++ b/base/allocator/partition_allocator/partition_alloc_base/memory/ref_counted.h
@@ -8,9 +8,8 @@ #include "base/allocator/partition_allocator/partition_alloc_base/atomic_ref_count.h" #include "base/allocator/partition_allocator/partition_alloc_base/compiler_specific.h" #include "base/allocator/partition_allocator/partition_alloc_base/memory/scoped_refptr.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "base/base_export.h" -#include "base/check.h" -#include "base/check_op.h" #include "base/dcheck_is_on.h" #include "build/build_config.h" @@ -61,37 +60,37 @@ void Adopted() const { #if DCHECK_IS_ON() - DCHECK(needs_adopt_ref_); + PA_DCHECK(needs_adopt_ref_); needs_adopt_ref_ = false; #endif } PA_ALWAYS_INLINE void AddRefImpl() const { #if DCHECK_IS_ON() - DCHECK(!in_dtor_); + PA_DCHECK(!in_dtor_); // This RefCounted object is created with non-zero reference count. // The first reference to such a object has to be made by AdoptRef or // MakeRefCounted. - DCHECK(!needs_adopt_ref_); + PA_DCHECK(!needs_adopt_ref_); #endif ref_count_.Increment(); } PA_ALWAYS_INLINE void AddRefWithCheckImpl() const { #if DCHECK_IS_ON() - DCHECK(!in_dtor_); + PA_DCHECK(!in_dtor_); // This RefCounted object is created with non-zero reference count. // The first reference to such a object has to be made by AdoptRef or // MakeRefCounted. - DCHECK(!needs_adopt_ref_); + PA_DCHECK(!needs_adopt_ref_); #endif - CHECK_GT(ref_count_.Increment(), 0); + PA_CHECK(ref_count_.Increment() > 0); } PA_ALWAYS_INLINE bool ReleaseImpl() const { #if DCHECK_IS_ON() - DCHECK(!in_dtor_); - DCHECK(!ref_count_.IsZero()); + PA_DCHECK(!in_dtor_); + PA_DCHECK(!ref_count_.IsZero()); #endif if (!ref_count_.Decrement()) { #if DCHECK_IS_ON()
diff --git a/base/allocator/partition_allocator/partition_alloc_base/memory/scoped_refptr.h b/base/allocator/partition_allocator/partition_alloc_base/memory/scoped_refptr.h index b7d417e0..857c0a6 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/memory/scoped_refptr.h +++ b/base/allocator/partition_allocator/partition_alloc_base/memory/scoped_refptr.h
@@ -12,7 +12,7 @@ #include <utility> #include "base/allocator/partition_allocator/partition_alloc_base/compiler_specific.h" -#include "base/check.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" namespace partition_alloc::internal { @@ -70,8 +70,8 @@ static_assert(std::is_same<subtle::StartRefCountFromOneTag, Tag>::value, "Use AdoptRef only if the reference count starts from one."); - DCHECK(obj); - DCHECK(obj->HasOneRef()); + PA_DCHECK(obj); + PA_DCHECK(obj->HasOneRef()); obj->Adopted(); return scoped_refptr<T>(obj, subtle::kAdoptRefTag); } @@ -225,12 +225,12 @@ T* get() const { return ptr_; } T& operator*() const { - DCHECK(ptr_); + PA_DCHECK(ptr_); return *ptr_; } T* operator->() const { - DCHECK(ptr_); + PA_DCHECK(ptr_); return ptr_; }
diff --git a/base/allocator/partition_allocator/partition_alloc_base/native_library_posix.cc b/base/allocator/partition_allocator/partition_alloc_base/native_library_posix.cc index 43be0aaf..b025cfbc 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/native_library_posix.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/native_library_posix.cc
@@ -7,7 +7,7 @@ #include <dlfcn.h> #include "base/allocator/partition_allocator/partition_alloc_base/files/file_path.h" -#include "base/check.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "build/build_config.h" namespace partition_alloc::internal::base { @@ -36,7 +36,7 @@ // Certain platforms don't define RTLD_DEEPBIND. Android dlopen() requires // further investigation, as it might vary across versions. Crash here to // warn developers that they're trying to rely on uncertain behavior. - CHECK(!options.prefer_own_symbols); + PA_CHECK(!options.prefer_own_symbols); #else if (options.prefer_own_symbols) flags |= RTLD_DEEPBIND;
diff --git a/base/allocator/partition_allocator/partition_alloc_base/rand_util.cc b/base/allocator/partition_allocator/partition_alloc_base/rand_util.cc index 6b0566b3..4915e02 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/rand_util.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/rand_util.cc
@@ -10,7 +10,7 @@ #include <limits> -#include "base/check_op.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" namespace partition_alloc::internal::base { @@ -21,7 +21,7 @@ } uint64_t RandGenerator(uint64_t range) { - DCHECK_GT(range, 0u); + PA_DCHECK(range > 0u); // We must discard random results above this number, as they would // make the random generator non-uniform (consider e.g. if // MAX_UINT64 was 7 and |range| was 5, then a result of 1 would be twice
diff --git a/base/allocator/partition_allocator/partition_alloc_base/rand_util_pa_unittest.cc b/base/allocator/partition_allocator/partition_alloc_base/rand_util_pa_unittest.cc index f4fe93c..742deec2 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/rand_util_pa_unittest.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/rand_util_pa_unittest.cc
@@ -15,7 +15,7 @@ #include "base/allocator/partition_allocator/partition_alloc_base/logging.h" #include "base/allocator/partition_allocator/partition_alloc_base/time/time.h" -#include "base/check_op.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "testing/gtest/include/gtest/gtest.h" namespace partition_alloc::internal::base { @@ -180,7 +180,7 @@ int from_bit, int num_bits) { const int range = 1 << num_bits; - CHECK_EQ(static_cast<int>(n % range), 0) << "Makes computations simpler"; + PA_CHECK(static_cast<int>(n % range) == 0) << "Makes computations simpler"; std::vector<size_t> samples(range, 0); // Count how many samples pf each value are found. All buckets should be
diff --git a/base/allocator/partition_allocator/partition_alloc_base/rand_util_posix.cc b/base/allocator/partition_allocator/partition_alloc_base/rand_util_posix.cc index 859cb0d5..8e9df218 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/rand_util_posix.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/rand_util_posix.cc
@@ -15,7 +15,7 @@ #include "base/allocator/partition_allocator/partition_alloc_base/files/file_util.h" #include "base/allocator/partition_allocator/partition_alloc_base/no_destructor.h" #include "base/allocator/partition_allocator/partition_alloc_base/posix/eintr_wrapper.h" -#include "base/check.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "build/build_config.h" #if (BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS)) && !BUILDFLAG(IS_NACL) @@ -42,7 +42,7 @@ class URandomFd { public: URandomFd() : fd_(PA_HANDLE_EINTR(open("/dev/urandom", kOpenFlags))) { - CHECK(fd_ >= 0) << "Cannot open /dev/urandom"; + PA_CHECK(fd_ >= 0) << "Cannot open /dev/urandom"; } ~URandomFd() { close(fd_); } @@ -96,7 +96,7 @@ const int urandom_fd = GetUrandomFD(); const bool success = ReadFromFD(urandom_fd, static_cast<char*>(output), output_length); - CHECK(success); + PA_CHECK(success); } } // namespace partition_alloc::internal::base
diff --git a/base/allocator/partition_allocator/partition_alloc_base/rand_util_win.cc b/base/allocator/partition_allocator/partition_alloc_base/rand_util_win.cc index fa8c636..b5775ad 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/rand_util_win.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/rand_util_win.cc
@@ -18,7 +18,7 @@ #include <algorithm> #include <limits> -#include "base/check.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" namespace partition_alloc::internal::base { @@ -29,7 +29,7 @@ output_length, static_cast<size_t>(std::numeric_limits<ULONG>::max()))); const bool success = RtlGenRandom(output_ptr, output_bytes_this_pass) != FALSE; - CHECK(success); + PA_CHECK(success); output_length -= output_bytes_this_pass; output_ptr += output_bytes_this_pass; }
diff --git a/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_mac_for_testing.mm b/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_mac_for_testing.mm index 8b5d028..d9046021 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_mac_for_testing.mm +++ b/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_mac_for_testing.mm
@@ -15,6 +15,7 @@ #include <algorithm> #include <atomic> +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "base/mac/foundation_util.h" #include "base/mac/mac_util.h" #include "build/build_config.h" @@ -38,7 +39,7 @@ withObject:nil]; multithreaded = YES; - DCHECK([NSThread isMultiThreaded]); + PA_DCHECK([NSThread isMultiThreaded]); } }
diff --git a/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_posix_for_testing.cc b/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_posix_for_testing.cc index a1a44c6..4947e7b7 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_posix_for_testing.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_posix_for_testing.cc
@@ -16,7 +16,7 @@ #include "base/allocator/buildflags.h" #include "base/allocator/partition_allocator/partition_alloc_base/logging.h" #include "base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_internal_posix.h" -#include "base/check_op.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "build/build_config.h" #if BUILDFLAG(IS_FUCHSIA) @@ -71,7 +71,7 @@ bool CreateThread(size_t stack_size, PlatformThreadForTesting::Delegate* delegate, PlatformThreadHandle* thread_handle) { - DCHECK(thread_handle); + PA_DCHECK(thread_handle); base::InitThreading(); pthread_attr_t attributes; @@ -135,7 +135,7 @@ // // base::internal::ScopedBlockingCallWithBaseSyncPrimitives // scoped_blocking_call(base::BlockingType::MAY_BLOCK); - CHECK_EQ(0, pthread_join(thread_handle.platform_handle(), nullptr)); + PA_CHECK(0 == pthread_join(thread_handle.platform_handle(), nullptr)); } // static
diff --git a/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_win_for_testing.cc b/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_win_for_testing.cc index cdf045f..501e49e 100644 --- a/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_win_for_testing.cc +++ b/base/allocator/partition_allocator/partition_alloc_base/threading/platform_thread_win_for_testing.cc
@@ -8,8 +8,7 @@ #include "base/allocator/buildflags.h" #include "base/allocator/partition_allocator/partition_alloc_base/debug/alias.h" -#include "base/check.h" -#include "base/check_op.h" +#include "base/allocator/partition_allocator/partition_alloc_check.h" #include "base/process/memory.h" #include "build/build_config.h" @@ -156,7 +155,7 @@ // static void PlatformThreadForTesting::Join(PlatformThreadHandle thread_handle) { - DCHECK(thread_handle.platform_handle()); + PA_DCHECK(thread_handle.platform_handle()); DWORD thread_id = 0; thread_id = ::GetThreadId(thread_handle.platform_handle()); @@ -178,7 +177,7 @@ // Wait for the thread to exit. It should already have terminated but make // sure this assumption is valid. - CHECK_EQ(WAIT_OBJECT_0, + PA_CHECK(WAIT_OBJECT_0 == WaitForSingleObject(thread_handle.platform_handle(), INFINITE)); CloseHandle(thread_handle.platform_handle()); } @@ -187,7 +186,7 @@ bool PlatformThreadForTesting::Create(size_t stack_size, Delegate* delegate, PlatformThreadHandle* thread_handle) { - DCHECK(thread_handle); + PA_DCHECK(thread_handle); return CreateThreadInternal(stack_size, delegate, thread_handle); }
diff --git a/base/allocator/partition_allocator/partition_alloc_check.h b/base/allocator/partition_allocator/partition_alloc_check.h index 58ad5c39..c888f86 100644 --- a/base/allocator/partition_allocator/partition_alloc_check.h +++ b/base/allocator/partition_allocator/partition_alloc_check.h
@@ -9,9 +9,9 @@ #include "base/allocator/buildflags.h" #include "base/allocator/partition_allocator/page_allocator_constants.h" +#include "base/allocator/partition_allocator/partition_alloc_base/check.h" #include "base/allocator/partition_allocator/partition_alloc_base/debug/alias.h" #include "base/allocator/partition_allocator/partition_alloc_base/immediate_crash.h" -#include "base/check.h" #include "base/dcheck_is_on.h" #include "build/build_config.h" @@ -32,22 +32,22 @@ #if defined(OFFICIAL_BUILD) && defined(NDEBUG) // See base/check.h for implementation details. #define PA_CHECK(condition) \ - UNLIKELY(!(condition)) ? PA_IMMEDIATE_CRASH() : EAT_CHECK_STREAM_PARAMS() + UNLIKELY(!(condition)) ? PA_IMMEDIATE_CRASH() : PA_EAT_CHECK_STREAM_PARAMS() #else // PartitionAlloc uses async-signal-safe RawCheck() for error reporting. // Async-signal-safe functions are guaranteed to not allocate as otherwise they // could operate with inconsistent allocator state. #define PA_CHECK(condition) \ UNLIKELY(!(condition)) \ - ? ::logging::RawCheck( \ + ? ::partition_alloc::internal::logging::RawCheck( \ __FILE__ "(" PA_STRINGIFY(__LINE__) ") Check failed: " #condition) \ - : EAT_CHECK_STREAM_PARAMS() + : PA_EAT_CHECK_STREAM_PARAMS() #endif // defined(OFFICIAL_BUILD) && defined(NDEBUG) #if DCHECK_IS_ON() #define PA_DCHECK(condition) PA_CHECK(condition) #else -#define PA_DCHECK(condition) EAT_CHECK_STREAM_PARAMS(!(condition)) +#define PA_DCHECK(condition) PA_EAT_CHECK_STREAM_PARAMS(!(condition)) #endif // DCHECK_IS_ON() #define PA_PCHECK(condition) \ @@ -57,10 +57,17 @@ PA_IMMEDIATE_CRASH(); \ } +#if DCHECK_IS_ON() +#define PA_DPCHECK(condition) PA_PCHECK(condition) #else -#define PA_CHECK(condition) CHECK(condition) -#define PA_DCHECK(condition) DCHECK(condition) -#define PA_PCHECK(condition) PCHECK(condition) +#define PA_DPCHECK(condition) PA_EAT_CHECK_STREAM_PARAMS(!(condition)) +#endif // DCHECK_IS_ON() + +#else +#define PA_CHECK(condition) PA_BASE_CHECK(condition) +#define PA_DCHECK(condition) PA_BASE_DCHECK(condition) +#define PA_PCHECK(condition) PA_BASE_PCHECK(condition) +#define PA_DPCHECK(condition) PA_BASE_DPCHECK(condition) #endif // BUILDFLAG(USE_PARTITION_ALLOC_AS_MALLOC) // Expensive dchecks that run within *Scan. These checks are only enabled in @@ -74,7 +81,7 @@ #if PA_SCAN_DCHECK_IS_ON() #define PA_SCAN_DCHECK(expr) PA_DCHECK(expr) #else -#define PA_SCAN_DCHECK(expr) EAT_CHECK_STREAM_PARAMS(!(expr)) +#define PA_SCAN_DCHECK(expr) PA_EAT_CHECK_STREAM_PARAMS(!(expr)) #endif #if defined(PAGE_ALLOCATOR_CONSTANTS_ARE_CONSTEXPR)
diff --git a/base/allocator/partition_allocator/partition_alloc_notreached.h b/base/allocator/partition_allocator/partition_alloc_notreached.h index e04fe42..b745e958 100644 --- a/base/allocator/partition_allocator/partition_alloc_notreached.h +++ b/base/allocator/partition_allocator/partition_alloc_notreached.h
@@ -6,7 +6,6 @@ #define BASE_ALLOCATOR_PARTITION_ALLOCATOR_PARTITION_ALLOC_NOTREACHED_H_ #include "base/allocator/partition_allocator/partition_alloc_check.h" -#include "base/check.h" #include "base/dcheck_is_on.h" #include "base/logging_buildflags.h" @@ -16,10 +15,10 @@ // So PA_NOTREACHED() uses PA_DCHECK() instead of DCHECK(). #if BUILDFLAG(ENABLE_LOG_ERROR_NOT_REACHED) -#define PA_NOTREACHED() \ - true ? ::logging::RawError(__FILE__ \ - "(" PA_STRINGIFY(__LINE__) ") NOTREACHED() hit.") \ - : EAT_CHECK_STREAM_PARAMS() +#define PA_NOTREACHED() \ + true ? ::partition_alloc::internal::logging::RawError( \ + __FILE__ "(" PA_STRINGIFY(__LINE__) ") PA_NOTREACHED() hit.") \ + : PA_EAT_CHECK_STREAM_PARAMS() #elif BUILDFLAG(USE_PARTITION_ALLOC_AS_MALLOC) && defined(OFFICIAL_BUILD) && \ defined(NDEBUG) && DCHECK_IS_ON() @@ -37,11 +36,11 @@ // case Y: // ... // So define PA_NOTREACHED() by using async-signal-safe RawCheck(). -#define PA_NOTREACHED() \ - UNLIKELY(true) \ - ? ::logging::RawCheck(__FILE__ \ - "(" PA_STRINGIFY(__LINE__) ") NOTREACHED() hit.") \ - : EAT_CHECK_STREAM_PARAMS() +#define PA_NOTREACHED() \ + UNLIKELY(true) \ + ? ::partition_alloc::internal::logging::RawCheck( \ + __FILE__ "(" PA_STRINGIFY(__LINE__) ") PA_NOTREACHED() hit.") \ + : PA_EAT_CHECK_STREAM_PARAMS() #else
diff --git a/base/allocator/partition_allocator/partition_alloc_perftest.cc b/base/allocator/partition_allocator/partition_alloc_perftest.cc index f0ea1cf..b8b6d0a3 100644 --- a/base/allocator/partition_allocator/partition_alloc_perftest.cc +++ b/base/allocator/partition_allocator/partition_alloc_perftest.cc
@@ -193,7 +193,7 @@ do { auto* next = reinterpret_cast<MemoryAllocationPerfNode*>( allocator->Alloc(kAllocSize)); - CHECK_NE(next, nullptr); + PA_CHECK(next != nullptr); cur->SetNext(next); cur = next; timer.NextLap(); @@ -224,7 +224,7 @@ base::LapTimer timer(kWarmupRuns, kTimeLimit, kTimeCheckInterval); do { void* cur = allocator->Alloc(kAllocSize); - CHECK_NE(cur, nullptr); + PA_CHECK(cur != nullptr); allocator->Free(cur); timer.NextLap(); } while (!timer.HasTimeLimitExpired()); @@ -246,7 +246,7 @@ size_t size = kMultiBucketMinimumSize + (i * kMultiBucketIncrement); auto* next = reinterpret_cast<MemoryAllocationPerfNode*>(allocator->Alloc(size)); - CHECK_NE(next, nullptr); + PA_CHECK(next != nullptr); cur->SetNext(next); cur = next; allocated_memory += size; @@ -278,7 +278,7 @@ for (int i = 0; i < kMultiBucketRounds; i++) { void* cur = allocator->Alloc(kMultiBucketMinimumSize + (i * kMultiBucketIncrement)); - CHECK_NE(cur, nullptr); + PA_CHECK(cur != nullptr); elems.push_back(cur); } @@ -287,7 +287,7 @@ for (int i = 0; i < kMultiBucketRounds; i++) { void* cur = allocator->Alloc(kMultiBucketMinimumSize + (i * kMultiBucketIncrement)); - CHECK_NE(cur, nullptr); + PA_CHECK(cur != nullptr); allocator->Free(cur); } timer.NextLap(); @@ -306,7 +306,7 @@ base::LapTimer timer(kWarmupRuns, kTimeLimit, kTimeCheckInterval); do { void* cur = allocator->Alloc(kSize); - CHECK_NE(cur, nullptr); + PA_CHECK(cur != nullptr); allocator->Free(cur); timer.NextLap(); } while (!timer.HasTimeLimitExpired());
diff --git a/base/allocator/partition_allocator/partition_alloc_unittest.cc b/base/allocator/partition_allocator/partition_alloc_unittest.cc index e65dbc8..bb4f06b 100644 --- a/base/allocator/partition_allocator/partition_alloc_unittest.cc +++ b/base/allocator/partition_allocator/partition_alloc_unittest.cc
@@ -2831,7 +2831,7 @@ const size_t kSecondAllocPages = kHasLargePages ? 31 : 61; // Detect case (1) from above. - DCHECK_LT(kFirstAllocPages * SystemPageSize(), 1UL << kMaxBucketedOrder); + PA_DCHECK(kFirstAllocPages * SystemPageSize() < (1UL << kMaxBucketedOrder)); const size_t kDeltaPages = kFirstAllocPages - kSecondAllocPages; @@ -4289,7 +4289,7 @@ const size_t min_pool_size = PartitionAddressSpace::ConfigurablePoolMinSize(); for (size_t pool_size = max_pool_size; pool_size >= min_pool_size; pool_size /= 2) { - DCHECK(partition_alloc::internal::base::bits::IsPowerOfTwo(pool_size)); + PA_DCHECK(partition_alloc::internal::base::bits::IsPowerOfTwo(pool_size)); EXPECT_FALSE(IsConfigurablePoolAvailable()); uintptr_t pool_base = AllocPages( pool_size, pool_size, PageAccessibilityConfiguration::kInaccessible,
diff --git a/base/allocator/partition_allocator/partition_bucket.cc b/base/allocator/partition_allocator/partition_bucket.cc index 840d062..70d06a0 100644 --- a/base/allocator/partition_allocator/partition_bucket.cc +++ b/base/allocator/partition_allocator/partition_bucket.cc
@@ -31,7 +31,6 @@ #include "base/allocator/partition_allocator/reservation_offset_table.h" #include "base/allocator/partition_allocator/starscan/state_bitmap.h" #include "base/allocator/partition_allocator/tagging.h" -#include "base/check.h" #include "build/build_config.h" namespace partition_alloc::internal {
diff --git a/base/win/scoped_handle_unittest.cc b/base/win/scoped_handle_unittest.cc index 1b4ccbc..1b41733e 100644 --- a/base/win/scoped_handle_unittest.cc +++ b/base/win/scoped_handle_unittest.cc
@@ -105,7 +105,8 @@ FailureMessage("CloseHandle failed")); } -TEST_P(ScopedHandleDeathTest, HandleVerifierCloseTrackedHandle) { +// TODO(crbug.com/1328022): Flaky on Windows 7, deflake and re-enable. +TEST_P(ScopedHandleDeathTest, DISABLED_HandleVerifierCloseTrackedHandle) { // This test is only valid if hooks are enabled. if (!HooksEnabled()) return; @@ -130,7 +131,8 @@ FailureMessage("CloseHandleHook validation failure")); } -TEST_P(ScopedHandleDeathTest, HandleVerifierDoubleTracking) { +// TODO(crbug.com/1328022): Flaky on Windows 7, deflake and re-enable. +TEST_P(ScopedHandleDeathTest, DISABLED_HandleVerifierDoubleTracking) { HANDLE handle = ::CreateMutex(nullptr, false, nullptr); ASSERT_NE(HANDLE(nullptr), handle); @@ -139,7 +141,8 @@ ASSERT_DEATH({ base::win::CheckedScopedHandle handle_holder2(handle); }, ""); } -TEST_P(ScopedHandleDeathTest, HandleVerifierWrongOwner) { +// TODO(crbug.com/1328022): Flaky on Windows 7, deflake and re-enable. +TEST_P(ScopedHandleDeathTest, DISABLED_HandleVerifierWrongOwner) { HANDLE handle = ::CreateMutex(nullptr, false, nullptr); ASSERT_NE(HANDLE(nullptr), handle); @@ -154,7 +157,8 @@ handle_holder.Close(); } -TEST_P(ScopedHandleDeathTest, HandleVerifierUntrackedHandle) { +// TODO(crbug.com/1328022): Flaky on Windows 7, deflake and re-enable. +TEST_P(ScopedHandleDeathTest, DISABLED_HandleVerifierUntrackedHandle) { HANDLE handle = ::CreateMutex(nullptr, false, nullptr); ASSERT_NE(HANDLE(nullptr), handle);
diff --git a/build/toolchain/win/ml.py b/build/toolchain/win/ml.py deleted file mode 100755 index 6a1b6e57..0000000 --- a/build/toolchain/win/ml.py +++ /dev/null
@@ -1,290 +0,0 @@ -#!/usr/bin/env python -# 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. - -"""Wraps ml.exe or ml64.exe and postprocesses the output to be deterministic. -Sets timestamp in .obj file to 0, hence incompatible with link.exe /incremental. - -Use by prefixing the ml(64).exe invocation with this script: - python ml.py ml.exe [args...]""" - -import array -import collections -import struct -import subprocess -import sys - - -class Struct(object): - """A thin wrapper around the struct module that returns a namedtuple""" - def __init__(self, name, *args): - """Pass the name of the return type, and then an interleaved list of - format strings as used by the struct module and of field names.""" - self.fmt = '<' + ''.join(args[0::2]) - self.type = collections.namedtuple(name, args[1::2]) - - def pack_into(self, buffer, offset, data): - return struct.pack_into(self.fmt, buffer, offset, *data) - - def unpack_from(self, buffer, offset=0): - return self.type(*struct.unpack_from(self.fmt, buffer, offset)) - - def size(self): - return struct.calcsize(self.fmt) - - -def Subtract(nt, **kwargs): - """Subtract(nt, f=2) returns a new namedtuple with 2 subtracted from nt.f""" - return nt._replace(**{k: getattr(nt, k) - v for k, v in kwargs.items()}) - - -def MakeDeterministic(objdata): - # Takes data produced by ml(64).exe (without any special flags) and - # 1. Sets the timestamp to 0 - # 2. Strips the .debug$S section (which contains an unwanted absolute path) - - # This makes several assumptions about ml's output: - # - Section data is in the same order as the corresponding section headers: - # section headers preceding the .debug$S section header have their data - # preceding the .debug$S section data; likewise for section headers - # following the .debug$S section. - # - The .debug$S section contains only the absolute path to the obj file and - # nothing else, in particular there's only a single entry in the symbol - # table referring to the .debug$S section. - # - There are no COFF line number entries. - # - There's no IMAGE_SYM_CLASS_CLR_TOKEN symbol. - # These seem to hold in practice; if they stop holding this script needs to - # become smarter. - - objdata = array.array('b', objdata) # Writable, e.g. via struct.pack_into. - - # Read coff header. - COFFHEADER = Struct('COFFHEADER', - 'H', 'Machine', - 'H', 'NumberOfSections', - 'I', 'TimeDateStamp', - 'I', 'PointerToSymbolTable', - 'I', 'NumberOfSymbols', - - 'H', 'SizeOfOptionalHeader', - 'H', 'Characteristics') - coff_header = COFFHEADER.unpack_from(objdata) - assert coff_header.SizeOfOptionalHeader == 0 # Only set for binaries. - - # Read section headers following coff header. - SECTIONHEADER = Struct('SECTIONHEADER', - '8s', 'Name', - 'I', 'VirtualSize', - 'I', 'VirtualAddress', - - 'I', 'SizeOfRawData', - 'I', 'PointerToRawData', - 'I', 'PointerToRelocations', - 'I', 'PointerToLineNumbers', - - 'H', 'NumberOfRelocations', - 'H', 'NumberOfLineNumbers', - 'I', 'Characteristics') - section_headers = [] - debug_section_index = -1 - for i in range(0, coff_header.NumberOfSections): - section_header = SECTIONHEADER.unpack_from( - objdata, offset=COFFHEADER.size() + i * SECTIONHEADER.size()) - assert not section_header[0].startswith(b'/') # Support short names only. - section_headers.append(section_header) - - if section_header.Name == b'.debug$S': - assert debug_section_index == -1 - debug_section_index = i - assert debug_section_index != -1 - - data_start = COFFHEADER.size() + len(section_headers) * SECTIONHEADER.size() - - # Verify the .debug$S section looks like we expect. - assert section_headers[debug_section_index].Name == b'.debug$S' - assert section_headers[debug_section_index].VirtualSize == 0 - assert section_headers[debug_section_index].VirtualAddress == 0 - debug_size = section_headers[debug_section_index].SizeOfRawData - debug_offset = section_headers[debug_section_index].PointerToRawData - assert section_headers[debug_section_index].PointerToRelocations == 0 - assert section_headers[debug_section_index].PointerToLineNumbers == 0 - assert section_headers[debug_section_index].NumberOfRelocations == 0 - assert section_headers[debug_section_index].NumberOfLineNumbers == 0 - - # Make sure sections in front of .debug$S have their data preceding it. - for header in section_headers[:debug_section_index]: - assert header.PointerToRawData < debug_offset - assert header.PointerToRelocations < debug_offset - assert header.PointerToLineNumbers < debug_offset - - # Make sure sections after of .debug$S have their data following it. - for header in section_headers[debug_section_index + 1:]: - # Make sure the .debug$S data is at the very end of section data: - assert header.PointerToRawData > debug_offset - assert header.PointerToRelocations == 0 - assert header.PointerToLineNumbers == 0 - - # Make sure the first non-empty section's data starts right after the section - # headers. - for section_header in section_headers: - if section_header.PointerToRawData == 0: - assert section_header.PointerToRelocations == 0 - assert section_header.PointerToLineNumbers == 0 - continue - assert section_header.PointerToRawData == data_start - break - - # Make sure the symbol table (and hence, string table) appear after the last - # section: - assert (coff_header.PointerToSymbolTable >= - section_headers[-1].PointerToRawData + section_headers[-1].SizeOfRawData) - - # The symbol table contains a symbol for the no-longer-present .debug$S - # section. If we leave it there, lld-link will complain: - # - # lld-link: error: .debug$S should not refer to non-existent section 5 - # - # so we need to remove that symbol table entry as well. This shifts symbol - # entries around and we need to update symbol table indices in: - # - relocations - # - line number records (never present) - # - one aux symbol entry (IMAGE_SYM_CLASS_CLR_TOKEN; not present in ml output) - SYM = Struct('SYM', - '8s', 'Name', - 'I', 'Value', - 'h', 'SectionNumber', # Note: Signed! - 'H', 'Type', - - 'B', 'StorageClass', - 'B', 'NumberOfAuxSymbols') - i = 0 - debug_sym = -1 - while i < coff_header.NumberOfSymbols: - sym_offset = coff_header.PointerToSymbolTable + i * SYM.size() - sym = SYM.unpack_from(objdata, sym_offset) - - # 107 is IMAGE_SYM_CLASS_CLR_TOKEN, which has aux entry "CLR Token - # Definition", which contains a symbol index. Check it's never present. - assert sym.StorageClass != 107 - - # Note: sym.SectionNumber is 1-based, debug_section_index is 0-based. - if sym.SectionNumber - 1 == debug_section_index: - assert debug_sym == -1, 'more than one .debug$S symbol found' - debug_sym = i - # Make sure the .debug$S symbol looks like we expect. - # In particular, it should have exactly one aux symbol. - assert sym.Name == b'.debug$S' - assert sym.Value == 0 - assert sym.Type == 0 - assert sym.StorageClass == 3 - assert sym.NumberOfAuxSymbols == 1 - elif sym.SectionNumber > debug_section_index: - sym = Subtract(sym, SectionNumber=1) - SYM.pack_into(objdata, sym_offset, sym) - i += 1 + sym.NumberOfAuxSymbols - assert debug_sym != -1, '.debug$S symbol not found' - - # Note: Usually the .debug$S section is the last, but for files saying - # `includelib foo.lib`, like safe_terminate_process.asm in 32-bit builds, - # this isn't true: .drectve is after .debug$S. - - # Update symbol table indices in relocations. - # There are a few processor types that have one or two relocation types - # where SymbolTableIndex has a different meaning, but not for x86. - REL = Struct('REL', - 'I', 'VirtualAddress', - 'I', 'SymbolTableIndex', - 'H', 'Type') - for header in section_headers[0:debug_section_index]: - for j in range(0, header.NumberOfRelocations): - rel_offset = header.PointerToRelocations + j * REL.size() - rel = REL.unpack_from(objdata, rel_offset) - assert rel.SymbolTableIndex != debug_sym - if rel.SymbolTableIndex > debug_sym: - rel = Subtract(rel, SymbolTableIndex=2) - REL.pack_into(objdata, rel_offset, rel) - - # Update symbol table indices in line numbers -- just check they don't exist. - for header in section_headers: - assert header.NumberOfLineNumbers == 0 - - # Now that all indices are updated, remove the symbol table entry referring to - # .debug$S and its aux entry. - del objdata[coff_header.PointerToSymbolTable + debug_sym * SYM.size(): - coff_header.PointerToSymbolTable + (debug_sym + 2) * SYM.size()] - - # Now we know that it's safe to write out the input data, with just the - # timestamp overwritten to 0, the last section header cut out (and the - # offsets of all other section headers decremented by the size of that - # one section header), and the last section's data cut out. The symbol - # table offset needs to be reduced by one section header and the size of - # the missing section. - # (The COFF spec only requires on-disk sections to be aligned in image files, - # for obj files it's not required. If that wasn't the case, deleting slices - # if data would not generally be safe.) - - # Update section offsets and remove .debug$S section data. - for i in range(0, debug_section_index): - header = section_headers[i] - if header.SizeOfRawData: - header = Subtract(header, PointerToRawData=SECTIONHEADER.size()) - if header.NumberOfRelocations: - header = Subtract(header, PointerToRelocations=SECTIONHEADER.size()) - if header.NumberOfLineNumbers: - header = Subtract(header, PointerToLineNumbers=SECTIONHEADER.size()) - SECTIONHEADER.pack_into( - objdata, COFFHEADER.size() + i * SECTIONHEADER.size(), header) - for i in range(debug_section_index + 1, len(section_headers)): - header = section_headers[i] - shift = SECTIONHEADER.size() + debug_size - if header.SizeOfRawData: - header = Subtract(header, PointerToRawData=shift) - if header.NumberOfRelocations: - header = Subtract(header, PointerToRelocations=shift) - if header.NumberOfLineNumbers: - header = Subtract(header, PointerToLineNumbers=shift) - SECTIONHEADER.pack_into( - objdata, COFFHEADER.size() + i * SECTIONHEADER.size(), header) - - del objdata[debug_offset:debug_offset + debug_size] - - # Finally, remove .debug$S section header and update coff header. - coff_header = coff_header._replace(TimeDateStamp=0) - coff_header = Subtract(coff_header, - NumberOfSections=1, - PointerToSymbolTable=SECTIONHEADER.size() + debug_size, - NumberOfSymbols=2) - COFFHEADER.pack_into(objdata, 0, coff_header) - - del objdata[ - COFFHEADER.size() + debug_section_index * SECTIONHEADER.size(): - COFFHEADER.size() + (debug_section_index + 1) * SECTIONHEADER.size()] - - # All done! - if sys.version_info.major == 2: - return objdata.tostring() - else: - return objdata.tobytes() - - -def main(): - ml_result = subprocess.call(sys.argv[1:]) - if ml_result != 0: - return ml_result - - objfile = None - for i in range(1, len(sys.argv)): - if sys.argv[i].startswith('/Fo'): - objfile = sys.argv[i][len('/Fo'):] - assert objfile, 'failed to find ml output' - - with open(objfile, 'rb') as f: - objdata = f.read() - objdata = MakeDeterministic(objdata) - with open(objfile, 'wb') as f: - f.write(objdata) - - -if __name__ == '__main__': - sys.exit(main())
diff --git a/build/toolchain/win/toolchain.gni b/build/toolchain/win/toolchain.gni index e7fd6209..9cdcc6bf 100644 --- a/build/toolchain/win/toolchain.gni +++ b/build/toolchain/win/toolchain.gni
@@ -254,11 +254,12 @@ ml = "armasm64.exe" } } else { - # x86/x64 builds always use the MSVC assembler. + prefix = rebase_path("$clang_base_path/bin", root_build_dir) + ml = "$prefix/llvm-ml.exe" if (toolchain_args.current_cpu == "x64") { - ml = "ml64.exe" + ml += " --m64" } else { - ml = "ml.exe" + ml += " --m32" } } @@ -270,16 +271,6 @@ if (toolchain_args.current_cpu != "arm64") { ml += " /c" } - if (use_lld) { - # Wrap ml(64).exe with a script that makes its output deterministic. - # It's lld only because the script zaps obj Timestamp which - # link.exe /incremental looks at. - # TODO(https://crbug.com/762167): If we end up writing an llvm-ml64, - # make sure it has deterministic output (maybe with /Brepro or - # something) and remove this wrapper. - ml_py = rebase_path("//build/toolchain/win/ml.py", root_build_dir) - ml = "$python_path $ml_py $ml" - } } if (toolchain_args.current_cpu != "arm64" || toolchain_is_clang) { command = "$python_path $_tool_wrapper_path asm-wrapper $env $ml {{defines}} {{include_dirs}} {{asmflags}} {{source}}"
diff --git a/chrome/android/chrome_java_sources.gni b/chrome/android/chrome_java_sources.gni index ebf4a04..7629f1f 100644 --- a/chrome/android/chrome_java_sources.gni +++ b/chrome/android/chrome_java_sources.gni
@@ -712,7 +712,6 @@ "java/src/org/chromium/chrome/browser/init/NativeStartupBridge.java", "java/src/org/chromium/chrome/browser/init/ProcessInitializationHandler.java", "java/src/org/chromium/chrome/browser/init/SingleWindowKeyboardVisibilityDelegate.java", - "java/src/org/chromium/chrome/browser/init/StartupTabPreloader.java", "java/src/org/chromium/chrome/browser/installedapp/InstalledAppProviderFactory.java", "java/src/org/chromium/chrome/browser/instantapps/AuthenticatedProxyActivity.java", "java/src/org/chromium/chrome/browser/instantapps/InstantAppsBannerData.java",
diff --git a/chrome/android/chrome_test_java_sources.gni b/chrome/android/chrome_test_java_sources.gni index 1255160..b80d1f9 100644 --- a/chrome/android/chrome_test_java_sources.gni +++ b/chrome/android/chrome_test_java_sources.gni
@@ -165,7 +165,6 @@ "javatests/src/org/chromium/chrome/browser/customtabs/IncognitoCustomTabActivityTestRule.java", "javatests/src/org/chromium/chrome/browser/customtabs/TabReparentingTest.java", "javatests/src/org/chromium/chrome/browser/customtabs/TrustedCdnPublisherUrlTest.java", - "javatests/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabControllerTest.java", "javatests/src/org/chromium/chrome/browser/customtabs/content/TabObserverRegistrarTest.java", "javatests/src/org/chromium/chrome/browser/dependency_injection/ModuleOverridesRule.java", "javatests/src/org/chromium/chrome/browser/device_dialog/BluetoothChooserDialogTest.java", @@ -263,9 +262,6 @@ "javatests/src/org/chromium/chrome/browser/init/ChainedTasksTest.java", "javatests/src/org/chromium/chrome/browser/init/ChromeBrowserInitializerTest.java", "javatests/src/org/chromium/chrome/browser/init/FirstDrawDetectorTest.java", - "javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderCustomTabTest.java", - "javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderTest.java", - "javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderUnitTest.java", "javatests/src/org/chromium/chrome/browser/input/SelectPopupOtherContentViewTest.java", "javatests/src/org/chromium/chrome/browser/instantapps/InstantAppsHandlerTest.java", "javatests/src/org/chromium/chrome/browser/interstitials/LookalikeInterstitialTest.java",
diff --git a/chrome/android/expectations/lint-baseline.xml b/chrome/android/expectations/lint-baseline.xml index dfae2cf..2d71bed6 100644 --- a/chrome/android/expectations/lint-baseline.xml +++ b/chrome/android/expectations/lint-baseline.xml
@@ -7580,18 +7580,7 @@ column="85"/> </issue> - <issue - id="WrongConstant" - message="Must be one of: LoadDecisionReason.DISABLED_BY_INTENT, LoadDecisionReason.INCOGNITO, LoadDecisionReason.INTENT_IGNORED, LoadDecisionReason.NO_URL, LoadDecisionReason.NO_TAB_CREATOR, LoadDecisionReason.WRONG_TAB_CREATOR, LoadDecisionReason.DISABLED_BY_FEATURE, LoadDecisionReason.ALL_SATISFIED" - errorLine1=" getLoadDecisionReason(), LoadDecisionReason.NUM_ENTRIES);" - errorLine2=" ~~~~~~~~~~~"> - <location - file="../../chrome/android/java/src/org/chromium/chrome/browser/init/StartupTabPreloader.java" - line="356" - column="65"/> - </issue> - - <issue + <issue id="WrongConstant" message="Must be one of: ApiCall.ADD_WEB_MESSAGE_LISTENER, ApiCall.CLEAR_PROXY_OVERRIDE, ApiCall.GET_PROXY_CONTROLLER, ApiCall.GET_SAFE_BROWSING_PRIVACY_POLICY_URL, ApiCall.GET_SERVICE_WORKER_CONTROLLER, ApiCall.GET_SERVICE_WORKER_WEB_SETTINGS, ApiCall.GET_TRACING_CONTROLLER, ApiCall.GET_WEBCHROME_CLIENT, ApiCall.GET_WEBVIEW_CLIENT, ApiCall.GET_WEBVIEW_RENDERER, ApiCall.GET_WEBVIEW_RENDERER_CLIENT, ApiCall.INIT_SAFE_BROWSING, ApiCall.INSERT_VISUAL_STATE_CALLBACK, ApiCall.IS_MULTI_PROCESS_ENABLED, ApiCall.JS_REPLY_POST_MESSAGE, ApiCall.POST_MESSAGE_TO_MAIN_FRAME, ApiCall.REMOVE_WEB_MESSAGE_LISTENER, ApiCall.SERVICE_WORKER_SETTINGS_GET_ALLOW_CONTENT_ACCESS, ApiCall.SERVICE_WORKER_SETTINGS_GET_ALLOW_FILE_ACCESS, ApiCall.SERVICE_WORKER_SETTINGS_GET_BLOCK_NETWORK_LOADS, ApiCall.SERVICE_WORKER_SETTINGS_GET_CACHE_MODE, ApiCall.SERVICE_WORKER_SETTINGS_SET_ALLOW_CONTENT_ACCESS, ApiCall.SERVICE_WORKER_SETTINGS_SET_ALLOW_FILE_ACCESS, ApiCall.SERVICE_WORKER_SETTINGS_SET_BLOCK_NETWORK_LOADS, ApiCall.SERVICE_WORKER_SETTINGS_SET_CACHE_MODE, ApiCall.SET_PROXY_OVERRIDE, ApiCall.SET_SAFE_BROWSING_ALLOWLIST_DEPRECATED_NAME, ApiCall.SET_SERVICE_WORKER_CLIENT, ApiCall.SET_WEBVIEW_RENDERER_CLIENT, ApiCall.TRACING_CONTROLLER_IS_TRACING, ApiCall.TRACING_CONTROLLER_START, ApiCall.TRACING_CONTROLLER_STOP, ApiCall.WEB_MESSAGE_GET_DATA, ApiCall.WEB_MESSAGE_GET_PORTS, ApiCall.WEB_MESSAGE_PORT_CLOSE, ApiCall.WEB_MESSAGE_PORT_POST_MESSAGE, ApiCall.WEB_MESSAGE_PORT_SET_CALLBACK, ApiCall.WEB_MESSAGE_PORT_SET_CALLBACK_WITH_HANDLER, ApiCall.WEB_RESOURCE_REQUEST_IS_REDIRECT, ApiCall.WEB_SETTINGS_GET_DISABLED_ACTION_MODE_MENU_ITEMS, ApiCall.WEB_SETTINGS_GET_FORCE_DARK, ApiCall.WEB_SETTINGS_GET_FORCE_DARK_BEHAVIOR, ApiCall.WEB_SETTINGS_GET_OFFSCREEN_PRE_RASTER, ApiCall.WEB_SETTINGS_GET_SAFE_BROWSING_ENABLED, ApiCall.WEB_SETTINGS_GET_WILL_SUPPRESS_ERROR_PAGE, ApiCall.WEB_SETTINGS_SET_DISABLED_ACTION_MODE_MENU_ITEMS, ApiCall.WEB_SETTINGS_SET_FORCE_DARK, ApiCall.WEB_SETTINGS_SET_FORCE_DARK_BEHAVIOR, ApiCall.WEB_SETTINGS_SET_OFFSCREEN_PRE_RASTER, ApiCall.WEB_SETTINGS_SET_SAFE_BROWSING_ENABLED, ApiCall.WEB_SETTINGS_SET_WILL_SUPPRESS_ERROR_PAGE, ApiCall.WEBVIEW_RENDERER_TERMINATE, ApiCall.ADD_DOCUMENT_START_SCRIPT, ApiCall.REMOVE_DOCUMENT_START_SCRIPT, ApiCall.SET_SAFE_BROWSING_ALLOWLIST, ApiCall.SET_PROXY_OVERRIDE_REVERSE_BYPASS" errorLine1=" "Android.WebView.AndroidX.ApiCall", apiCall, ApiCall.COUNT);"
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java b/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java index c5742ba..ed86565 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java
@@ -1934,14 +1934,12 @@ }; } return Pair.create( - new ChromeTabCreator(this, getWindowAndroid(), getStartupTabPreloader(), - this::getTabDelegateFactory, false, overviewNTPCreator, - AsyncTabParamsManagerSingleton.getInstance(), getTabModelSelectorSupplier(), - getCompositorViewHolderSupplier()), - new ChromeTabCreator(this, getWindowAndroid(), getStartupTabPreloader(), - this::getTabDelegateFactory, true, overviewNTPCreator, - AsyncTabParamsManagerSingleton.getInstance(), getTabModelSelectorSupplier(), - getCompositorViewHolderSupplier())); + new ChromeTabCreator(this, getWindowAndroid(), this::getTabDelegateFactory, false, + overviewNTPCreator, AsyncTabParamsManagerSingleton.getInstance(), + getTabModelSelectorSupplier(), getCompositorViewHolderSupplier()), + new ChromeTabCreator(this, getWindowAndroid(), this::getTabDelegateFactory, true, + overviewNTPCreator, AsyncTabParamsManagerSingleton.getInstance(), + getTabModelSelectorSupplier(), getCompositorViewHolderSupplier())); } @Override
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/DEPS b/chrome/android/java/src/org/chromium/chrome/browser/DEPS index c7655683..d1dac274 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/DEPS +++ b/chrome/android/java/src/org/chromium/chrome/browser/DEPS
@@ -102,9 +102,6 @@ "IncognitoNotificationServiceImpl\.java": [ "+chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java" ], - "StartupTabPreloader\.java": [ - "+chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java" - ], "MultiInstanceChromeTabbedActivity\.java": [ "+chrome/android/java/src/org/chromium/chrome/browser/ChromeTabbedActivity.java" ],
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java b/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java index 16bb332..5dd38e4 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/app/ChromeActivity.java
@@ -123,7 +123,6 @@ import org.chromium.chrome.browser.history.HistoryManagerUtils; import org.chromium.chrome.browser.init.AsyncInitializationActivity; import org.chromium.chrome.browser.init.ProcessInitializationHandler; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.keyboard_accessory.ManualFillingComponent; import org.chromium.chrome.browser.keyboard_accessory.ManualFillingComponentFactory; import org.chromium.chrome.browser.keyboard_accessory.ManualFillingComponentSupplier; @@ -381,9 +380,6 @@ @Nullable private BottomContainer mBottomContainer; - @Nullable - private StartupTabPreloader mStartupTabPreloader; - private LaunchCauseMetrics mLaunchCauseMetrics; private GSAAccountChangeListener mGSAAccountChangeListener; @@ -839,19 +835,6 @@ } /** - * @return The {@link StartupTabPreloader} associated with this ChromeActivity. If there isn't - * one it creates it. - */ - protected StartupTabPreloader getStartupTabPreloader() { - if (mStartupTabPreloader == null) { - mStartupTabPreloader = new StartupTabPreloader(this::getIntent, - getLifecycleDispatcher(), getWindowAndroid(), this, mIntentHandler, - getActivityTabStartupMetricsTracker()); - } - return mStartupTabPreloader; - } - - /** * @return The {@link TabModelOrchestrator} owned by this {@link ChromeActivity}. */ protected abstract TabModelOrchestrator createTabModelOrchestrator();
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 d7f9193..470cef6 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
@@ -90,7 +90,6 @@ add(ChromeFeatureList.EARLY_LIBRARY_LOAD); add(ChromeFeatureList.ELASTIC_OVERSCROLL); add(ChromeFeatureList.ELIDE_PRIORITIZATION_OF_PRE_NATIVE_BOOTSTRAP_TASKS); - add(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP); add(ChromeFeatureList.FEED_LOADING_PLACEHOLDER); add(ChromeFeatureList .GIVE_JAVA_UI_THREAD_DEFAULT_TASK_TRAITS_USER_BLOCKING_PRIORITY);
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java index 3aed83a..3d62f84dc 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/BaseCustomTabActivity.java
@@ -184,12 +184,11 @@ BaseCustomTabActivityModule baseCustomTabsModule = overridenBaseCustomTabFactory != null ? overridenBaseCustomTabFactory.create(mIntentDataProvider, - getStartupTabPreloader(), mNightModeStateController, - intentIgnoringCriterion, getTopUiThemeColorProvider(), - new DefaultBrowserProviderImpl()) - : new BaseCustomTabActivityModule(mIntentDataProvider, getStartupTabPreloader(), mNightModeStateController, intentIgnoringCriterion, - getTopUiThemeColorProvider(), new DefaultBrowserProviderImpl()); + getTopUiThemeColorProvider(), new DefaultBrowserProviderImpl()) + : new BaseCustomTabActivityModule(mIntentDataProvider, mNightModeStateController, + intentIgnoringCriterion, getTopUiThemeColorProvider(), + new DefaultBrowserProviderImpl()); BaseCustomTabActivityComponent component = ChromeApplicationImpl.getComponent().createBaseCustomTabActivityComponent( commonsModule, baseCustomTabsModule);
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabController.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabController.java index bfa7245..5887ede 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabController.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabController.java
@@ -16,7 +16,6 @@ import androidx.annotation.Nullable; import androidx.appcompat.app.AppCompatActivity; import androidx.browser.customtabs.CustomTabsSessionToken; -import androidx.browser.trusted.sharing.ShareTarget; import org.chromium.base.metrics.RecordHistogram; import org.chromium.base.supplier.Supplier; @@ -29,7 +28,6 @@ import org.chromium.chrome.browser.app.tab_activity_glue.ReparentingDelegateFactory; import org.chromium.chrome.browser.app.tabmodel.TabModelOrchestrator; import org.chromium.chrome.browser.browserservices.intents.BrowserServicesIntentDataProvider; -import org.chromium.chrome.browser.browserservices.intents.WebApkExtras; import org.chromium.chrome.browser.compositor.CompositorViewHolder; import org.chromium.chrome.browser.customtabs.CustomTabDelegateFactory; import org.chromium.chrome.browser.customtabs.CustomTabIncognitoManager; @@ -42,7 +40,6 @@ import org.chromium.chrome.browser.customtabs.PageLoadMetricsObserver; import org.chromium.chrome.browser.customtabs.ReparentingTaskProvider; import org.chromium.chrome.browser.dependency_injection.ActivityScope; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.lifecycle.ActivityLifecycleDispatcher; import org.chromium.chrome.browser.lifecycle.InflationObserver; import org.chromium.chrome.browser.profiles.Profile; @@ -51,7 +48,6 @@ import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.browser.tab.TabAssociatedApp; import org.chromium.chrome.browser.tab.TabCreationState; -import org.chromium.chrome.browser.tab.TabLaunchType; import org.chromium.chrome.browser.tab.TabObserver; import org.chromium.chrome.browser.tabmodel.AsyncTabParams; import org.chromium.chrome.browser.tabmodel.AsyncTabParamsManager; @@ -61,10 +57,7 @@ import org.chromium.chrome.browser.tabmodel.TabModelSelectorBase; import org.chromium.chrome.browser.tabmodel.TabReparentingParams; import org.chromium.chrome.browser.translate.TranslateBridge; -import org.chromium.content_public.browser.LoadUrlParams; import org.chromium.content_public.browser.WebContents; -import org.chromium.content_public.common.Referrer; -import org.chromium.network.mojom.ReferrerPolicy; import org.chromium.ui.base.ActivityWindowAndroid; import java.lang.annotation.Retention; @@ -107,7 +100,6 @@ private final CustomTabNavigationEventObserver mTabNavigationEventObserver; private final ActivityTabProvider mActivityTabProvider; private final CustomTabActivityTabProvider mTabProvider; - private final StartupTabPreloader mStartupTabPreloader; private final ReparentingTaskProvider mReparentingTaskProvider; private final Lazy<CustomTabIncognitoManager> mCustomTabIncognitoManager; private final Lazy<AsyncTabParamsManager> mAsyncTabParamsManager; @@ -129,7 +121,7 @@ CustomTabTabPersistencePolicy persistencePolicy, CustomTabActivityTabFactory tabFactory, Lazy<CustomTabObserver> customTabObserver, WebContentsFactory webContentsFactory, CustomTabNavigationEventObserver tabNavigationEventObserver, - CustomTabActivityTabProvider tabProvider, StartupTabPreloader startupTabPreloader, + CustomTabActivityTabProvider tabProvider, ReparentingTaskProvider reparentingTaskProvider, Lazy<CustomTabIncognitoManager> customTabIncognitoManager, Lazy<AsyncTabParamsManager> asyncTabParamsManager, @@ -149,7 +141,6 @@ mTabNavigationEventObserver = tabNavigationEventObserver; mActivityTabProvider = activityTabProvider; mTabProvider = tabProvider; - mStartupTabPreloader = startupTabPreloader; mReparentingTaskProvider = reparentingTaskProvider; mCustomTabIncognitoManager = customTabIncognitoManager; mAsyncTabParamsManager = asyncTabParamsManager; @@ -275,51 +266,6 @@ } } - /** - * @return A tab if mStartupTabPreloader contains a tab matching the intent. - */ - private Tab maybeTakeTabFromStartupTabPreloader() { - // Don't overwrite any pre-existing tab. - if (mTabProvider.getTab() != null) return null; - - if (checkIsLikelyPostNavigation()) { - // The navigation is likely a POST. This does not match StartupTabPreloader's GET - // navigation. - return null; - } - - LoadUrlParams loadUrlParams = new LoadUrlParams(mIntentDataProvider.getUrlToLoad()); - String referrer = IntentHandler.getReferrerUrlIncludingExtraHeaders(mIntent); - if (!TextUtils.isEmpty(referrer)) { - loadUrlParams.setReferrer(new Referrer(referrer, ReferrerPolicy.DEFAULT)); - } - - Tab tab = mStartupTabPreloader.takeTabIfMatchingOrDestroy( - loadUrlParams, TabLaunchType.FROM_EXTERNAL_APP); - if (tab == null) return null; - - TabAssociatedApp.from(tab).setAppId(mConnection.getClientPackageNameForSession(mSession)); - initializeTab(tab); - return tab; - } - - /** - * Checks if the launch intent is likely a POST navigation (likely because we don't do a POST - * navigation if the POST target is outside of the TWA/WebAPK scope.) - */ - private boolean checkIsLikelyPostNavigation() { - if (mIntentDataProvider.getShareData() == null) return false; - - WebApkExtras webApkExtras = mIntentDataProvider.getWebApkExtras(); - if (webApkExtras != null && webApkExtras.shareTarget != null - && webApkExtras.shareTarget.isShareMethodPost()) { - return true; - } - - ShareTarget shareTarget = mIntentDataProvider.getShareTarget(); - return shareTarget != null && ShareTarget.METHOD_POST.equals(shareTarget.method); - } - // Creates the tab on native init, if it hasn't been created yet, and does all the additional // initialization steps necessary at this stage. private void finalizeCreatingTab(TabModelOrchestrator tabModelOrchestrator, TabModel tabModel) { @@ -337,15 +283,7 @@ } if (tab == null) { - // No tab was restored or created early, check if we preloaded a tab. - tab = maybeTakeTabFromStartupTabPreloader(); - if (tab != null) mode = TabCreationMode.FROM_STARTUP_TAB_PRELOADER; - } else { - mStartupTabPreloader.onDestroy(); - } - - if (tab == null) { - // No tab was restored, preloaded or created early, creating a new tab. + // No tab was restored or created early, creating a new tab. tab = createTab(); mode = TabCreationMode.DEFAULT; }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabFactory.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabFactory.java index 37877ee..d2b1acb 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabFactory.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabFactory.java
@@ -22,7 +22,6 @@ import org.chromium.chrome.browser.customtabs.CustomTabDelegateFactory; import org.chromium.chrome.browser.customtabs.CustomTabTabPersistencePolicy; import org.chromium.chrome.browser.dependency_injection.ActivityScope; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.browser.tab.TabBuilder; import org.chromium.chrome.browser.tab.TabDelegateFactory; @@ -56,9 +55,6 @@ private final Supplier<TabModelSelector> mTabModelSelectorSupplier; private final Supplier<CompositorViewHolder> mCompositorViewHolderSupplier; - @Nullable - private final StartupTabPreloader mStartupTabPreloader; - private final Lazy<AsyncTabParamsManager> mAsyncTabParamsManager; @Nullable @@ -71,7 +67,6 @@ Lazy<ActivityWindowAndroid> activityWindowAndroid, Lazy<CustomTabDelegateFactory> customTabDelegateFactory, BrowserServicesIntentDataProvider intentDataProvider, - @Nullable StartupTabPreloader startupTabPreloader, Lazy<AsyncTabParamsManager> asyncTabParamsManager, TabCreatorManager tabCreatorManager, Supplier<TabModelSelector> tabModelSelectorSupplier, Supplier<CompositorViewHolder> compositorViewHolderSupplier) { @@ -81,7 +76,6 @@ mActivityWindowAndroid = activityWindowAndroid; mCustomTabDelegateFactory = customTabDelegateFactory; mIntentDataProvider = intentDataProvider; - mStartupTabPreloader = startupTabPreloader; mAsyncTabParamsManager = asyncTabParamsManager; mTabCreatorManager = tabCreatorManager; mTabModelSelectorSupplier = tabModelSelectorSupplier; @@ -131,7 +125,7 @@ } private ChromeTabCreator createTabCreator(boolean incognito) { - return new ChromeTabCreator(mActivity, mActivityWindowAndroid.get(), mStartupTabPreloader, + return new ChromeTabCreator(mActivity, mActivityWindowAndroid.get(), mCustomTabDelegateFactory::get, incognito, null, AsyncTabParamsManagerSingleton.getInstance(), mTabModelSelectorSupplier, mCompositorViewHolderSupplier);
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/DefaultCustomTabIntentHandlingStrategy.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/DefaultCustomTabIntentHandlingStrategy.java index ce3de2fa..5036a5d 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/DefaultCustomTabIntentHandlingStrategy.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/DefaultCustomTabIntentHandlingStrategy.java
@@ -50,8 +50,7 @@ public void handleInitialIntent(BrowserServicesIntentDataProvider intentDataProvider) { @TabCreationMode int initialTabCreationMode = mTabProvider.getInitialTabCreationMode(); - if (initialTabCreationMode == TabCreationMode.HIDDEN - || initialTabCreationMode == TabCreationMode.FROM_STARTUP_TAB_PRELOADER) { + if (initialTabCreationMode == TabCreationMode.HIDDEN) { handleInitialLoadForHiddenTab(initialTabCreationMode, intentDataProvider); } else { LoadUrlParams params = new LoadUrlParams(intentDataProvider.getUrlToLoad()); @@ -100,17 +99,11 @@ // No actual load to do if the hidden tab already has the exact correct url. String speculatedUrl = mTabProvider.getSpeculatedUrl(); - if (TextUtils.equals(speculatedUrl, url) - || initialTabCreationMode == TabCreationMode.FROM_STARTUP_TAB_PRELOADER) { - // In the TabCreationMode.FROM_STARTUP_TAB_PRELOADER case: - // - CustomActivityTabProvider#getSpeculatedUrl() is not set. - // - The tab creation mode is only set in CustomTabActivityTabController if the URL - // being loaded is the one we want. - + if (TextUtils.equals(speculatedUrl, url)) { if (tab.isLoading()) { // CustomTabObserver and CustomTabActivityNavigationObserver are attached // as observers in CustomTabActivityTabController, not when the navigation is - // initiated in HiddenTabHolder or StartupTabPreloader. + // initiated in HiddenTabHolder. mCustomTabObserver.get().onPageLoadStarted(tab, gurl); mNavigationEventObserver.onPageLoadStarted(tab, gurl); }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/TabCreationMode.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/TabCreationMode.java index bf904fe..9f94f12 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/TabCreationMode.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/content/TabCreationMode.java
@@ -7,7 +7,6 @@ import androidx.annotation.IntDef; import org.chromium.chrome.browser.customtabs.CustomTabsConnection; -import org.chromium.chrome.browser.init.StartupTabPreloader; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; @@ -16,8 +15,7 @@ * Specifies the way the initial Tab in a Custom Tab activity was created. */ @IntDef({TabCreationMode.NONE, TabCreationMode.DEFAULT, TabCreationMode.EARLY, - TabCreationMode.RESTORED, TabCreationMode.HIDDEN, - TabCreationMode.FROM_STARTUP_TAB_PRELOADER}) + TabCreationMode.RESTORED, TabCreationMode.HIDDEN}) @Retention(RetentionPolicy.SOURCE) public @interface TabCreationMode { /** The tab has not been created yet */ @@ -39,7 +37,4 @@ * A hidden tab that was created preemptively via {@link CustomTabsConnection#mayLaunchUrl}. */ int HIDDEN = 4; - - /** Opened speculatively by the {@link StartupTabPreloader}.. */ - int FROM_STARTUP_TAB_PRELOADER = 5; }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/dependency_injection/BaseCustomTabActivityModule.java b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/dependency_injection/BaseCustomTabActivityModule.java index 1d48dd50..7e204ce 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/customtabs/dependency_injection/BaseCustomTabActivityModule.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/customtabs/dependency_injection/BaseCustomTabActivityModule.java
@@ -21,7 +21,6 @@ import org.chromium.chrome.browser.customtabs.content.CustomTabIntentHandlingStrategy; import org.chromium.chrome.browser.customtabs.content.DefaultCustomTabIntentHandlingStrategy; import org.chromium.chrome.browser.flags.ActivityType; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.tabmodel.IncognitoTabHostRegistry; import org.chromium.chrome.browser.theme.TopUiThemeColorProvider; import org.chromium.chrome.browser.webapps.WebApkPostShareTargetNavigator; @@ -37,7 +36,6 @@ @Module public class BaseCustomTabActivityModule { private final BrowserServicesIntentDataProvider mIntentDataProvider; - private final StartupTabPreloader mStartupTabPreloader; private final @ActivityType int mActivityType; private final CustomTabNightModeStateController mNightModeController; private final IntentIgnoringCriterion mIntentIgnoringCriterion; @@ -46,13 +44,11 @@ .DefaultBrowserProvider mDefaultBrowserProvider; public BaseCustomTabActivityModule(BrowserServicesIntentDataProvider intentDataProvider, - StartupTabPreloader startupTabPreloader, CustomTabNightModeStateController nightModeController, IntentIgnoringCriterion intentIgnoringCriterion, TopUiThemeColorProvider topUiThemeColorProvider, CustomTabActivityNavigationController.DefaultBrowserProvider defaultBrowserProvider) { mIntentDataProvider = intentDataProvider; - mStartupTabPreloader = startupTabPreloader; mActivityType = intentDataProvider.getActivityType(); mNightModeController = nightModeController; mIntentIgnoringCriterion = intentIgnoringCriterion; @@ -76,11 +72,6 @@ } @Provides - public StartupTabPreloader provideStartupTabPreloader() { - return mStartupTabPreloader; - } - - @Provides public Verifier provideVerifier(Lazy<WebApkVerifier> webApkVerifier, Lazy<AddToHomescreenVerifier> addToHomescreenVerifier, Lazy<TwaVerifier> twaVerifier, Lazy<EmptyVerifier> emptyVerifier) { @@ -142,7 +133,6 @@ public interface Factory { BaseCustomTabActivityModule create(BrowserServicesIntentDataProvider intentDataProvider, - StartupTabPreloader startupTabPreloader, CustomTabNightModeStateController nightModeController, IntentIgnoringCriterion intentIgnoringCriterion, TopUiThemeColorProvider topUiThemeColorProvider,
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/init/StartupTabPreloader.java b/chrome/android/java/src/org/chromium/chrome/browser/init/StartupTabPreloader.java deleted file mode 100644 index 6dccc7e..0000000 --- a/chrome/android/java/src/org/chromium/chrome/browser/init/StartupTabPreloader.java +++ /dev/null
@@ -1,492 +0,0 @@ -// Copyright 2019 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.chrome.browser.init; - -import android.content.Intent; -import android.os.SystemClock; -import android.text.TextUtils; - -import androidx.annotation.IntDef; -import androidx.annotation.VisibleForTesting; - -import org.chromium.base.IntentUtils; -import org.chromium.base.TraceEvent; -import org.chromium.base.metrics.RecordHistogram; -import org.chromium.base.supplier.Supplier; -import org.chromium.chrome.browser.ChromeTabbedActivity; -import org.chromium.chrome.browser.IntentHandler; -import org.chromium.chrome.browser.WebContentsFactory; -import org.chromium.chrome.browser.flags.ChromeFeatureList; -import org.chromium.chrome.browser.lifecycle.ActivityLifecycleDispatcher; -import org.chromium.chrome.browser.lifecycle.DestroyObserver; -import org.chromium.chrome.browser.metrics.ActivityTabStartupMetricsTracker; -import org.chromium.chrome.browser.profiles.Profile; -import org.chromium.chrome.browser.profiles.ProfileManager; -import org.chromium.chrome.browser.tab.EmptyTabObserver; -import org.chromium.chrome.browser.tab.Tab; -import org.chromium.chrome.browser.tab.TabBuilder; -import org.chromium.chrome.browser.tab.TabLaunchType; -import org.chromium.chrome.browser.tabmodel.ChromeTabCreator; -import org.chromium.chrome.browser.tabmodel.TabCreator; -import org.chromium.chrome.browser.tabmodel.TabCreatorManager; -import org.chromium.components.url_formatter.UrlFormatter; -import org.chromium.content_public.browser.LoadUrlParams; -import org.chromium.content_public.browser.WebContents; -import org.chromium.content_public.common.Referrer; -import org.chromium.network.mojom.ReferrerPolicy; -import org.chromium.ui.base.WindowAndroid; -import org.chromium.url.GURL; - -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; - -/** - * This class attempts to preload the tab if the url is known from the intent when the profile - * is created. This is done to improve startup latency. - */ -public class StartupTabPreloader implements ProfileManager.Observer, DestroyObserver, - ActivityTabStartupMetricsTracker.Observer { - public static final String EXTRA_DISABLE_STARTUP_TAB_PRELOADER = - "org.chromium.chrome.browser.init.DISABLE_STARTUP_TAB_PRELOADER"; - private static boolean sFailNextTabMatchForTesting; - - // These values are persisted in histograms. Please do not renumber. Append only. - @VisibleForTesting - @IntDef({LoadDecisionReason.DISABLED_BY_INTENT, LoadDecisionReason.INCOGNITO, - LoadDecisionReason.INTENT_IGNORED, LoadDecisionReason.NO_URL, - LoadDecisionReason.NO_TAB_CREATOR, LoadDecisionReason.WRONG_TAB_CREATOR, - LoadDecisionReason.DISABLED_BY_FEATURE, LoadDecisionReason.ALL_SATISFIED}) - @Retention(RetentionPolicy.SOURCE) - @interface LoadDecisionReason { - int DISABLED_BY_INTENT = 0; - int INCOGNITO = 1; - int INTENT_IGNORED = 2; - int NO_URL = 3; - int NO_TAB_CREATOR = 4; - int WRONG_TAB_CREATOR = 5; - int DISABLED_BY_FEATURE = 6; - int ALL_SATISFIED = 7; - - int NUM_ENTRIES = 8; - } - - private final Supplier<Intent> mIntentSupplier; - private final ActivityLifecycleDispatcher mActivityLifecycleDispatcher; - private final WindowAndroid mWindowAndroid; - private final TabCreatorManager mTabCreatorManager; - private final IntentHandler mIntentHandler; - private LoadUrlParams mLoadUrlParams; - private Tab mTab; - private StartupTabObserver mObserver; - private ActivityTabStartupMetricsTracker mStartupMetricsTracker; - - // The time at which the tab preload decision was made. Recorded only for non-incognito - // startups. - private long mLoadDecisionMs; - // Records whether a preload was triggered. - boolean mTriggerPreload; - // Records the reason for the last preload decision. - @LoadDecisionReason - int mLoadDecisionReason; - // Records whether a preloaded tab matched. - boolean mTabMatches; - // Records whether we have already recorded the histogram for the duration between the load - // decision and the match decision; this histogram should be recorded only on the first match - // decision. - private boolean mRecordedLoadDecisionToMatchDecisionHistogram; - - // Whether a tab preload was prevented only by the ElideTabPreloadAtStartup feature. - private boolean mPreloadPreventedOnlyByFeature; - // The params that would have been used for the preload if not prevented by the feature. - // NOTE: We explicitly track only the params that are necessary for comparison of tab matching - // to avoid calling IntentHandler#createLoadUrlParamsForIntent(). The latter is undesirable - // because it is destructive to the intent metadata, which is problematic in the case where the - // LoadUrlParams are not intended for usage (as they're not here). - private String mUrlForPreloadPreventedOnlyByFeature; - private String mReferrerForPreloadPreventedOnlyByFeature; - // Whether the tab preload that was prevented only by the feature would have matched. - private boolean mPreloadPreventedOnlyByFeatureWouldHaveMatched; - - // The time at which the first navigation start occurred. - private long mFirstNavigationStartMs; - - public static void failNextTabMatchForTesting() { - sFailNextTabMatchForTesting = true; - } - - public StartupTabPreloader(Supplier<Intent> intentSupplier, - ActivityLifecycleDispatcher activityLifecycleDispatcher, WindowAndroid windowAndroid, - TabCreatorManager tabCreatorManager, IntentHandler intentHandler, - ActivityTabStartupMetricsTracker startupMetricsTracker) { - mIntentSupplier = intentSupplier; - mActivityLifecycleDispatcher = activityLifecycleDispatcher; - mWindowAndroid = windowAndroid; - mTabCreatorManager = tabCreatorManager; - mIntentHandler = intentHandler; - mStartupMetricsTracker = startupMetricsTracker; - - mActivityLifecycleDispatcher.register(this); - ProfileManager.addObserver(this); - ActivityTabStartupMetricsTracker.addObserver(this); - } - - // Returns true if a startup tab preload either (a) was triggered or (b) was prevented - // from triggering only by the ElideTabPreloadAtStartup Feature. - private boolean preloadWasViable() { - return mTriggerPreload || mPreloadPreventedOnlyByFeature; - } - - // Returns true if a match of a preloaded tab either (a) occurred or (b) was prevented from - // occurring only by the ElideTabPreloadAtStartup Feature. - private boolean tabMatchWasViable() { - return mTabMatches || mPreloadPreventedOnlyByFeatureWouldHaveMatched; - } - - @Override - public void onDestroy() { - if (mTab != null) mTab.destroy(); - mTab = null; - - ProfileManager.removeObserver(this); - ActivityTabStartupMetricsTracker.removeObserver(this); - mActivityLifecycleDispatcher.unregister(this); - } - - @Override - public void onFirstNavigationStart() { - mFirstNavigationStartMs = SystemClock.uptimeMillis(); - } - - @Override - public void onFirstVisibleContent() { - recordDurationFromLoadDecisionIntoPostTabMatchHistogram( - "Android.StartupTabPreloader.LoadDecisionToFirstVisibleContent"); - } - - @Override - public void onFirstNavigationCommit() { - recordDurationFromLoadDecisionIntoPostTabMatchHistogram( - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationCommit"); - - // We record the metric for navigation start here as well, as we want that metric to be - // recorded only for navigations that result in the first navigation commit startup metric - // being recorded. - assert mFirstNavigationStartMs > 0; - recordDurationFromLoadDecisionToEventTimeIntoPreTabMatchHistogram( - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationStart", - mFirstNavigationStartMs); - } - - @Override - public void onFirstContentfulPaint() { - recordDurationFromLoadDecisionIntoPostTabMatchHistogram( - "Android.StartupTabPreloader.LoadDecisionToFirstContentfulPaint"); - } - - // Records the duration from the load decision to the current time into |histogram| (suffixed - // by the state of the tab preload decision). To be used when the current time is before the - // tab match decision has occurred. - private void recordDurationFromLoadDecisionIntoPreTabMatchHistogram(String histogram) { - recordDurationFromLoadDecisionToEventTimeIntoPreTabMatchHistogram( - histogram, SystemClock.uptimeMillis()); - } - - // Records the duration from the load decision to |eventTimeMs| into |histogram| (suffixed - // by the state of the tab preload decision). To be used when the corresponding event occurred - // before the tab match decision has occurred. - private void recordDurationFromLoadDecisionToEventTimeIntoPreTabMatchHistogram( - String histogram, long eventTimeMs) { - if (mLoadDecisionMs == 0 || eventTimeMs == 0) return; - - long triggerpointToEventTimeMs = eventTimeMs - mLoadDecisionMs; - - String suffix = preloadWasViable() ? ".Load" : ".NoLoad"; - RecordHistogram.recordMediumTimesHistogram(histogram + suffix, triggerpointToEventTimeMs); - } - - // Records the duration from the load decision to the current time into |histogram| (suffixed - // by the state of the tab preload and match decisions). To be used when the tab match decision - // may have already occurred at the present time. - private void recordDurationFromLoadDecisionIntoPostTabMatchHistogram(String histogram) { - if (mLoadDecisionMs == 0) return; - - long currentTimeMs = SystemClock.uptimeMillis(); - long triggerpointToCurrentTimeMs = currentTimeMs - mLoadDecisionMs; - - String suffix = ".NoLoad"; - if (preloadWasViable()) { - // Check whether the tab match decision has yet occurred. It is still pending if (1) the - // preloaded tab is non-null, or (2) in the case where preloading is disabled by - // feature, the stored state used to calculate whether the preload would have matched is - // non-null. - boolean tabMatchStillPending = - mTab != null || mUrlForPreloadPreventedOnlyByFeature != null; - if (tabMatchStillPending) { - suffix = ".LoadPreMatch"; - } else if (tabMatchWasViable()) { - suffix = ".LoadAndMatch"; - } else { - suffix = ".LoadAndMismatch"; - } - } - - RecordHistogram.recordMediumTimesHistogram(histogram + suffix, triggerpointToCurrentTimeMs); - } - - // Returns whether the state specified for the tab preload and the actual load match. - private boolean doesPreloadStateMatch(@TabLaunchType int preconnectLaunchType, - @TabLaunchType int loadLaunchType, LoadUrlParams preconnectParams, - LoadUrlParams loadParams) { - boolean tabMatch = preconnectLaunchType == loadLaunchType - && doLoadUrlParamsMatchForWarmupManagerNavigation(preconnectParams, loadParams) - && !sFailNextTabMatchForTesting; - sFailNextTabMatchForTesting = false; - - return tabMatch; - } - - /** - * Returns the Tab if loadUrlParams and type match, otherwise the Tab is discarded. - * - * @param loadUrlParams The actual parameters of the url load. @param type The actual launch - * type type. @return The results of maybeNavigate() if they match loadUrlParams and type or - * null otherwise. - */ - public Tab takeTabIfMatchingOrDestroy(LoadUrlParams loadUrlParams, @TabLaunchType int type) { - if (!mRecordedLoadDecisionToMatchDecisionHistogram - && mStartupMetricsTracker.isTrackingStartupMetrics()) { - // NOTE: This histogram is segmented only by state of the load decision as it covers the - // duration from the load decision *up to* the tab match decision. Additionally, note - // that we record the metric only when tracking startup metrics to ensure that the - // latencies of this metric are comparable to those ones. - recordDurationFromLoadDecisionIntoPreTabMatchHistogram( - "Android.StartupTabPreloader.LoadDecisionToMatchDecision"); - mRecordedLoadDecisionToMatchDecisionHistogram = true; - - // Similarly, we record this metric only now to avoid recording cases where startup - // metrics are tracked at the time of the load decision but have been cancelled by the - // time of the tab match decision (e.g., due to a decision being made to show an - // overview). - RecordHistogram.recordMediumTimesHistogram( - "Android.StartupTabPreloader.ActivityStartToLoadDecision", - mLoadDecisionMs - mStartupMetricsTracker.getActivityStartTimeMs()); - } - - if (mTab == null) { - if (mUrlForPreloadPreventedOnlyByFeature != null) { - // Construct a LoadUrlParams object for the preload that would have occurred. - LoadUrlParams loadUrlParamsForPreloadPreventedOnlyByFeature = - new LoadUrlParams(mUrlForPreloadPreventedOnlyByFeature); - if (mReferrerForPreloadPreventedOnlyByFeature != null) { - loadUrlParamsForPreloadPreventedOnlyByFeature.setReferrer(new Referrer( - mReferrerForPreloadPreventedOnlyByFeature, ReferrerPolicy.DEFAULT)); - } - - // Calculate whether a tab match *would have* occurred if the preload wasn't - // prevented by the feature. This is used later for metrics tracking. - mPreloadPreventedOnlyByFeatureWouldHaveMatched = - doesPreloadStateMatch(TabLaunchType.FROM_EXTERNAL_APP, type, - loadUrlParamsForPreloadPreventedOnlyByFeature, loadUrlParams); - mUrlForPreloadPreventedOnlyByFeature = null; - mReferrerForPreloadPreventedOnlyByFeature = null; - } - - return null; - } - - mTabMatches = - doesPreloadStateMatch(mTab.getLaunchType(), type, mLoadUrlParams, loadUrlParams); - - RecordHistogram.recordBooleanHistogram( - "Startup.Android.StartupTabPreloader.TabTaken", mTabMatches); - - if (!mTabMatches) { - mStartupMetricsTracker.onStartupTabPreloadDropped(); - - mTab.destroy(); - mTab = null; - mLoadUrlParams = null; - return null; - } - - Tab tab = mTab; - mTab = null; - mLoadUrlParams = null; - tab.removeObserver(mObserver); - return tab; - } - - @VisibleForTesting - static boolean doLoadUrlParamsMatchForWarmupManagerNavigation( - LoadUrlParams preconnectParams, LoadUrlParams loadParams) { - if (!TextUtils.equals(preconnectParams.getUrl(), loadParams.getUrl())) return false; - - String preconnectReferrer = preconnectParams.getReferrer() != null - ? preconnectParams.getReferrer().getUrl() - : null; - String loadParamsReferrer = - loadParams.getReferrer() != null ? loadParams.getReferrer().getUrl() : null; - - return TextUtils.equals(preconnectReferrer, loadParamsReferrer); - } - - /** - * Called by the ProfileManager when a profile has been created. This occurs during startup - * and it's the earliest point at which we can create and load a tab. If the url can be - * determined from the intent, then a tab will be loaded and potentially adopted by - * {@link ChromeTabCreator}. - */ - @Override - public void onProfileAdded(Profile profile) { - try (TraceEvent e = TraceEvent.scoped("StartupTabPreloader.onProfileAdded")) { - // We only care about the first non-incognito profile that's created during startup. - if (profile.isOffTheRecord()) return; - - ProfileManager.removeObserver(this); - mTriggerPreload = shouldLoadTab(); - mLoadDecisionMs = SystemClock.uptimeMillis(); - - if (mTriggerPreload) loadTab(); - RecordHistogram.recordBooleanHistogram( - "Startup.Android.StartupTabPreloader.TabLoaded", mTriggerPreload); - RecordHistogram.recordEnumeratedHistogram( - "Startup.Android.StartupTabPreloader.LoadDecisionReason", - getLoadDecisionReason(), LoadDecisionReason.NUM_ENTRIES); - } - } - - @Override - public void onProfileDestroyed(Profile profile) {} - - /** - * @returns The reason for the decision returned by the most recent invocation of - * shouldLoadTab(). - */ - @VisibleForTesting - @LoadDecisionReason - int getLoadDecisionReason() { - return mLoadDecisionReason; - } - - /** - * @returns True if based on the intent we should load the tab, returns false otherwise. - */ - @VisibleForTesting - boolean shouldLoadTab() { - // If mTab isn't null we've been called before and there is nothing to do. - if (mTab != null) return false; - - mPreloadPreventedOnlyByFeature = false; - - Intent intent = mIntentSupplier.get(); - if (IntentUtils.safeGetBooleanExtra(intent, EXTRA_DISABLE_STARTUP_TAB_PRELOADER, false)) { - mLoadDecisionReason = LoadDecisionReason.DISABLED_BY_INTENT; - return false; - } - - // We don't support incognito tabs. NOTE: This check is before the check for whether the - // intent should be ignored to allow capturing the metric for this case separately, as - // IntentHandler also disallows incognito tab intents not sent by Chrome (i.e., - // IntentHandler#shouldIgnoreIntent() returns true in this case). - boolean incognito = IntentUtils.safeGetBooleanExtra( - intent, IntentHandler.EXTRA_OPEN_NEW_INCOGNITO_TAB, false); - if (incognito) { - mLoadDecisionReason = LoadDecisionReason.INCOGNITO; - return false; - } - if (mIntentHandler.shouldIgnoreIntent(intent, /*startedActivity=*/true)) { - mLoadDecisionReason = LoadDecisionReason.INTENT_IGNORED; - return false; - } - if (getUrlFromIntent(intent) == null) { - mLoadDecisionReason = LoadDecisionReason.NO_URL; - return false; - } - - // The TabCreatorManager throws an IllegalStateException if it is not ready to provide a - // TabCreator. - TabCreator tabCreator; - try { - tabCreator = mTabCreatorManager.getTabCreator(incognito); - } catch (IllegalStateException e) { - mLoadDecisionReason = LoadDecisionReason.NO_TAB_CREATOR; - return false; - } - - // We want to get the TabDelegateFactory but only ChromeTabCreator has one. - if (!(tabCreator instanceof ChromeTabCreator)) { - mLoadDecisionReason = LoadDecisionReason.WRONG_TAB_CREATOR; - return false; - } - - if (ChromeFeatureList.isEnabled(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP)) { - mPreloadPreventedOnlyByFeature = true; - mLoadDecisionReason = LoadDecisionReason.DISABLED_BY_FEATURE; - GURL url = UrlFormatter.fixupUrl(getUrlFromIntent(intent)); - - // NOTE: We avoid calling IntentHandler.createLoadUrlParamsForIntent() here as that - // call is destructive to the metadata associated with the intent. Instead, we save the - // parameters of the load that are used in the check for matching later. This is - // fragile, but this state is used only for evaluating the effectiveness of startup tab - // preloading. - mUrlForPreloadPreventedOnlyByFeature = url.getSpec(); - mReferrerForPreloadPreventedOnlyByFeature = - IntentHandler.getReferrerUrlIncludingExtraHeaders(intent); - - return false; - } - - mLoadDecisionReason = LoadDecisionReason.ALL_SATISFIED; - return true; - } - - private void loadTab() { - Intent intent = mIntentSupplier.get(); - GURL url = UrlFormatter.fixupUrl(getUrlFromIntent(intent)); - - ChromeTabCreator chromeTabCreator = - (ChromeTabCreator) mTabCreatorManager.getTabCreator(false); - WebContents webContents = - WebContentsFactory.createWebContents(Profile.getLastUsedRegularProfile(), false); - - mLoadUrlParams = mIntentHandler.createLoadUrlParamsForIntent(url.getSpec(), intent); - - // Create a detached tab, but don't add it to the tab model yet. We'll do that - // later if the loadUrlParams etc... match. - mTab = TabBuilder.createLiveTab(false) - .setIncognito(false) - .setLaunchType(TabLaunchType.FROM_EXTERNAL_APP) - .setWindow(mWindowAndroid) - .setWebContents(webContents) - .setDelegateFactory(chromeTabCreator.createDefaultTabDelegateFactory()) - .build(); - - mObserver = new StartupTabObserver(); - mTab.addObserver(mObserver); - mTab.loadUrl(mLoadUrlParams); - } - - private static String getUrlFromIntent(Intent intent) { - String action = intent.getAction(); - if (Intent.ACTION_VIEW.equals(action) || Intent.ACTION_MAIN.equals(action) - || (action == null - && ChromeTabbedActivity.MAIN_LAUNCHER_ACTIVITY_NAME.equals( - intent.getComponent().getClassName()))) { - // TODO(alexclarke): For ACTION_MAIN maybe refactor TabPersistentStore so we can - // instantiate (a subset of that) here to extract the URL if it's not set in the - // intent. - return IntentHandler.getUrlFromIntent(intent); - } else { - return null; - } - } - - private class StartupTabObserver extends EmptyTabObserver { - @Override - public void onCrash(Tab tab) { - onDestroy(); - } - } -}
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/metrics/ActivityTabStartupMetricsTracker.java b/chrome/android/java/src/org/chromium/chrome/browser/metrics/ActivityTabStartupMetricsTracker.java index e4a7b08..e967362 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/metrics/ActivityTabStartupMetricsTracker.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/metrics/ActivityTabStartupMetricsTracker.java
@@ -108,13 +108,6 @@ recordFirstContentfulPaint(navigationStartMicros / 1000 + firstContentfulPaintMs); } - - void resetMetricsRecordingStateForInitialNavigation() { - // NOTE: |mInvokedOnFirstNavigationStart| is intentionally not reset to avoid duplicate - // observer notifications. - mNavigationId = NO_NAVIGATION_ID; - mShouldRecordHistograms = false; - } }; private final long mActivityStartTimeMs; @@ -250,21 +243,6 @@ } /** - * Invoked when a tab preloaded at startup is dropped rather than taken, meaning that a new tab - * will need to be created to do the initial navigation. Resets state related to observation of - * the initial navigation to ensure that loading startup metrics are properly recorded in this - * case. Note that it is not necessary to reset the state of |mTabModelSelectorTabObserver| in - * this case, as that observer tracks state starting only from the addition of a tab to the tab - * model, which by definition has not yet occurred at this point. - */ - public void onStartupTabPreloadDropped() { - // Note that observers are not created in all contexts (e.g., CCT). - if (mPageLoadMetricsObserver == null) return; - - mPageLoadMetricsObserver.resetMetricsRecordingStateForInitialNavigation(); - } - - /** * Marks that startup metrics should be tracked with the |histogramSuffix|. * Must only be called on the UI thread. */
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/tabmodel/ChromeTabCreator.java b/chrome/android/java/src/org/chromium/chrome/browser/tabmodel/ChromeTabCreator.java index 82a82811..7c11415 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/tabmodel/ChromeTabCreator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/tabmodel/ChromeTabCreator.java
@@ -20,7 +20,6 @@ import org.chromium.chrome.browser.app.tab_activity_glue.ReparentingDelegateFactory; import org.chromium.chrome.browser.app.tab_activity_glue.ReparentingTask; import org.chromium.chrome.browser.compositor.CompositorViewHolder; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.ntp.NewTabPageLaunchOrigin; import org.chromium.chrome.browser.ntp.NewTabPageUtils; import org.chromium.chrome.browser.tab.RedirectHandlerTabHelper; @@ -71,7 +70,6 @@ private static final String TAG = "ChromeTabCreator"; private final Activity mActivity; - private final StartupTabPreloader mStartupTabPreloader; private final boolean mIncognito; private WindowAndroid mNativeWindow; @@ -85,13 +83,11 @@ private final Supplier<CompositorViewHolder> mCompositorViewHolderSupplier; public ChromeTabCreator(Activity activity, WindowAndroid nativeWindow, - StartupTabPreloader startupTabPreloader, Supplier<TabDelegateFactory> tabDelegateFactory, boolean incognito, OverviewNTPCreator overviewNTPCreator, AsyncTabParamsManager asyncTabParamsManager, Supplier<TabModelSelector> tabModelSelectorSupplier, Supplier<CompositorViewHolder> compositorViewHolderSupplier) { mActivity = activity; - mStartupTabPreloader = startupTabPreloader; mNativeWindow = nativeWindow; mTabDelegateFactorySupplier = tabDelegateFactory; mIncognito = incognito; @@ -222,31 +218,24 @@ .build(); creationState = TabCreationState.FROZEN_FOR_LAZY_LOAD; } else { - tab = (mStartupTabPreloader != null) - ? mStartupTabPreloader.takeTabIfMatchingOrDestroy(loadUrlParams, type) - : null; - - if (tab == null) { - TraceEvent.begin("ChromeTabCreator.loadUrl"); - Callback<Tab> action = null; - if (mOverviewNTPCreator != null) { - action = (newTab) -> { - mOverviewNTPCreator.preTabInitialization( - newTab, loadUrlParams.getUrl()); - }; - } - tab = TabBuilder.createLiveTab(!openInForeground) - .setParent(parent) - .setIncognito(mIncognito) - .setWindow(mNativeWindow) - .setLaunchType(type) - .setDelegateFactory(delegateFactory) - .setInitiallyHidden(!openInForeground) - .setPreInitializeAction(action) - .build(); - tab.loadUrl(loadUrlParams); - TraceEvent.end("ChromeTabCreator.loadUrl"); + TraceEvent.begin("ChromeTabCreator.loadUrl"); + Callback<Tab> action = null; + if (mOverviewNTPCreator != null) { + action = (newTab) -> { + mOverviewNTPCreator.preTabInitialization(newTab, loadUrlParams.getUrl()); + }; } + tab = TabBuilder.createLiveTab(!openInForeground) + .setParent(parent) + .setIncognito(mIncognito) + .setWindow(mNativeWindow) + .setLaunchType(type) + .setDelegateFactory(delegateFactory) + .setInitiallyHidden(!openInForeground) + .setPreInitializeAction(action) + .build(); + tab.loadUrl(loadUrlParams); + TraceEvent.end("ChromeTabCreator.loadUrl"); } // When tab reparenting the |intent| is the reparenting intent, not the intent that // created the tab.
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityAppMenuTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityAppMenuTest.java index 3ea998a..d5b9231 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityAppMenuTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityAppMenuTest.java
@@ -48,7 +48,6 @@ import org.chromium.chrome.browser.dependency_injection.ModuleOverridesRule; import org.chromium.chrome.browser.document.ChromeLauncherActivity; import org.chromium.chrome.browser.firstrun.FirstRunStatus; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.test.ScreenShooter; import org.chromium.chrome.browser.theme.TopUiThemeColorProvider; import org.chromium.chrome.browser.ui.appmenu.AppMenuCoordinator; @@ -76,17 +75,16 @@ public CustomTabActivityTestRule mCustomTabActivityTestRule = new CustomTabActivityTestRule(); - private final TestRule mModuleOverridesRule = new ModuleOverridesRule().setOverride( - BaseCustomTabActivityModule.Factory.class, - (BrowserServicesIntentDataProvider intentDataProvider, - StartupTabPreloader startupTabPreloader, - CustomTabNightModeStateController nightModeController, - CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, - TopUiThemeColorProvider topUiThemeColorProvider, - DefaultBrowserProviderImpl customTabDefaultBrowserProvider) - -> new BaseCustomTabActivityModule(intentDataProvider, startupTabPreloader, - nightModeController, intentIgnoringCriterion, topUiThemeColorProvider, - new FakeDefaultBrowserProviderImpl())); + private final TestRule mModuleOverridesRule = + new ModuleOverridesRule().setOverride(BaseCustomTabActivityModule.Factory.class, + (BrowserServicesIntentDataProvider intentDataProvider, + CustomTabNightModeStateController nightModeController, + CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, + TopUiThemeColorProvider topUiThemeColorProvider, + DefaultBrowserProviderImpl customTabDefaultBrowserProvider) + -> new BaseCustomTabActivityModule(intentDataProvider, + nightModeController, intentIgnoringCriterion, + topUiThemeColorProvider, new FakeDefaultBrowserProviderImpl())); @Rule public RuleChain mRuleChain = RuleChain.emptyRuleChain()
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityTest.java index 9f3468f..0b3293b 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/CustomTabActivityTest.java
@@ -862,10 +862,8 @@ */ @Test @SmallTest - @EnableFeatures({ChromeFeatureList.ELIDE_PRIORITIZATION_OF_PRE_NATIVE_BOOTSTRAP_TASKS, - ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP}) - public void - testNavigationHistogramsRecorded() throws Exception { + @EnableFeatures({ChromeFeatureList.ELIDE_PRIORITIZATION_OF_PRE_NATIVE_BOOTSTRAP_TASKS}) + public void testNavigationHistogramsRecorded() throws Exception { String startHistogramPrefix = "CustomTabs.IntentToFirstNavigationStartTime"; String commitHistogramPrefix = "CustomTabs.IntentToFirstCommitNavigationTime3"; assertSuffixedHistogramTotalCount(0, startHistogramPrefix);
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/TabReparentingTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/TabReparentingTest.java index 60f6fef3..0f0cc6a 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/TabReparentingTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/TabReparentingTest.java
@@ -44,7 +44,6 @@ import org.chromium.chrome.browser.firstrun.FirstRunStatus; import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.infobar.InfoBarContainer; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.tab.EmptyTabObserver; import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.browser.tab.TabHidingType; @@ -76,17 +75,16 @@ @Rule public CustomTabActivityTestRule mCustomTabActivityTestRule = new CustomTabActivityTestRule(); - private final TestRule mModuleOverridesRule = new ModuleOverridesRule().setOverride( - BaseCustomTabActivityModule.Factory.class, - (BrowserServicesIntentDataProvider intentDataProvider, - StartupTabPreloader startupTabPreloader, - CustomTabNightModeStateController nightModeController, - CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, - TopUiThemeColorProvider topUiThemeColorProvider, - DefaultBrowserProviderImpl customTabDefaultBrowserProvider) - -> new BaseCustomTabActivityModule(intentDataProvider, startupTabPreloader, - nightModeController, intentIgnoringCriterion, topUiThemeColorProvider, - new FakeDefaultBrowserProviderImpl())); + private final TestRule mModuleOverridesRule = + new ModuleOverridesRule().setOverride(BaseCustomTabActivityModule.Factory.class, + (BrowserServicesIntentDataProvider intentDataProvider, + CustomTabNightModeStateController nightModeController, + CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, + TopUiThemeColorProvider topUiThemeColorProvider, + DefaultBrowserProviderImpl customTabDefaultBrowserProvider) + -> new BaseCustomTabActivityModule(intentDataProvider, + nightModeController, intentIgnoringCriterion, + topUiThemeColorProvider, new FakeDefaultBrowserProviderImpl())); @Rule public RuleChain mRuleChain = RuleChain.emptyRuleChain()
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabControllerTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabControllerTest.java deleted file mode 100644 index c5ff57dc..0000000 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityTabControllerTest.java +++ /dev/null
@@ -1,117 +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. - -package org.chromium.chrome.browser.customtabs.content; - -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertNotEquals; - -import android.content.Intent; -import android.support.test.InstrumentationRegistry; - -import androidx.test.filters.MediumTest; - -import org.junit.Rule; -import org.junit.Test; -import org.junit.runner.RunWith; - -import org.chromium.base.IntentUtils; -import org.chromium.base.test.params.ParameterAnnotations.ClassParameter; -import org.chromium.base.test.params.ParameterAnnotations.UseRunnerDelegate; -import org.chromium.base.test.params.ParameterSet; -import org.chromium.base.test.params.ParameterizedRunner; -import org.chromium.base.test.util.CommandLineFlags; -import org.chromium.base.test.util.Feature; -import org.chromium.base.test.util.UrlUtils; -import org.chromium.chrome.browser.browserservices.intents.BrowserServicesIntentDataProvider.CustomTabsUiType; -import org.chromium.chrome.browser.customtabs.BaseCustomTabActivity; -import org.chromium.chrome.browser.customtabs.CustomTabActivityTestRule; -import org.chromium.chrome.browser.customtabs.CustomTabActivityTypeTestUtils; -import org.chromium.chrome.browser.customtabs.CustomTabIntentDataProvider; -import org.chromium.chrome.browser.customtabs.CustomTabsTestUtils; -import org.chromium.chrome.browser.flags.ActivityType; -import org.chromium.chrome.browser.flags.ChromeFeatureList; -import org.chromium.chrome.browser.flags.ChromeSwitches; -import org.chromium.chrome.test.ChromeActivityTestRule; -import org.chromium.chrome.test.ChromeJUnit4RunnerDelegate; -import org.chromium.chrome.test.util.ChromeTabUtils; -import org.chromium.chrome.test.util.browser.Features.DisableFeatures; - -import java.util.Arrays; -import java.util.List; -import java.util.concurrent.TimeoutException; - -/** - * Tests for {@link CustomTabActivityTabController}. - */ -@RunWith(ParameterizedRunner.class) -@UseRunnerDelegate(ChromeJUnit4RunnerDelegate.class) -@CommandLineFlags.Add({ChromeSwitches.DISABLE_FIRST_RUN_EXPERIENCE}) -public class CustomTabActivityTabControllerTest { - // Do not test TWAs because {@link CustomTabActivityTypeTestUtils#launchActivity} warms up the - // {@link CustomTabsConnection} which bypasses {@link StartupTabPreloader}. - @ClassParameter - public static List<ParameterSet> sClassParams = - Arrays.asList(new ParameterSet().value(ActivityType.WEBAPP).name("Webapp"), - new ParameterSet().value(ActivityType.CUSTOM_TAB).name("CustomTab")); - - private @ActivityType int mActivityType; - - @Rule - public final ChromeActivityTestRule<? extends BaseCustomTabActivity> mActivityTestRule; - - public CustomTabActivityTabControllerTest(@ActivityType int activityType) { - mActivityType = activityType; - mActivityTestRule = CustomTabActivityTypeTestUtils.createActivityTestRule(activityType); - } - - /** - * Test that the {@link StartupTabPreloader} tab is used by default. - */ - @Test - @MediumTest - @Feature({"CustomTabs"}) - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testUseStartupPreloaderTab() throws TimeoutException { - // TODO(https://crbug.com/1314766): Resolve the flake that occurs when running this test - // within the context of Custom Tabs. - if (mActivityType == ActivityType.CUSTOM_TAB) return; - - CustomTabActivityTypeTestUtils.launchActivity( - mActivityType, mActivityTestRule, "about:blank"); - CustomTabActivityTabProvider tabProvider = getActivityTabProvider(); - assertEquals(TabCreationMode.FROM_STARTUP_TAB_PRELOADER, - tabProvider.getInitialTabCreationMode()); - } - - /** - * Test that the {@link StartupTabPreloader} tab is not used if the preloaded URL is different - * than - * {@link IntentDataProvider#getUrlToLoad()}. - */ - @Test - @MediumTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testDontUseStartupPreloaderMediaViewerUrl() throws TimeoutException { - if (mActivityType != ActivityType.CUSTOM_TAB) return; - - String mediaViewerUrl = UrlUtils.getTestFileUrl("google.png"); - Intent intent = CustomTabsTestUtils.createMinimalCustomTabIntent( - InstrumentationRegistry.getTargetContext(), "about:blank"); - intent.putExtra(CustomTabIntentDataProvider.EXTRA_UI_TYPE, CustomTabsUiType.MEDIA_VIEWER); - intent.putExtra(CustomTabIntentDataProvider.EXTRA_MEDIA_VIEWER_URL, mediaViewerUrl); - IntentUtils.addTrustedIntentExtras(intent); - ((CustomTabActivityTestRule) mActivityTestRule).startCustomTabActivityWithIntent(intent); - - CustomTabActivityTabProvider tabProvider = getActivityTabProvider(); - assertEquals( - mediaViewerUrl, ChromeTabUtils.getUrlOnUiThread(tabProvider.getTab()).getSpec()); - assertNotEquals(TabCreationMode.FROM_STARTUP_TAB_PRELOADER, - tabProvider.getInitialTabCreationMode()); - } - - private CustomTabActivityTabProvider getActivityTabProvider() { - return mActivityTestRule.getActivity().getComponent().resolveTabProvider(); - } -}
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderCustomTabTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderCustomTabTest.java deleted file mode 100644 index d21da2f5..0000000 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderCustomTabTest.java +++ /dev/null
@@ -1,70 +0,0 @@ -// Copyright 2019 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.chrome.browser.init; - -import android.content.Intent; -import android.net.Uri; -import android.support.test.InstrumentationRegistry; - -import androidx.test.filters.LargeTest; - -import org.junit.Assert; -import org.junit.Rule; -import org.junit.Test; -import org.junit.runner.RunWith; - -import org.chromium.base.metrics.RecordHistogram; -import org.chromium.base.test.util.CommandLineFlags; -import org.chromium.base.test.util.DisableIf; -import org.chromium.chrome.browser.LaunchIntentDispatcher; -import org.chromium.chrome.browser.customtabs.CustomTabActivityTestRule; -import org.chromium.chrome.browser.flags.ChromeFeatureList; -import org.chromium.chrome.browser.flags.ChromeSwitches; -import org.chromium.chrome.test.ChromeJUnit4ClassRunner; -import org.chromium.chrome.test.util.browser.Features.DisableFeatures; -import org.chromium.content_public.browser.test.util.TestThreadUtils; -import org.chromium.net.test.EmbeddedTestServerRule; - -/** - * Browser tests for {@link StartupTabPreloader}. - */ -@RunWith(ChromeJUnit4ClassRunner.class) -@CommandLineFlags.Add(ChromeSwitches.DISABLE_FIRST_RUN_EXPERIENCE) -public class StartupTabPreloaderCustomTabTest { - private static final String TEST_PAGE = "/chrome/test/data/android/google.html"; - private static final String TAB_LOADED_HISTOGRAM = - "Startup.Android.StartupTabPreloader.TabLoaded"; - private static final String TAB_TAKEN_HISTOGRAM = - "Startup.Android.StartupTabPreloader.TabTaken"; - - @Rule - public CustomTabActivityTestRule mActivityRule = new CustomTabActivityTestRule(); - - @Rule - public EmbeddedTestServerRule mServerRule = new EmbeddedTestServerRule(); - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - @DisableIf.Build(supported_abis_includes = "x86", message = "https://crbug.com/1323858") - @DisableIf.Build(supported_abis_includes = "x86_64", message = "https://crbug.com/1323858") - public void testStartupTabPreloaderWithCustomTab() throws Exception { - Uri uri = Uri.parse(mServerRule.getServer().getURL(TEST_PAGE)); - Intent customTabActivityIntent = TestThreadUtils.runOnUiThreadBlockingNoException(() -> { - Intent intent = new Intent(Intent.ACTION_VIEW, uri); - intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); - return LaunchIntentDispatcher.createCustomTabActivityIntent( - InstrumentationRegistry.getTargetContext(), intent); - }); - - mActivityRule.startCustomTabActivityWithIntent(customTabActivityIntent); - - // The StartupTabPreloader should have loaded a url. - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - } -}
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderTest.java deleted file mode 100644 index 7228484..0000000 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderTest.java +++ /dev/null
@@ -1,585 +0,0 @@ -// Copyright 2019 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.chrome.browser.init; - -import android.content.Intent; - -import androidx.test.filters.LargeTest; - -import org.junit.Assert; -import org.junit.Rule; -import org.junit.Test; -import org.junit.runner.RunWith; - -import org.chromium.base.metrics.RecordHistogram; -import org.chromium.base.test.util.CommandLineFlags; -import org.chromium.base.test.util.CriteriaHelper; -import org.chromium.base.test.util.DisabledTest; -import org.chromium.chrome.browser.ChromeTabbedActivity; -import org.chromium.chrome.browser.IntentHandler; -import org.chromium.chrome.browser.flags.ChromeFeatureList; -import org.chromium.chrome.browser.flags.ChromeSwitches; -import org.chromium.chrome.browser.metrics.UmaUtils; -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.browser.Features.DisableFeatures; -import org.chromium.chrome.test.util.browser.Features.EnableFeatures; -import org.chromium.content_public.browser.test.util.TestThreadUtils; -import org.chromium.net.test.EmbeddedTestServerRule; - -/** - * Browser tests for {@link StartupTabPreloader}. - */ -@RunWith(ChromeJUnit4ClassRunner.class) -@CommandLineFlags.Add(ChromeSwitches.DISABLE_FIRST_RUN_EXPERIENCE) -public class StartupTabPreloaderTest { - private static final String TEST_PAGE = "/chrome/test/data/android/google.html"; - private static final String TEST_PAGE2 = "/chrome/test/data/android/about.html"; - private static final String TAB_LOADED_HISTOGRAM = - "Startup.Android.StartupTabPreloader.TabLoaded"; - private static final String TAB_TAKEN_HISTOGRAM = - "Startup.Android.StartupTabPreloader.TabTaken"; - private static final String FIRST_COMMIT_HISTOGRAM = - "Startup.Android.Cold.TimeToFirstNavigationCommit" - + ChromeTabbedActivity.STARTUP_UMA_HISTOGRAM_SUFFIX; - private static final String FIRST_CONTENTFUL_PAINT_HISTOGRAM = - "Startup.Android.Cold.TimeToFirstContentfulPaint" - + ChromeTabbedActivity.STARTUP_UMA_HISTOGRAM_SUFFIX; - private static final String FIRST_VISIBLE_CONTENT_HISTOGRAM = - "Startup.Android.Cold.TimeToFirstVisibleContent"; - private static final String VISIBLE_CONTENT_HISTOGRAM = - "Startup.Android.Cold.TimeToVisibleContent"; - private static final String ACTIVITY_START_TO_PRELOAD_TRIGGER = - "Android.StartupTabPreloader.ActivityStartToLoadDecision"; - private static final String PRELOAD_TRIGGER_TO_MATCH_DECISION_PRELOAD = - "Android.StartupTabPreloader.LoadDecisionToMatchDecision.Load"; - private static final String PRELOAD_TRIGGER_TO_MATCH_DECISION_NO_PRELOAD = - "Android.StartupTabPreloader.LoadDecisionToMatchDecision.NoLoad"; - private static final String PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_START_PRELOAD = - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationStart.Load"; - private static final String PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_START_NO_PRELOAD = - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationStart.NoLoad"; - private static final String PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_PRELOAD_BEFORE_MATCH = - "Android.StartupTabPreloader.LoadDecisionToFirstVisibleContent.LoadPreMatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_PRELOAD_AND_TAKE = - "Android.StartupTabPreloader.LoadDecisionToFirstVisibleContent.LoadAndMatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_PRELOAD_AND_DROP = - "Android.StartupTabPreloader.LoadDecisionToFirstVisibleContent.LoadAndMismatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_NO_PRELOAD = - "Android.StartupTabPreloader.LoadDecisionToFirstVisibleContent.NoLoad"; - private static final String PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_PRELOAD_BEFORE_MATCH = - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationCommit.LoadPreMatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_PRELOAD_AND_TAKE = - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationCommit.LoadAndMatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_PRELOAD_AND_DROP = - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationCommit.LoadAndMismatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_NO_PRELOAD = - "Android.StartupTabPreloader.LoadDecisionToFirstNavigationCommit.NoLoad"; - private static final String PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_PRELOAD_BEFORE_MATCH = - "Android.StartupTabPreloader.LoadDecisionToFirstContentfulPaint.LoadPreMatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_PRELOAD_AND_TAKE = - "Android.StartupTabPreloader.LoadDecisionToFirstContentfulPaint.LoadAndMatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_PRELOAD_AND_DROP = - "Android.StartupTabPreloader.LoadDecisionToFirstContentfulPaint.LoadAndMismatch"; - private static final String PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_NO_PRELOAD = - "Android.StartupTabPreloader.LoadDecisionToFirstContentfulPaint.NoLoad"; - private static final String LOAD_DECISION_REASON = - "Startup.Android.StartupTabPreloader.LoadDecisionReason"; - - // Used for verifying expected histogram counts. - private static final int NO_PRELOAD = 0; - private static final int PRELOAD = 1; - private static final int NO_PRELOAD_MATCH = 0; - private static final int PRELOAD_MATCH = 1; - - @Rule - public ChromeTabbedActivityTestRule mActivityRule = new ChromeTabbedActivityTestRule(); - - @Rule - public EmbeddedTestServerRule mServerRule = new EmbeddedTestServerRule(); - - // Verifies the state of various startup metrics being recorded appropriately for the varues of - // |preload| and |preloadMatch| (specified by the constants above). - private void assertStartupMetricsRecorded(int preload, int preloadMatch) { - int noPreload = 1 - preload; - int preloadMismatch = (preload == 1 && preloadMatch == 0) ? 1 : 0; - - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - ACTIVITY_START_TO_PRELOAD_TRIGGER)); - - Assert.assertEquals(preload, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_START_PRELOAD)); - Assert.assertEquals(noPreload, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_START_NO_PRELOAD)); - - Assert.assertEquals(preload, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_MATCH_DECISION_PRELOAD)); - Assert.assertEquals(noPreload, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_MATCH_DECISION_NO_PRELOAD)); - - Assert.assertEquals(preloadMatch, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_PRELOAD_AND_TAKE)); - Assert.assertEquals(preloadMismatch, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_PRELOAD_AND_DROP)); - Assert.assertEquals(noPreload, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_NO_PRELOAD)); - - Assert.assertEquals(preloadMatch, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_PRELOAD_AND_TAKE)); - Assert.assertEquals(preloadMismatch, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_PRELOAD_AND_DROP)); - Assert.assertEquals(noPreload, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_NO_PRELOAD)); - - Assert.assertEquals(preloadMatch, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_PRELOAD_AND_TAKE)); - Assert.assertEquals(preloadMismatch, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_PRELOAD_AND_DROP)); - Assert.assertEquals(noPreload, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_NO_PRELOAD)); - - // This case never triggers in these tests. - Assert.assertEquals(0, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_VISIBLE_CONTENT_PRELOAD_BEFORE_MATCH)); - Assert.assertEquals(0, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_NAVIGATION_COMMIT_PRELOAD_BEFORE_MATCH)); - Assert.assertEquals(0, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_FIRST_CONTENTFUL_PAINT_PRELOAD_BEFORE_MATCH)); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderWithViewIntent() throws Exception { - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should have loaded a url. - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED)); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - @DisabledTest(message = "https://crbug.com/1271158") - public void testStartupTabPreloaderStartupLoadingMetricsRecordedWhenTabTaken() - throws Exception { - // Force the browser to regard itself as being in the foreground to work around the - // fact that the navigation here can happen before ChromeActivity records the - // browser as being in the foreground, in which case startup metrics are erroneously - // not recorded. TODO(crbug.com/1273097): Eliminate this call when we fix startup - // metrics to be recorded in this case. - TestThreadUtils.runOnUiThreadBlocking(() -> UmaUtils.recordForegroundStartTime()); - - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should have loaded a url. - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED)); - - // First contentful paint should be recorded. - CriteriaHelper.pollUiThread(() - -> RecordHistogram.getHistogramTotalCountForTesting( - FIRST_CONTENTFUL_PAINT_HISTOGRAM) - == 1); - // First contentful paint is the last startup metric to be recorded, so the other startup - // metrics should also have been recorded at this point. - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(FIRST_COMMIT_HISTOGRAM)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting(FIRST_VISIBLE_CONTENT_HISTOGRAM)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(VISIBLE_CONTENT_HISTOGRAM)); - - // Startup tab preload-specific startup metrics should also have been recorded. - assertStartupMetricsRecorded(PRELOAD, PRELOAD_MATCH); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderStartupLoadingMetricsRecordedWhenTabDropped() - throws Exception { - // Force the browser to regard itself as being in the foreground to work around the - // fact that the navigation here can happen before ChromeActivity records the - // browser as being in the foreground, in which case startup metrics are erroneously - // not recorded. TODO(crbug.com/1273097): Eliminate this call when we fix startup - // metrics to be recorded in this case. - TestThreadUtils.runOnUiThreadBlocking(() -> UmaUtils.recordForegroundStartTime()); - - StartupTabPreloader.failNextTabMatchForTesting(); - - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED)); - - // The StartupTabPreloader should have loaded a url, but it should not have been taken. - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - - // First contentful paint should be recorded. - CriteriaHelper.pollUiThread(() - -> RecordHistogram.getHistogramTotalCountForTesting( - FIRST_CONTENTFUL_PAINT_HISTOGRAM) - == 1); - - // First contentful paint is the last startup metric to be recorded, so the other startup - // metrics should also have been recorded at this point. - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(FIRST_COMMIT_HISTOGRAM)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting(FIRST_VISIBLE_CONTENT_HISTOGRAM)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(VISIBLE_CONTENT_HISTOGRAM)); - - // Startup tab preload-specific startup metrics should also have been recorded. - assertStartupMetricsRecorded(PRELOAD, NO_PRELOAD_MATCH); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderStartupLoadingMetricsRecordedWhenTabNotPreloaded() - throws Exception { - // Force the browser to regard itself as being in the foreground to work around the - // fact that the navigation here can happen before ChromeActivity records the - // browser as being in the foreground, in which case startup metrics are erroneously - // not recorded. TODO(crbug.com/1273097): Eliminate this call when we fix startup - // metrics to be recorded in this case. - TestThreadUtils.runOnUiThreadBlocking(() -> UmaUtils.recordForegroundStartTime()); - - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - intent.putExtra(StartupTabPreloader.EXTRA_DISABLE_STARTUP_TAB_PRELOADER, true); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should not have loaded a url. - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.DISABLED_BY_INTENT)); - - // First contentful paint should be recorded. - CriteriaHelper.pollUiThread(() - -> RecordHistogram.getHistogramTotalCountForTesting( - FIRST_CONTENTFUL_PAINT_HISTOGRAM) - == 1); - // First contentful paint is the last startup metric to be recorded, so the other startup - // metrics should also have been recorded at this point. - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(FIRST_COMMIT_HISTOGRAM)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting(FIRST_VISIBLE_CONTENT_HISTOGRAM)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(VISIBLE_CONTENT_HISTOGRAM)); - - // Startup tab preload-specific startup metrics should also have been recorded. - assertStartupMetricsRecorded(NO_PRELOAD, NO_PRELOAD_MATCH); - } - - @Test - @LargeTest - @EnableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void - testStartupTabPreloaderStartupLoadingMetricsRecordedWhenTabWouldBeTakenIfNotPreventedByFeature() - throws Exception { - // Force the browser to regard itself as being in the foreground to work around the - // fact that the navigation here can happen before ChromeActivity records the - // browser as being in the foreground, in which case startup metrics are erroneously - // not recorded. TODO(crbug.com/1273097): Eliminate this call when we fix startup - // metrics to be recorded in this case. - TestThreadUtils.runOnUiThreadBlocking(() -> UmaUtils.recordForegroundStartTime()); - - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should not have actually loaded a url. - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.DISABLED_BY_FEATURE)); - - // First contentful paint should be recorded. - CriteriaHelper.pollUiThread(() - -> RecordHistogram.getHistogramTotalCountForTesting( - FIRST_CONTENTFUL_PAINT_HISTOGRAM) - == 1); - // First contentful paint is the last startup metric to be recorded, so the other startup - // metrics should also have been recorded at this point. - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(FIRST_COMMIT_HISTOGRAM)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting(FIRST_VISIBLE_CONTENT_HISTOGRAM)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(VISIBLE_CONTENT_HISTOGRAM)); - - // Startup tab preload-specific startup metrics should also have been recorded, with the - // state reflecting what it would have been if startup tab preloading were not prevented by - // the base::Feature. - assertStartupMetricsRecorded(PRELOAD, PRELOAD_MATCH); - } - - @Test - @LargeTest - @EnableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void - testStartupTabPreloaderStartupLoadingMetricsRecordedWhenTabWouldBeDroppedIfNotPreventedByFeature() - throws Exception { - // Force the browser to regard itself as being in the foreground to work around the - // fact that the navigation here can happen before ChromeActivity records the - // browser as being in the foreground, in which case startup metrics are erroneously - // not recorded. TODO(crbug.com/1273097): Eliminate this call when we fix startup - // metrics to be recorded in this case. - TestThreadUtils.runOnUiThreadBlocking(() -> UmaUtils.recordForegroundStartTime()); - - StartupTabPreloader.failNextTabMatchForTesting(); - - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should not have actually loaded a url. - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.DISABLED_BY_FEATURE)); - - // First contentful paint should be recorded. - CriteriaHelper.pollUiThread(() - -> RecordHistogram.getHistogramTotalCountForTesting( - FIRST_CONTENTFUL_PAINT_HISTOGRAM) - == 1); - - // First contentful paint is the last startup metric to be recorded, so the other startup - // metrics should also have been recorded at this point. - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(FIRST_COMMIT_HISTOGRAM)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting(FIRST_VISIBLE_CONTENT_HISTOGRAM)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramTotalCountForTesting(VISIBLE_CONTENT_HISTOGRAM)); - - // Startup tab preload-specific startup metrics should also have been recorded, with the - // state reflecting what it would have been if startup tab preloading were not prevented by - // the base::Feature. - assertStartupMetricsRecorded(PRELOAD, NO_PRELOAD_MATCH); - } - - @Test - @LargeTest - @EnableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderWithViewIntentFeatureDisabled() throws Exception { - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should have ignored the intent. - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderWithIncognitoViewIntent() throws Exception { - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - intent.putExtra(IntentHandler.EXTRA_OPEN_NEW_INCOGNITO_TAB, true); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // Incognito requests should be ignored. - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting( - LOAD_DECISION_REASON, StartupTabPreloader.LoadDecisionReason.INCOGNITO)); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderWithMainIntentWithUrl() throws Exception { - Intent intent = new Intent(Intent.ACTION_MAIN); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should have loaded a url. - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED)); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderWithMainIntentWithoutUrl() throws Exception { - Intent intent = new Intent(Intent.ACTION_MAIN); - intent.addCategory(Intent.CATEGORY_HOME); - mActivityRule.startMainActivityFromIntent(intent, null); - - // There is no url so the StartupTabPreloader should ignore it. - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting( - LOAD_DECISION_REASON, StartupTabPreloader.LoadDecisionReason.NO_URL)); - } - - @Test - @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderWithMultipleViewIntents() throws Exception { - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should have loaded a url. - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - ACTIVITY_START_TO_PRELOAD_TRIGGER)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_MATCH_DECISION_PRELOAD)); - Assert.assertEquals(0, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_MATCH_DECISION_NO_PRELOAD)); - - Tab currentTab = mActivityRule.getActivity().getActivityTab(); - - intent = new Intent(Intent.ACTION_VIEW); - String url = mServerRule.getServer().getURL(TEST_PAGE2); - mActivityRule.getActivity().startActivity(mActivityRule.prepareUrlIntent(intent, url)); - - CriteriaHelper.pollUiThread( - () -> mActivityRule.getActivity().getActivityTab() != currentTab); - ChromeTabUtils.waitForTabPageLoaded(mActivityRule.getActivity().getActivityTab(), url); - - // The second intent should be ignored and not increment the counters. - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 1, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - Assert.assertEquals(1, - RecordHistogram.getHistogramValueCountForTesting(LOAD_DECISION_REASON, - StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - ACTIVITY_START_TO_PRELOAD_TRIGGER)); - Assert.assertEquals(1, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_MATCH_DECISION_PRELOAD)); - Assert.assertEquals(0, - RecordHistogram.getHistogramTotalCountForTesting( - PRELOAD_TRIGGER_TO_MATCH_DECISION_NO_PRELOAD)); - } - - @Test - @LargeTest - @EnableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testStartupTabPreloaderMultipleTabCreationWithFeatureEnabled() throws Exception { - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.addCategory(Intent.CATEGORY_LAUNCHER); - mActivityRule.startMainActivityFromIntent( - intent, mServerRule.getServer().getURL(TEST_PAGE)); - - // The StartupTabPreloader should not have loaded a url. - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - - Tab currentTab = mActivityRule.getActivity().getActivityTab(); - - // Creating a second tab should not cause a browser crash. Verifies safety of subtle - // logic handling metrics in the case where the feature is enabled. - intent = new Intent(Intent.ACTION_VIEW); - String url = mServerRule.getServer().getURL(TEST_PAGE2); - mActivityRule.getActivity().startActivity(mActivityRule.prepareUrlIntent(intent, url)); - - CriteriaHelper.pollUiThread( - () -> mActivityRule.getActivity().getActivityTab() != currentTab); - ChromeTabUtils.waitForTabPageLoaded(mActivityRule.getActivity().getActivityTab(), url); - - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_LOADED_HISTOGRAM, 1)); - Assert.assertEquals( - 0, RecordHistogram.getHistogramValueCountForTesting(TAB_TAKEN_HISTOGRAM, 1)); - } -}
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderUnitTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderUnitTest.java deleted file mode 100644 index acca223..0000000 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/init/StartupTabPreloaderUnitTest.java +++ /dev/null
@@ -1,256 +0,0 @@ -// Copyright 2019 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.chrome.browser.init; - -import android.content.ComponentName; -import android.content.Intent; -import android.net.Uri; - -import androidx.test.filters.SmallTest; - -import org.junit.Assert; -import org.junit.Rule; -import org.junit.Test; -import org.junit.runner.RunWith; - -import org.chromium.base.Callback; -import org.chromium.base.ThreadUtils; -import org.chromium.base.supplier.ObservableSupplier; -import org.chromium.base.supplier.Supplier; -import org.chromium.chrome.browser.IntentHandler; -import org.chromium.chrome.browser.flags.ChromeFeatureList; -import org.chromium.chrome.browser.metrics.ActivityTabStartupMetricsTracker; -import org.chromium.chrome.browser.tabmodel.ChromeTabCreator; -import org.chromium.chrome.browser.tabmodel.TabCreator; -import org.chromium.chrome.browser.tabmodel.TabCreatorManager; -import org.chromium.chrome.browser.tabmodel.TabModelSelector; -import org.chromium.chrome.browser.tabmodel.document.TabDelegate; -import org.chromium.chrome.test.ChromeJUnit4ClassRunner; -import org.chromium.chrome.test.util.browser.Features; -import org.chromium.chrome.test.util.browser.Features.DisableFeatures; -import org.chromium.chrome.test.util.browser.Features.EnableFeatures; -import org.chromium.content_public.browser.LoadUrlParams; -import org.chromium.content_public.common.Referrer; -import org.chromium.network.mojom.ReferrerPolicy; - -/** - * Unit tests for {@link StartupTabPreloader}. - */ -@RunWith(ChromeJUnit4ClassRunner.class) -public class StartupTabPreloaderUnitTest { - private static final String SITE_A = "https://a.com"; - private static final String SITE_B = "https://b.com"; - private static final String SITE_C = "https://c.com"; - private static final String INVALID_SCHEME = "javascript:alert()"; - private static final Intent VIEW_INTENT = - new Intent(Intent.ACTION_VIEW).setData(Uri.parse(SITE_A)); - private static final Intent CHROME_MAIN_COMPONENT_INTENT = - new Intent() - .setComponent(new ComponentName("com.google.android.apps.chrome", - "com.google.android.apps.chrome.Main")) - .setData(Uri.parse(SITE_A)); - private static final Intent INCOGNITO_VIEW_INTENT = - new Intent(Intent.ACTION_VIEW) - .setData(Uri.parse(SITE_A)) - .putExtra(IntentHandler.EXTRA_OPEN_NEW_INCOGNITO_TAB, true); - private static final Intent VIEW_INTENT_WITH_INVALID_SCHEME = - new Intent(Intent.ACTION_VIEW).setData(Uri.parse(INVALID_SCHEME)); - private static final Intent MAIN_INTENT_WITH_URL = - new Intent(Intent.ACTION_MAIN).setData(Uri.parse(SITE_B)); - private static final Intent MAIN_INTENT_WITHOUT_URL = new Intent(Intent.ACTION_MAIN); - private static final TabCreatorManager sChromeTabCreator = new ChromeTabCreatorManager(); - private static final TabCreatorManager sUninitializedChromeTabCreatorManager = - new UninitializedChromeTabCreatorManager(); - private static final TabCreatorManager sNonChromeTabCreator = new NonChromeTabCreatorManager(); - - @Rule - public Features.JUnitProcessor processor = new Features.JUnitProcessor(); - - @Test - @SmallTest - public void testDoLoadUrlParamsMatchForWarmupManagerNavigation() { - LoadUrlParams siteAWithSiteBReferrer_1 = new LoadUrlParams(SITE_A); - siteAWithSiteBReferrer_1.setReferrer(new Referrer(SITE_B, ReferrerPolicy.DEFAULT)); - LoadUrlParams siteAWithSiteBReferrer_2 = new LoadUrlParams(SITE_A); - siteAWithSiteBReferrer_2.setReferrer(new Referrer(SITE_B, ReferrerPolicy.DEFAULT)); - - LoadUrlParams siteAWithSiteBReferrer = new LoadUrlParams(SITE_A); - siteAWithSiteBReferrer.setReferrer(new Referrer(SITE_B, ReferrerPolicy.DEFAULT)); - - LoadUrlParams siteAWithSiteCReferrer = new LoadUrlParams(SITE_A); - siteAWithSiteCReferrer.setReferrer(new Referrer(SITE_C, ReferrerPolicy.DEFAULT)); - - LoadUrlParams siteAWithNoReferrer = new LoadUrlParams(SITE_A); - LoadUrlParams siteBWithNoReferrer_1 = new LoadUrlParams(SITE_B); - LoadUrlParams siteBWithNoReferrer_2 = new LoadUrlParams(SITE_B); - - Assert.assertTrue(StartupTabPreloader.doLoadUrlParamsMatchForWarmupManagerNavigation( - siteAWithSiteBReferrer_1, siteAWithSiteBReferrer_2)); - Assert.assertTrue(StartupTabPreloader.doLoadUrlParamsMatchForWarmupManagerNavigation( - siteBWithNoReferrer_2, siteBWithNoReferrer_2)); - - Assert.assertFalse(StartupTabPreloader.doLoadUrlParamsMatchForWarmupManagerNavigation( - siteAWithSiteBReferrer_1, siteAWithSiteCReferrer)); - Assert.assertFalse(StartupTabPreloader.doLoadUrlParamsMatchForWarmupManagerNavigation( - siteAWithSiteBReferrer_1, siteAWithNoReferrer)); - Assert.assertFalse(StartupTabPreloader.doLoadUrlParamsMatchForWarmupManagerNavigation( - siteAWithSiteBReferrer_1, siteBWithNoReferrer_1)); - Assert.assertFalse(StartupTabPreloader.doLoadUrlParamsMatchForWarmupManagerNavigation( - siteAWithNoReferrer, siteBWithNoReferrer_1)); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_AllowViewIntents() { - StartupTabPreloader preloader = createStartupTabPreloader(VIEW_INTENT, sChromeTabCreator); - Assert.assertTrue(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED, - preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_AllowChromeMainComponentIntentWithUrl() { - StartupTabPreloader preloader = - createStartupTabPreloader(CHROME_MAIN_COMPONENT_INTENT, sChromeTabCreator); - Assert.assertTrue(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED, - preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_AllowMainIntentsWithUrl() { - StartupTabPreloader preloader = - createStartupTabPreloader(MAIN_INTENT_WITH_URL, sChromeTabCreator); - Assert.assertTrue(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.ALL_SATISFIED, - preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_BlockedMainIntentsWithoutUrl() { - StartupTabPreloader preloader = - createStartupTabPreloader(MAIN_INTENT_WITHOUT_URL, sChromeTabCreator); - Assert.assertFalse(preloader.shouldLoadTab()); - Assert.assertEquals( - StartupTabPreloader.LoadDecisionReason.NO_URL, preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @EnableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_BlockedWhenSpecifiedByFeature() { - StartupTabPreloader preloader = createStartupTabPreloader(VIEW_INTENT, sChromeTabCreator); - Assert.assertFalse(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.DISABLED_BY_FEATURE, - preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_BlockedInvalidSchemeIntent() { - StartupTabPreloader preloader = - createStartupTabPreloader(VIEW_INTENT_WITH_INVALID_SCHEME, sChromeTabCreator); - Assert.assertFalse(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.INTENT_IGNORED, - preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_BlockedNonChromeTabCreators() { - StartupTabPreloader preloader = - createStartupTabPreloader(VIEW_INTENT, sNonChromeTabCreator); - Assert.assertFalse(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.WRONG_TAB_CREATOR, - preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_BlockedIncognitoIntents() { - StartupTabPreloader preloader = - createStartupTabPreloader(INCOGNITO_VIEW_INTENT, sChromeTabCreator); - Assert.assertFalse(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.INCOGNITO, - preloader.getLoadDecisionReason()); - } - - @Test - @SmallTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) - public void testShouldLoadTab_UninitializedTabCreatorManager() { - StartupTabPreloader preloader = - createStartupTabPreloader(VIEW_INTENT, sUninitializedChromeTabCreatorManager); - Assert.assertFalse(preloader.shouldLoadTab()); - Assert.assertEquals(StartupTabPreloader.LoadDecisionReason.NO_TAB_CREATOR, - preloader.getLoadDecisionReason()); - } - - private StartupTabPreloader createStartupTabPreloader( - Intent intent, TabCreatorManager tabCreatorManager) { - // StartupTabPreloader calls into code that asserts that it is on the UI thread, which - // doesn't exist in this unittesting context. - ThreadUtils.setThreadAssertsDisabledForTesting(true); - - return new StartupTabPreloader( - new Supplier<Intent>() { - @Override - public Intent get() { - return intent; - } - }, - new ActivityLifecycleDispatcherImpl(null), null, tabCreatorManager, - new IntentHandler(null, null), - new ActivityTabStartupMetricsTracker(new ObservableSupplier<TabModelSelector>() { - @Override - public TabModelSelector addObserver(Callback<TabModelSelector> obs) { - return null; - } - - @Override - public void removeObserver(Callback<TabModelSelector> obs) {} - - @Override - public TabModelSelector get() { - return null; - } - })); - } - - private static class ChromeTabCreatorManager implements TabCreatorManager { - @Override - public TabCreator getTabCreator(boolean incognito) { - Assert.assertFalse(incognito); - return new ChromeTabCreator(null, null, null, null, false, null, null, null, null); - } - } - - private static class UninitializedChromeTabCreatorManager implements TabCreatorManager { - @Override - public TabCreator getTabCreator(boolean incognito) { - throw new IllegalStateException("uninitialized for test"); - } - } - - private static class NonChromeTabCreatorManager implements TabCreatorManager { - @Override - public TabCreator getTabCreator(boolean incognito) { - Assert.assertFalse(incognito); - - // The important thing is this isn't ChromeTabCreator. - return new TabDelegate(false); - } - } -}
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/metrics/StartupLoadingMetricsTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/metrics/StartupLoadingMetricsTest.java index 8f99732b..a62edc6 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/metrics/StartupLoadingMetricsTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/metrics/StartupLoadingMetricsTest.java
@@ -24,7 +24,6 @@ import org.chromium.base.test.util.DisableIf; import org.chromium.base.test.util.DisabledTest; import org.chromium.chrome.browser.ChromeTabbedActivity; -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.browser.webapps.WebApkActivityLifecycleUmaTracker; @@ -34,7 +33,6 @@ import org.chromium.chrome.test.ChromeTabbedActivityTestRule; import org.chromium.chrome.test.util.ChromeApplicationTestUtils; import org.chromium.chrome.test.util.ChromeTabUtils; -import org.chromium.chrome.test.util.browser.Features.DisableFeatures; import org.chromium.content_public.browser.test.util.TestThreadUtils; import org.chromium.net.test.EmbeddedTestServer; @@ -274,7 +272,6 @@ @Test @LargeTest - @DisableFeatures(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP) @DisabledTest(message = "https://crbug.com/1313210") public void testRecordingOfFirstNavigationCommitPreForeground() throws Exception { UmaUtils.skipRecordingNextForegroundStartTimeForTesting();
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappActionsNotificationTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappActionsNotificationTest.java index c35f3cb..941a4f1 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappActionsNotificationTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappActionsNotificationTest.java
@@ -43,7 +43,6 @@ import org.chromium.chrome.browser.customtabs.dependency_injection.BaseCustomTabActivityModule; import org.chromium.chrome.browser.dependency_injection.ModuleOverridesRule; import org.chromium.chrome.browser.flags.ChromeSwitches; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.notifications.NotificationConstants; import org.chromium.chrome.browser.theme.TopUiThemeColorProvider; import org.chromium.chrome.test.ChromeJUnit4ClassRunner; @@ -63,17 +62,16 @@ @Rule public final WebappActivityTestRule mActivityTestRule = new WebappActivityTestRule(); - private final TestRule mModuleOverridesRule = new ModuleOverridesRule().setOverride( - BaseCustomTabActivityModule.Factory.class, - (BrowserServicesIntentDataProvider intentDataProvider, - StartupTabPreloader startupTabPreloader, - CustomTabNightModeStateController nightModeController, - CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, - TopUiThemeColorProvider topUiThemeColorProvider, - DefaultBrowserProviderImpl customTabDefaultBrowserProvider) - -> new BaseCustomTabActivityModule(intentDataProvider, startupTabPreloader, - nightModeController, intentIgnoringCriterion, topUiThemeColorProvider, - new FakeDefaultBrowserProviderImpl())); + private final TestRule mModuleOverridesRule = + new ModuleOverridesRule().setOverride(BaseCustomTabActivityModule.Factory.class, + (BrowserServicesIntentDataProvider intentDataProvider, + CustomTabNightModeStateController nightModeController, + CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, + TopUiThemeColorProvider topUiThemeColorProvider, + DefaultBrowserProviderImpl customTabDefaultBrowserProvider) + -> new BaseCustomTabActivityModule(intentDataProvider, + nightModeController, intentIgnoringCriterion, + topUiThemeColorProvider, new FakeDefaultBrowserProviderImpl())); @Rule public RuleChain mRuleChain =
diff --git a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java index ef3ce75..6fbcf0f 100644 --- a/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java +++ b/chrome/android/javatests/src/org/chromium/chrome/browser/webapps/WebappNavigationTest.java
@@ -55,7 +55,6 @@ import org.chromium.chrome.browser.dependency_injection.ModuleOverridesRule; import org.chromium.chrome.browser.firstrun.FirstRunStatus; import org.chromium.chrome.browser.flags.ChromeSwitches; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.tab.Tab; import org.chromium.chrome.browser.test.MockCertVerifierRuleAndroid; import org.chromium.chrome.browser.theme.TopUiThemeColorProvider; @@ -86,17 +85,16 @@ public MockCertVerifierRuleAndroid mCertVerifierRule = new MockCertVerifierRuleAndroid(0 /* net::OK */); - private final TestRule mModuleOverridesRule = new ModuleOverridesRule().setOverride( - BaseCustomTabActivityModule.Factory.class, - (BrowserServicesIntentDataProvider intentDataProvider, - StartupTabPreloader startupTabPreloader, - CustomTabNightModeStateController nightModeController, - CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, - TopUiThemeColorProvider topUiThemeColorProvider, - DefaultBrowserProviderImpl customTabDefaultBrowserProvider) - -> new BaseCustomTabActivityModule(intentDataProvider, startupTabPreloader, - nightModeController, intentIgnoringCriterion, topUiThemeColorProvider, - new FakeDefaultBrowserProviderImpl())); + private final TestRule mModuleOverridesRule = + new ModuleOverridesRule().setOverride(BaseCustomTabActivityModule.Factory.class, + (BrowserServicesIntentDataProvider intentDataProvider, + CustomTabNightModeStateController nightModeController, + CustomTabIntentHandler.IntentIgnoringCriterion intentIgnoringCriterion, + TopUiThemeColorProvider topUiThemeColorProvider, + DefaultBrowserProviderImpl customTabDefaultBrowserProvider) + -> new BaseCustomTabActivityModule(intentDataProvider, + nightModeController, intentIgnoringCriterion, + topUiThemeColorProvider, new FakeDefaultBrowserProviderImpl())); @Rule public RuleChain mRuleChain = RuleChain.emptyRuleChain()
diff --git a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityContentTestEnvironment.java b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityContentTestEnvironment.java index dbc81ba7..220fc6c1 100644 --- a/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityContentTestEnvironment.java +++ b/chrome/android/junit/src/org/chromium/chrome/browser/customtabs/content/CustomTabActivityContentTestEnvironment.java
@@ -6,7 +6,6 @@ import static org.mockito.ArgumentMatchers.any; import static org.mockito.ArgumentMatchers.anyBoolean; -import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; @@ -50,7 +49,6 @@ import org.chromium.chrome.browser.flags.ActivityType; import org.chromium.chrome.browser.fullscreen.FullscreenManager; import org.chromium.chrome.browser.init.ChromeBrowserInitializer; -import org.chromium.chrome.browser.init.StartupTabPreloader; import org.chromium.chrome.browser.lifecycle.ActivityLifecycleDispatcher; import org.chromium.chrome.browser.password_manager.PasswordChangeSuccessTrackerBridge; import org.chromium.chrome.browser.tab.Tab; @@ -105,7 +103,6 @@ @Mock public ToolbarManager toolbarManager; @Mock public ChromeBrowserInitializer browserInitializer; @Mock public FullscreenManager fullscreenManager; - @Mock public StartupTabPreloader startupTabPreloader; @Mock public CustomTabIncognitoManager customTabIncognitoManager; @Mock public TabModelInitializer tabModelInitializer; // clang-format on @@ -150,7 +147,6 @@ // Default setup is toolbarManager doesn't consume back press event. when(toolbarManager.back()).thenReturn(false); - when(startupTabPreloader.takeTabIfMatchingOrDestroy(any(), anyInt())).thenReturn(null); when(reparentingTaskProvider.get(any())).thenReturn(reparentingTask); when(activityTabProvider.addObserver(activityTabObserverCaptor.capture())).thenReturn(null); when(intentDataProvider.getColorProvider()).thenReturn(colorProvider); @@ -178,7 +174,7 @@ connection, intentDataProvider, activityTabProvider, tabObserverRegistrar, () -> compositorViewHolder, lifecycleDispatcher, warmupManager, tabPersistencePolicy, tabFactory, () -> customTabObserver, webContentsFactory, - navigationEventObserver, tabProvider, startupTabPreloader, reparentingTaskProvider, + navigationEventObserver, tabProvider, reparentingTaskProvider, () -> customTabIncognitoManager, () -> realAsyncTabParamsManager, () -> activity.getSavedInstanceState(), activity.getWindowAndroid(), tabModelInitializer);
diff --git a/chrome/app/chromeos_strings.grdp b/chrome/app/chromeos_strings.grdp index 0722cae..87a01366 100644 --- a/chrome/app/chromeos_strings.grdp +++ b/chrome/app/chromeos_strings.grdp
@@ -5625,6 +5625,9 @@ <message name="IDS_ACCOUNT_MANAGER_DIALOG_ADD_ACCOUNT_LABEL" desc="Label of the Add account button on Account picker screen."> Add Google Account </message> + <message name="IDS_ACCOUNT_MANAGER_DIALOG_ADD_SCHOOL_ACCOUNT_LABEL" desc="Label of the button to add a school/EDU account on Account picker screen."> + Add school account + </message> <message name="IDS_ACCOUNT_MANAGER_DIALOG_WELCOME_CHECKBOX" desc="Checkbox text for the Welcome screen in ChromeOS 'Add account' dialog. If user checks this checkbox, this screen will not be shown the next time they open the dialog."> Don't remind me next time </message>
diff --git a/chrome/app/chromeos_strings_grdp/IDS_ACCOUNT_MANAGER_DIALOG_ADD_SCHOOL_ACCOUNT_LABEL.png.sha1 b/chrome/app/chromeos_strings_grdp/IDS_ACCOUNT_MANAGER_DIALOG_ADD_SCHOOL_ACCOUNT_LABEL.png.sha1 new file mode 100644 index 0000000..4945b74 --- /dev/null +++ b/chrome/app/chromeos_strings_grdp/IDS_ACCOUNT_MANAGER_DIALOG_ADD_SCHOOL_ACCOUNT_LABEL.png.sha1
@@ -0,0 +1 @@ +a4ba9bcb44572b660c6253f82bcb052c9892216e \ No newline at end of file
diff --git a/chrome/app/generated_resources.grd b/chrome/app/generated_resources.grd index 5a1c38d..e51e9f4 100644 --- a/chrome/app/generated_resources.grd +++ b/chrome/app/generated_resources.grd
@@ -13082,6 +13082,9 @@ <message name="IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_DESCRIPTION" translateable="false"> During trials, Chrome is exploring ways to limit spam, fraud, and sharing between sites. Chrome also <ph name="ESTIMATE_INTERESTS_LINK">$1<ex>estimates your interests</ex></ph> that sites can use to show you ads. You can manage your interests in settings. </message> + <message name="IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_SETTINGS_LINK" translateable="false"> + Go to settings + </message> <message name="IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_DESCRIPTION_ESTIMATES_INTERESTS_LINK" translateable="false"> estimates your interests </message>
diff --git a/chrome/browser/about_flags.cc b/chrome/browser/about_flags.cc index ec10a086..0f98bd2 100644 --- a/chrome/browser/about_flags.cc +++ b/chrome/browser/about_flags.cc
@@ -7467,11 +7467,12 @@ {"incognito-screenshot", flag_descriptions::kIncognitoScreenshotName, flag_descriptions::kIncognitoScreenshotDescription, kOsAndroid, FEATURE_VALUE_TYPE(chrome::android::kIncognitoScreenshot)}, -#endif + {"incognito-downloads-warning", flag_descriptions::kIncognitoDownloadsWarningName, - flag_descriptions::kIncognitoDownloadsWarningDescription, kOsAll, + flag_descriptions::kIncognitoDownloadsWarningDescription, kOsAndroid, FEATURE_VALUE_TYPE(features::kIncognitoDownloadsWarning)}, +#endif {"incognito-ntp-revamp", flag_descriptions::kIncognitoNtpRevampName, flag_descriptions::kIncognitoNtpRevampDescription, kOsAll,
diff --git a/chrome/browser/apps/app_service/menu_util.cc b/chrome/browser/apps/app_service/menu_util.cc index 68b973cf..7e65c199 100644 --- a/chrome/browser/apps/app_service/menu_util.cc +++ b/chrome/browser/apps/app_service/menu_util.cc
@@ -231,9 +231,9 @@ } apps::mojom::MenuType MenuTypeFromString(base::StringPiece menu_type) { - if (base::LowerCaseEqualsASCII(menu_type, "shelf")) + if (base::EqualsCaseInsensitiveASCII(menu_type, "shelf")) return apps::mojom::MenuType::kShelf; - if (base::LowerCaseEqualsASCII(menu_type, "applist")) + if (base::EqualsCaseInsensitiveASCII(menu_type, "applist")) return apps::mojom::MenuType::kAppList; return apps::mojom::MenuType::kShelf; }
diff --git a/chrome/browser/ash/arc/fileapi/arc_documents_provider_root.h b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root.h index 6d80ceda..f3ad0b10 100644 --- a/chrome/browser/ash/arc/fileapi/arc_documents_provider_root.h +++ b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root.h
@@ -221,6 +221,9 @@ void GetRootSize(GetRootSizeCallback callback); private: + friend class ArcDocumentsProviderRootMapTest; + FRIEND_TEST_ALL_PREFIXES(ArcDocumentsProviderRootMapTest, Lookup); + struct WatcherData; struct DirectoryCache;
diff --git a/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.cc b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.cc index 961e6c8f..0b8b699 100644 --- a/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.cc +++ b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.cc
@@ -5,6 +5,8 @@ #include "chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.h" #include "ash/components/arc/session/arc_service_manager.h" +#include "ash/constants/ash_features.h" +#include "base/feature_list.h" #include "chrome/browser/ash/arc/fileapi/arc_documents_provider_root.h" #include "chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map_factory.h" #include "chrome/browser/ash/arc/fileapi/arc_documents_provider_util.h" @@ -26,19 +28,18 @@ const char* authority; const char* root_document_id; const char* root_id; - bool read_only; }; // List of documents providers for media views. constexpr DocumentsProviderSpec kDocumentsProviderAllowlist[] = { {kMediaDocumentsProviderAuthority, kImagesRootDocumentId, - kImagesRootDocumentId, true}, + kImagesRootDocumentId}, {kMediaDocumentsProviderAuthority, kVideosRootDocumentId, - kVideosRootDocumentId, true}, + kVideosRootDocumentId}, {kMediaDocumentsProviderAuthority, kAudioRootDocumentId, - kAudioRootDocumentId, true}, + kAudioRootDocumentId}, {kMediaDocumentsProviderAuthority, kDocumentsRootDocumentId, - kDocumentsRootDocumentId, true}, + kDocumentsRootDocumentId}, }; } // namespace @@ -55,6 +56,13 @@ return GetForBrowserContext(ArcServiceManager::Get()->browser_context()); } +// static +// TODO(crbug.com/1327496): can be removed once this flag is on by default. +bool ArcDocumentsProviderRootMap::IsDocumentProviderRootReadOnly() { + // All roots are read-only unless this flag is on. + return !base::FeatureList::IsEnabled(chromeos::features::kFiltersInRecentsV2); +} + ArcDocumentsProviderRootMap::ArcDocumentsProviderRootMap(Profile* profile) : runner_(ArcFileSystemOperationRunner::GetForBrowserContext(profile)) { DCHECK_CURRENTLY_ON(BrowserThread::UI); @@ -62,9 +70,10 @@ // in ArcDocumentsProviderRootMapFactory. DCHECK(runner_); + const bool read_only = IsDocumentProviderRootReadOnly(); for (const auto& spec : kDocumentsProviderAllowlist) { - RegisterRoot(spec.authority, spec.root_document_id, spec.root_id, - spec.read_only, {}); + RegisterRoot(spec.authority, spec.root_document_id, spec.root_id, read_only, + {}); } } @@ -114,7 +123,7 @@ Key key(authority, root_document_id); if (map_.find(key) != map_.end()) { VLOG(1) << "Trying to register (" << authority << ", " << root_document_id - << ") which is already regisered."; + << ") which is already registered."; return; } map_.emplace(key, std::make_unique<ArcDocumentsProviderRoot>(
diff --git a/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.h b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.h index b8d03c3..919314c 100644 --- a/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.h +++ b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map.h
@@ -52,6 +52,9 @@ // its delegates. static ArcDocumentsProviderRootMap* GetForArcBrowserContext(); + // Checks if a given document provider root is read only or not. + static bool IsDocumentProviderRootReadOnly(); + // Looks up a root corresponding to |url|. // |path| is set to the remaining path part of |url|. // Returns nullptr if |url| is invalid or no corresponding root is registered.
diff --git a/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map_unittest.cc b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map_unittest.cc new file mode 100644 index 0000000..c434780a --- /dev/null +++ b/chrome/browser/ash/arc/fileapi/arc_documents_provider_root_map_unittest.cc
@@ -0,0 +1,147 @@ +// Copyright 2022 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/ash/arc/fileapi/arc_documents_provider_root_map.h" + +#include <memory> + +#include "ash/components/arc/session/arc_bridge_service.h" +#include "ash/components/arc/session/arc_service_manager.h" +#include "ash/components/arc/test/connection_holder_util.h" +#include "ash/components/arc/test/fake_file_system_instance.h" +#include "ash/constants/ash_features.h" +#include "base/bind.h" +#include "base/memory/raw_ptr.h" +#include "base/test/scoped_feature_list.h" +#include "chrome/browser/ash/arc/fileapi/arc_documents_provider_root.h" +#include "chrome/browser/ash/arc/fileapi/arc_file_system_operation_runner.h" +#include "chrome/browser/ash/arc/fileapi/arc_media_view_util.h" +#include "chrome/test/base/testing_profile.h" +#include "content/public/test/browser_task_environment.h" +#include "testing/gtest/include/gtest/gtest.h" + +namespace arc { +namespace { + +constexpr char kTestRootId[] = "abc_root"; + +std::unique_ptr<KeyedService> CreateFileSystemOperationRunnerForTesting( + content::BrowserContext* context) { + return ArcFileSystemOperationRunner::CreateForTesting( + context, ArcServiceManager::Get()->arc_bridge_service()); +} + +} // namespace + +class ArcDocumentsProviderRootMapTest : public testing::Test { + public: + ArcDocumentsProviderRootMapTest() = default; + ArcDocumentsProviderRootMapTest(const ArcDocumentsProviderRootMapTest&) = + delete; + ArcDocumentsProviderRootMapTest& operator=( + const ArcDocumentsProviderRootMapTest&) = delete; + ~ArcDocumentsProviderRootMapTest() override = default; + + protected: + void SetUp() override { + profile_ = std::make_unique<TestingProfile>(); + SetUpARC(); + arc_documents_provider_root_map_ = + ArcDocumentsProviderRootMap::GetForBrowserContext(profile_.get()); + } + + void TearDown() override { + arc_documents_provider_root_map_->Shutdown(); + TearDownARC(); + profile_.reset(); + } + + ArcDocumentsProviderRootMap* GetRootMap() const { + return arc_documents_provider_root_map_.get(); + } + + private: + void SetUpARC() { + arc_service_manager_ = std::make_unique<ArcServiceManager>(); + arc_service_manager_->set_browser_context(profile_.get()); + ArcFileSystemOperationRunner::GetFactory()->SetTestingFactoryAndUse( + profile_.get(), + base::BindRepeating(&CreateFileSystemOperationRunnerForTesting)); + arc_service_manager_->arc_bridge_service()->file_system()->SetInstance( + &fake_file_system_); + WaitForInstanceReady( + arc_service_manager_->arc_bridge_service()->file_system()); + ASSERT_TRUE(fake_file_system_.InitCalled()); + } + + void TearDownARC() { + arc_service_manager_->arc_bridge_service()->file_system()->CloseInstance( + &fake_file_system_); + } + + content::BrowserTaskEnvironment task_environment_; + std::unique_ptr<TestingProfile> profile_; + FakeFileSystemInstance fake_file_system_; + std::unique_ptr<ArcServiceManager> arc_service_manager_; + raw_ptr<ArcDocumentsProviderRootMap> arc_documents_provider_root_map_; +}; + +TEST_F(ArcDocumentsProviderRootMapTest, Lookup) { + ArcDocumentsProviderRoot* images_root = GetRootMap()->Lookup( + kMediaDocumentsProviderAuthority, kImagesRootDocumentId); + EXPECT_EQ(images_root->authority_, kMediaDocumentsProviderAuthority); + EXPECT_EQ(images_root->root_id_, kImagesRootDocumentId); + ArcDocumentsProviderRoot* audio_root = GetRootMap()->Lookup( + kMediaDocumentsProviderAuthority, kAudioRootDocumentId); + EXPECT_EQ(audio_root->authority_, kMediaDocumentsProviderAuthority); + EXPECT_EQ(audio_root->root_id_, kAudioRootDocumentId); + ArcDocumentsProviderRoot* videos_root = GetRootMap()->Lookup( + kMediaDocumentsProviderAuthority, kVideosRootDocumentId); + EXPECT_EQ(videos_root->authority_, kMediaDocumentsProviderAuthority); + EXPECT_EQ(videos_root->root_id_, kVideosRootDocumentId); + ArcDocumentsProviderRoot* documents_root = GetRootMap()->Lookup( + kMediaDocumentsProviderAuthority, kDocumentsRootDocumentId); + EXPECT_EQ(documents_root->authority_, kMediaDocumentsProviderAuthority); + EXPECT_EQ(documents_root->root_id_, kDocumentsRootDocumentId); + + EXPECT_EQ(GetRootMap()->Lookup(kMediaDocumentsProviderAuthority, kTestRootId), + nullptr); +} + +TEST_F(ArcDocumentsProviderRootMapTest, RegisterRoot) { + EXPECT_EQ(GetRootMap()->Lookup(kMediaDocumentsProviderAuthority, kTestRootId), + nullptr); + GetRootMap()->RegisterRoot(kMediaDocumentsProviderAuthority, kTestRootId, + kTestRootId, false, {}); + EXPECT_NE(GetRootMap()->Lookup(kMediaDocumentsProviderAuthority, kTestRootId), + nullptr); +} + +TEST_F(ArcDocumentsProviderRootMapTest, UnregisterRoot) { + GetRootMap()->RegisterRoot(kMediaDocumentsProviderAuthority, kTestRootId, + kTestRootId, true, {}); + EXPECT_NE(GetRootMap()->Lookup(kMediaDocumentsProviderAuthority, kTestRootId), + nullptr); + GetRootMap()->UnregisterRoot(kMediaDocumentsProviderAuthority, kTestRootId); + EXPECT_EQ(GetRootMap()->Lookup(kMediaDocumentsProviderAuthority, kTestRootId), + nullptr); +} + +TEST(ArcDocumentsProviderRootMapStaticTest, + IsDocumentProviderRootReadOnly_FeatureEnabled) { + base::test::ScopedFeatureList feature_list; + feature_list.InitWithFeatures({chromeos::features::kFiltersInRecentsV2}, {}); + + EXPECT_FALSE(ArcDocumentsProviderRootMap::IsDocumentProviderRootReadOnly()); +} + +TEST(ArcDocumentsProviderRootMapStaticTest, + IsDocumentProviderRootReadOnly_FeatureDisabled) { + base::test::ScopedFeatureList feature_list; + feature_list.InitWithFeatures({}, {chromeos::features::kFiltersInRecentsV2}); + + EXPECT_TRUE(ArcDocumentsProviderRootMap::IsDocumentProviderRootReadOnly()); +} + +} // namespace arc
diff --git a/chrome/browser/ash/borealis/borealis_task.cc b/chrome/browser/ash/borealis/borealis_task.cc index df36723..b3b10b2 100644 --- a/chrome/browser/ash/borealis/borealis_task.cc +++ b/chrome/browser/ash/borealis/borealis_task.cc
@@ -251,13 +251,13 @@ if (external_disk) { base::ScopedFD fd(external_disk->TakePlatformFile()); request.add_fds(vm_tools::concierge::StartVmRequest::STORAGE); - ash::ConciergeClient::Get()->StartTerminaVmWithFd( + ash::ConciergeClient::Get()->StartVmWithFd( std::move(fd), std::move(request), base::BindOnce(&StartBorealisVm::OnStartBorealisVm, weak_factory_.GetWeakPtr(), context)); return; } - ash::ConciergeClient::Get()->StartTerminaVm( + ash::ConciergeClient::Get()->StartVm( std::move(request), base::BindOnce(&StartBorealisVm::OnStartBorealisVm, weak_factory_.GetWeakPtr(), context)); }
diff --git a/chrome/browser/ash/borealis/borealis_task_unittest.cc b/chrome/browser/ash/borealis/borealis_task_unittest.cc index 65bce081..18ec382 100644 --- a/chrome/browser/ash/borealis/borealis_task_unittest.cc +++ b/chrome/browser/ash/borealis/borealis_task_unittest.cc
@@ -157,7 +157,7 @@ task.Run(context_.get(), callback_factory.BindOnce()); task_environment_.RunUntilIdle(); - EXPECT_GE(FakeConciergeClient()->start_termina_vm_call_count(), 1); + EXPECT_GE(FakeConciergeClient()->start_vm_call_count(), 1); } TEST_F(BorealisTasksTest, @@ -173,7 +173,7 @@ task.Run(context_.get(), callback_factory.BindOnce()); task_environment_.RunUntilIdle(); - EXPECT_GE(FakeConciergeClient()->start_termina_vm_call_count(), 1); + EXPECT_GE(FakeConciergeClient()->start_vm_call_count(), 1); } TEST_F(BorealisTasksTest, @@ -343,7 +343,7 @@ task.Run(context_.get(), callback_factory.BindOnce()); task_environment_.RunUntilIdle(); - EXPECT_GE(FakeConciergeClient()->start_termina_vm_call_count(), 1); + EXPECT_GE(FakeConciergeClient()->start_vm_call_count(), 1); } INSTANTIATE_TEST_SUITE_P(
diff --git a/chrome/browser/ash/crostini/crostini_installer_unittest.cc b/chrome/browser/ash/crostini/crostini_installer_unittest.cc index 841dce80..c938284 100644 --- a/chrome/browser/ash/crostini/crostini_installer_unittest.cc +++ b/chrome/browser/ash/crostini/crostini_installer_unittest.cc
@@ -68,11 +68,11 @@ explicit WaitingFakeConciergeClient(ash::FakeCiceroneClient* client) : ash::FakeConciergeClient(client) {} - void StartTerminaVm( + void StartVm( const vm_tools::concierge::StartVmRequest& request, chromeos::DBusMethodCallback<vm_tools::concierge::StartVmResponse> callback) override { - ash::FakeConciergeClient::StartTerminaVm(request, std::move(callback)); + ash::FakeConciergeClient::StartVm(request, std::move(callback)); if (quit_closure_) { base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE, std::move(quit_closure_)); @@ -83,7 +83,7 @@ base::RunLoop loop; quit_closure_ = loop.QuitClosure(); loop.Run(); - EXPECT_GE(start_termina_vm_call_count(), 1); + EXPECT_GE(start_vm_call_count(), 1); } private:
diff --git a/chrome/browser/ash/crostini/crostini_manager.cc b/chrome/browser/ash/crostini/crostini_manager.cc index 853ef5bd..f1a3bcb 100644 --- a/chrome/browser/ash/crostini/crostini_manager.cc +++ b/chrome/browser/ash/crostini/crostini_manager.cc
@@ -1446,7 +1446,7 @@ disk_image->set_writable(true); disk_image->set_do_mount(false); - GetConciergeClient()->StartTerminaVm( + GetConciergeClient()->StartVm( request, base::BindOnce(&CrostiniManager::OnStartTerminaVm, weak_ptr_factory_.GetWeakPtr(), request.name(), std::move(callback)));
diff --git a/chrome/browser/ash/crostini/crostini_manager.h b/chrome/browser/ash/crostini/crostini_manager.h index a14d117..a09bd61 100644 --- a/chrome/browser/ash/crostini/crostini_manager.h +++ b/chrome/browser/ash/crostini/crostini_manager.h
@@ -681,7 +681,7 @@ ListVmDisksCallback callback, absl::optional<vm_tools::concierge::ListVmDisksResponse> response); - // Callback for ConciergeClient::StartTerminaVm. Called after the Concierge + // Callback for ConciergeClient::StartVm. Called after the Concierge // service method finishes. Updates running containers list then calls the // |callback| if the container has already been started, otherwise passes the // callback to OnStartTremplin.
diff --git a/chrome/browser/ash/crostini/crostini_manager_unittest.cc b/chrome/browser/ash/crostini/crostini_manager_unittest.cc index 26e9b99..24fb20a4 100644 --- a/chrome/browser/ash/crostini/crostini_manager_unittest.cc +++ b/chrome/browser/ash/crostini/crostini_manager_unittest.cc
@@ -363,7 +363,7 @@ "", disk_path, {}, 0, base::BindOnce(&ExpectFailure, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); } TEST_F(CrostiniManagerTest, StartTerminaVmAnomalyDetectorNotConnectedError) { @@ -376,7 +376,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectFailure, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); } TEST_F(CrostiniManagerTest, StartTerminaVmDiskPathError) { @@ -386,7 +386,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectFailure, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); } TEST_F(CrostiniManagerTest, StartTerminaVmPowerwashRequestError) { @@ -416,7 +416,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectFailure, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); auto notification = notification_service.GetNotification( "crostini_powerwash_request_instead_of_run"); @@ -453,7 +453,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectFailure, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); auto notification = notification_service.GetNotification( "crostini_powerwash_request_cryptohome_error"); @@ -474,7 +474,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectFailure, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); histogram_tester.ExpectUniqueSample(kCrostiniCorruptionHistogram, CorruptionStates::MOUNT_FAILED, 1); } @@ -494,7 +494,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectSuccess, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); histogram_tester.ExpectUniqueSample(kCrostiniCorruptionHistogram, CorruptionStates::MOUNT_ROLLED_BACK, 1); } @@ -508,7 +508,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectSuccess, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); histogram_tester.ExpectTotalCount(kCrostiniCorruptionHistogram, 0); } @@ -528,7 +528,7 @@ base::BindOnce(&ExpectSuccess, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); auto notification = notification_service.GetNotification("crostini_low_disk"); EXPECT_NE(absl::nullopt, notification); } @@ -550,7 +550,7 @@ base::BindOnce(&ExpectSuccess, run_loop()->QuitClosure())); run_loop()->Run(); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); auto notification = notification_service.GetNotification("crostini_low_disk"); EXPECT_EQ(absl::nullopt, notification); } @@ -818,7 +818,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_EQ(1, restart_crostini_callback_count_); absl::optional<ContainerInfo> container_info = @@ -857,7 +857,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_EQ(1, restart_crostini_callback_count_); absl::optional<ContainerInfo> container_info = @@ -886,7 +886,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_EQ(1, restart_crostini_callback_count_); absl::optional<ContainerInfo> container_info = @@ -906,7 +906,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_EQ(1, restart_crostini_callback_count_); absl::optional<ContainerInfo> container_info = @@ -926,7 +926,7 @@ EXPECT_FALSE( profile_->GetPrefs()->GetBoolean(crostini::prefs::kCrostiniEnabled)); EXPECT_EQ(fake_concierge_client_->create_disk_image_call_count(), 0); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); } @@ -958,7 +958,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); histogram_tester_.ExpectTotalCount( @@ -980,7 +980,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_EQ(fake_concierge_client_->start_termina_vm_call_count(), 0); + EXPECT_EQ(fake_concierge_client_->start_vm_call_count(), 0); ExpectCrostiniRestartResult(CrostiniResult::CREATE_DISK_IMAGE_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1012,7 +1012,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); } @@ -1028,7 +1028,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::START_TERMINA_VM_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1047,7 +1047,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::START_TERMINA_VM_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1061,7 +1061,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); } @@ -1077,7 +1077,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::START_LXD_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1094,7 +1094,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::START_LXD_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1108,7 +1108,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); } @@ -1138,7 +1138,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::CREATE_CONTAINER_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1166,7 +1166,7 @@ ASSERT_EQ(1, restart_crostini_callback_count_); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::CREATE_CONTAINER_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1183,7 +1183,7 @@ run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_EQ(0, restart_crostini_callback_count_); ExpectRestarterUmaCount(1); } @@ -1197,7 +1197,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); } @@ -1211,7 +1211,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); } @@ -1227,7 +1227,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::SETUP_CONTAINER_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1257,7 +1257,7 @@ task_environment_.FastForwardBy(kLongTime); task_environment_.RunUntilIdle(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::START_CONTAINER_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1287,7 +1287,7 @@ ASSERT_EQ(1, restart_crostini_callback_count_); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::START_CONTAINER_TIMED_OUT); ExpectRestarterUmaCount(1); } @@ -1301,7 +1301,7 @@ this); run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); ExpectCrostiniRestartResult(CrostiniResult::RESTART_ABORTED); ExpectRestarterUmaCount(1); } @@ -1356,7 +1356,7 @@ run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_EQ(3, restart_crostini_callback_count_); EXPECT_FALSE(crostini_manager()->IsRestartPending(id1)); @@ -1386,7 +1386,7 @@ run_loop()->Run(); - EXPECT_EQ(1, fake_concierge_client_->start_termina_vm_call_count()); + EXPECT_EQ(1, fake_concierge_client_->start_vm_call_count()); EXPECT_FALSE(crostini_manager()->IsRestartPending(id1)); EXPECT_FALSE(crostini_manager()->IsRestartPending(id2)); EXPECT_FALSE(crostini_manager()->IsRestartPending(id3)); @@ -1402,7 +1402,7 @@ run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); // Mount only performed for termina/penguin. EXPECT_EQ(1, restart_crostini_callback_count_); @@ -1418,7 +1418,7 @@ kVmName, disk_path, {}, 0, base::BindOnce(&ExpectSuccess, run_loop2.QuitClosure())); run_loop2.Run(); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_TRUE(crostini_manager()->IsVmRunning(kVmName)); EXPECT_FALSE(crostini_manager()->GetContainerInfo(container_id())); ExpectRestarterUmaCount(1); @@ -1881,7 +1881,7 @@ run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_TRUE( fake_concierge_client_->get_vm_enterprise_reporting_info_call_count()); EXPECT_EQ(1, restart_crostini_callback_count_); @@ -1907,7 +1907,7 @@ run_loop()->Run(); EXPECT_GE(fake_concierge_client_->create_disk_image_call_count(), 1); - EXPECT_GE(fake_concierge_client_->start_termina_vm_call_count(), 1); + EXPECT_GE(fake_concierge_client_->start_vm_call_count(), 1); EXPECT_TRUE( fake_concierge_client_->get_vm_enterprise_reporting_info_call_count()); EXPECT_EQ(1, restart_crostini_callback_count_);
diff --git a/chrome/browser/ash/file_manager/delete_io_task.cc b/chrome/browser/ash/file_manager/delete_io_task.cc index 65f1f69..af5d4b31 100644 --- a/chrome/browser/ash/file_manager/delete_io_task.cc +++ b/chrome/browser/ash/file_manager/delete_io_task.cc
@@ -9,6 +9,7 @@ #include "base/callback.h" #include "base/files/file.h" #include "base/threading/sequenced_task_runner_handle.h" +#include "chrome/browser/ash/file_manager/io_task_util.h" #include "content/public/browser/browser_task_traits.h" #include "content/public/browser/browser_thread.h" #include "google_apis/common/task_util.h" @@ -18,20 +19,6 @@ namespace file_manager { namespace io_task { -namespace { - -// Starts the delete operation via FileSystemOperationRunner. -storage::FileSystemOperationRunner::OperationID StartDeleteOnIOThread( - scoped_refptr<storage::FileSystemContext> file_system_context, - const storage::FileSystemURL& file_url, - storage::FileSystemOperation::StatusCallback status_callback) { - DCHECK_CURRENTLY_ON(content::BrowserThread::IO); - return file_system_context->operation_runner()->Remove( - file_url, /*recursive=*/true, std::move(status_callback)); -} - -} // namespace - DeleteIOTask::DeleteIOTask( std::vector<storage::FileSystemURL> file_urls, scoped_refptr<storage::FileSystemContext> file_system_context)
diff --git a/chrome/browser/ash/file_manager/file_manager_browsertest_base.cc b/chrome/browser/ash/file_manager/file_manager_browsertest_base.cc index 2a62f15c..5950058 100644 --- a/chrome/browser/ash/file_manager/file_manager_browsertest_base.cc +++ b/chrome/browser/ash/file_manager/file_manager_browsertest_base.cc
@@ -3003,6 +3003,11 @@ return; } + if (name == "isFiltersInRecentsEnabledV2") { + *output = options.enable_filters_in_recents_v2 ? "true" : "false"; + return; + } + if (name == "switchLanguage") { const std::string* language = value.FindStringKey("language"); ASSERT_TRUE(language);
diff --git a/chrome/browser/ash/file_manager/file_manager_jstest.cc b/chrome/browser/ash/file_manager/file_manager_jstest.cc index 260742d1..2394711 100644 --- a/chrome/browser/ash/file_manager/file_manager_jstest.cc +++ b/chrome/browser/ash/file_manager/file_manager_jstest.cc
@@ -69,6 +69,10 @@ RunTestURL("foreground/js/directory_contents_unittest.m_gen.html"); } +IN_PROC_BROWSER_TEST_F(FileManagerJsTest, DirectoryModelTest) { + RunTestURL("foreground/js/directory_model_unittest.m_gen.html"); +} + IN_PROC_BROWSER_TEST_F(FileManagerJsTest, DirectoryTreeTest) { RunTestURL("foreground/js/ui/directory_tree_unittest.m_gen.html"); }
diff --git a/chrome/browser/ash/file_manager/io_task_util.cc b/chrome/browser/ash/file_manager/io_task_util.cc index 6b18599..00df4b8 100644 --- a/chrome/browser/ash/file_manager/io_task_util.cc +++ b/chrome/browser/ash/file_manager/io_task_util.cc
@@ -37,5 +37,14 @@ std::move(callback)); } +storage::FileSystemOperationRunner::OperationID StartDeleteOnIOThread( + scoped_refptr<storage::FileSystemContext> file_system_context, + const storage::FileSystemURL& file_url, + storage::FileSystemOperation::StatusCallback status_callback) { + DCHECK_CURRENTLY_ON(content::BrowserThread::IO); + return file_system_context->operation_runner()->Remove( + file_url, /*recursive=*/true, std::move(status_callback)); +} + } // namespace io_task } // namespace file_manager
diff --git a/chrome/browser/ash/file_manager/io_task_util.h b/chrome/browser/ash/file_manager/io_task_util.h index 93293ce2..36c113d 100644 --- a/chrome/browser/ash/file_manager/io_task_util.h +++ b/chrome/browser/ash/file_manager/io_task_util.h
@@ -31,6 +31,12 @@ int fields, storage::FileSystemOperation::GetMetadataCallback callback); +// Starts the delete operation via FileSystemOperationRunner. +storage::FileSystemOperationRunner::OperationID StartDeleteOnIOThread( + scoped_refptr<storage::FileSystemContext> file_system_context, + const storage::FileSystemURL& file_url, + storage::FileSystemOperation::StatusCallback status_callback); + } // namespace io_task } // namespace file_manager
diff --git a/chrome/browser/ash/file_manager/trash_io_task.cc b/chrome/browser/ash/file_manager/trash_io_task.cc index 69f02ac7..4bec5fa 100644 --- a/chrome/browser/ash/file_manager/trash_io_task.cc +++ b/chrome/browser/ash/file_manager/trash_io_task.cc
@@ -393,22 +393,81 @@ return; } - // TODO(b/231250202): Move the file to trash but on error remove the metadata - // file. - TrashComplete(source_idx, output_idx, base::File::Error::FILE_OK); + last_metadata_url_ = progress_.outputs[output_idx].url; + progress_.outputs[output_idx].error = base::File::FILE_OK; + TrashFile(source_idx, output_idx, destination_url); +} + +void TrashIOTask::TrashFile(size_t source_idx, + size_t output_idx, + const storage::FileSystemURL& destination_url) { + DCHECK(source_idx < progress_.sources.size()); + DCHECK(output_idx < progress_.outputs.size()); + progress_.outputs.emplace_back(destination_url, absl::nullopt); + + last_progress_size_ = 0; + + const storage::FileSystemURL& source_url = progress_.sources[source_idx].url; + + // File browsers generally default to preserving mtimes on copy/move so we + // should do the same. + storage::FileSystemOperation::CopyOrMoveOptionSet options( + storage::FileSystemOperation::CopyOrMoveOption::kPreserveLastModified, + storage::FileSystemOperation::CopyOrMoveOption:: + kRemovePartiallyCopiedFilesOnError); + + auto complete_callback = + base::BindPostTask(base::SequencedTaskRunnerHandle::Get(), + base::BindOnce(&TrashIOTask::TrashComplete, + weak_ptr_factory_.GetWeakPtr(), + source_idx, output_idx + 1)); + + // For move operations that occur on the same file system, the progress + // callback is never invoked. + content::GetIOThreadTaskRunner({})->PostTaskAndReplyWithResult( + FROM_HERE, + base::BindOnce(&StartMoveOnIOThread, file_system_context_, source_url, + destination_url, options, base::DoNothing(), + std::move(complete_callback)), + base::BindOnce(&TrashIOTask::SetCurrentOperationID, + weak_ptr_factory_.GetWeakPtr())); +} + +void TrashIOTask::OnMoveComplete(size_t source_idx, + size_t output_idx, + base::File::Error error) { + DCHECK(source_idx < progress_.sources.size()); + DCHECK(output_idx < progress_.outputs.size()); + if (error != base::File::FILE_OK) { + LOG(ERROR) << "Failed to move the file to trash folder: " << error; + auto complete_callback = base::BindPostTask( + base::SequencedTaskRunnerHandle::Get(), + base::BindOnce(&TrashIOTask::TrashComplete, + weak_ptr_factory_.GetWeakPtr(), source_idx, output_idx)); + + content::GetIOThreadTaskRunner({})->PostTaskAndReplyWithResult( + FROM_HERE, + base::BindOnce(&StartDeleteOnIOThread, file_system_context_, + last_metadata_url_, std::move(complete_callback)), + base::BindOnce(&TrashIOTask::SetCurrentOperationID, + weak_ptr_factory_.GetWeakPtr())); + return; + } + + TrashComplete(source_idx, output_idx, error); } void TrashIOTask::TrashComplete(size_t source_idx, size_t output_idx, base::File::Error error) { DCHECK(source_idx < progress_.sources.size()); - DCHECK(source_idx < trash_entries_.size()); DCHECK(output_idx < progress_.outputs.size()); operation_id_.reset(); progress_.sources[source_idx].error = error; progress_.outputs[output_idx].error = error; progress_.bytes_transferred += - trash_entries_[source_idx].trash_info_contents.size(); + trash_entries_[source_idx].trash_info_contents.size() + + (trash_entries_[source_idx].source_file_size - last_progress_size_); if (source_idx < progress_.sources.size() - 1) { progress_callback_.Run(progress_);
diff --git a/chrome/browser/ash/file_manager/trash_io_task.h b/chrome/browser/ash/file_manager/trash_io_task.h index d7c1eee..1ec8a1b 100644 --- a/chrome/browser/ash/file_manager/trash_io_task.h +++ b/chrome/browser/ash/file_manager/trash_io_task.h
@@ -12,7 +12,9 @@ #include "base/memory/raw_ptr.h" #include "base/memory/weak_ptr.h" #include "base/time/time.h" +#include "chrome/browser/ash/file_manager/file_manager_copy_or_move_hook_delegate.h" #include "chrome/browser/ash/file_manager/io_task.h" +#include "chrome/browser/ash/file_manager/speedometer.h" #include "storage/browser/file_system/file_system_context.h" #include "storage/browser/file_system/file_system_operation_runner.h" #include "storage/browser/file_system/file_system_url.h" @@ -163,6 +165,14 @@ void TrashComplete(size_t source_idx, size_t output_idx, base::File::Error error); + // Move a file from it's location to the final .Trash/files destination with + // a unique name determined by `GenerateDestinationURL`. + void TrashFile(size_t source_idx, + size_t output_idx, + const storage::FileSystemURL& destination_url); + void OnMoveComplete(size_t source_idx, + size_t output_idx, + base::File::Error error); raw_ptr<Profile> profile_; @@ -176,6 +186,18 @@ // with the underlying locations of the .Trash/{files,info} directories. FreeSpaceMap free_space_map_; + // Stores the size reported by the last progress update so we can compute the + // delta on the next progress update. + int64_t last_progress_size_; + + // Stores the last url for the most recently updated metadata file, in the + // event of a move failure this file is removed. + storage::FileSystemURL last_metadata_url_; + + // Speedometer for this operation, used to calculate the remaining time to + // finish the operation. + Speedometer speedometer_; + // Stores the id of the operations currently behind undertaken by Trash, // including directory creation. Enables cancelling an inflight operation. absl::optional<storage::FileSystemOperationRunner::OperationID> operation_id_;
diff --git a/chrome/browser/ash/file_manager/trash_io_task_unittest.cc b/chrome/browser/ash/file_manager/trash_io_task_unittest.cc index adef0f6..2f91102 100644 --- a/chrome/browser/ash/file_manager/trash_io_task_unittest.cc +++ b/chrome/browser/ash/file_manager/trash_io_task_unittest.cc
@@ -32,6 +32,7 @@ using ::base::test::RunClosure; using ::testing::_; +using ::testing::AnyNumber; using ::testing::ElementsAre; using ::testing::Field; using ::testing::Return; @@ -107,6 +108,11 @@ kInfoFolderName, file_name); } + const base::FilePath GenerateFilesPath(const std::string& file_name) { + return GenerateTrashPath(downloads_dir_.Append(kTrashFolderName), + kFilesFolderName, file_name); + } + const std::string CreateTrashInfoContentsFromPath( const base::FilePath& file_path) { std::string relative_restore_path = file_path.value(); @@ -271,17 +277,15 @@ // Completion callback should contain the one metadata file written with the // `total_expected_bytes` containing the size of both the file to trash and // the size of the metadata. - // TODO(b/231250202): Once trash has implemented, the `bytes_transferred` - // should be updated to the `total_expected_bytes`. EXPECT_CALL( complete_callback, Run(AllOf(Field(&ProgressStatus::state, State::kSuccess), - Field(&ProgressStatus::bytes_transferred, - file_trashinfo_contents.size()), + Field(&ProgressStatus::bytes_transferred, total_expected_bytes), Field(&ProgressStatus::total_bytes, total_expected_bytes), Field(&ProgressStatus::sources, EntryStatusUrls(source_urls)), Field(&ProgressStatus::outputs, - EntryStatusErrors(ElementsAre(base::File::FILE_OK)))))) + EntryStatusErrors(ElementsAre(base::File::FILE_OK, + base::File::FILE_OK)))))) .WillOnce(RunClosure(run_loop.QuitClosure())); { @@ -297,6 +301,7 @@ AssertTrashSetup(downloads_dir_); ExpectFileContents(GenerateInfoPath(file_name), file_trashinfo_contents); + ExpectFileContents(GenerateFilesPath(file_name), foo_contents); } TEST_F(TrashIOTaskTest, MultipleFilesInvokeProgress) { @@ -309,10 +314,9 @@ const base::FilePath file_path_2 = downloads_dir_.Append(file_name_2); const std::string file_trashinfo_contents_2 = CreateTrashInfoContentsFromPath(file_path_2); - const size_t expected_bytes_transferred = - file_trashinfo_contents_1.size() + file_trashinfo_contents_2.size(); - const size_t expected_total_bytes = - (kTestFileSize * 2) + expected_bytes_transferred; + const size_t expected_total_bytes = (kTestFileSize * 2) + + file_trashinfo_contents_1.size() + + file_trashinfo_contents_2.size(); ASSERT_TRUE(base::WriteFile(file_path_1, foo_contents)); ASSERT_TRUE(base::WriteFile(file_path_2, foo_contents)); @@ -331,28 +335,38 @@ AllOf(Field(&ProgressStatus::sources, EntryStatusUrls(source_urls)), Field(&ProgressStatus::total_bytes, expected_total_bytes)); - // Expect the `progress_callback` to be invoked after the first metadata file - // has been written with the size contents and - EXPECT_CALL( - progress_callback, - Run(AllOf(Field(&ProgressStatus::state, State::kInProgress), - Field(&ProgressStatus::bytes_transferred, - file_trashinfo_contents_1.size()), - Field(&ProgressStatus::outputs, - EntryStatusErrors(ElementsAre(base::File::FILE_OK))), - base_matcher))) - .Times(1); + // Progress callback may be called any number of times, so this expectation + // catches extra calls. + EXPECT_CALL(progress_callback, + Run(AllOf(Field(&ProgressStatus::state, State::kInProgress), + base_matcher))) + .Times(AnyNumber()); - // Expect the completion callback to be invoked after the final metadata file - // is written out. - EXPECT_CALL(complete_callback, - Run(AllOf(Field(&ProgressStatus::state, State::kSuccess), + // Expect the `progress_callback` to be invoked after the first metadata and + // trash file have been written and moved with their size in the + // `bytes_transferred`. + EXPECT_CALL(progress_callback, + Run(AllOf(Field(&ProgressStatus::state, State::kInProgress), Field(&ProgressStatus::bytes_transferred, - expected_bytes_transferred), + file_trashinfo_contents_1.size() + kTestFileSize), Field(&ProgressStatus::outputs, EntryStatusErrors(ElementsAre( base::File::FILE_OK, base::File::FILE_OK))), base_matcher))) + .Times(1); + + // Completion callback should contain 4 files successfully being written. Each + // `base::File::FILE_OK` in the outputs field corresponds to a successful + // write or move of the file and associated metadata. + EXPECT_CALL( + complete_callback, + Run(AllOf(Field(&ProgressStatus::state, State::kSuccess), + Field(&ProgressStatus::bytes_transferred, expected_total_bytes), + Field(&ProgressStatus::outputs, + EntryStatusErrors(ElementsAre( + base::File::FILE_OK, base::File::FILE_OK, + base::File::FILE_OK, base::File::FILE_OK))), + base_matcher))) .WillOnce(RunClosure(run_loop.QuitClosure())); { @@ -367,6 +381,8 @@ AssertTrashSetup(downloads_dir_); ExpectFileContents(GenerateInfoPath(file_name_1), file_trashinfo_contents_1); ExpectFileContents(GenerateInfoPath(file_name_2), file_trashinfo_contents_2); + ExpectFileContents(GenerateFilesPath(file_name_1), foo_contents); + ExpectFileContents(GenerateFilesPath(file_name_2), foo_contents); } } // namespace
diff --git a/chrome/browser/ash/file_manager/volume_manager.cc b/chrome/browser/ash/file_manager/volume_manager.cc index bff46fdb..922bb7cb 100644 --- a/chrome/browser/ash/file_manager/volume_manager.cc +++ b/chrome/browser/ash/file_manager/volume_manager.cc
@@ -416,7 +416,8 @@ arc::kMediaDocumentsProviderAuthority, root_document_id); volume->mount_condition_ = ash::disks::MOUNT_CONDITION_NONE; volume->volume_label_ = MediaViewDocumentIdToLabel(root_document_id); - volume->is_read_only_ = true; + volume->is_read_only_ = + arc::ArcDocumentsProviderRootMap::IsDocumentProviderRootReadOnly(); volume->watchable_ = false; volume->volume_id_ = arc::GetMediaViewVolumeId(root_document_id); return volume;
diff --git a/chrome/browser/ash/input_method/native_input_method_engine_unittest.cc b/chrome/browser/ash/input_method/native_input_method_engine_unittest.cc index 7a93911..4886d75 100644 --- a/chrome/browser/ash/input_method/native_input_method_engine_unittest.cc +++ b/chrome/browser/ash/input_method/native_input_method_engine_unittest.cc
@@ -740,7 +740,7 @@ // Each character in "ä½ å¥½" is three UTF-8 code units. EXPECT_CALL(mock_input_method, - OnSurroundingTextChanged(u8"ä½ å¥½", + OnSurroundingTextChanged("ä½ å¥½", /*offset=*/0, MojoEq(ime::mojom::SelectionRange( /*anchor=*/6, /*focus=*/6))));
diff --git a/chrome/browser/ash/login/enrollment/auto_enrollment_controller.cc b/chrome/browser/ash/login/enrollment/auto_enrollment_controller.cc index c1e2fa5f..54e99a1 100644 --- a/chrome/browser/ash/login/enrollment/auto_enrollment_controller.cc +++ b/chrome/browser/ash/login/enrollment/auto_enrollment_controller.cc
@@ -4,6 +4,8 @@ #include "chrome/browser/ash/login/enrollment/auto_enrollment_controller.h" +#include <memory> + #include "ash/components/tpm/install_attributes.h" #include "ash/constants/ash_switches.h" #include "base/bind.h" @@ -20,6 +22,7 @@ #include "chrome/browser/ash/policy/enrollment/private_membership/fake_private_membership_rlwe_client.h" #include "chrome/browser/ash/policy/enrollment/private_membership/private_membership_rlwe_client.h" #include "chrome/browser/ash/policy/enrollment/private_membership/private_membership_rlwe_client_impl.h" +#include "chrome/browser/ash/policy/enrollment/private_membership/psm_rlwe_dmserver_client_impl.h" #include "chrome/browser/ash/policy/enrollment/private_membership/psm_rlwe_id_provider_impl.h" #include "chrome/browser/ash/policy/server_backed_state/server_backed_state_keys_broker.h" #include "chrome/browser/ash/settings/device_settings_service.h" @@ -422,7 +425,11 @@ g_browser_process->system_network_context_manager() ->GetSharedURLLoaderFactory(), serial_number, rlz_brand_code, power_initial, power_limit, - psm_rlwe_client_factory_.get(), &psm_rlwe_id_provider_); + std::make_unique<policy::PsmRlweDmserverClientImpl>( + service, + g_browser_process->system_network_context_manager() + ->GetSharedURLLoaderFactory(), + psm_rlwe_client_factory_.get(), &psm_rlwe_id_provider_)); LOG(WARNING) << "Starting auto-enrollment client for Initial Enrollment."; client_->Start();
diff --git a/chrome/browser/ash/login/login_ui_shelf_visibility_browsertest.cc b/chrome/browser/ash/login/login_ui_shelf_visibility_browsertest.cc index 94800f2..441d59f 100644 --- a/chrome/browser/ash/login/login_ui_shelf_visibility_browsertest.cc +++ b/chrome/browser/ash/login/login_ui_shelf_visibility_browsertest.cc
@@ -15,11 +15,14 @@ #include "chrome/browser/ash/login/test/oobe_screen_waiter.h" #include "chrome/browser/ash/login/ui/login_display_host.h" #include "chrome/browser/ash/login/wizard_controller.h" +#include "chrome/browser/ash/policy/core/device_policy_cros_browser_test.h" +#include "chrome/browser/browser_process.h" #include "chrome/browser/ui/webui/chromeos/login/gaia_screen_handler.h" #include "chrome/browser/ui/webui/chromeos/login/oobe_ui.h" #include "chrome/browser/ui/webui/chromeos/login/os_install_screen_handler.h" #include "chrome/browser/ui/webui/chromeos/login/sync_consent_screen_handler.h" #include "chrome/browser/ui/webui/chromeos/login/user_creation_screen_handler.h" +#include "components/policy/proto/device_management_backend.pb.h" #include "content/public/test/browser_test.h" #include "net/dns/mock_host_resolver.h" @@ -179,4 +182,70 @@ EXPECT_TRUE(LoginScreenTestApi::IsGuestButtonShown()); } +namespace { + +// This is the constant that exists on the server side. It corresponds to +// the type of enrollment license. +constexpr char kKioskSkuName[] = "GOOGLE.CHROME_KIOSK_ANNUAL"; + +} // namespace + +class KioskSkuVisibilityTest : public LoginUIShelfVisibilityTest { + public: + KioskSkuVisibilityTest() { + device_state_.set_skip_initial_policy_setup(true); + } + ~KioskSkuVisibilityTest() override = default; + KioskSkuVisibilityTest(const KioskSkuVisibilityTest&) = delete; + void operator=(const KioskSkuVisibilityTest&) = delete; + + protected: + policy::DevicePolicyCrosTestHelper* policy_helper() { + return &policy_helper_; + } + + private: + ash::DeviceStateMixin device_state_{ + &mixin_host_, + ash::DeviceStateMixin::State::OOBE_COMPLETED_CLOUD_ENROLLED}; + policy::DevicePolicyCrosTestHelper policy_helper_; +}; + +// Verifies that shelf buttons of Guest mode and Add user are shown, and kiosk +// instruction bubble is hidden without kiosk SKU. +IN_PROC_BROWSER_TEST_F(KioskSkuVisibilityTest, WithoutKioskSku) { + EXPECT_TRUE(LoginScreenTestApi::IsLoginShelfShown()); + EXPECT_TRUE(LoginScreenTestApi::IsGuestButtonShown()); + EXPECT_TRUE(LoginScreenTestApi::IsAddUserButtonShown()); + EXPECT_FALSE(LoginScreenTestApi::IsKioskInstructionBubbleShown()); +} + +// Verifies that shelf buttons of Guest mode and Add user are hidden, and kiosk +// instruction bubble is hidden too without kiosk apps. +IN_PROC_BROWSER_TEST_F(KioskSkuVisibilityTest, WithoutApps) { + policy_helper()->device_policy()->policy_data().set_license_sku( + kKioskSkuName); + policy_helper()->RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); + + EXPECT_TRUE(LoginScreenTestApi::IsLoginShelfShown()); + EXPECT_FALSE(LoginScreenTestApi::IsGuestButtonShown()); + EXPECT_FALSE(LoginScreenTestApi::IsAddUserButtonShown()); + EXPECT_FALSE(LoginScreenTestApi::IsKioskInstructionBubbleShown()); +} + +// Verifies that shelf buttons of Guest mode and Add user are hidden, and kiosk +// instruction bubble is shown with kiosk apps. +IN_PROC_BROWSER_TEST_F(KioskSkuVisibilityTest, WithApps) { + policy_helper()->device_policy()->policy_data().set_license_sku( + kKioskSkuName); + KioskAppsMixin::AppendKioskAccount( + &policy_helper()->device_policy()->payload()); + policy_helper()->RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); + + EXPECT_TRUE(LoginScreenTestApi::IsLoginShelfShown()); + EXPECT_FALSE(LoginScreenTestApi::IsGuestButtonShown()); + EXPECT_FALSE(LoginScreenTestApi::IsAddUserButtonShown()); + EXPECT_TRUE(LoginScreenTestApi::IsKioskInstructionBubbleShown()); +} + } // namespace ash
diff --git a/chrome/browser/ash/login/saml/saml_browsertest.cc b/chrome/browser/ash/login/saml/saml_browsertest.cc index 3197c33..6e9083d 100644 --- a/chrome/browser/ash/login/saml/saml_browsertest.cc +++ b/chrome/browser/ash/login/saml/saml_browsertest.cc
@@ -735,14 +735,7 @@ 1); } -// Tests the no password scraped flow. -// TODO(crbug.com/1315447): Disabled for debug builds. -#if !defined(NDEBUG) -#define MAYBE_ScrapedNone DISABLED_ScrapedNone -#else -#define MAYBE_ScrapedNone ScrapedNone -#endif -IN_PROC_BROWSER_TEST_P(SamlTestWithFeatures, MAYBE_ScrapedNone) { +IN_PROC_BROWSER_TEST_P(SamlTestWithFeatures, ScrapedNone) { base::HistogramTester histogram_tester; fake_saml_idp()->SetLoginHTMLTemplate("saml_login_no_passwords.html"); @@ -833,15 +826,7 @@ WaitForSigninScreen(); } -// Tests the password confirm flow when more than one password is scraped: show -// error on the first failure and fatal error on the second failure. -// TODO(crbug.com/1315447): Disabled for debug builds. -#if !defined(NDEBUG) -#define MAYBE_PasswordConfirmFlow DISABLED_PasswordConfirmFlow -#else -#define MAYBE_PasswordConfirmFlow PasswordConfirmFlow -#endif -IN_PROC_BROWSER_TEST_P(SamlTestWithFeatures, MAYBE_PasswordConfirmFlow) { +IN_PROC_BROWSER_TEST_P(SamlTestWithFeatures, PasswordConfirmFlow) { base::HistogramTester histogram_tester; fake_saml_idp()->SetLoginHTMLTemplate("saml_login_two_passwords.html"); StartSamlAndWaitForIdpPageLoad(
diff --git a/chrome/browser/ash/policy/core/browser_policy_connector_ash_browsertest.cc b/chrome/browser/ash/policy/core/browser_policy_connector_ash_browsertest.cc index 06f3032..f99b0f02 100644 --- a/chrome/browser/ash/policy/core/browser_policy_connector_ash_browsertest.cc +++ b/chrome/browser/ash/policy/core/browser_policy_connector_ash_browsertest.cc
@@ -24,23 +24,6 @@ const char kMachineName[] = "machine_name"; const char kCustomManager[] = "user@acme.corp"; -void WaitUntilPolicyLoaded() { - BrowserPolicyConnectorAsh* connector = - g_browser_process->platform_part()->browser_policy_connector_ash(); - DeviceCloudPolicyStoreAsh* store = - connector->GetDeviceCloudPolicyManager()->device_store(); - if (!store->has_policy()) { - MockCloudPolicyStoreObserver observer; - base::RunLoop loop; - store->AddObserver(&observer); - EXPECT_CALL(observer, OnStoreLoaded(store)) - .Times(1) - .WillOnce(InvokeWithoutArgs(&loop, &base::RunLoop::Quit)); - loop.Run(); - store->RemoveObserver(&observer); - } -} - class BrowserPolicyConnectorAshTest : public DevicePolicyCrosBrowserTest { public: BrowserPolicyConnectorAshTest() { @@ -70,8 +53,7 @@ BrowserPolicyConnectorAsh* connector = g_browser_process->platform_part()->browser_policy_connector_ash(); device_policy()->policy_data().set_display_domain(kCustomDisplayDomain); - RefreshDevicePolicy(); - WaitUntilPolicyLoaded(); + policy_helper()->RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); // At this point display domain is set and policy is loaded so expect to see /// the display domain. EXPECT_EQ(kCustomDisplayDomain, connector->GetEnterpriseDomainManager()); @@ -89,8 +71,7 @@ device_policy()->policy_data().set_display_domain(kCustomDisplayDomain); device_policy()->policy_data().set_managed_by(kCustomManager); - RefreshDevicePolicy(); - WaitUntilPolicyLoaded(); + policy_helper()->RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); // Now that the managed_by is set expect to see that. EXPECT_EQ(kCustomManager, connector->GetEnterpriseDomainManager()); @@ -106,8 +87,7 @@ device_policy()->policy_data().set_market_segment( enterprise_management::PolicyData::ENROLLED_EDUCATION); - RefreshDevicePolicy(); - WaitUntilPolicyLoaded(); + policy_helper()->RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); EXPECT_EQ(MarketSegment::EDUCATION, connector->GetEnterpriseMarketSegment()); } @@ -116,8 +96,7 @@ g_browser_process->platform_part()->browser_policy_connector_ash(); EXPECT_EQ(std::string(), connector->GetMachineName()); device_policy()->policy_data().set_machine_name(kMachineName); - RefreshDevicePolicy(); - WaitUntilPolicyLoaded(); + policy_helper()->RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); // At this point custom display domain is set and policy is loaded so expect // to see the custom display domain. EXPECT_EQ(kMachineName, connector->GetMachineName());
diff --git a/chrome/browser/ash/policy/core/device_attributes_browsertest.cc b/chrome/browser/ash/policy/core/device_attributes_browsertest.cc index e020ab3e..b1151cc2 100644 --- a/chrome/browser/ash/policy/core/device_attributes_browsertest.cc +++ b/chrome/browser/ash/policy/core/device_attributes_browsertest.cc
@@ -27,23 +27,6 @@ namespace { -void WaitUntilPolicyLoaded() { - DeviceCloudPolicyStoreAsh* policy_store = g_browser_process->platform_part() - ->browser_policy_connector_ash() - ->GetDeviceCloudPolicyManager() - ->device_store(); - if (!policy_store->has_policy()) { - MockCloudPolicyStoreObserver observer; - base::RunLoop loop; - policy_store->AddObserver(&observer); - EXPECT_CALL(observer, OnStoreLoaded(policy_store)) - .Times(1) - .WillOnce(InvokeWithoutArgs(&loop, &base::RunLoop::Quit)); - loop.Run(); - policy_store->RemoveObserver(&observer); - } -} - constexpr char kFakeDomain[] = "fake.domain.acme.corp"; constexpr char kFakeDisplayDomain[] = "acme.corp"; constexpr char kFakeSSOProfile[] = "fake sso profile"; @@ -100,8 +83,7 @@ kFakeLogoURL); device_policy()->policy_data().set_market_segment( enterprise_management::PolicyData_MarketSegment_ENROLLED_ENTERPRISE); - RefreshDevicePolicy(); - WaitUntilPolicyLoaded(); + policy_helper()->RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); // Verify returned attributes correspond to what was set. EXPECT_EQ(kFakeDomain, attributes_.GetEnterpriseEnrollmentDomain());
diff --git a/chrome/browser/ash/policy/core/device_policy_cros_browser_test.cc b/chrome/browser/ash/policy/core/device_policy_cros_browser_test.cc index 911bd12..208cdf8 100644 --- a/chrome/browser/ash/policy/core/device_policy_cros_browser_test.cc +++ b/chrome/browser/ash/policy/core/device_policy_cros_browser_test.cc
@@ -16,21 +16,46 @@ #include "base/numerics/safe_conversions.h" #include "base/path_service.h" #include "base/threading/thread_restrictions.h" +#include "chrome/browser/ash/policy/core/browser_policy_connector_ash.h" +#include "chrome/browser/ash/policy/core/device_cloud_policy_store_ash.h" #include "chrome/browser/ash/policy/core/device_policy_builder.h" #include "chrome/browser/ash/settings/cros_settings.h" #include "chrome/browser/browser_process.h" +#include "chrome/browser/browser_process_platform_part_chromeos.h" #include "chrome/common/chrome_paths.h" #include "chromeos/dbus/constants/dbus_paths.h" #include "chromeos/dbus/session_manager/fake_session_manager_client.h" +#include "components/policy/core/common/cloud/cloud_policy_store.h" +#include "components/policy/core/common/cloud/mock_cloud_policy_store.h" #include "components/prefs/pref_service.h" #include "crypto/rsa_private_key.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" namespace policy { +namespace { namespace em = ::enterprise_management; +class CloudPolicyStoreWaiter : public CloudPolicyStore::Observer { + public: + CloudPolicyStoreWaiter() = default; + CloudPolicyStoreWaiter(const CloudPolicyStoreWaiter&) = delete; + CloudPolicyStoreWaiter& operator=(const CloudPolicyStoreWaiter&) = delete; + ~CloudPolicyStoreWaiter() override = default; + + void OnStoreLoaded(CloudPolicyStore* store) override { loop_.Quit(); } + + void OnStoreError(CloudPolicyStore* store) override { FAIL(); } + + void Wait() { loop_.Run(); } + + private: + base::RunLoop loop_; +}; + +} // namespace + void DeviceLocalAccountTestHelper::SetupDeviceLocalAccount( UserPolicyBuilder* policy_builder, const std::string& kAccountId, @@ -174,6 +199,22 @@ base::RunLoop().RunUntilIdle(); } +void DevicePolicyCrosTestHelper:: + RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated() { + policy::DeviceCloudPolicyStoreAsh* policy_store = + g_browser_process->platform_part() + ->browser_policy_connector_ash() + ->GetDeviceCloudPolicyManager() + ->device_store(); + if (!policy_store->has_policy()) { + CloudPolicyStoreWaiter waiter; + policy_store->AddObserver(&waiter); + RefreshDevicePolicy(); + waiter.Wait(); + policy_store->RemoveObserver(&waiter); + } +} + void DevicePolicyCrosTestHelper::UnsetPolicy( const std::vector<std::string>& settings) { em::ChromeDeviceSettingsProto& proto(device_policy()->payload());
diff --git a/chrome/browser/ash/policy/core/device_policy_cros_browser_test.h b/chrome/browser/ash/policy/core/device_policy_cros_browser_test.h index af43d8972..6504fa07 100644 --- a/chrome/browser/ash/policy/core/device_policy_cros_browser_test.h +++ b/chrome/browser/ash/policy/core/device_policy_cros_browser_test.h
@@ -8,9 +8,11 @@ #include <string> #include "chrome/browser/ash/login/test/device_state_mixin.h" +#include "chrome/browser/ash/policy/core/device_cloud_policy_store_ash.h" #include "chrome/browser/ash/policy/core/device_policy_builder.h" #include "chrome/test/base/mixin_based_in_process_browser_test.h" #include "chromeos/dbus/dbus_thread_manager.h" +#include "components/policy/core/common/cloud/mock_cloud_policy_store.h" #include "components/policy/core/common/cloud/test/policy_builder.h" #include "components/prefs/pref_change_registrar.h" @@ -96,6 +98,8 @@ // resolution setting. void RefreshPolicyAndWaitUntilDeviceSettingsUpdated( const std::vector<std::string>& settings); + // Refreshes the whole device cloud policies. + void RefreshPolicyAndWaitUntilDeviceCloudPolicyUpdated(); void UnsetPolicy(const std::vector<std::string>& settings); private:
diff --git a/chrome/browser/ash/policy/enrollment/auto_enrollment_client.h b/chrome/browser/ash/policy/enrollment/auto_enrollment_client.h index 626048d..cb366e4 100644 --- a/chrome/browser/ash/policy/enrollment/auto_enrollment_client.h +++ b/chrome/browser/ash/policy/enrollment/auto_enrollment_client.h
@@ -10,7 +10,6 @@ #include "base/callback.h" #include "base/memory/scoped_refptr.h" -#include "chrome/browser/ash/policy/enrollment/private_membership/private_membership_rlwe_client.h" class PrefService; @@ -21,7 +20,7 @@ namespace policy { class DeviceManagementService; -class PsmRlweIdProvider; +class PsmRlweDmserverClient; // Indicates the current state of the auto-enrollment check. (Numeric values // are just to make reading of log files easier.) @@ -90,8 +89,7 @@ const std::string& device_brand_code, int power_initial, int power_limit, - PrivateMembershipRlweClient::Factory* psm_rlwe_client_factory, - PsmRlweIdProvider* psm_rlwe_id_provider) = 0; + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client) = 0; }; virtual ~AutoEnrollmentClient() {}
diff --git a/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.cc b/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.cc index b2f8faf..41f9d1f 100644 --- a/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.cc +++ b/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.cc
@@ -16,7 +16,6 @@ #include "base/threading/thread_task_runner_handle.h" #include "chrome/browser/ash/login/enrollment/auto_enrollment_controller.h" #include "chrome/browser/ash/policy/enrollment/private_membership/psm_rlwe_dmserver_client.h" -#include "chrome/browser/ash/policy/enrollment/private_membership/psm_rlwe_id_provider.h" #include "chrome/browser/ash/policy/server_backed_state/server_backed_device_state.h" #include "chrome/common/chrome_content_client.h" #include "chrome/common/pref_names.h" @@ -45,9 +44,6 @@ using EnrollmentCheckType = em::DeviceAutoEnrollmentRequest::EnrollmentCheckType; -// Timeout for running PSM protocol. -constexpr base::TimeDelta kPsmTimeout = base::Seconds(15); - // Returns the power of the next power-of-2 starting at |value|. int NextPowerOf2(int64_t value) { for (int i = 0; i <= AutoEnrollmentClient::kMaximumPower; ++i) { @@ -196,470 +192,6 @@ const em::DeviceManagementResponse& response) = 0; }; -class PsmHelper { - public: - // Callback will be triggered after completing the protocol, in case of a - // successful determination or stopping due to an error. - // The `psm_result` represents the final result of PSM protocol. - using CompletionCallback = base::OnceCallback<void(PsmResult psm_result)>; - - // The PsmHelper doesn't take ownership of |device_management_service|, - // |local_state|, |psm_rlwe_client_factory| and |psm_rlwe_id_provider|. - // All of them must not be nullptr. Also, |device_management_service|, - // and |local_state| must outlive PsmHelper. - PsmHelper(DeviceManagementService* device_management_service, - scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory, - PrefService* local_state, - PrivateMembershipRlweClient::Factory* psm_rlwe_client_factory, - PsmRlweIdProvider* psm_rlwe_id_provider) - : random_device_id_(base::GenerateGUID()), - url_loader_factory_(url_loader_factory), - device_management_service_(device_management_service), - local_state_(local_state) { - CHECK(device_management_service); - CHECK(psm_rlwe_client_factory); - CHECK(psm_rlwe_id_provider); - DCHECK(local_state_); - - psm_rlwe_id_ = psm_rlwe_id_provider->ConstructRlweId(); - - // Create PSM client for |psm_rlwe_id_| with use case as CROS_DEVICE_STATE. - std::vector<psm_rlwe::RlwePlaintextId> psm_ids = {psm_rlwe_id_}; - auto status_or_client = psm_rlwe_client_factory->Create( - psm_rlwe::RlweUseCase::CROS_DEVICE_STATE, psm_ids); - if (!status_or_client.ok()) { - // If the PSM RLWE client hasn't been created successfully, then report - // the error and don't run the protocol. - LOG(ERROR) - << "PSM error: unexpected internal logic error during creating " - "PSM RLWE client"; - last_psm_execution_result_ = PsmResult::kCreateRlweClientLibraryError; - base::UmaHistogramEnumeration(kUMAPsmResult + uma_suffix_, - PsmResult::kCreateRlweClientLibraryError); - return; - } - - psm_rlwe_client_ = std::move(status_or_client).value(); - } - - // Disallow copy constructor and assignment operator. - PsmHelper(const PsmHelper&) = delete; - PsmHelper& operator=(const PsmHelper&) = delete; - - // Cancels the ongoing PSM operation, if any (without calling the operation's - // callbacks). - ~PsmHelper() { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); } - - // Determines the PSM for the |psm_rlwe_id_|. Then, will call |callback| upon - // completing the protocol, whether it finished with a successful - // determination or stopped in case of errors. Also, the |callback| has to be - // non-null. - // Note: This method should be called only when there is no PSM requests in - // progress (i.e. `IsCheckMembershipInProgress` is false). - void CheckMembership(CompletionCallback callback) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - DCHECK(callback); - - // Ignore new calls and execute `callback` with - // |last_psm_execution_result_|, in case any error occurred while running - // PSM previously. - if (HasPsmError()) { - std::move(callback).Run(last_psm_execution_result_.value()); - return; - } - - // There should not be any pending PSM requests. - CHECK(!psm_request_job_); - - time_start_ = base::TimeTicks::Now(); - - // Set the initial PSM execution result as unknown until it finishes - // successfully or due to an error. - // Also, clear the PSM determination timestamp. - local_state_->SetInteger(prefs::kEnrollmentPsmResult, - em::DeviceRegisterRequest::PSM_RESULT_UNKNOWN); - local_state_->ClearPref(prefs::kEnrollmentPsmDeterminationTime); - - on_completion_callback_ = std::move(callback); - - // Start the protocol and its timeout timer. - psm_timeout_.Start( - FROM_HERE, kPsmTimeout, - base::BindOnce(&PsmHelper::StoreErrorAndStop, base::Unretained(this), - PsmResult::kTimeout)); - SendPsmRlweOprfRequest(); - } - - // Tries to load the result of a previous execution of the PSM protocol from - // local state. Returns decision value if it has been made and is valid, - // otherwise nullopt. - absl::optional<bool> GetPsmCachedDecision() const { - const PrefService::Preference* has_psm_server_state_pref = - local_state_->FindPreference(prefs::kShouldRetrieveDeviceState); - - if (!has_psm_server_state_pref || - has_psm_server_state_pref->IsDefaultValue() || - !has_psm_server_state_pref->GetValue()->is_bool()) { - return absl::nullopt; - } - - return has_psm_server_state_pref->GetValue()->GetBool(); - } - - // Indicate whether an error occurred while executing the PSM protocol. - bool HasPsmError() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - return last_psm_execution_result_ && - last_psm_execution_result_.value() != - PsmResult::kSuccessfulDetermination; - } - - // Returns true if the PSM protocol is still running, - // otherwise false. - bool IsCheckMembershipInProgress() const { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - return psm_request_job_ != nullptr; - } - - private: - void StoreErrorAndStop(PsmResult psm_result) { - // Note that kUMAPsmResult histogram is only using initial enrollment as a - // suffix until PSM support FRE. - base::UmaHistogramEnumeration(kUMAPsmResult + uma_suffix_, psm_result); - - // Records the PSM execution as an error in local_state, so that value will - // be used in the DeviceRegisterRequest during the enrollment flow. - local_state_->SetInteger(prefs::kEnrollmentPsmResult, - em::DeviceRegisterRequest::PSM_RESULT_ERROR); - local_state_->CommitPendingWrite(); - - // Stop the PSM timer. - psm_timeout_.Stop(); - - // Stop the current |psm_request_job_|. - psm_request_job_.reset(); - - last_psm_execution_result_ = psm_result; - std::move(on_completion_callback_).Run(psm_result); - } - - // Constructs and sends the PSM RLWE OPRF request. - void SendPsmRlweOprfRequest() { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - - // Create RLWE OPRF request. - const auto status_or_oprf_request = psm_rlwe_client_->CreateOprfRequest(); - if (!status_or_oprf_request.ok()) { - // If the RLWE OPRF request hasn't been created successfully, then report - // the error and stop the protocol. - LOG(ERROR) - << "PSM error: unexpected internal logic error during creating " - "RLWE OPRF request"; - StoreErrorAndStop(PsmResult::kCreateOprfRequestLibraryError); - return; - } - - LOG(WARNING) << "PSM: prepare and send out the RLWE OPRF request"; - - // Prepare the RLWE OPRF request job. - // The passed callback will not be called if |psm_request_job_| is - // destroyed, so it's safe to use base::Unretained. - std::unique_ptr<DMServerJobConfiguration> config = - CreatePsmRequestJobConfiguration(base::BindOnce( - &PsmHelper::OnRlweOprfRequestCompletion, base::Unretained(this))); - - em::DeviceManagementRequest* request = config->request(); - em::PrivateSetMembershipRlweRequest* psm_rlwe_request = - request->mutable_private_set_membership_request() - ->mutable_rlwe_request(); - - *psm_rlwe_request->mutable_oprf_request() = status_or_oprf_request.value(); - psm_request_job_ = device_management_service_->CreateJob(std::move(config)); - } - - // If the completion was successful, then it makes another request to - // DMServer for performing phase two. - void OnRlweOprfRequestCompletion( - DeviceManagementService::Job* job, - DeviceManagementStatus status, - int net_error, - const em::DeviceManagementResponse& response) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - - base::UmaHistogramSparse(kUMAPsmDmServerRequestStatus + uma_suffix_, - status); - - switch (status) { - case DM_STATUS_SUCCESS: { - // Check if the RLWE OPRF response is empty. - if (!response.private_set_membership_response().has_rlwe_response() || - !response.private_set_membership_response() - .rlwe_response() - .has_oprf_response()) { - LOG(ERROR) << "PSM error: empty OPRF RLWE response"; - StoreErrorAndStop(PsmResult::kEmptyOprfResponseError); - return; - } - - LOG(WARNING) << "PSM RLWE OPRF request completed successfully"; - SendPsmRlweQueryRequest(response.private_set_membership_response()); - return; - } - case DM_STATUS_REQUEST_FAILED: { - LOG(ERROR) - << "PSM error: RLWE OPRF request failed due to connection error"; - base::UmaHistogramSparse(kUMAPsmNetworkErrorCode + uma_suffix_, - -net_error); - StoreErrorAndStop(PsmResult::kConnectionError); - return; - } - default: { - LOG(ERROR) << "PSM error: RLWE OPRF request failed due to server error"; - StoreErrorAndStop(PsmResult::kServerError); - return; - } - } - } - - // Constructs and sends the PSM RLWE Query request. - void SendPsmRlweQueryRequest( - const em::PrivateSetMembershipResponse& psm_response) { - // Extract the oprf_response from |psm_response|. - const psm_rlwe::PrivateMembershipRlweOprfResponse oprf_response = - psm_response.rlwe_response().oprf_response(); - - const auto status_or_query_request = - psm_rlwe_client_->CreateQueryRequest(oprf_response); - - // Create RLWE query request. - if (!status_or_query_request.ok()) { - // If the RLWE query request hasn't been created successfully, then report - // the error and stop the protocol. - LOG(ERROR) - << "PSM error: unexpected internal logic error during creating " - "RLWE query request"; - StoreErrorAndStop(PsmResult::kCreateQueryRequestLibraryError); - return; - } - - LOG(WARNING) << "PSM: prepare and send out the RLWE query request"; - - // Prepare the RLWE query request job. - std::unique_ptr<DMServerJobConfiguration> config = - CreatePsmRequestJobConfiguration( - base::BindOnce(&PsmHelper::OnRlweQueryRequestCompletion, - base::Unretained(this), oprf_response)); - - em::DeviceManagementRequest* request = config->request(); - em::PrivateSetMembershipRlweRequest* psm_rlwe_request = - request->mutable_private_set_membership_request() - ->mutable_rlwe_request(); - - *psm_rlwe_request->mutable_query_request() = - status_or_query_request.value(); - psm_request_job_ = device_management_service_->CreateJob(std::move(config)); - } - - // If the completion was successful, then it will parse the result and call - // the |on_completion_callback_| for |psm_id_|. - void OnRlweQueryRequestCompletion( - const psm_rlwe::PrivateMembershipRlweOprfResponse& oprf_response, - DeviceManagementService::Job* job, - DeviceManagementStatus status, - int net_error, - const em::DeviceManagementResponse& response) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - - base::UmaHistogramSparse(kUMAPsmDmServerRequestStatus + uma_suffix_, - status); - - switch (status) { - case DM_STATUS_SUCCESS: { - // Check if the RLWE query response is empty. - if (!response.private_set_membership_response().has_rlwe_response() || - !response.private_set_membership_response() - .rlwe_response() - .has_query_response()) { - LOG(ERROR) << "PSM error: empty query RLWE response"; - StoreErrorAndStop(PsmResult::kEmptyQueryResponseError); - return; - } - - const psm_rlwe::PrivateMembershipRlweQueryResponse query_response = - response.private_set_membership_response() - .rlwe_response() - .query_response(); - - auto status_or_responses = - psm_rlwe_client_->ProcessQueryResponse(query_response); - - if (!status_or_responses.ok()) { - // If the RLWE query response hasn't processed successfully, then - // report the error and stop the protocol. - LOG(ERROR) << "PSM error: unexpected internal logic error during " - "processing the " - "RLWE query response"; - StoreErrorAndStop(PsmResult::kProcessingQueryResponseLibraryError); - return; - } - - LOG(WARNING) << "PSM query request completed successfully"; - - last_psm_execution_result_ = PsmResult::kSuccessfulDetermination; - base::UmaHistogramEnumeration(kUMAPsmResult + uma_suffix_, - PsmResult::kSuccessfulDetermination); - RecordPsmSuccessTimeHistogram(); - - // The RLWE query response has been processed successfully. Extract - // the membership response, and report the result. - - psm_rlwe::RlweMembershipResponses rlwe_membership_responses = - std::move(status_or_responses).value(); - - // Ensure the existence of one membership response. Then, verify that it - // is regarding the current PSM ID. - if (rlwe_membership_responses.membership_responses_size() != 1 || - rlwe_membership_responses.membership_responses(0) - .plaintext_id() - .sensitive_id() != psm_rlwe_id_.sensitive_id()) { - LOG(ERROR) - << "PSM error: RLWE membership responses are either empty or its " - "first response's ID is not the same as the current PSM ID."; - // TODO(crbug.com/1302982): Record that error separately and merge it - // with PsmResult. - StoreErrorAndStop(PsmResult::kEmptyQueryResponseError); - return; - } - - const bool membership_result = - rlwe_membership_responses.membership_responses(0) - .membership_response() - .is_member(); - - LOG(WARNING) << "PSM determination successful. Identifier " - << (membership_result ? "" : "not ") - << "present on the server"; - - // Reset the |psm_request_job_| to allow another call to - // CheckMembership. - psm_request_job_.reset(); - - // Stop the PSM timer. - psm_timeout_.Stop(); - - // Cache the decision in local_state, so that it is reused in case - // the device reboots before completing OOBE. - // Also, record the PSM determination timestamp and its execution - // result in local state. Because both values will be used in the - // DeviceRegisterRequest during the enrollment flow. - local_state_->SetBoolean(prefs::kShouldRetrieveDeviceState, - membership_result); - local_state_->SetTime(prefs::kEnrollmentPsmDeterminationTime, - base::Time::Now()); - local_state_->SetInteger( - prefs::kEnrollmentPsmResult, - membership_result - ? em::DeviceRegisterRequest::PSM_RESULT_SUCCESSFUL_WITH_STATE - : em::DeviceRegisterRequest:: - PSM_RESULT_SUCCESSFUL_WITHOUT_STATE); - local_state_->CommitPendingWrite(); - - std::move(on_completion_callback_) - .Run(PsmResult::kSuccessfulDetermination); - return; - } - case DM_STATUS_REQUEST_FAILED: { - LOG(ERROR) - << "PSM error: RLWE query request failed due to connection error"; - base::UmaHistogramSparse(kUMAPsmNetworkErrorCode + uma_suffix_, - -net_error); - StoreErrorAndStop(PsmResult::kConnectionError); - return; - } - default: { - LOG(ERROR) - << "PSM error: RLWE query request failed due to server error"; - StoreErrorAndStop(PsmResult::kServerError); - return; - } - } - } - - // Returns a job config that has TYPE_PSM_REQUEST as job type and |callback| - // will be executed on completion. - std::unique_ptr<DMServerJobConfiguration> CreatePsmRequestJobConfiguration( - DMServerJobConfiguration::Callback callback) { - return std::make_unique<DMServerJobConfiguration>( - device_management_service_, - DeviceManagementService::JobConfiguration:: - TYPE_PSM_HAS_DEVICE_STATE_REQUEST, - random_device_id_, - /*critical=*/true, DMAuth::NoAuth(), - /*oauth_token=*/absl::nullopt, url_loader_factory_, - std::move(callback)); - } - - // Record UMA histogram for timing of successful PSM request. - void RecordPsmSuccessTimeHistogram() { - // These values determine bucketing of the histogram, they should not be - // changed. - static const base::TimeDelta kMin = base::Milliseconds(1); - static const base::TimeDelta kMax = base::Seconds(25); - static const int kBuckets = 50; - - base::TimeTicks now = base::TimeTicks::Now(); - if (!time_start_.is_null()) { - base::TimeDelta delta = now - time_start_; - base::UmaHistogramCustomTimes(kUMAPsmSuccessTime, delta, kMin, kMax, - kBuckets); - } - } - - // PSM RLWE client, used for preparing PSM requests and parsing PSM responses. - std::unique_ptr<PrivateMembershipRlweClient> psm_rlwe_client_; - - // Randomly generated device id for the PSM requests. - std::string random_device_id_; - - // The loader factory to use to perform PSM requests. - scoped_refptr<network::SharedURLLoaderFactory> url_loader_factory_; - - // Unowned by PsmHelper. Its used to communicate with the device management - // service. - DeviceManagementService* device_management_service_; - - // Its being used for both PSM requests e.g. RLWE OPRF request and RLWE query - // request. - std::unique_ptr<DeviceManagementService::Job> psm_request_job_; - - // Callback will be triggered upon completing of the protocol. - CompletionCallback on_completion_callback_; - - // PrefService where the PSM protocol result is cached. - PrefService* const local_state_; - - // PSM identifier, which is going to be used while preparing the PSM requests. - psm_rlwe::RlwePlaintextId psm_rlwe_id_; - - // A timer that puts a hard limit on the maximum time to wait for PSM - // protocol. - base::OneShotTimer psm_timeout_; - - // The time when the PSM request started. - base::TimeTicks time_start_; - - // Represents the last PSM protocol execution result. - absl::optional<PsmResult> last_psm_execution_result_; - - // The UMA histogram suffix. It's set only to ".InitialEnrollment" for an - // |AutoEnrollmentClient| until PSM will support FRE. - const std::string uma_suffix_ = kUMASuffixInitialEnrollment; - - // A sequence checker to prevent the race condition of having the possibility - // of the destructor being called and any of the callbacks. - SEQUENCE_CHECKER(sequence_checker_); -}; - namespace { // Handles DeviceInitialEnrollmentStateRequest / // DeviceInitialEnrollmentStateResponse for Forced Initial Enrollment. @@ -849,8 +381,7 @@ const std::string& device_brand_code, int power_initial, int power_limit, - PrivateMembershipRlweClient::Factory* psm_rlwe_client_factory, - PsmRlweIdProvider* psm_rlwe_id_provider) { + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client) { return base::WrapUnique(new AutoEnrollmentClientImpl( progress_callback, device_management_service, local_state, url_loader_factory, @@ -858,9 +389,7 @@ std::make_unique<StateDownloadMessageProcessorInitialEnrollment>( device_serial_number, device_brand_code), power_initial, power_limit, kUMASuffixInitialEnrollment, - std::make_unique<PsmHelper>(device_management_service, url_loader_factory, - local_state, psm_rlwe_client_factory, - psm_rlwe_id_provider))); + std::move(psm_rlwe_dmserver_client))); } AutoEnrollmentClientImpl::~AutoEnrollmentClientImpl() { @@ -934,7 +463,7 @@ int power_initial, int power_limit, std::string uma_suffix, - std::unique_ptr<PsmHelper> private_set_membership_helper) + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client) : progress_callback_(callback), state_(AUTO_ENROLLMENT_STATE_IDLE), has_server_state_(false), @@ -950,7 +479,7 @@ std::move(device_identifier_provider_fre)), state_download_message_processor_( std::move(state_download_message_processor)), - psm_helper_(std::move(private_set_membership_helper)), + psm_rlwe_dmserver_client_(std::move(psm_rlwe_dmserver_client)), uma_suffix_(uma_suffix) { DCHECK_LE(current_power_, power_limit_); DCHECK(!progress_callback_.is_null()); @@ -976,20 +505,25 @@ bool AutoEnrollmentClientImpl::RetrievePsmCachedDecision() { // PSM protocol has to be enabled whenever this function is called. - DCHECK(psm_helper_); + DCHECK(psm_rlwe_dmserver_client_); - const absl::optional<bool> private_set_membership_server_state = - psm_helper_->GetPsmCachedDecision(); + const PrefService::Preference* has_psm_server_state_pref = + local_state_->FindPreference(prefs::kShouldRetrieveDeviceState); - if (private_set_membership_server_state.has_value()) { - has_server_state_ = std::move(private_set_membership_server_state); - return true; + if (!has_psm_server_state_pref || + has_psm_server_state_pref->IsDefaultValue()) { + // Verify the pref is registered as a boolean. + DCHECK(has_psm_server_state_pref->GetValue()->is_bool()); + + return false; } - return false; + + has_server_state_ = has_psm_server_state_pref->GetValue()->GetBool(); + return true; } bool AutoEnrollmentClientImpl::IsClientForInitialEnrollment() const { - return psm_helper_ != nullptr; + return psm_rlwe_dmserver_client_ != nullptr; } bool AutoEnrollmentClientImpl::ShouldSendDeviceStateRequest() const { @@ -1026,15 +560,15 @@ bool AutoEnrollmentClientImpl::PsmRetryStep() { // PSM protocol has to be enabled whenever this function is called. - DCHECK(psm_helper_); + DCHECK(psm_rlwe_dmserver_client_); // Don't retry if the protocol had an error. - if (psm_helper_->HasPsmError()) + if (psm_result_holder_ && psm_result_holder_->IsError()) return false; // If the PSM protocol is in progress, signal to the caller // that nothing else needs to be done. - if (psm_helper_->IsCheckMembershipInProgress()) + if (psm_rlwe_dmserver_client_->IsCheckMembershipInProgress()) return true; if (RetrievePsmCachedDecision()) { @@ -1042,15 +576,42 @@ << has_server_state_.value(); return false; } else { - psm_helper_->CheckMembership( + // Set the initial PSM execution result as unknown until it finishes + // successfully or due to an error. + // Also, clear the PSM determination timestamp. + local_state_->SetInteger(prefs::kEnrollmentPsmResult, + em::DeviceRegisterRequest::PSM_RESULT_UNKNOWN); + local_state_->ClearPref(prefs::kEnrollmentPsmDeterminationTime); + + psm_rlwe_dmserver_client_->CheckMembership( base::BindOnce(&AutoEnrollmentClientImpl::HandlePsmCompletion, base::Unretained(this))); return true; } } -void AutoEnrollmentClientImpl::HandlePsmCompletion(PsmResult psm_result) { - switch (psm_result) { +void AutoEnrollmentClientImpl::HandlePsmCompletion( + PsmRlweDmserverClient::ResultHolder psm_result_holder) { + psm_result_holder_ = std::move(psm_result_holder); + + // Update `local_state_` PSM's prefs with their corresponding result values. + if (psm_result_holder_->psm_result != PsmResult::kSuccessfulDetermination) { + local_state_->SetInteger(prefs::kEnrollmentPsmResult, + em::DeviceRegisterRequest::PSM_RESULT_ERROR); + } else { + local_state_->SetBoolean(prefs::kShouldRetrieveDeviceState, + psm_result_holder_->membership_result.value()); + local_state_->SetTime( + prefs::kEnrollmentPsmDeterminationTime, + psm_result_holder_->membership_determination_time.value()); + local_state_->SetInteger( + prefs::kEnrollmentPsmResult, + psm_result_holder_->membership_result.value() + ? em::DeviceRegisterRequest::PSM_RESULT_SUCCESSFUL_WITH_STATE + : em::DeviceRegisterRequest::PSM_RESULT_SUCCESSFUL_WITHOUT_STATE); + } + + switch (psm_result_holder_->psm_result) { case PsmResult::kConnectionError: ReportProgress(AUTO_ENROLLMENT_STATE_CONNECTION_ERROR); break;
diff --git a/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.h b/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.h index 34d3498..bbb969d 100644 --- a/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.h +++ b/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl.h
@@ -29,14 +29,6 @@ namespace policy { -class PsmRlweIdProvider; - -// A class that handles all communications related to PSM protocol with -// DMServer. Also, upon successful determination, it caches the membership state -// of a given identifier in the local_state PrefService. Upon a failed -// determination it won't allow another membership check. -class PsmHelper; - // Interacts with the device management service and determines whether this // machine should automatically enter the Enterprise Enrollment screen during // OOBE. @@ -81,8 +73,8 @@ const std::string& device_brand_code, int power_initial, int power_limit, - PrivateMembershipRlweClient::Factory* psm_rlwe_client_factory, - PsmRlweIdProvider* psm_rlwe_id_provider) override; + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client) + override; }; AutoEnrollmentClientImpl(const AutoEnrollmentClientImpl&) = delete; @@ -119,7 +111,7 @@ int power_initial, int power_limit, std::string uma_suffix, - std::unique_ptr<PsmHelper> psm_helper); + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client); // Tries to load the result of a previous execution of the protocol from // local state. Returns true if that decision has been made and is valid. @@ -150,7 +142,8 @@ // Calls `NextStep` in case of successful execution of PSM protocol. // Otherwise, reports the failure reason of PSM protocol execution. - void HandlePsmCompletion(PsmResult psm_result); + void HandlePsmCompletion( + PsmRlweDmserverClient::ResultHolder psm_result_holder); // Cleans up and invokes |progress_callback_|. void ReportProgress(AutoEnrollmentState state); @@ -213,6 +206,9 @@ // information. absl::optional<bool> has_server_state_; + // Holds the cached PSM execution result. + absl::optional<PsmRlweDmserverClient::ResultHolder> psm_result_holder_; + // Whether the download of server-kept device state completed successfully. bool device_state_available_; @@ -250,8 +246,9 @@ std::unique_ptr<StateDownloadMessageProcessor> state_download_message_processor_; - // Obtains the device state using PSM protocol. - std::unique_ptr<PsmHelper> psm_helper_; + // Obtains the device state using PSM protocol. Handles all communications + // related to PSM protocol with DMServer. + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client_; // Times used to determine the duration of the protocol, and the extra time // needed to complete after the signin was complete.
diff --git a/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl_unittest.cc b/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl_unittest.cc index c4ef557..638d24c8 100644 --- a/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl_unittest.cc +++ b/chrome/browser/ash/policy/enrollment/auto_enrollment_client_impl_unittest.cc
@@ -28,6 +28,7 @@ #include "base/values.h" #include "chrome/browser/ash/login/enrollment/auto_enrollment_controller.h" #include "chrome/browser/ash/policy/enrollment/private_membership/psm_rlwe_dmserver_client.h" +#include "chrome/browser/ash/policy/enrollment/private_membership/psm_rlwe_dmserver_client_impl.h" #include "chrome/browser/ash/policy/enrollment/private_membership/testing_private_membership_rlwe_client.h" #include "chrome/browser/ash/policy/enrollment/private_membership/testing_psm_rlwe_id_provider.h" #include "chrome/browser/ash/policy/server_backed_state/server_backed_device_state.h" @@ -182,6 +183,7 @@ shared_url_loader_factory_ = base::MakeRefCounted<network::WeakWrapperSharedURLLoaderFactory>( &url_loader_factory_); + if (GetAutoEnrollmentProtocol() == AutoEnrollmentProtocol::kFRE) { client_ = AutoEnrollmentClientImpl::FactoryImpl().CreateForFRE( progress_callback, service_.get(), local_state_, @@ -196,8 +198,11 @@ AutoEnrollmentClientImpl::FactoryImpl().CreateForInitialEnrollment( progress_callback, service_.get(), local_state_, shared_url_loader_factory_, kSerialNumber, kBrandCode, - power_initial, power_limit, psm_rlwe_test_client_factory_.get(), - testing_psm_rlwe_id_provider_.get()); + power_initial, power_limit, + std::make_unique<PsmRlweDmserverClientImpl>( + service_.get(), shared_url_loader_factory_, + psm_rlwe_test_client_factory_.get(), + testing_psm_rlwe_id_provider_.get())); } }
diff --git a/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.cc b/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.cc index 068719d..28074d4 100644 --- a/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.cc +++ b/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.cc
@@ -4,6 +4,7 @@ #include "chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.h" +#include "chrome/browser/ash/policy/enrollment/private_membership/psm_rlwe_dmserver_client.h" #include "services/network/public/cpp/shared_url_loader_factory.h" namespace policy { @@ -40,8 +41,7 @@ const std::string& device_brand_code, int power_initial, int power_limit, - PrivateMembershipRlweClient::Factory* psm_rlwe_client_factory, - PsmRlweIdProvider* psm_rlwe_id_provider) { + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client) { std::unique_ptr<FakeAutoEnrollmentClient> fake_client = std::make_unique<FakeAutoEnrollmentClient>(progress_callback); fake_client_created_callback_.Run(fake_client.get());
diff --git a/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.h b/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.h index 0b5c5e8..ee77aadb 100644 --- a/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.h +++ b/chrome/browser/ash/policy/enrollment/fake_auto_enrollment_client.h
@@ -16,7 +16,7 @@ namespace policy { class DeviceManagementService; -class PsmRlweIdProvider; +class PsmRlweDmserverClient; // A fake AutoEnrollmentClient. The test code can control its state. class FakeAutoEnrollmentClient : public AutoEnrollmentClient { @@ -53,8 +53,8 @@ const std::string& device_brand_code, int power_initial, int power_limit, - PrivateMembershipRlweClient::Factory* psm_rlwe_client_factory, - PsmRlweIdProvider* psm_rlwe_id_provider) override; + std::unique_ptr<PsmRlweDmserverClient> psm_rlwe_dmserver_client) + override; private: base::RepeatingCallback<void(FakeAutoEnrollmentClient*)>
diff --git a/chrome/browser/autofill/autofill_uitest_util.cc b/chrome/browser/autofill/autofill_uitest_util.cc index 08ffdec9..fdfb10f 100644 --- a/chrome/browser/autofill/autofill_uitest_util.cc +++ b/chrome/browser/autofill/autofill_uitest_util.cc
@@ -136,7 +136,9 @@ ContentAutofillDriver* driver = static_cast<ContentAutofillDriver*>( absl::get<AutofillDriver*>(autofill_external_delegate->GetDriver())); - driver->AskForValuesToFill(query_id, form, field, bounds, false); + driver->AskForValuesToFill(query_id, form, field, bounds, + /*autoselect_first_suggestion=*/false, + TouchToFillEligible(false)); std::vector<Suggestion> suggestions = {Suggestion(u"Test suggestion")}; autofill_external_delegate->OnSuggestionsReturned(
diff --git a/chrome/browser/chromeos/BUILD.gn b/chrome/browser/chromeos/BUILD.gn index fb46d80..690f7fa 100644 --- a/chrome/browser/chromeos/BUILD.gn +++ b/chrome/browser/chromeos/BUILD.gn
@@ -3630,6 +3630,7 @@ "../ash/arc/fileapi/arc_content_file_system_file_stream_reader_unittest.cc", "../ash/arc/fileapi/arc_content_file_system_file_stream_writer_unittest.cc", "../ash/arc/fileapi/arc_content_file_system_url_util_unittest.cc", + "../ash/arc/fileapi/arc_documents_provider_root_map_unittest.cc", "../ash/arc/fileapi/arc_documents_provider_root_unittest.cc", "../ash/arc/fileapi/arc_documents_provider_util_unittest.cc", "../ash/arc/fileapi/arc_file_system_bridge_unittest.cc",
diff --git a/chrome/browser/chromeos/extensions/autotest_private/autotest_private_api.cc b/chrome/browser/chromeos/extensions/autotest_private/autotest_private_api.cc index b22b2ade..51f3485 100644 --- a/chrome/browser/chromeos/extensions/autotest_private/autotest_private_api.cc +++ b/chrome/browser/chromeos/extensions/autotest_private/autotest_private_api.cc
@@ -46,6 +46,7 @@ #include "base/base64.h" #include "base/bind.h" #include "base/command_line.h" +#include "base/compiler_specific.h" #include "base/feature_list.h" #include "base/json/json_reader.h" #include "base/lazy_instance.h" @@ -224,7 +225,7 @@ constexpr char kCrostiniNotAvailableForCurrentUserError[] = "Crostini is not available for the current user"; -int AccessArray(const volatile int arr[], const volatile int* index) { +NOINLINE int AccessArray(const int arr[], const int* index) { return arr[*index]; } @@ -1492,11 +1493,10 @@ DVLOG(1) << "AutotestPrivateSimulateAsanMemoryBugFunction"; if (!IsTestMode(browser_context())) { - // This array is volatile not to let compiler optimize us out. - volatile int testarray[3] = {0, 0, 0}; + int testarray[3] = {0, 0, 0}; // Cause Address Sanitizer to abort this process. - volatile int index = 5; + int index = 5; AccessArray(testarray, &index); } return RespondNow(NoArguments());
diff --git a/chrome/browser/chromeos/extensions/file_manager/private_api_file_system.cc b/chrome/browser/chromeos/extensions/file_manager/private_api_file_system.cc index fbeb42a..3175fb26 100644 --- a/chrome/browser/chromeos/extensions/file_manager/private_api_file_system.cc +++ b/chrome/browser/chromeos/extensions/file_manager/private_api_file_system.cc
@@ -1590,8 +1590,9 @@ std::move(source_urls), std::move(destination_folder_url), *type); break; } - volume_manager->io_task_controller()->Add(std::move(task)); - return RespondNow(NoArguments()); + const auto taskId = + volume_manager->io_task_controller()->Add(std::move(task)); + return RespondNow(OneArgument(base::Value(static_cast<int>(taskId)))); } ExtensionFunction::ResponseAction
diff --git a/chrome/browser/chromeos/extensions/file_manager/private_api_misc.cc b/chrome/browser/chromeos/extensions/file_manager/private_api_misc.cc index 66b7114..c82e706 100644 --- a/chrome/browser/chromeos/extensions/file_manager/private_api_misc.cc +++ b/chrome/browser/chromeos/extensions/file_manager/private_api_misc.cc
@@ -1223,6 +1223,7 @@ model->GetRecentFiles( file_system_context.get(), source_url(), file_type, + params->invalidate_cache, base::BindOnce( &FileManagerPrivateInternalGetRecentFilesFunction::OnGetRecentFiles, this, params->restriction));
diff --git a/chrome/browser/chromeos/fileapi/recent_model.cc b/chrome/browser/chromeos/fileapi/recent_model.cc index a32fc6f..69f1ea21 100644 --- a/chrome/browser/chromeos/fileapi/recent_model.cc +++ b/chrome/browser/chromeos/fileapi/recent_model.cc
@@ -87,12 +87,19 @@ storage::FileSystemContext* file_system_context, const GURL& origin, FileType file_type, + bool invalidate_cache, GetRecentFilesCallback callback) { DCHECK_CURRENTLY_ON(BrowserThread::UI); - // Use cache if available. + /** + * Use cache only if: + * * cache has value. + * * invalidate_cache = false. + * * cached file type matches the query file type. + * Otherwise clear cache if it has values. + */ if (cached_files_.has_value()) { - if (cached_files_type_ == file_type) { + if (!invalidate_cache && cached_files_type_ == file_type) { std::move(callback).Run(cached_files_.value()); return; }
diff --git a/chrome/browser/chromeos/fileapi/recent_model.h b/chrome/browser/chromeos/fileapi/recent_model.h index 169fd60a..d5f5e2a 100644 --- a/chrome/browser/chromeos/fileapi/recent_model.h +++ b/chrome/browser/chromeos/fileapi/recent_model.h
@@ -60,6 +60,7 @@ void GetRecentFiles(storage::FileSystemContext* file_system_context, const GURL& origin, FileType file_type, + bool invalidate_cache, GetRecentFilesCallback callback); // KeyedService overrides: @@ -68,7 +69,10 @@ private: friend class RecentModelFactory; friend class RecentModelTest; + friend class RecentModelCacheTest; FRIEND_TEST_ALL_PREFIXES(RecentModelTest, GetRecentFiles_UmaStats); + FRIEND_TEST_ALL_PREFIXES(RecentModelCacheTest, + GetRecentFiles_InvalidateCache); static const char kLoadHistogramName[];
diff --git a/chrome/browser/chromeos/fileapi/recent_model_unittest.cc b/chrome/browser/chromeos/fileapi/recent_model_unittest.cc index a633a07..7c81312 100644 --- a/chrome/browser/chromeos/fileapi/recent_model_unittest.cc +++ b/chrome/browser/chromeos/fileapi/recent_model_unittest.cc
@@ -47,6 +47,29 @@ return sources; } +std::vector<RecentFile> GetRecentFiles(RecentModel* model, + RecentModel::FileType file_type, + bool invalidate_cache) { + std::vector<RecentFile> files; + + base::RunLoop run_loop; + + model->GetRecentFiles( + nullptr /* file_system_context */, GURL() /* origin */, file_type, + invalidate_cache, + base::BindOnce( + [](base::RunLoop* run_loop, std::vector<RecentFile>* files_out, + const std::vector<RecentFile>& files) { + *files_out = files; + run_loop->Quit(); + }, + &run_loop, &files)); + + run_loop.Run(); + + return files; +} + } // namespace class RecentModelTest : public testing::Test { @@ -61,7 +84,8 @@ RecentSourceListFactory source_list_factory, size_t max_files, const base::Time& cutoff_time, - RecentModel::FileType file_type) { + RecentModel::FileType file_type, + bool invalidate_cache) { RecentModel* model = static_cast<RecentModel*>( RecentModelFactory::GetInstance()->SetTestingFactoryAndUse( &profile_, @@ -76,23 +100,7 @@ model->SetMaxFilesForTest(max_files); model->SetForcedCutoffTimeForTest(cutoff_time); - std::vector<RecentFile> files; - - base::RunLoop run_loop; - - model->GetRecentFiles( - nullptr /* file_system_context */, GURL() /* origin */, file_type, - base::BindOnce( - [](base::RunLoop* run_loop, std::vector<RecentFile>* files_out, - const std::vector<RecentFile>& files) { - *files_out = files; - run_loop->Quit(); - }, - &run_loop, &files)); - - run_loop.Run(); - - return files; + return GetRecentFiles(model, file_type, invalidate_cache); } content::BrowserTaskEnvironment task_environment_; @@ -100,9 +108,9 @@ }; TEST_F(RecentModelTest, GetRecentFiles) { - std::vector<RecentFile> files = - BuildModelAndGetRecentFiles(base::BindRepeating(&BuildDefaultSources), 10, - base::Time(), RecentModel::FileType::kAll); + std::vector<RecentFile> files = BuildModelAndGetRecentFiles( + base::BindRepeating(&BuildDefaultSources), 10, base::Time(), + RecentModel::FileType::kAll, false); ASSERT_EQ(4u, files.size()); EXPECT_EQ("ddd.ogg", files[0].url().path().value()); @@ -116,9 +124,9 @@ } TEST_F(RecentModelTest, GetRecentFiles_MaxFiles) { - std::vector<RecentFile> files = - BuildModelAndGetRecentFiles(base::BindRepeating(&BuildDefaultSources), 3, - base::Time(), RecentModel::FileType::kAll); + std::vector<RecentFile> files = BuildModelAndGetRecentFiles( + base::BindRepeating(&BuildDefaultSources), 3, base::Time(), + RecentModel::FileType::kAll, false); ASSERT_EQ(3u, files.size()); EXPECT_EQ("ddd.ogg", files[0].url().path().value()); @@ -132,7 +140,7 @@ TEST_F(RecentModelTest, GetRecentFiles_CutoffTime) { std::vector<RecentFile> files = BuildModelAndGetRecentFiles( base::BindRepeating(&BuildDefaultSources), 10, - base::Time::FromJavaTime(2500), RecentModel::FileType::kAll); + base::Time::FromJavaTime(2500), RecentModel::FileType::kAll, false); ASSERT_EQ(2u, files.size()); EXPECT_EQ("ddd.ogg", files[0].url().path().value()); @@ -146,15 +154,15 @@ BuildModelAndGetRecentFiles( base::BindRepeating([]() { return RecentSourceList(); }), 10, - base::Time(), RecentModel::FileType::kAll); + base::Time(), RecentModel::FileType::kAll, false); histogram_tester.ExpectTotalCount(RecentModel::kLoadHistogramName, 1); } TEST_F(RecentModelTest, GetRecentFiles_Audio) { - std::vector<RecentFile> files = - BuildModelAndGetRecentFiles(base::BindRepeating(&BuildDefaultSources), 10, - base::Time(), RecentModel::FileType::kAudio); + std::vector<RecentFile> files = BuildModelAndGetRecentFiles( + base::BindRepeating(&BuildDefaultSources), 10, base::Time(), + RecentModel::FileType::kAudio, false); ASSERT_EQ(1u, files.size()); EXPECT_EQ("ddd.ogg", files[0].url().path().value()); @@ -162,9 +170,9 @@ } TEST_F(RecentModelTest, GetRecentFiles_Image) { - std::vector<RecentFile> files = - BuildModelAndGetRecentFiles(base::BindRepeating(&BuildDefaultSources), 10, - base::Time(), RecentModel::FileType::kImage); + std::vector<RecentFile> files = BuildModelAndGetRecentFiles( + base::BindRepeating(&BuildDefaultSources), 10, base::Time(), + RecentModel::FileType::kImage, false); ASSERT_EQ(2u, files.size()); EXPECT_EQ("bbb.png", files[0].url().path().value()); @@ -174,13 +182,40 @@ } TEST_F(RecentModelTest, GetRecentFiles_Video) { - std::vector<RecentFile> files = - BuildModelAndGetRecentFiles(base::BindRepeating(&BuildDefaultSources), 10, - base::Time(), RecentModel::FileType::kVideo); + std::vector<RecentFile> files = BuildModelAndGetRecentFiles( + base::BindRepeating(&BuildDefaultSources), 10, base::Time(), + RecentModel::FileType::kVideo, false); ASSERT_EQ(1u, files.size()); EXPECT_EQ("ccc.mp4", files[0].url().path().value()); EXPECT_EQ(base::Time::FromJavaTime(3000), files[0].last_modified()); } +// Do not use RecentModelTest fixture, because we need to get a reference of +// RecentModel and call GetRecentFiles() multiple times. +TEST(RecentModelCacheTest, GetRecentFiles_InvalidateCache) { + content::BrowserTaskEnvironment task_environment; + std::unique_ptr<RecentModel> model = + RecentModel::CreateForTest(BuildDefaultSources()); + model->SetForcedCutoffTimeForTest(base::Time()); + + std::vector<RecentFile> files1 = + GetRecentFiles(model.get(), RecentModel::FileType::kAll, false); + ASSERT_EQ(4u, files1.size()); + + // Shutdown() will clear all sources. + model->Shutdown(); + + // The returned file list should still has 4 files even though all sources has + // been cleared in Shutdown(), because it hits cache. + std::vector<RecentFile> files2 = + GetRecentFiles(model.get(), RecentModel::FileType::kAll, false); + ASSERT_EQ(4u, files2.size()); + + // Inalidate cache and query again. + std::vector<RecentFile> files3 = + GetRecentFiles(model.get(), RecentModel::FileType::kAll, true); + ASSERT_EQ(0u, files3.size()); +} + } // namespace chromeos
diff --git a/chrome/browser/extensions/active_tab_permission_granter.cc b/chrome/browser/extensions/active_tab_permission_granter.cc index 3c487b7..09d9c77 100644 --- a/chrome/browser/extensions/active_tab_permission_granter.cc +++ b/chrome/browser/extensions/active_tab_permission_granter.cc
@@ -162,8 +162,8 @@ const PermissionsData* permissions_data = extension->permissions_data(); - // TODO(crbug.com/698985): This should be GetLastCommittedURL(). - const GURL& url = web_contents()->GetVisibleURL(); + const GURL& url = + web_contents()->GetMainFrame()->GetLastCommittedOrigin().GetURL(); // If the extension requested the host permission to |url| but had it // withheld, we grant it active tab-style permissions, even if it doesn't have @@ -185,7 +185,7 @@ if (!util::AllowFileAccess(extension->id(), browser_context)) { valid_schemes &= ~URLPattern::SCHEME_FILE; } - new_hosts.AddOrigin(valid_schemes, url.DeprecatedGetOriginAsURL()); + new_hosts.AddOrigin(valid_schemes, url); new_apis.insert(mojom::APIPermissionID::kTab); if (permissions_data->HasAPIPermission(
diff --git a/chrome/browser/extensions/api/vpn_provider/OWNERS b/chrome/browser/extensions/api/vpn_provider/OWNERS index a913a05..499be61f 100644 --- a/chrome/browser/extensions/api/vpn_provider/OWNERS +++ b/chrome/browser/extensions/api/vpn_provider/OWNERS
@@ -1,2 +1,3 @@ bartfab@chromium.org emaxx@chromium.org +greengrape@google.com
diff --git a/chrome/browser/flags/android/chrome_feature_list.cc b/chrome/browser/flags/android/chrome_feature_list.cc index b6e4df3..5280289 100644 --- a/chrome/browser/flags/android/chrome_feature_list.cc +++ b/chrome/browser/flags/android/chrome_feature_list.cc
@@ -117,7 +117,6 @@ &shared_highlighting::kSharedHighlightingAmp, &features::kElasticOverscroll, &features::kElidePrioritizationOfPreNativeBootstrapTasks, - &features::kElideTabPreloadAtStartup, &features::kGiveJavaUiThreadDefaultTaskTraitsUserBlockingPriority, &features::kPrivacyGuide, &features::kPushMessagingDisallowSenderIDs,
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 637bfda..11eb8762 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
@@ -58,7 +58,6 @@ .put(ChromeFeatureList.EARLY_LIBRARY_LOAD, true) .put(ChromeFeatureList.ELASTIC_OVERSCROLL, true) .put(ChromeFeatureList.ELIDE_PRIORITIZATION_OF_PRE_NATIVE_BOOTSTRAP_TASKS, true) - .put(ChromeFeatureList.ELIDE_TAB_PRELOAD_AT_STARTUP, true) .put(ChromeFeatureList .GIVE_JAVA_UI_THREAD_DEFAULT_TASK_TRAITS_USER_BLOCKING_PRIORITY, 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 8aa7e2c..ab455bf 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
@@ -332,7 +332,6 @@ public static final String EARLY_LIBRARY_LOAD = "EarlyLibraryLoad"; public static final String ELIDE_PRIORITIZATION_OF_PRE_NATIVE_BOOTSTRAP_TASKS = "ElidePrioritizationOfPreNativeBootstrapTasks"; - public static final String ELIDE_TAB_PRELOAD_AT_STARTUP = "ElideTabPreloadAtStartup"; public static final String ENABLE_AUTOMATIC_SNOOZE = "EnableAutomaticSnooze"; public static final String ELASTIC_OVERSCROLL = "ElasticOverscroll"; public static final String EXPERIMENTS_FOR_AGSA = "ExperimentsForAgsa";
diff --git a/chrome/browser/nearby_sharing/nearby_notification_manager_unittest.cc b/chrome/browser/nearby_sharing/nearby_notification_manager_unittest.cc index 7ec1c8f..f7a7faf 100644 --- a/chrome/browser/nearby_sharing/nearby_notification_manager_unittest.cc +++ b/chrome/browser/nearby_sharing/nearby_notification_manager_unittest.cc
@@ -579,7 +579,7 @@ TEST_P(NearbyNotificationManagerTest, ShowProgress_DeviceNameEncoding) { ShareTarget share_target; - share_target.device_name = u8"\xf0\x9f\x8c\xb5"; // Cactus emoji. + share_target.device_name = "🌵"; TransferMetadata transfer_metadata = TransferMetadataBuilder().set_progress(75.0).build(); @@ -869,7 +869,7 @@ TEST_P(NearbyNotificationManagerTest, ShowConnectionRequest_DeviceNameEncoding) { ShareTarget share_target; - share_target.device_name = u8"\xf0\x9f\x8c\xb5"; // Cactus emoji. + share_target.device_name = "🌵"; manager()->ShowConnectionRequest(share_target, TransferMetadataBuilder().build()); @@ -1017,7 +1017,7 @@ TEST_P(NearbyNotificationManagerTest, ShowSuccess_DeviceNameEncoding) { ShareTarget share_target; - share_target.device_name = u8"\xf0\x9f\x8c\xb5"; // Cactus emoji. + share_target.device_name = "🌵"; manager()->ShowSuccess(share_target); std::vector<message_center::Notification> notifications = @@ -1036,7 +1036,7 @@ TEST_P(NearbyNotificationManagerTest, ShowCancelled_DeviceNameEncoding) { ShareTarget share_target; - share_target.device_name = u8"\xf0\x9f\x8c\xb5"; // Cactus emoji. + share_target.device_name = "🌵"; manager()->ShowCancelled(share_target); std::vector<message_center::Notification> notifications = @@ -1069,7 +1069,7 @@ TEST_P(NearbyNotificationManagerTest, ShowFailure_DeviceNameEncoding) { ShareTarget share_target; - share_target.device_name = u8"\xf0\x9f\x8c\xb5"; // Cactus emoji. + share_target.device_name = "🌵"; manager()->ShowFailure(share_target, TransferMetadataBuilder().build()); std::vector<message_center::Notification> notifications =
diff --git a/chrome/browser/net/system_network_context_manager.cc b/chrome/browser/net/system_network_context_manager.cc index 0269a741..dbac783 100644 --- a/chrome/browser/net/system_network_context_manager.cc +++ b/chrome/browser/net/system_network_context_manager.cc
@@ -124,7 +124,7 @@ kMaxValue = kDisabledBecauseOfFailedLaunch }; -// The global instance of the SystemNetworkContextmanager. +// The global instance of the SystemNetworkContextManager. SystemNetworkContextManager* g_system_network_context_manager = nullptr; // Whether or not any instance of the system network context manager has @@ -216,7 +216,7 @@ #endif // Note: intentionally checking the feature state here rather than falling // back to CertVerifierImpl::kDefault, as browser-side network context - // initializition for TrialComparisonCertVerifier depends on knowing which + // initialization for TrialComparisonCertVerifier depends on knowing which // verifier will be used. return base::FeatureList::IsEnabled( net::features::kCertVerifierBuiltinFeature); @@ -229,7 +229,7 @@ bool ShouldUseChromeRootStore(PrefService* local_state) { // Note: intentionally checking the feature state here rather than falling // back to ChromeRootImpl::kRootDefault, as browser-side network context - // initializition for TrialComparisonCertVerifier depends on knowing which + // initialization for TrialComparisonCertVerifier depends on knowing which // verifier will be used. return base::FeatureList::IsEnabled(net::features::kChromeRootStoreUsed); }
diff --git a/chrome/browser/net/system_network_context_manager.h b/chrome/browser/net/system_network_context_manager.h index bcfa282..52bd8ae 100644 --- a/chrome/browser/net/system_network_context_manager.h +++ b/chrome/browser/net/system_network_context_manager.h
@@ -111,7 +111,7 @@ void DisableQuic(); // Returns an mojo::PendingReceiver<SSLConfigClient> that can be passed as a - // NetorkContextParam. + // NetworkContextParam. mojo::PendingReceiver<network::mojom::SSLConfigClient> GetSSLConfigClientReceiver();
diff --git a/chrome/browser/page_load_metrics/observers/document_write_page_load_metrics_observer.cc b/chrome/browser/page_load_metrics/observers/document_write_page_load_metrics_observer.cc index 5b74d44..d5256d1 100644 --- a/chrome/browser/page_load_metrics/observers/document_write_page_load_metrics_observer.cc +++ b/chrome/browser/page_load_metrics/observers/document_write_page_load_metrics_observer.cc
@@ -22,11 +22,13 @@ "Background"; } // namespace internal -// TODO(https://crbug.com/1317494): Audit and use appropriate policy. page_load_metrics::PageLoadMetricsObserver::ObservePolicy DocumentWritePageLoadMetricsObserver::OnFencedFramesStart( content::NavigationHandle* navigation_handle, const GURL& currently_committed_url) { + // This class is interested in events that are dispatched only for the primary + // page or preprocessed by PageLoadTracker to be per-outermost page. So, no + // need to forward events at the observer layer. return STOP_OBSERVING; }
diff --git a/chrome/browser/page_load_metrics/observers/https_engagement_metrics/https_engagement_page_load_metrics_observer.cc b/chrome/browser/page_load_metrics/observers/https_engagement_metrics/https_engagement_page_load_metrics_observer.cc index 54de87fd..1b9c04c 100644 --- a/chrome/browser/page_load_metrics/observers/https_engagement_metrics/https_engagement_page_load_metrics_observer.cc +++ b/chrome/browser/page_load_metrics/observers/https_engagement_metrics/https_engagement_page_load_metrics_observer.cc
@@ -19,11 +19,12 @@ HttpsEngagementServiceFactory::GetForBrowserContext(context); } -// TODO(https://crbug.com/1317494): Audit and use appropriate policy. page_load_metrics::PageLoadMetricsObserver::ObservePolicy HttpsEngagementPageLoadMetricsObserver::OnFencedFramesStart( content::NavigationHandle* navigation_handle, const GURL& currently_committed_url) { + // This class is interested only in the primary page's end of life timing, + // and doesn't need to continue observing FencedFrame pages. return STOP_OBSERVING; }
diff --git a/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer.cc b/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer.cc index 77c1115..96c1770 100644 --- a/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer.cc +++ b/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer.cc
@@ -101,11 +101,15 @@ return CONTINUE_OBSERVING; } -// TODO(https://crbug.com/1317494): Audit and use appropriate policy. page_load_metrics::PageLoadMetricsObserver::ObservePolicy SecurityStatePageLoadMetricsObserver::OnFencedFramesStart( content::NavigationHandle* navigation_handle, const GURL& currently_committed_url) { + // All data aggregation are done in SiteEngagementService and + // SecurityStateTabHelper, and this class just monitors the timings to record + // the aggregated data. As the outermost page's OnCommit and OnComplete are + // the timing this class is interested in, it just stops observing + // FencedFrames. return STOP_OBSERVING; }
diff --git a/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer_browsertest.cc b/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer_browsertest.cc index 7cde8e8..a00447a 100644 --- a/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer_browsertest.cc +++ b/chrome/browser/page_load_metrics/observers/security_state_page_load_metrics_observer_browsertest.cc
@@ -665,11 +665,8 @@ content::test::FencedFrameTestHelper fenced_frame_helper_; }; -// TODO(crbug.com/1301880): This test will be enabled after toyoshim@'s CL -// restricts call to SecurityStatePageLoadMetricsObserver::OnCommit for fenced -// frames" IN_PROC_BROWSER_TEST_F(SecurityStatePageLoadMetricsFencedFrameBrowserTest, - DISABLED_DoNotRecordOnCommitSecurityLevelHistogram) { + DoNotRecordOnCommitSecurityLevelHistogram) { StartHttpsServer(net::EmbeddedTestServer::CERT_OK); GURL https_url = https_test_server()->GetURL("/title1.html");
diff --git a/chrome/browser/page_load_metrics/observers/service_worker_page_load_metrics_observer.cc b/chrome/browser/page_load_metrics/observers/service_worker_page_load_metrics_observer.cc index 15b5589c..6162a6f 100644 --- a/chrome/browser/page_load_metrics/observers/service_worker_page_load_metrics_observer.cc +++ b/chrome/browser/page_load_metrics/observers/service_worker_page_load_metrics_observer.cc
@@ -106,11 +106,12 @@ ServiceWorkerPageLoadMetricsObserver::ServiceWorkerPageLoadMetricsObserver() {} -// TODO(https://crbug.com/1317494): Audit and use appropriate policy. page_load_metrics::PageLoadMetricsObserver::ObservePolicy ServiceWorkerPageLoadMetricsObserver::OnFencedFramesStart( content::NavigationHandle* navigation_handle, const GURL& currently_committed_url) { + // All events this class is interested in are preprocessed and forwarded at + // PageLoadTracker and observer doesn't need to care for forwarding. return STOP_OBSERVING; }
diff --git a/chrome/browser/page_load_metrics/observers/session_restore_page_load_metrics_observer.cc b/chrome/browser/page_load_metrics/observers/session_restore_page_load_metrics_observer.cc index 4ba952a..b41e0699 100644 --- a/chrome/browser/page_load_metrics/observers/session_restore_page_load_metrics_observer.cc +++ b/chrome/browser/page_load_metrics/observers/session_restore_page_load_metrics_observer.cc
@@ -49,11 +49,12 @@ return CONTINUE_OBSERVING; } -// TODO(https://crbug.com/1317494): Audit and use appropriate policy. page_load_metrics::PageLoadMetricsObserver::ObservePolicy SessionRestorePageLoadMetricsObserver::OnFencedFramesStart( content::NavigationHandle* navigation_handle, const GURL& currently_committed_url) { + // This class is interested only in preprocessed lifecycle events that are + // already dispatched also to the outermost page observer. return STOP_OBSERVING; }
diff --git a/chrome/browser/page_load_metrics/observers/signed_exchange_page_load_metrics_observer.cc b/chrome/browser/page_load_metrics/observers/signed_exchange_page_load_metrics_observer.cc index f431cb2c..6e44968 100644 --- a/chrome/browser/page_load_metrics/observers/signed_exchange_page_load_metrics_observer.cc +++ b/chrome/browser/page_load_metrics/observers/signed_exchange_page_load_metrics_observer.cc
@@ -104,11 +104,13 @@ SignedExchangePageLoadMetricsObserver::SignedExchangePageLoadMetricsObserver() { } -// TODO(https://crbug.com/1317494): Audit and use appropriate policy. page_load_metrics::PageLoadMetricsObserver::ObservePolicy SignedExchangePageLoadMetricsObserver::OnFencedFramesStart( content::NavigationHandle* navigation_handle, const GURL& currently_committed_url) { + // This class is interested only in events that are preprocessed and + // dispatched also to the outermost page at PageLoadTracker. So, this class + // doesn't need to forward events for FencedFrames. return STOP_OBSERVING; }
diff --git a/chrome/browser/policy/messaging_layer/upload/record_handler_impl_unittest.cc b/chrome/browser/policy/messaging_layer/upload/record_handler_impl_unittest.cc index be14080e..ca2a450 100644 --- a/chrome/browser/policy/messaging_layer/upload/record_handler_impl_unittest.cc +++ b/chrome/browser/policy/messaging_layer/upload/record_handler_impl_unittest.cc
@@ -68,9 +68,6 @@ using TestEncryptionKeyAttached = MockFunction<void(SignedEncryptionInfo)>; -// TODO(https://crbug.com/1297261): Change the various out params in the helper -// functions below to return by value instead. - class RecordHandlerImplTest : public ::testing::TestWithParam< ::testing::tuple</*need_encryption_key*/ bool, /*force_confirm*/ bool>> {
diff --git a/chrome/browser/prefetch/prefetch_proxy/prefetch_proxy_browsertest.cc b/chrome/browser/prefetch/prefetch_proxy/prefetch_proxy_browsertest.cc index 68508d68..be148e3 100644 --- a/chrome/browser/prefetch/prefetch_proxy/prefetch_proxy_browsertest.cc +++ b/chrome/browser/prefetch/prefetch_proxy/prefetch_proxy_browsertest.cc
@@ -4246,11 +4246,14 @@ ukm::builders::PrefetchProxy_AfterSRPClick:: kSRPClickPrefetchStatusName)); + // In addition to "prefetch.js" and "prefetch-redirect-start.js", + // "favicon.ico" is also counted here, because the favicon loading is + // triggered from `FrameLoader::DidFinishNavigation()` at the end of NSP. histogram_tester.ExpectUniqueSample( - "PrefetchProxy.Prefetch.Subresources.NetError", net::OK, 2); + "PrefetchProxy.Prefetch.Subresources.NetError", net::OK, 3); histogram_tester.ExpectUniqueSample( "PrefetchProxy.Prefetch.Subresources.Quantity", 4, 1); - histogram_tester.ExpectUniqueSample( + histogram_tester.ExpectBucketCount( "PrefetchProxy.Prefetch.Subresources.RespCode", 200, 2); histogram_tester.ExpectUniqueSample( "PrefetchProxy.AfterClick.Subresources.UsedCache", true, 2);
diff --git a/chrome/browser/resources/chromeos/arc_account_picker/BUILD.gn b/chrome/browser/resources/chromeos/arc_account_picker/BUILD.gn index 785b10e..7437fca 100644 --- a/chrome/browser/resources/chromeos/arc_account_picker/BUILD.gn +++ b/chrome/browser/resources/chromeos/arc_account_picker/BUILD.gn
@@ -67,6 +67,7 @@ deps = [ ":arc_account_picker_browser_proxy", "//third_party/polymer/v3_0/components-chromium/polymer:polymer_bundled", + "//ui/webui/resources/js:load_time_data.m", ] }
diff --git a/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.html b/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.html index 278e2a4..bd83db56 100644 --- a/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.html +++ b/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.html
@@ -94,44 +94,68 @@ #addAccountButton > .account-name > .primary { margin-bottom: 0; } + + .use-two-column-layout.main-container { + /* Add top margin to account for the button bar and match next pages */ + --margin-top: 96px; + display: flex; + flex-direction: row; + height: calc(100% - var(--margin-top)); + margin-top: var(--margin-top); + } + + .use-two-column-layout .column-1 { + flex: 1 1 0; + margin-inline-end: 80px; + } + + .use-two-column-layout .column-2 { + flex: 1.5 1 0; + /* Size of the icon + margin */ + margin-top: calc(24px + 28px); + } </style> -<div class="main-container"> - <if expr="_google_chrome"> - <img class="google-full-logo" - src="chrome://theme/IDR_LOGO_GOOGLE_COLOR_90" alt=""> - </if> +<div class$="[[getMainContainerClass_(useTwoColumnLayout)]]"> + <div class="column-1"> + <if expr="_google_chrome"> + <img class="google-full-logo" + src="chrome://theme/IDR_LOGO_GOOGLE_COLOR_90" alt=""> + </if> - <h1>$i18n{accountManagerDialogArcAccountPickerTitle}</h1> - <p class="secondary text-body" + <h1>$i18n{accountManagerDialogArcAccountPickerTitle}</h1> + <p class="secondary text-body" >$i18nRaw{accountManagerDialogArcAccountPickerBody}</p> + </div> - <template is="dom-repeat" id="accountsContainer" items="[[accounts_]]"> - <div class="account-item" on-click="makeAvailableInArc_" - on-keypress="onAccountKeyPress_" - tabindex="0" role="button" - aria-labelledby$="fullName-[[index]] email-[[index]]" - aria-description="$i18n{accountUseInArcButtonLabel}"> - <div class="account-icon" aria-hidden="true" - style="background-image: [[getIconImageSet_(item.image)]]"> + <div class="column-2"> + <template is="dom-repeat" id="accountsContainer" items="[[accounts_]]"> + <div class="account-item" on-click="makeAvailableInArc_" + on-keypress="onAccountKeyPress_" + tabindex="0" role="button" + aria-labelledby$="fullName-[[index]] email-[[index]]" + aria-description="$i18n{accountUseInArcButtonLabel}"> + <div class="account-icon" aria-hidden="true" + style="background-image: [[getIconImageSet_(item.image)]]"> + </div> + <div class="account-name"> + <span class="primary" id="fullName-[[index]]" + aria-hidden="true">[[item.fullName]]</span> + <span class="secondary" id="email-[[index]]" + aria-hidden="true">[[item.email]]</span> + </div> </div> - <div class="account-name"> - <span class="primary" id="fullName-[[index]]" - aria-hidden="true">[[item.fullName]]</span> - <span class="secondary" id="email-[[index]]" - aria-hidden="true">[[item.email]]</span> - </div> - </div> - </template> + </template> - <div class="account-item" id="addAccountButton" on-click="addAccount_" - on-keypress="onAddAccountKeyPress_" tabindex="0" role="button" - aria-label="$i18n{addAccountLabel}"> - <div class="account-icon" aria-hidden="true"> - <div class="add-icon"></div> - </div> - <div class="account-name" aria-hidden="true"> - <span class="primary">$i18n{addAccountLabel}</span> + <div class="account-item" id="addAccountButton" on-click="addAccount_" + on-keypress="onAddAccountKeyPress_" tabindex="0" role="button" + aria-label="[[getAddAccountButtonLabel_(isChildUser_)]]"> + <div class="account-icon" aria-hidden="true"> + <div class="add-icon"></div> + </div> + <div class="account-name" aria-hidden="true"> + <span class="primary">[[getAddAccountButtonLabel_(isChildUser_)]]</span> + </div> </div> </div>
diff --git a/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.js b/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.js index 4307a37..7926fd1 100644 --- a/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.js +++ b/chrome/browser/resources/chromeos/arc_account_picker/arc_account_picker_app.js
@@ -3,9 +3,12 @@ // found in the LICENSE file. import '../account_manager_shared_css.js'; +import '../strings.m.js'; import {getImage} from '//resources/js/icon.js'; import {html, PolymerElement} from '//resources/polymer/v3_0/polymer/polymer_bundled.min.js'; +import {loadTimeData} from 'chrome://resources/js/load_time_data.m.js'; + import {Account, ArcAccountPickerBrowserProxy, ArcAccountPickerBrowserProxyImpl} from './arc_account_picker_browser_proxy.js'; /** @@ -39,6 +42,23 @@ static get properties() { return { /** + * Whether two column layout should be used. + * @public {boolean} + */ + useTwoColumnLayout: { + type: Boolean, + value: false, + }, + + /** @private {boolean} */ + isChildUser_: { + type: Boolean, + value() { + return loadTimeData.getBoolean('isChild'); + }, + }, + + /** * Accounts which are not available in ARC and are shown on the ARC picker * screen. * @private {!Array<!Account>} @@ -84,6 +104,27 @@ } /** + * @return {string} A class name list for the main container. + * @private + */ + getMainContainerClass_() { + if (this.useTwoColumnLayout) { + return 'main-container use-two-column-layout'; + } + + return 'main-container'; + } + + /** + * @return {string} A label for 'add account' button. + * @private + */ + getAddAccountButtonLabel_() { + return loadTimeData.getString( + this.isChildUser_ ? 'addSchoolAccountLabel' : 'addAccountLabel'); + } + + /** * @param {string} iconUrl * @return {string} A CSS image-set for multiple scale factors. * @private
diff --git a/chrome/browser/resources/chromeos/edu_coexistence/edu_coexistence_app.html b/chrome/browser/resources/chromeos/edu_coexistence/edu_coexistence_app.html index d64cca5..51c4a90 100644 --- a/chrome/browser/resources/chromeos/edu_coexistence/edu_coexistence_app.html +++ b/chrome/browser/resources/chromeos/edu_coexistence/edu_coexistence_app.html
@@ -6,6 +6,7 @@ <edu-coexistence-error id="edu-coexistence-error" slot="view"> </edu-coexistence-error> <arc-account-picker-app id="arc-account-picker" slot="view" + use-two-column-layout="true" on-opened-new-window="closeDialog_" on-add-account="showAddAccount_"> </arc-account-picker-app>
diff --git a/chrome/browser/resources/chromeos/login/security_token_pin_browsertest.js b/chrome/browser/resources/chromeos/login/security_token_pin_browsertest.js index 0e41c14..c28547f 100644 --- a/chrome/browser/resources/chromeos/login/security_token_pin_browsertest.js +++ b/chrome/browser/resources/chromeos/login/security_token_pin_browsertest.js
@@ -38,13 +38,7 @@ } }; -// This times out regularly on debug builds, see https://crbug.com/1304295 -GEN('#if !defined(NDEBUG)'); -GEN('#define MAYBE_All DISABLED_All'); -GEN('#else'); -GEN('#define MAYBE_All All'); -GEN('#endif'); -TEST_F('PolymerSecurityTokenPinTest', 'MAYBE_All', function() { +TEST_F('PolymerSecurityTokenPinTest', 'All', function() { const DEFAULT_PARAMETERS = { enableUserInput: true, hasError: false,
diff --git a/chrome/browser/site_isolation/site_per_process_interactive_browsertest.cc b/chrome/browser/site_isolation/site_per_process_interactive_browsertest.cc index c68baea..d568be4 100644 --- a/chrome/browser/site_isolation/site_per_process_interactive_browsertest.cc +++ b/chrome/browser/site_isolation/site_per_process_interactive_browsertest.cc
@@ -1618,7 +1618,14 @@ } // Check that window.focus works for cross-process popups. -IN_PROC_BROWSER_TEST_F(SitePerProcessInteractiveBrowserTest, PopupWindowFocus) { +// Flaky on ChromeOS debug and ASAN builds. https://crbug.com/1326293 +#if BUILDFLAG(IS_CHROMEOS) && (!defined(NDEBUG) || defined(ADDRESS_SANITIZER)) +#define MAYBE_PopupWindowFocus DISABLED_PopupWindowFocus +#else +#define MAYBE_PopupWindowFocus PopupWindowFocus +#endif +IN_PROC_BROWSER_TEST_F(SitePerProcessInteractiveBrowserTest, + MAYBE_PopupWindowFocus) { GURL main_url(embedded_test_server()->GetURL("/page_with_focus_events.html")); ASSERT_TRUE(ui_test_utils::NavigateToURL(browser(), main_url));
diff --git a/chrome/browser/sync/test/integration/preferences_helper.cc b/chrome/browser/sync/test/integration/preferences_helper.cc index b304972..6b7d3df1 100644 --- a/chrome/browser/sync/test/integration/preferences_helper.cc +++ b/chrome/browser/sync/test/integration/preferences_helper.cc
@@ -75,8 +75,11 @@ auto pref_store = base::MakeRefCounted<JsonPrefStore>( profile->GetPath().Append(chrome::kPreferencesFilename)); base::ScopedAllowBlockingForTesting allow_blocking; - if (pref_store->ReadPrefs() != PersistentPrefStore::PREF_READ_ERROR_NONE) { - ADD_FAILURE() << " Failed reading the prefs file into the store."; + PersistentPrefStore::PrefReadError result = pref_store->ReadPrefs(); + if (result != PersistentPrefStore::PREF_READ_ERROR_NONE) { + ADD_FAILURE() + << " Failed reading the prefs file into the store, error code " + << result; } return pref_store;
diff --git a/chrome/browser/ui/BUILD.gn b/chrome/browser/ui/BUILD.gn index 2b055fcf..90f0551 100644 --- a/chrome/browser/ui/BUILD.gn +++ b/chrome/browser/ui/BUILD.gn
@@ -3339,8 +3339,8 @@ "views/hats/hats_next_web_dialog.h", "views/privacy_sandbox/privacy_sandbox_dialog_view.cc", "views/privacy_sandbox/privacy_sandbox_dialog_view.h", - "views/privacy_sandbox/privacy_sandbox_notice_bubble_view.cc", - "views/privacy_sandbox/privacy_sandbox_notice_bubble_view.h", + "views/privacy_sandbox/privacy_sandbox_notice_bubble.cc", + "views/privacy_sandbox/privacy_sandbox_notice_bubble.h", "views/profiles/incognito_menu_view.cc", "views/profiles/incognito_menu_view.h", "views/profiles/profile_menu_view_base.cc",
diff --git a/chrome/browser/ui/views/payments/payment_request_use_stats_browsertest.cc b/chrome/browser/ui/views/payments/payment_request_use_stats_browsertest.cc index ef0ec58..88ed7e96c 100644 --- a/chrome/browser/ui/views/payments/payment_request_use_stats_browsertest.cc +++ b/chrome/browser/ui/views/payments/payment_request_use_stats_browsertest.cc
@@ -6,6 +6,8 @@ #include "base/strings/utf_string_conversions.h" #include "base/test/scoped_feature_list.h" +#include "build/build_config.h" +#include "build/buildflag.h" #include "chrome/browser/ui/browser_commands.h" #include "chrome/browser/ui/views/payments/payment_request_browsertest_base.h" #include "chrome/browser/ui/views/payments/payment_request_dialog_view_ids.h" @@ -224,7 +226,14 @@ // Tests that use stats for the contact address used in a Payment Request are // properly updated upon completion. -IN_PROC_BROWSER_TEST_F(PaymentRequestContactAddressUseStatsTest, RecordUse) { +// TODO(crbug.com/1328016): Flaky on Linux, investigate and re-enable. +#if BUILDFLAG(IS_LINUX) +#define MAYBE_RecordUse DISABLED_RecordUse +#else +#define MAYBE_RecordUse RecordUse +#endif +IN_PROC_BROWSER_TEST_F(PaymentRequestContactAddressUseStatsTest, + MAYBE_RecordUse) { NavigateTo("/payment_request_name_test.html"); autofill::TestAutofillClock test_clock; test_clock.SetNow(kSomeDate); @@ -348,8 +357,11 @@ // Tests that use stats for an address that was used both as a shipping and // contact address in a Payment Request are properly updated upon completion. +// TODO(crbug.com/1328016): Flaky on Linux, investigate and re-enable. +// MAYBE_RecordUse defined above (PaymentRequestContactAddressUseStatsTest +// fixture). IN_PROC_BROWSER_TEST_F(PaymentRequestSameShippingAndContactAddressUseStatsTest, - RecordUse) { + MAYBE_RecordUse) { NavigateTo("/payment_request_contact_details_and_free_shipping_test.html"); autofill::TestAutofillClock test_clock; test_clock.SetNow(kSomeDate);
diff --git a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.cc b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.cc new file mode 100644 index 0000000..fe009be --- /dev/null +++ b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.cc
@@ -0,0 +1,135 @@ +// Copyright 2022 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/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.h" + +#include "chrome/browser/privacy_sandbox/privacy_sandbox_service.h" +#include "chrome/browser/privacy_sandbox/privacy_sandbox_service_factory.h" +#include "chrome/browser/ui/browser.h" +#include "chrome/browser/ui/chrome_pages.h" +#include "chrome/browser/ui/privacy_sandbox/privacy_sandbox_prompt.h" +#include "chrome/browser/ui/views/bubble_anchor_util_views.h" +#include "chrome/grit/generated_resources.h" +#include "chrome/grit/theme_resources.h" +#include "ui/base/l10n/l10n_util.h" +#include "ui/views/bubble/bubble_dialog_model_host.h" + +using PromptAction = PrivacySandboxService::PromptAction; + +namespace { + +class PrivacySandboxNoticeBubbleModelDelegate : public ui::DialogModelDelegate { + public: + explicit PrivacySandboxNoticeBubbleModelDelegate(Browser* browser) + : browser_(browser) { + if (auto* privacy_sandbox_serivce = + PrivacySandboxServiceFactory::GetForProfile(browser_->profile())) { + privacy_sandbox_serivce->DialogOpenedForBrowser(browser_); + } + NotifyServiceAboutPromptAction(PromptAction::kNoticeShown); + } + + void OnDialogDestroying() { + if (!has_user_interacted_) { + NotifyServiceAboutPromptAction(PromptAction::kNoticeClosedNoInteraction); + } + if (auto* privacy_sandbox_serivce = + PrivacySandboxServiceFactory::GetForProfile(browser_->profile())) { + privacy_sandbox_serivce->DialogClosedForBrowser(browser_); + } + } + + void OnOkButtonPressed() { + has_user_interacted_ = true; + NotifyServiceAboutPromptAction(PromptAction::kNoticeAcknowledge); + } + + void OnSettingsLinkPressed() { + has_user_interacted_ = true; + chrome::ShowPrivacySandboxSettings(browser_); + NotifyServiceAboutPromptAction(PromptAction::kNoticeOpenSettings); + } + + void OnLearnMoreLinkPressed() { + has_user_interacted_ = true; + chrome::ShowPrivacySandboxLearnMore(browser_); + NotifyServiceAboutPromptAction(PromptAction::kNoticeLearnMore); + } + + void OnDialogExplicitlyClosed() { + if (!has_user_interacted_) { + NotifyServiceAboutPromptAction(PromptAction::kNoticeDismiss); + } + has_user_interacted_ = true; + } + + void NotifyServiceAboutPromptAction(PromptAction action) { + if (auto* service = + PrivacySandboxServiceFactory::GetForProfile(browser_->profile())) { + service->PromptActionOccurred(action); + } + } + + private: + Browser* browser_; + bool has_user_interacted_ = false; +}; + +} // namespace + +// static +void ShowPrivacySandboxNoticeBubble(Browser* browser) { + auto bubble_delegate_unique = + std::make_unique<PrivacySandboxNoticeBubbleModelDelegate>(browser); + PrivacySandboxNoticeBubbleModelDelegate* bubble_delegate = + bubble_delegate_unique.get(); + auto& bundle = ui::ResourceBundle::GetSharedInstance(); + auto dialog_model = + ui::DialogModel::Builder(std::move(bubble_delegate_unique)) + .SetTitle(l10n_util::GetStringUTF16( + IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_TITLE)) + .SetInternalName(kPrivacySandboxNoticeBubbleName) + .SetIcon(ui::ImageModel::FromImageSkia(*bundle.GetImageSkiaNamed( + IDR_PRIVACY_SANDBOX_CONFIRMATION_BANNER)), + ui::ImageModel::FromImageSkia(*bundle.GetImageSkiaNamed( + IDR_PRIVACY_SANDBOX_CONFIRMATION_BANNER_DARK))) + .AddBodyText(ui::DialogModelLabel::CreateWithLink( + IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_DESCRIPTION, + ui::DialogModelLabel::Link( + IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_DESCRIPTION_ESTIMATES_INTERESTS_LINK, + base::BindRepeating(&PrivacySandboxNoticeBubbleModelDelegate:: + OnLearnMoreLinkPressed, + base::Unretained(bubble_delegate))))) + .AddOkButton( + base::BindRepeating( + &PrivacySandboxNoticeBubbleModelDelegate::OnOkButtonPressed, + base::Unretained(bubble_delegate)), + l10n_util::GetStringUTF16( + IDS_PRIVACY_SANDBOX_DIALOG_NOTICE_ACKNOWLEDGE_BUTTON)) + .AddExtraLink(ui::DialogModelLabel::Link( + IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_SETTINGS_LINK, + base::BindRepeating(&PrivacySandboxNoticeBubbleModelDelegate:: + OnSettingsLinkPressed, + base::Unretained(bubble_delegate)))) + .SetCloseActionCallback( + base::BindOnce(&PrivacySandboxNoticeBubbleModelDelegate:: + OnDialogExplicitlyClosed, + base::Unretained(bubble_delegate))) + .SetDialogDestroyingCallback(base::BindOnce( + &PrivacySandboxNoticeBubbleModelDelegate::OnDialogDestroying, + base::Unretained(bubble_delegate))) + .Build(); + + bubble_anchor_util::AnchorConfiguration configuration = + bubble_anchor_util::GetAppMenuAnchorConfiguration(browser); + auto bubble = std::make_unique<views::BubbleDialogModelHost>( + std::move(dialog_model), configuration.anchor_view, + configuration.bubble_arrow); + // The bubble isn't opened as a result of a user action. It shouldn't take the + // focus away from the current tasks. Open the bubble starting as inactive + // also avoids unintentionally closing it due to focus loss until the user has + // interacted with it. After a user interaction, it may be closed on focus + // loss. + views::BubbleDialogDelegate::CreateBubble(std::move(bubble))->ShowInactive(); +}
diff --git a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.h b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.h new file mode 100644 index 0000000..58e37bb --- /dev/null +++ b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.h
@@ -0,0 +1,11 @@ +// Copyright 2022 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_UI_VIEWS_PRIVACY_SANDBOX_PRIVACY_SANDBOX_NOTICE_BUBBLE_H_ +#define CHROME_BROWSER_UI_VIEWS_PRIVACY_SANDBOX_PRIVACY_SANDBOX_NOTICE_BUBBLE_H_ + +static constexpr char kPrivacySandboxNoticeBubbleName[] = + "PrivacySandboxNoticeBubble"; + +#endif // CHROME_BROWSER_UI_VIEWS_PRIVACY_SANDBOX_PRIVACY_SANDBOX_NOTICE_BUBBLE_H_
diff --git a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view_browsertest.cc b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_browsertest.cc similarity index 82% rename from chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view_browsertest.cc rename to chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_browsertest.cc index 4ca2773..73dc469 100644 --- a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view_browsertest.cc +++ b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_browsertest.cc
@@ -13,8 +13,11 @@ #include "chrome/browser/ui/tabs/tab_strip_model.h" #include "chrome/browser/ui/test/test_browser_dialog.h" #include "chrome/browser/ui/views/frame/browser_view.h" -#include "chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.h" +#include "chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble.h" +#include "chrome/common/webui_url_constants.h" +#include "chrome/test/base/ui_test_utils.h" #include "components/privacy_sandbox/privacy_sandbox_features.h" +#include "components/privacy_sandbox/privacy_sandbox_prefs.h" #include "content/public/browser/web_contents.h" #include "content/public/test/browser_test.h" #include "testing/gmock/include/gmock/gmock.h" @@ -28,15 +31,14 @@ namespace { views::Widget* ShowBubble(Browser* browser) { - views::NamedWidgetShownWaiter waiter( - views::test::AnyWidgetTestPasskey{}, - PrivacySandboxNoticeBubbleView::kViewClassName); + views::NamedWidgetShownWaiter waiter(views::test::AnyWidgetTestPasskey{}, + kPrivacySandboxNoticeBubbleName); ShowPrivacySandboxPrompt(browser, PrivacySandboxService::PromptType::kNotice); return waiter.WaitIfNeededAndGet(); } void ClickButton(views::BubbleDialogDelegate* bubble_delegate, - views::Button* button) { + views::View* button) { // Reset the timer to make sure that test click isn't discarded as possibly // unintended. bubble_delegate->ResetViewShownTimeStampForTesting(); @@ -50,7 +52,7 @@ } // namespace -class PrivacySandboxNoticeBubbleViewBrowserTest : public DialogBrowserTest { +class PrivacySandboxNoticeBubbleBrowserTest : public DialogBrowserTest { public: void SetUpOnMainThread() override { mock_service_ = static_cast<MockPrivacySandboxService*>( @@ -89,7 +91,7 @@ base::test::ScopedFeatureList feature_list_; }; -IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleViewBrowserTest, +IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleBrowserTest, InvokeUi_NoticeBubble) { EXPECT_CALL( *mock_service(), @@ -101,7 +103,7 @@ ShowAndVerifyUi(); } -IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleViewBrowserTest, +IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleBrowserTest, EscapeClosesNotice) { // Check that when the escape key is pressed, the notice bubble is closed. EXPECT_CALL( @@ -120,8 +122,10 @@ VerifyBubbleWasClosed(bubble); } -IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleViewBrowserTest, - AppMenuClosesNotice) { +// TODO(crbug.com/1321587): Figure out what to do with the bubble when the app +// menu is shown. Update the test to test that. +IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleBrowserTest, + DISABLED_AppMenuClosesNotice) { // Check that when the app menu is opened, the notice bubble is closed. EXPECT_CALL( *mock_service(), @@ -139,7 +143,7 @@ VerifyBubbleWasClosed(bubble); } -IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleViewBrowserTest, +IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleBrowserTest, AcknowledgeNotice) { EXPECT_CALL( *mock_service(), @@ -159,7 +163,7 @@ VerifyBubbleWasClosed(bubble); } -IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleViewBrowserTest, +IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleBrowserTest, OpenSettingsNotice) { EXPECT_CALL( *mock_service(), @@ -175,12 +179,15 @@ auto* bubble = ShowBubble(browser()); auto* bubble_delegate = bubble->widget_delegate()->AsBubbleDialogDelegate(); - ClickButton(bubble_delegate, bubble_delegate->GetCancelButton()); - VerifyBubbleWasClosed(bubble); + ClickButton(bubble_delegate, bubble_delegate->GetExtraView()); + // TODO(crbug.com/1321587): Bubble should be closed. Figure out why opening + // settings page doesn't take over the focus (only in tests). } -IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleViewBrowserTest, - OpenLearnMoreNotice) { +// TODO(crbug.com/1321587, crbug.com/1327190): Update how the link is accessed +// after the API for DialogModel is added. +IN_PROC_BROWSER_TEST_F(PrivacySandboxNoticeBubbleBrowserTest, + DISABLED_OpenLearnMoreNotice) { EXPECT_CALL( *mock_service(), PromptActionOccurred(PrivacySandboxService::PromptAction::kNoticeShown)); @@ -194,9 +201,6 @@ .Times(0); auto* bubble = ShowBubble(browser()); - auto* label = - static_cast<views::StyledLabel*>(bubble->GetRootView()->GetViewByID( - PrivacySandboxNoticeBubbleView::kNoticeLearnMoreLinkId)); - label->ClickLinkForTesting(); + // TODO(crbug.com/1321587): Get the link from the bubble and click on it. VerifyBubbleWasClosed(bubble); }
diff --git a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.cc b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.cc deleted file mode 100644 index e14f947..0000000 --- a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.cc +++ /dev/null
@@ -1,227 +0,0 @@ -// Copyright 2022 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/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.h" - -#include "chrome/browser/privacy_sandbox/privacy_sandbox_service.h" -#include "chrome/browser/privacy_sandbox/privacy_sandbox_service_factory.h" -#include "chrome/browser/ui/browser.h" -#include "chrome/browser/ui/chrome_pages.h" -#include "chrome/browser/ui/privacy_sandbox/privacy_sandbox_prompt.h" -#include "chrome/browser/ui/views/accessibility/theme_tracking_non_accessible_image_view.h" -#include "chrome/browser/ui/views/bubble_anchor_util_views.h" -#include "chrome/browser/ui/views/chrome_layout_provider.h" -#include "chrome/browser/ui/views/frame/app_menu_button.h" -#include "chrome/browser/ui/views/frame/browser_view.h" -#include "chrome/browser/ui/views/toolbar/toolbar_view.h" -#include "chrome/grit/generated_resources.h" -#include "chrome/grit/theme_resources.h" -#include "ui/base/l10n/l10n_util.h" -#include "ui/base/metadata/metadata_impl_macros.h" -#include "ui/views/bubble/bubble_dialog_delegate_view.h" -#include "ui/views/controls/label.h" -#include "ui/views/controls/styled_label.h" -#include "ui/views/layout/box_layout.h" -#include "ui/views/view_class_properties.h" - -using PromptAction = PrivacySandboxService::PromptAction; - -namespace { - -constexpr int kDialogWidth = 448; - -void NotifyServiceAboutPromptAction(Profile* profile, PromptAction action) { - if (auto* service = PrivacySandboxServiceFactory::GetForProfile(profile)) { - service->PromptActionOccurred(action); - } -} - -AppMenuButton* GetAppMenuButton(Browser* browser) { - BrowserView* browser_view = BrowserView::GetBrowserViewForBrowser(browser); - // The notice bubble is anchored to the browser. If the browser is destroyed, - // the bubble will be too. Because of that browser should always be present - // while bubble is active. - DCHECK(browser_view); - return browser_view->toolbar_button_provider()->GetAppMenuButton(); -} - -class PrivacySandboxNoticeBubbleDelegate : public views::BubbleDialogDelegate { - public: - explicit PrivacySandboxNoticeBubbleDelegate( - bubble_anchor_util::AnchorConfiguration configuration, - Browser* browser) - : BubbleDialogDelegate(configuration.anchor_view, - configuration.bubble_arrow), - browser_(browser) { - if (auto* privacy_sandbox_serivce = - PrivacySandboxServiceFactory::GetForProfile(browser->profile())) { - privacy_sandbox_serivce->DialogOpenedForBrowser(browser); - } - SetCloseCallback(base::BindOnce( - &PrivacySandboxNoticeBubbleDelegate::OnClose, base::Unretained(this))); - } - - void OnClose() { - if (auto* privacy_sandbox_serivce = - PrivacySandboxServiceFactory::GetForProfile(browser_->profile())) { - privacy_sandbox_serivce->DialogClosedForBrowser(browser_); - } - } - - void WindowClosing() override { - switch (GetWidget()->closed_reason()) { - case views::Widget::ClosedReason::kEscKeyPressed: - NotifyServiceAboutPromptAction(browser_->profile(), - PromptAction::kNoticeDismiss); - break; - case views::Widget::ClosedReason::kUnspecified: - NotifyServiceAboutPromptAction( - browser_->profile(), PromptAction::kNoticeClosedNoInteraction); - break; - default: - break; - } - } - - private: - Browser* browser_; -}; - -} // namespace - -// static -void ShowPrivacySandboxNoticeBubble(Browser* browser) { - auto bubble_delegate = std::make_unique<PrivacySandboxNoticeBubbleDelegate>( - bubble_anchor_util::GetAppMenuAnchorConfiguration(browser), browser); - bubble_delegate->SetShowTitle(false); - bubble_delegate->SetShowCloseButton(false); - bubble_delegate->set_close_on_deactivate(false); - bubble_delegate->set_margins( - ChromeLayoutProvider::Get()->GetInsetsMetric(views::INSETS_DIALOG)); - bubble_delegate->set_fixed_width( - ChromeLayoutProvider::Get()->GetSnappedDialogWidth(kDialogWidth)); - - bubble_delegate->SetButtonLabel( - ui::DIALOG_BUTTON_OK, - l10n_util::GetStringUTF16( - IDS_PRIVACY_SANDBOX_DIALOG_NOTICE_ACKNOWLEDGE_BUTTON)); - bubble_delegate->SetAcceptCallback(base::BindOnce( - [](Browser* browser) { - NotifyServiceAboutPromptAction(browser->profile(), - PromptAction::kNoticeAcknowledge); - }, - base::Unretained(browser))); - - bubble_delegate->SetButtonLabel( - ui::DIALOG_BUTTON_CANCEL, - l10n_util::GetStringUTF16( - IDS_PRIVACY_SANDBOX_DIALOG_NOTICE_OPEN_SETTINGS_BUTTON)); - bubble_delegate->SetCancelCallback(base::BindOnce( - [](Browser* browser) { - chrome::ShowPrivacySandboxSettings(browser); - NotifyServiceAboutPromptAction(browser->profile(), - PromptAction::kNoticeOpenSettings); - }, - base::Unretained(browser))); - - auto& bundle = ui::ResourceBundle::GetSharedInstance(); - auto image = std::make_unique<ThemeTrackingNonAccessibleImageView>( - *bundle.GetImageSkiaNamed(IDR_PRIVACY_SANDBOX_CONFIRMATION_BANNER), - *bundle.GetImageSkiaNamed(IDR_PRIVACY_SANDBOX_CONFIRMATION_BANNER_DARK), - base::BindRepeating(&views::BubbleDialogDelegate::GetBackgroundColor, - base::Unretained(bubble_delegate.get()))); - - bubble_delegate->SetContentsView( - std::make_unique<PrivacySandboxNoticeBubbleView>(browser, - std::move(image))); - views::BubbleDialogDelegate::CreateBubble(std::move(bubble_delegate))->Show(); -} - -PrivacySandboxNoticeBubbleView::PrivacySandboxNoticeBubbleView( - Browser* browser, - std::unique_ptr<views::View> image) - : browser_(browser) { - SetLayoutManager(std::make_unique<views::BoxLayout>( - views::BoxLayout::Orientation::kHorizontal)) - ->set_cross_axis_alignment(views::BoxLayout::CrossAxisAlignment::kStart); - - // Add image view, that was created with the reference to bubble delegate to - // support changing color for the theme. - AddChildView(std::move(image)); - - // Set up the container for the right side. It contains a title and a - // description. - auto* container = AddChildView(std::make_unique<views::View>()); - container->SetLayoutManager(std::make_unique<views::BoxLayout>( - views::BoxLayout::Orientation::kVertical, gfx::Insets(), - ChromeLayoutProvider::Get()->GetDistanceMetric( - DISTANCE_CONTENT_LIST_VERTICAL_SINGLE))); - container->SetProperty( - views::kMarginsKey, - gfx::Insets::TLBR(0, - ChromeLayoutProvider::Get()->GetDistanceMetric( - views::DISTANCE_RELATED_LABEL_HORIZONTAL), - 0, 0)); - - // Create the title view. - auto* title_label = container->AddChildView(std::make_unique<views::Label>( - l10n_util::GetStringUTF16(IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_TITLE), - views::style::CONTEXT_DIALOG_TITLE)); - title_label->SetHorizontalAlignment(gfx::ALIGN_LEFT); - title_label->SetFontList( - views::style::GetFont(views::style::TextContext::CONTEXT_DIALOG_TITLE, - views::style::TextStyle::STYLE_PRIMARY) - .DeriveWithWeight(gfx::Font::Weight::MEDIUM)); - - // Create the description view. - auto* description_label = - container->AddChildView(std::make_unique<views::StyledLabel>()); - description_label->SetHorizontalAlignment(gfx::ALIGN_LEFT); - description_label->SetID(kNoticeLearnMoreLinkId); - // The description contains a link that opens settings page. Find the position - // of the link by inserting text into the placeholder. - auto intesets_settings_link = l10n_util::GetStringUTF16( - IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_DESCRIPTION_ESTIMATES_INTERESTS_LINK); - size_t offset; - description_label->SetText( - l10n_util::GetStringFUTF16(IDS_PRIVACY_SANDBOX_BUBBLE_NOTICE_DESCRIPTION, - intesets_settings_link, &offset)); - gfx::Range range(offset, offset + intesets_settings_link.length()); - views::StyledLabel::RangeStyleInfo link_style = - views::StyledLabel::RangeStyleInfo::CreateForLink(base::BindRepeating( - &PrivacySandboxNoticeBubbleView::OpenAboutAdPersonalizationSettings, - base::Unretained(this))); - description_label->AddStyleRange(range, link_style); - - // Observe app menu button to close the bubble when app menu is shown. - if (auto* app_menu_button = GetAppMenuButton(browser_)) { - app_menu_button->AddObserver(this); - } - - NotifyServiceAboutPromptAction(browser_->profile(), - PromptAction::kNoticeShown); -} - -PrivacySandboxNoticeBubbleView::~PrivacySandboxNoticeBubbleView() { - if (auto* app_menu_button = GetAppMenuButton(browser_)) { - app_menu_button->RemoveObserver(this); - } -} - -void PrivacySandboxNoticeBubbleView::AppMenuShown() { - NotifyServiceAboutPromptAction(browser_->profile(), - PromptAction::kNoticeDismiss); - GetWidget()->CloseWithReason(views::Widget::ClosedReason::kLostFocus); -} - -void PrivacySandboxNoticeBubbleView::OpenAboutAdPersonalizationSettings() { - chrome::ShowPrivacySandboxLearnMore(browser_); - NotifyServiceAboutPromptAction(browser_->profile(), - PromptAction::kNoticeLearnMore); - GetWidget()->CloseWithReason( - views::Widget::ClosedReason::kCancelButtonClicked); -} - -BEGIN_METADATA(PrivacySandboxNoticeBubbleView, views::View) -END_METADATA
diff --git a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.h b/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.h deleted file mode 100644 index 3477c618..0000000 --- a/chrome/browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view.h +++ /dev/null
@@ -1,41 +0,0 @@ -// Copyright 2022 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_UI_VIEWS_PRIVACY_SANDBOX_PRIVACY_SANDBOX_NOTICE_BUBBLE_VIEW_H_ -#define CHROME_BROWSER_UI_VIEWS_PRIVACY_SANDBOX_PRIVACY_SANDBOX_NOTICE_BUBBLE_VIEW_H_ - -#include "chrome/browser/ui/views/frame/app_menu_button_observer.h" -#include "ui/base/metadata/metadata_header_macros.h" -#include "ui/views/view.h" - -class Browser; - -// Content view of PrivacySandboxDialog notice UI. The bubble is anchored to -// three-dot menu. It contains image, title, description and action buttons. -class PrivacySandboxNoticeBubbleView : public views::View, - public AppMenuButtonObserver { - public: - METADATA_HEADER(PrivacySandboxNoticeBubbleView); - - PrivacySandboxNoticeBubbleView(Browser* browser, - std::unique_ptr<views::View> image); - ~PrivacySandboxNoticeBubbleView() override; - - // AppMenuButtonObserver: - void AppMenuShown() override; - - protected: - FRIEND_TEST_ALL_PREFIXES(PrivacySandboxNoticeBubbleViewBrowserTest, - OpenLearnMoreNotice); - // View ID of the description label that contains "Learn more" link. Used for - // testing. - static constexpr int kNoticeLearnMoreLinkId = 1; - - private: - void OpenAboutAdPersonalizationSettings(); - - raw_ptr<Browser> browser_; -}; - -#endif // CHROME_BROWSER_UI_VIEWS_PRIVACY_SANDBOX_PRIVACY_SANDBOX_NOTICE_BUBBLE_VIEW_H_
diff --git a/chrome/browser/ui/web_applications/web_app_launch_utils.cc b/chrome/browser/ui/web_applications/web_app_launch_utils.cc index 6c447f4..c355bc8 100644 --- a/chrome/browser/ui/web_applications/web_app_launch_utils.cc +++ b/chrome/browser/ui/web_applications/web_app_launch_utils.cc
@@ -4,18 +4,25 @@ #include "chrome/browser/ui/web_applications/web_app_launch_utils.h" -#include "base/feature_list.h" +#include <atomic> + +#include "base/check.h" +#include "base/check_op.h" +#include "base/memory/raw_ptr.h" +#include "base/metrics/histogram_base.h" #include "base/metrics/histogram_macros.h" -#include "base/strings/string_util.h" -#include "base/trace_event/base_tracing.h" +#include "base/metrics/histogram_macros_internal.h" +#include "base/one_shot_event.h" +#include "base/time/time.h" +#include "base/trace_event/typed_macros.h" +#include "base/tracing/protos/chrome_track_event.pbzero.h" +#include "build/buildflag.h" #include "build/chromeos_buildflags.h" #include "chrome/browser/app_mode/app_mode_utils.h" -#include "chrome/browser/buildflags.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/sessions/app_session_service.h" #include "chrome/browser/sessions/app_session_service_factory.h" #include "chrome/browser/sessions/session_service_base.h" -#include "chrome/browser/sessions/session_service_factory.h" #include "chrome/browser/sessions/session_service_lookup.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_commands.h" @@ -29,20 +36,25 @@ #include "chrome/browser/ui/web_applications/system_web_app_ui_utils.h" #include "chrome/browser/ui/web_applications/web_app_browser_controller.h" #include "chrome/browser/web_applications/system_web_apps/system_web_app_manager.h" +#include "chrome/browser/web_applications/web_app_constants.h" #include "chrome/browser/web_applications/web_app_helpers.h" +#include "chrome/browser/web_applications/web_app_install_utils.h" #include "chrome/browser/web_applications/web_app_provider.h" #include "chrome/browser/web_applications/web_app_registrar.h" #include "chrome/browser/web_applications/web_app_sync_bridge.h" #include "chrome/browser/web_applications/web_app_tab_helper.h" -#include "chrome/common/chrome_features.h" -#include "components/omnibox/browser/location_bar_model.h" +#include "chrome/browser/web_applications/web_app_utils.h" #include "components/site_engagement/content/site_engagement_service.h" #include "content/public/browser/navigation_controller.h" #include "content/public/browser/navigation_entry.h" +#include "content/public/browser/render_frame_host.h" #include "content/public/browser/web_contents.h" -#include "content/public/common/content_features.h" +#include "extensions/buildflags/buildflags.h" #include "extensions/common/constants.h" #include "third_party/blink/public/common/renderer_preferences/renderer_preferences.h" +#include "ui/base/page_transition_types.h" +#include "ui/base/ui_base_types.h" +#include "ui/base/window_open_disposition.h" #include "url/gurl.h" #if BUILDFLAG(ENABLE_EXTENSIONS) @@ -114,11 +126,6 @@ web_contents->GetMainFrame()->GetLastCommittedURL()); } -bool IsInScope(const GURL& url, const GURL& scope) { - return base::StartsWith(url.spec(), scope.spec(), - base::CompareCase::SENSITIVE); -} - void PrunePreScopeNavigationHistory(const GURL& scope, content::WebContents* contents) { content::NavigationController& navigation_controller =
diff --git a/chrome/browser/ui/web_applications/web_app_launch_utils.h b/chrome/browser/ui/web_applications/web_app_launch_utils.h index 9b77e86..7f3cc48 100644 --- a/chrome/browser/ui/web_applications/web_app_launch_utils.h +++ b/chrome/browser/ui/web_applications/web_app_launch_utils.h
@@ -5,11 +5,12 @@ #ifndef CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_LAUNCH_UTILS_H_ #define CHROME_BROWSER_UI_WEB_APPLICATIONS_WEB_APP_LAUNCH_UTILS_H_ +#include <stdint.h> #include <memory> #include <string> #include "chrome/browser/web_applications/web_app_id.h" -#include "components/services/app_service/public/mojom/types.mojom-forward.h" +#include "components/services/app_service/public/mojom/types.mojom-shared.h" #include "extensions/common/constants.h" #include "third_party/abseil-cpp/absl/types/optional.h" #include "ui/gfx/geometry/rect.h" @@ -30,8 +31,6 @@ absl::optional<AppId> GetWebAppForActiveTab(Browser* browser); -bool IsInScope(const GURL& url, const GURL& scope_spec); - // Clears navigation history prior to user entering app scope. void PrunePreScopeNavigationHistory(const GURL& scope, content::WebContents* contents);
diff --git a/chrome/browser/ui/web_applications/web_share_target_browsertest.cc b/chrome/browser/ui/web_applications/web_share_target_browsertest.cc index 9872ac4..3b1ab9c6 100644 --- a/chrome/browser/ui/web_applications/web_share_target_browsertest.cc +++ b/chrome/browser/ui/web_applications/web_share_target_browsertest.cc
@@ -185,6 +185,7 @@ file_system_context.get(), /*origin=*/GURL(), /*file_type=*/chromeos::RecentModel::FileType::kAll, + /*invalidate_cache=*/false, base::BindLambdaForTesting( [&result, &run_loop](const std::vector<chromeos::RecentFile>& files) {
diff --git a/chrome/browser/ui/webui/settings/chromeos/search/search_concept.h b/chrome/browser/ui/webui/settings/chromeos/search/search_concept.h index 156e6c81..7fbeb7d 100644 --- a/chrome/browser/ui/webui/settings/chromeos/search/search_concept.h +++ b/chrome/browser/ui/webui/settings/chromeos/search/search_concept.h
@@ -25,9 +25,6 @@ static constexpr size_t kMaxAltTagsPerConcept = 5; static constexpr int kAltTagEnd = 0; - SearchConcept(const SearchConcept& other) = default; - SearchConcept& operator=(const SearchConcept& other) = default; - // Message ID (from os_settings_search_tag_strings.grdp) corresponding to the // canonical search tag for this concept. int canonical_message_id;
diff --git a/chrome/browser/ui/webui/signin/inline_login_ui.cc b/chrome/browser/ui/webui/signin/inline_login_ui.cc index f530b8c..bff59693d 100644 --- a/chrome/browser/ui/webui/signin/inline_login_ui.cc +++ b/chrome/browser/ui/webui/signin/inline_login_ui.cc
@@ -96,6 +96,9 @@ source->AddLocalizedString("eduCoexistenceErrorDescription", IDS_EDU_COEXISTENCE_ERROR_DESCRIPTION); source->AddLocalizedString("loadingMessage", IDS_LOGIN_GAIA_LOADING_MESSAGE); + source->AddLocalizedString( + "addSchoolAccountLabel", + IDS_ACCOUNT_MANAGER_DIALOG_ADD_SCHOOL_ACCOUNT_LABEL); } #endif // BUILDFLAG(IS_CHROMEOS_ASH) @@ -283,6 +286,9 @@ ui::GetChromeOSDeviceName())); } + source->AddBoolean("isChild", + user_manager::UserManager::Get()->IsLoggedInAsChildUser()); + user_manager::User* user = ash::ProfileHelper::Get()->GetUserByProfile(profile); DCHECK(user);
diff --git a/chrome/browser/web_applications/BUILD.gn b/chrome/browser/web_applications/BUILD.gn index dab37d9..dff8093 100644 --- a/chrome/browser/web_applications/BUILD.gn +++ b/chrome/browser/web_applications/BUILD.gn
@@ -460,6 +460,7 @@ "//components/keyed_service/content", "//components/services/app_service/public/cpp:app_update", "//components/services/app_service/public/cpp:app_url_handling", + "//components/services/app_service/public/cpp:protocol_handling", "//components/services/app_service/public/cpp:types", "//components/sync:test_support_model", "//components/sync_preferences:test_support", @@ -709,6 +710,7 @@ "//components/services/app_service/public/cpp:app_update", "//components/services/app_service/public/cpp:icon_types", "//components/services/app_service/public/cpp:intents", + "//components/services/app_service/public/cpp:protocol_handling", "//components/services/app_service/public/cpp:run_on_os_login", "//components/services/app_service/public/cpp:types", "//components/webapps/browser",
diff --git a/chrome/browser/web_applications/alternative_error_page_override_info_browsertest.cc b/chrome/browser/web_applications/alternative_error_page_override_info_browsertest.cc index bce8375..9fddd99 100644 --- a/chrome/browser/web_applications/alternative_error_page_override_info_browsertest.cc +++ b/chrome/browser/web_applications/alternative_error_page_override_info_browsertest.cc
@@ -14,6 +14,7 @@ #include "chrome/test/base/in_process_browser_test.h" #include "chrome/test/base/ui_test_utils.h" #include "components/url_formatter/url_formatter.h" +#include "content/public/common/alternative_error_page_override_info.mojom.h" #include "content/public/common/content_client.h" #include "content/public/test/browser_test.h" #include "content/public/test/test_utils.h"
diff --git a/chrome/browser/web_applications/manifest_update_manager_browsertest.cc b/chrome/browser/web_applications/manifest_update_manager_browsertest.cc index c12c5c9..2eccd9a6 100644 --- a/chrome/browser/web_applications/manifest_update_manager_browsertest.cc +++ b/chrome/browser/web_applications/manifest_update_manager_browsertest.cc
@@ -4,35 +4,47 @@ #include "chrome/browser/web_applications/manifest_update_manager.h" +#include <ios> #include <map> #include <memory> #include <string> +#include <tuple> +#include <type_traits> +#include <utility> #include <vector> -#include "base/callback_helpers.h" +#include "base/bind.h" +#include "base/check.h" +#include "base/check_op.h" #include "base/containers/contains.h" +#include "base/containers/flat_tree.h" +#include "base/feature_list.h" #include "base/memory/raw_ptr.h" -#include "base/memory/scoped_refptr.h" +#include "base/notreached.h" +#include "base/numerics/clamped_math.h" +#include "base/numerics/safe_conversions.h" +#include "base/run_loop.h" +#include "base/strings/string_number_conversions.h" #include "base/strings/string_util.h" -#include "base/strings/utf_string_conversions.h" #include "base/test/bind.h" #include "base/test/metrics/histogram_tester.h" #include "base/test/scoped_feature_list.h" #include "base/time/time.h" #include "build/build_config.h" +#include "build/buildflag.h" #include "build/chromeos_buildflags.h" -#include "chrome/app/chrome_command_ids.h" -#include "chrome/browser/browser_features.h" -#include "chrome/browser/content_settings/host_content_settings_map_factory.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_commands.h" #include "chrome/browser/ui/browser_dialogs.h" +#include "chrome/browser/ui/tabs/tab_strip_model.h" #include "chrome/browser/ui/web_applications/test/web_app_browsertest_util.h" #include "chrome/browser/web_applications/commands/fetch_manifest_and_install_command.h" +#include "chrome/browser/web_applications/commands/web_app_command.h" +#include "chrome/browser/web_applications/external_install_options.h" #include "chrome/browser/web_applications/externally_managed_app_manager.h" +#include "chrome/browser/web_applications/manifest_update_task.h" #include "chrome/browser/web_applications/os_integration/os_integration_manager.h" -#include "chrome/browser/web_applications/os_integration/web_app_file_handler_registration.h" -#include "chrome/browser/web_applications/os_integration/web_app_shortcut_manager.h" +#include "chrome/browser/web_applications/os_integration/web_app_shortcut.h" #include "chrome/browser/web_applications/system_web_apps/test/test_system_web_app_installation.h" #include "chrome/browser/web_applications/test/web_app_icon_test_utils.h" #include "chrome/browser/web_applications/test/web_app_install_test_utils.h" @@ -41,12 +53,15 @@ #include "chrome/browser/web_applications/test/web_app_test_utils.h" #include "chrome/browser/web_applications/user_display_mode.h" #include "chrome/browser/web_applications/web_app.h" +#include "chrome/browser/web_applications/web_app_callback_app_identity.h" #include "chrome/browser/web_applications/web_app_command_manager.h" +#include "chrome/browser/web_applications/web_app_constants.h" #include "chrome/browser/web_applications/web_app_helpers.h" #include "chrome/browser/web_applications/web_app_icon_generator.h" +#include "chrome/browser/web_applications/web_app_icon_manager.h" +#include "chrome/browser/web_applications/web_app_id.h" #include "chrome/browser/web_applications/web_app_install_finalizer.h" #include "chrome/browser/web_applications/web_app_install_info.h" -#include "chrome/browser/web_applications/web_app_install_manager.h" #include "chrome/browser/web_applications/web_app_install_params.h" #include "chrome/browser/web_applications/web_app_provider.h" #include "chrome/browser/web_applications/web_app_registrar.h" @@ -56,21 +71,37 @@ #include "chrome/common/chrome_features.h" #include "chrome/test/base/in_process_browser_test.h" #include "chrome/test/base/ui_test_utils.h" -#include "components/content_settings/core/browser/host_content_settings_map.h" -#include "components/content_settings/core/common/content_settings.h" +#include "components/services/app_service/public/cpp/file_handler.h" +#include "components/services/app_service/public/cpp/icon_info.h" +#include "components/services/app_service/public/cpp/protocol_handler_info.h" +#include "components/services/app_service/public/cpp/share_target.h" +#include "components/services/app_service/public/cpp/url_handler_info.h" #include "components/webapps/browser/install_result_code.h" #include "components/webapps/browser/installable/installable_metrics.h" #include "components/webapps/browser/uninstall_result_code.h" +#include "content/public/browser/web_contents.h" #include "content/public/test/browser_test.h" #include "content/public/test/url_loader_interceptor.h" -#include "extensions/browser/extension_registry.h" +#include "mojo/public/cpp/bindings/remote.h" +#include "net/base/net_errors.h" +#include "net/http/http_status_code.h" +#include "net/test/embedded_test_server/embedded_test_server.h" #include "net/test/embedded_test_server/http_request.h" #include "net/test/embedded_test_server/http_response.h" +#include "services/network/public/cpp/resource_request.h" +#include "services/network/public/mojom/url_loader.mojom.h" #include "testing/gtest/include/gtest/gtest.h" +#include "third_party/abseil-cpp/absl/types/optional.h" #include "third_party/blink/public/common/features.h" -#include "third_party/blink/public/mojom/manifest/handle_links.mojom.h" +#include "third_party/blink/public/mojom/manifest/handle_links.mojom-shared.h" +#include "third_party/skia/include/core/SkBitmap.h" #include "third_party/skia/include/core/SkColor.h" #include "ui/gfx/color_utils.h" +#include "ui/gfx/geometry/size.h" +#include "ui/gfx/image/image.h" +#include "ui/gfx/image/image_family.h" +#include "url/gurl.h" +#include "url/origin.h" #if BUILDFLAG(IS_MAC) #include "base/mac/mac_util.h" @@ -87,6 +118,10 @@ #include "ash/constants/ash_features.h" #endif +#if BUILDFLAG(IS_LINUX) +#include "chrome/browser/web_applications/os_integration/web_app_file_handler_registration.h" +#endif + namespace web_app { namespace { @@ -3416,6 +3451,200 @@ EXPECT_TRUE(web_app->protocol_handlers().empty()); } +class ManifestUpdateManagerBrowserTest_LockScreen + : public ManifestUpdateManagerBrowserTest { + base::test::ScopedFeatureList feature_list_{ + blink::features::kWebAppManifestLockScreen}; +}; + +IN_PROC_BROWSER_TEST_F(ManifestUpdateManagerBrowserTest_LockScreen, + CheckFindsAddedLockScreenStartUrl) { + constexpr char kManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "icons": $1 + } + )"; + + constexpr char kLockScreenStartUrlManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "lock_screen": { + "start_url": "/lock-screen-start" + }, + "icons": $1 + } + )"; + + OverrideManifest(kManifestTemplate, {kInstallableIconList}); + AppId app_id = InstallWebApp(); + const WebApp* web_app = GetProvider().registrar().GetAppById(app_id); + EXPECT_TRUE(web_app->lock_screen_start_url().is_empty()); + + OverrideManifest(kLockScreenStartUrlManifestTemplate, {kInstallableIconList}); + EXPECT_EQ(ManifestUpdateResult::kAppUpdated, + GetResultAfterPageLoad(GetAppURL())); + histogram_tester_.ExpectBucketCount(kUpdateHistogramName, + ManifestUpdateResult::kAppUpdated, 1); + EXPECT_EQ(http_server_.GetURL("/lock-screen-start"), + web_app->lock_screen_start_url().spec()); +} + +IN_PROC_BROWSER_TEST_F(ManifestUpdateManagerBrowserTest_LockScreen, + CheckIgnoresUnchangedLockScreenStartUrl) { + constexpr char kLockScreenStartUrlManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "lock_screen": { + "start_url": "/lock-screen-start" + }, + "icons": $1 + } + )"; + + OverrideManifest(kLockScreenStartUrlManifestTemplate, {kInstallableIconList}); + AppId app_id = InstallWebApp(); + const WebApp* web_app = GetProvider().registrar().GetAppById(app_id); + EXPECT_EQ(http_server_.GetURL("/lock-screen-start"), + web_app->lock_screen_start_url().spec()); + + OverrideManifest(kLockScreenStartUrlManifestTemplate, {kInstallableIconList}); + EXPECT_EQ(ManifestUpdateResult::kAppUpToDate, + GetResultAfterPageLoad(GetAppURL())); + histogram_tester_.ExpectBucketCount(kUpdateHistogramName, + ManifestUpdateResult::kAppUpToDate, 1); + EXPECT_EQ(http_server_.GetURL("/lock-screen-start"), + web_app->lock_screen_start_url().spec()); +} + +IN_PROC_BROWSER_TEST_F(ManifestUpdateManagerBrowserTest_LockScreen, + CheckFindsChangedLockScreenStartUrl) { + constexpr char kLockScreenStartUrlManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "lock_screen": { + "start_url": "$1" + }, + "icons": $2 + } + )"; + + OverrideManifest(kLockScreenStartUrlManifestTemplate, + {"old-relative-url", kInstallableIconList}); + AppId app_id = InstallWebApp(); + const WebApp* web_app = GetProvider().registrar().GetAppById(app_id); + // URL parsed relative to manifest URL, which is in /banners/. + EXPECT_EQ(http_server_.GetURL("/banners/old-relative-url"), + web_app->lock_screen_start_url().spec()); + + OverrideManifest(kLockScreenStartUrlManifestTemplate, + {"/lock-screen-starter", kInstallableIconList}); + EXPECT_EQ(ManifestUpdateResult::kAppUpdated, + GetResultAfterPageLoad(GetAppURL())); + histogram_tester_.ExpectBucketCount(kUpdateHistogramName, + ManifestUpdateResult::kAppUpdated, 1); + EXPECT_EQ(http_server_.GetURL("/lock-screen-starter"), + web_app->lock_screen_start_url().spec()); +} + +IN_PROC_BROWSER_TEST_F(ManifestUpdateManagerBrowserTest_LockScreen, + CheckFindsDeletedLockScreenStartUrl) { + constexpr char kLockScreenStartUrlManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "lock_screen": { + "start_url": "/lock-screen-start" + }, + "icons": $1 + } + )"; + + constexpr char kManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "icons": $1 + } + )"; + + OverrideManifest(kLockScreenStartUrlManifestTemplate, {kInstallableIconList}); + AppId app_id = InstallWebApp(); + const WebApp* web_app = GetProvider().registrar().GetAppById(app_id); + EXPECT_FALSE(web_app->lock_screen_start_url().is_empty()); + + OverrideManifest(kManifestTemplate, {kInstallableIconList}); + EXPECT_EQ(ManifestUpdateResult::kAppUpdated, + GetResultAfterPageLoad(GetAppURL())); + histogram_tester_.ExpectBucketCount(kUpdateHistogramName, + ManifestUpdateResult::kAppUpdated, 1); + EXPECT_TRUE(web_app->lock_screen_start_url().is_empty()); +} + +class ManifestUpdateManagerBrowserTest_NoLockScreen + : public ManifestUpdateManagerBrowserTest { + public: + ManifestUpdateManagerBrowserTest_NoLockScreen() { + feature_list_.InitAndDisableFeature( + blink::features::kWebAppManifestLockScreen); + } + base::test::ScopedFeatureList feature_list_; +}; + +IN_PROC_BROWSER_TEST_F(ManifestUpdateManagerBrowserTest_NoLockScreen, + WithoutLockScreenFlag_CheckIgnoresLockScreenStartUrl) { + constexpr char kManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "icons": $1 + } + )"; + + constexpr char kLockScreenStartUrlManifestTemplate[] = R"( + { + "name": "Test app name", + "start_url": ".", + "scope": "/", + "display": "minimal-ui", + "lock_screen": { + "start_url": "/lock-screen-start" + }, + "icons": $1 + } + )"; + + OverrideManifest(kManifestTemplate, {kInstallableIconList}); + AppId app_id = InstallWebApp(); + const WebApp* web_app = GetProvider().registrar().GetAppById(app_id); + EXPECT_TRUE(web_app->lock_screen_start_url().is_empty()); + + OverrideManifest(kLockScreenStartUrlManifestTemplate, {kInstallableIconList}); + EXPECT_EQ(ManifestUpdateResult::kAppUpToDate, + GetResultAfterPageLoad(GetAppURL())); + histogram_tester_.ExpectBucketCount(kUpdateHistogramName, + ManifestUpdateResult::kAppUpToDate, 1); + EXPECT_TRUE(web_app->lock_screen_start_url().is_empty()); +} + IN_PROC_BROWSER_TEST_F(ManifestUpdateManagerBrowserTest, CheckFindsAddedNewNoteUrl) { constexpr char kManifestTemplate[] = R"(
diff --git a/chrome/browser/web_applications/manifest_update_task.cc b/chrome/browser/web_applications/manifest_update_task.cc index 2ab0f1bc..febb8fd 100644 --- a/chrome/browser/web_applications/manifest_update_task.cc +++ b/chrome/browser/web_applications/manifest_update_task.cc
@@ -387,6 +387,12 @@ if (install_info_->url_handlers != app->url_handlers()) return true; + if (base::FeatureList::IsEnabled( + blink::features::kWebAppManifestLockScreen) && + install_info_->lock_screen_start_url != app->lock_screen_start_url()) { + return true; + } + if (install_info_->note_taking_new_note_url != app->note_taking_new_note_url()) { return true;
diff --git a/chrome/browser/web_applications/proto/web_app.proto b/chrome/browser/web_applications/proto/web_app.proto index ee11410..0f2557bc 100644 --- a/chrome/browser/web_applications/proto/web_app.proto +++ b/chrome/browser/web_applications/proto/web_app.proto
@@ -346,4 +346,7 @@ // The amount of storage (in bytes) used by the app and its related data. optional uint64 app_size_in_bytes = 54; optional uint64 data_size_in_bytes = 55; + + // If present, the URL to use to launch the app on the lock screen. + optional string lock_screen_start_url = 56; }
diff --git a/chrome/browser/web_applications/test/web_app_test_utils.cc b/chrome/browser/web_applications/test/web_app_test_utils.cc index 3b9171d..34ba680 100644 --- a/chrome/browser/web_applications/test/web_app_test_utils.cc +++ b/chrome/browser/web_applications/test/web_app_test_utils.cc
@@ -4,32 +4,67 @@ #include "chrome/browser/web_applications/test/web_app_test_utils.h" +#include <algorithm> +#include <cstdint> +#include <ostream> #include <random> +#include <set> +#include <string> +#include <type_traits> +#include <utility> +#include <vector> +#include "base/bind.h" +#include "base/check.h" +#include "base/check_op.h" +#include "base/containers/flat_map.h" +#include "base/containers/flat_set.h" #include "base/json/json_reader.h" +#include "base/location.h" +#include "base/memory/scoped_refptr.h" +#include "base/numerics/clamped_math.h" +#include "base/numerics/safe_conversions.h" +#include "base/run_loop.h" +#include "base/strings/string_number_conversions.h" #include "base/strings/utf_string_conversions.h" +#include "base/task/single_thread_task_runner.h" #include "base/test/bind.h" #include "base/threading/thread_task_runner_handle.h" +#include "base/time/time.h" #include "base/values.h" #include "chrome/app/chrome_command_ids.h" +#include "chrome/browser/profiles/profile.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_commands.h" #include "chrome/browser/ui/browser_dialogs.h" #include "chrome/browser/web_applications/test/web_app_test_observers.h" #include "chrome/browser/web_applications/user_display_mode.h" +#include "chrome/browser/web_applications/web_app.h" +#include "chrome/browser/web_applications/web_app_chromeos_data.h" #include "chrome/browser/web_applications/web_app_constants.h" #include "chrome/browser/web_applications/web_app_helpers.h" #include "chrome/browser/web_applications/web_app_install_info.h" #include "chrome/browser/web_applications/web_app_utils.h" #include "chrome/common/pref_names.h" +#include "components/prefs/pref_service.h" +#include "components/services/app_service/public/cpp/file_handler.h" +#include "components/services/app_service/public/cpp/icon_info.h" +#include "components/services/app_service/public/cpp/protocol_handler_info.h" +#include "components/services/app_service/public/cpp/share_target.h" #include "components/services/app_service/public/cpp/url_handler_info.h" -#include "components/sync_preferences/testing_pref_service_syncable.h" #include "components/webapps/browser/installable/installable_metrics.h" #include "content/public/browser/service_worker_context.h" #include "content/public/browser/storage_partition.h" +#include "third_party/abseil-cpp/absl/types/optional.h" #include "third_party/blink/public/common/manifest/manifest.h" +#include "third_party/blink/public/common/permissions_policy/permissions_policy.h" #include "third_party/blink/public/common/permissions_policy/policy_helper_public.h" +#include "third_party/blink/public/common/storage_key/storage_key.h" +#include "third_party/blink/public/mojom/manifest/capture_links.mojom-shared.h" +#include "third_party/blink/public/mojom/manifest/handle_links.mojom-shared.h" +#include "third_party/skia/include/core/SkColor.h" #include "url/gurl.h" +#include "url/origin.h" namespace { @@ -428,6 +463,10 @@ app->SetProtocolHandlers(CreateRandomProtocolHandlers(random.next_uint())); app->SetUrlHandlers(CreateRandomUrlHandlers(random.next_uint())); if (random.next_bool()) { + app->SetLockScreenStartUrl(scope.Resolve( + "lock_screen_start_url" + base::NumberToString(random.next_uint()))); + } + if (random.next_bool()) { app->SetNoteTakingNewNoteUrl( scope.Resolve("new_note" + base::NumberToString(random.next_uint()))); }
diff --git a/chrome/browser/web_applications/test/web_app_test_utils.h b/chrome/browser/web_applications/test/web_app_test_utils.h index af752c8..1b7585e4 100644 --- a/chrome/browser/web_applications/test/web_app_test_utils.h +++ b/chrome/browser/web_applications/test/web_app_test_utils.h
@@ -5,16 +5,19 @@ #ifndef CHROME_BROWSER_WEB_APPLICATIONS_TEST_WEB_APP_TEST_UTILS_H_ #define CHROME_BROWSER_WEB_APPLICATIONS_TEST_WEB_APP_TEST_UTILS_H_ +#include <stdint.h> #include <memory> -#include "chrome/browser/web_applications/web_app.h" +#include "base/strings/string_piece_forward.h" +#include "chrome/browser/web_applications/web_app_constants.h" +#include "chrome/browser/web_applications/web_app_id.h" #include "chrome/browser/web_applications/web_app_install_params.h" -#include "chrome/browser/web_applications/web_app_install_utils.h" #include "content/public/browser/service_worker_context.h" +#include "url/gurl.h" -struct WebAppInstallInfo; class Browser; -class GURL; +class Profile; +struct WebAppInstallInfo; namespace content { class StoragePartition; @@ -22,6 +25,9 @@ } // namespace content namespace web_app { + +class WebApp; + namespace test { std::unique_ptr<WebApp> CreateWebApp(
diff --git a/chrome/browser/web_applications/web_app.cc b/chrome/browser/web_applications/web_app.cc index 78965d7..2f9ee3d 100644 --- a/chrome/browser/web_applications/web_app.cc +++ b/chrome/browser/web_applications/web_app.cc
@@ -286,6 +286,11 @@ url_handlers_ = std::move(url_handlers); } +void WebApp::SetLockScreenStartUrl(const GURL& lock_screen_start_url) { + DCHECK(lock_screen_start_url.is_empty() || lock_screen_start_url.is_valid()); + lock_screen_start_url_ = lock_screen_start_url; +} + void WebApp::SetNoteTakingNewNoteUrl(const GURL& note_taking_new_note_url) { DCHECK(note_taking_new_note_url.is_empty() || note_taking_new_note_url.is_valid()); @@ -507,6 +512,7 @@ app.allowed_launch_protocols_, app.disallowed_launch_protocols_, app.url_handlers_, + app.lock_screen_start_url_, app.note_taking_new_note_url_, app.last_badging_time_, app.last_launch_time_, @@ -731,6 +737,9 @@ root.SetStringKey("manifest_url", ConvertToString(manifest_url_)); + root.SetStringKey("lock_screen_start_url", + ConvertToString(lock_screen_start_url_)); + root.SetStringKey("note_taking_new_note_url", ConvertToString(note_taking_new_note_url_));
diff --git a/chrome/browser/web_applications/web_app.h b/chrome/browser/web_applications/web_app.h index d0ca130..67bb1ad 100644 --- a/chrome/browser/web_applications/web_app.h +++ b/chrome/browser/web_applications/web_app.h
@@ -180,6 +180,10 @@ return disallowed_launch_protocols_; } + // URL within scope to launch for a "show on lock screen" action. Valid iff + // this is considered a lock-screen-capable app. + const GURL& lock_screen_start_url() const { return lock_screen_start_url_; } + // URL within scope to launch for a "new note" action. Valid iff this is // considered a note-taking app. const GURL& note_taking_new_note_url() const { @@ -350,6 +354,7 @@ void SetDisallowedLaunchProtocols( base::flat_set<std::string> disallowed_launch_protocols); void SetUrlHandlers(apps::UrlHandlers url_handlers); + void SetLockScreenStartUrl(const GURL& lock_screen_start_url); void SetNoteTakingNewNoteUrl(const GURL& note_taking_new_note_url); void SetLastBadgingTime(const base::Time& time); void SetLastLaunchTime(const base::Time& time); @@ -434,6 +439,7 @@ base::flat_set<std::string> allowed_launch_protocols_; base::flat_set<std::string> disallowed_launch_protocols_; apps::UrlHandlers url_handlers_; + GURL lock_screen_start_url_; GURL note_taking_new_note_url_; base::Time last_badging_time_; base::Time last_launch_time_; @@ -485,7 +491,9 @@ // - WebAppDatabase::CreateWebApp() // - WebAppDatabase::CreateWebAppProto() // - CreateRandomWebApp() + // If parsed from manifest, also add to: // - ManifestUpdateTask::IsUpdateNeededForManifest() + // - SetWebAppManifestFields() }; // For logging and debug purposes.
diff --git a/chrome/browser/web_applications/web_app_database.cc b/chrome/browser/web_applications/web_app_database.cc index a2fe38e..bbbf16a 100644 --- a/chrome/browser/web_applications/web_app_database.cc +++ b/chrome/browser/web_applications/web_app_database.cc
@@ -603,6 +603,11 @@ url_handler_proto->set_has_origin_wildcard(url_handler.has_origin_wildcard); } + if (web_app.lock_screen_start_url().is_valid()) { + local_data->set_lock_screen_start_url( + web_app.lock_screen_start_url().spec()); + } + if (web_app.note_taking_new_note_url().is_valid()) { local_data->set_note_taking_new_note_url( web_app.note_taking_new_note_url().spec()); @@ -1139,6 +1144,10 @@ } web_app->SetUrlHandlers(std::move(url_handlers)); + if (local_data.has_lock_screen_start_url()) { + web_app->SetLockScreenStartUrl(GURL(local_data.lock_screen_start_url())); + } + if (local_data.has_note_taking_new_note_url()) { web_app->SetNoteTakingNewNoteUrl( GURL(local_data.note_taking_new_note_url()));
diff --git a/chrome/browser/web_applications/web_app_install_info.h b/chrome/browser/web_applications/web_app_install_info.h index 19324bb8..6e96223 100644 --- a/chrome/browser/web_applications/web_app_install_info.h +++ b/chrome/browser/web_applications/web_app_install_info.h
@@ -294,6 +294,10 @@ // information. apps::UrlHandlers url_handlers; + // URL within scope to launch on the lock screen for a "show on lock screen" + // action. Valid iff this is considered a lock-screen-capable app. + GURL lock_screen_start_url; + // URL within scope to launch for a "new note" action. Valid iff this is // considered a note-taking app. GURL note_taking_new_note_url;
diff --git a/chrome/browser/web_applications/web_app_install_utils.cc b/chrome/browser/web_applications/web_app_install_utils.cc index 17655066..344a33f 100644 --- a/chrome/browser/web_applications/web_app_install_utils.cc +++ b/chrome/browser/web_applications/web_app_install_utils.cc
@@ -35,7 +35,10 @@ #include "chrome/browser/web_applications/os_integration/os_integration_manager.h" #include "chrome/browser/web_applications/os_integration/web_app_file_handler_manager.h" #include "chrome/browser/web_applications/web_app.h" +#include "chrome/browser/web_applications/web_app_chromeos_data.h" #include "chrome/browser/web_applications/web_app_icon_generator.h" +#include "chrome/browser/web_applications/web_app_install_params.h" +#include "chrome/browser/web_applications/web_app_system_web_app_data.h" #include "chrome/browser/web_applications/web_app_utils.h" #include "chrome/common/chrome_features.h" #include "components/services/app_service/public/cpp/icon_info.h" @@ -542,7 +545,19 @@ web_app_info->url_handlers = ToWebAppUrlHandlers(manifest.url_handlers); - if (manifest.note_taking && manifest.note_taking->new_note_url.is_valid()) { + GURL inferred_scope = web_app_info->scope.is_valid() ? web_app_info->scope + : web_app_info->start_url.is_valid() + ? web_app_info->start_url.GetWithoutFilename() + : GURL(); + if (base::FeatureList::IsEnabled( + blink::features::kWebAppManifestLockScreen) && + manifest.lock_screen && manifest.lock_screen->start_url.is_valid() && + IsInScope(manifest.lock_screen->start_url, inferred_scope)) { + web_app_info->lock_screen_start_url = manifest.lock_screen->start_url; + } + + if (manifest.note_taking && manifest.note_taking->new_note_url.is_valid() && + IsInScope(manifest.note_taking->new_note_url, inferred_scope)) { web_app_info->note_taking_new_note_url = manifest.note_taking->new_note_url; } @@ -952,6 +967,10 @@ web_app.SetShareTarget(web_app_info.share_target); web_app.SetProtocolHandlers(web_app_info.protocol_handlers); web_app.SetUrlHandlers(web_app_info.url_handlers); + + if (base::FeatureList::IsEnabled(blink::features::kWebAppManifestLockScreen)) + web_app.SetLockScreenStartUrl(web_app_info.lock_screen_start_url); + web_app.SetNoteTakingNewNoteUrl(web_app_info.note_taking_new_note_url); web_app.SetCaptureLinks(web_app_info.capture_links);
diff --git a/chrome/browser/web_applications/web_app_install_utils.h b/chrome/browser/web_applications/web_app_install_utils.h index 1d8d6b0..91944be 100644 --- a/chrome/browser/web_applications/web_app_install_utils.h +++ b/chrome/browser/web_applications/web_app_install_utils.h
@@ -13,7 +13,6 @@ #include "chrome/browser/web_applications/web_app_id.h" #include "chrome/browser/web_applications/web_app_install_finalizer.h" #include "chrome/browser/web_applications/web_app_install_info.h" -#include "chrome/browser/web_applications/web_app_install_params.h" #include "components/services/app_service/public/cpp/file_handler.h" #include "third_party/blink/public/mojom/manifest/manifest.mojom-forward.h" @@ -38,6 +37,7 @@ class WebApp; class WebAppRegistrar; +struct WebAppInstallParams; enum class ForInstallableSite { kYes,
diff --git a/chrome/browser/web_applications/web_app_install_utils_unittest.cc b/chrome/browser/web_applications/web_app_install_utils_unittest.cc index c402e99..b8ecf07 100644 --- a/chrome/browser/web_applications/web_app_install_utils_unittest.cc +++ b/chrome/browser/web_applications/web_app_install_utils_unittest.cc
@@ -96,8 +96,10 @@ } // namespace TEST(WebAppInstallUtils, UpdateWebAppInfoFromManifest) { - base::test::ScopedFeatureList feature_list( - blink::features::kFileHandlingIcons); + base::test::ScopedFeatureList feature_list; + feature_list.InitWithFeatures({blink::features::kFileHandlingIcons, + blink::features::kWebAppManifestLockScreen}, + /*disabled_features=*/{}); WebAppInstallInfo web_app_info; web_app_info.title = kAlternativeAppTestTitle; @@ -113,7 +115,6 @@ manifest.scope = kAppUrl.GetWithoutFilename(); manifest.short_name = kAppTestShortName; - const GURL kFileHandlingIcon("fav1.png"); { auto handler = blink::mojom::ManifestFileHandler::New(); handler->action = GURL("http://example.com/open-files"); @@ -121,7 +122,7 @@ handler->name = u"Images"; { blink::Manifest::ImageResource icon; - icon.src = kFileHandlingIcon; + icon.src = GURL("fav1.png"); icon.purpose = {Purpose::ANY, Purpose::MONOCHROME}; handler->icons.push_back(icon); } @@ -155,7 +156,8 @@ } { - // Ensure an empty NoteTaking struct is ignored. + // Ensure empty structs are ignored. + manifest.lock_screen = blink::mojom::ManifestLockScreen::New(); manifest.note_taking = blink::mojom::ManifestNoteTaking::New(); } @@ -167,6 +169,7 @@ EXPECT_EQ(DisplayMode::kBrowser, web_app_info.display_mode); EXPECT_TRUE(web_app_info.display_override.empty()); EXPECT_EQ(kAppManifestUrl, web_app_info.manifest_url); + EXPECT_TRUE(web_app_info.lock_screen_start_url.is_empty()); EXPECT_TRUE(web_app_info.note_taking_new_note_url.is_empty()); // The icon info from |web_app_info| should be left as is, since the manifest @@ -199,9 +202,16 @@ manifest.display_override.push_back(DisplayMode::kStandalone); { + auto lock_screen = blink::mojom::ManifestLockScreen::New(); + lock_screen->start_url = + GURL("http://www.chromium.org/lock-screen-start-url"); + manifest.lock_screen = std::move(lock_screen); + } + + { // Update with a valid new_note_url. auto note_taking = blink::mojom::ManifestNoteTaking::New(); - note_taking->new_note_url = GURL("http://example.com/new-note-url"); + note_taking->new_note_url = GURL("http://www.chromium.org/new-note-url"); manifest.note_taking = std::move(note_taking); } @@ -240,7 +250,11 @@ EXPECT_EQ(url_handler.origin, url::Origin::Create(GURL("https://url_handlers_origin.com/"))); EXPECT_FALSE(url_handler.has_origin_wildcard); - EXPECT_EQ(GURL("http://example.com/new-note-url"), + + EXPECT_EQ(GURL("http://www.chromium.org/lock-screen-start-url"), + web_app_info.lock_screen_start_url); + + EXPECT_EQ(GURL("http://www.chromium.org/new-note-url"), web_app_info.note_taking_new_note_url); // Check permissions policy was updated. @@ -391,8 +405,8 @@ // Tests that WebAppInfo is correctly updated when Manifest contains Shortcuts. TEST(WebAppInstallUtils, UpdateWebAppInfoFromManifestWithShortcuts) { - base::test::ScopedFeatureList feature_list; - feature_list.InitWithFeatures({blink::features::kFileHandlingIcons}, {}); + base::test::ScopedFeatureList feature_list( + blink::features::kFileHandlingIcons); WebAppInstallInfo web_app_info; web_app_info.title = kAlternativeAppTestTitle; @@ -408,7 +422,6 @@ manifest.scope = kAppUrl.GetWithoutFilename(); manifest.short_name = kAppTestShortName; - const GURL kFileHandlingIcon("fav1.png"); { auto handler = blink::mojom::ManifestFileHandler::New(); handler->action = GURL("http://example.com/open-files"); @@ -416,7 +429,7 @@ handler->name = u"Images"; { blink::Manifest::ImageResource icon; - icon.src = kFileHandlingIcon; + icon.src = GURL("fav1.png"); icon.purpose = {Purpose::ANY, Purpose::MONOCHROME}; handler->icons.push_back(icon); } @@ -692,6 +705,67 @@ EXPECT_EQ(2U, all_icons.size()); } +TEST(WebAppInstallUtils, + UpdateWebAppInfoFromManifest_CrossOriginUrls_DropsFields) { + base::test::ScopedFeatureList feature_list( + blink::features::kWebAppManifestLockScreen); + + WebAppInstallInfo install_info; + + blink::mojom::Manifest manifest; + const GURL kAppUrl("http://www.chromium.org/index.html"); + manifest.start_url = kAppUrl; + manifest.scope = kAppUrl.GetWithoutFilename(); + + { + auto lock_screen = blink::mojom::ManifestLockScreen::New(); + lock_screen->start_url = + GURL("http://www.some-other-origin.com/lock-screen-start-url"); + manifest.lock_screen = std::move(lock_screen); + } + + { + auto note_taking = blink::mojom::ManifestNoteTaking::New(); + note_taking->new_note_url = + GURL("http://www.some-other-origin.com/new-note-url"); + manifest.note_taking = std::move(note_taking); + } + + UpdateWebAppInfoFromManifest( + manifest, GURL("http://www.chromium.org/manifest.json"), &install_info); + + EXPECT_EQ(kAppUrl, install_info.start_url); + EXPECT_TRUE(install_info.lock_screen_start_url.is_empty()); + EXPECT_TRUE(install_info.note_taking_new_note_url.is_empty()); +} + +TEST(WebAppInstallUtils, + UpdateWebAppInfoFromManifest_WithoutLockscreenFlag_DropsField) { + base::test::ScopedFeatureList feature_list; + feature_list.InitAndDisableFeature( + blink::features::kWebAppManifestLockScreen); + + WebAppInstallInfo install_info; + + blink::mojom::Manifest manifest; + const GURL kAppUrl("http://www.chromium.org/index.html"); + manifest.start_url = kAppUrl; + manifest.scope = kAppUrl.GetWithoutFilename(); + + { + auto lock_screen = blink::mojom::ManifestLockScreen::New(); + lock_screen->start_url = + GURL("http://www.chromium.org/lock-screen-start-url"); + manifest.lock_screen = std::move(lock_screen); + } + + UpdateWebAppInfoFromManifest( + manifest, GURL("http://www.chromium.org/manifest.json"), &install_info); + + EXPECT_EQ(kAppUrl, install_info.start_url); + EXPECT_TRUE(install_info.lock_screen_start_url.is_empty()); +} + // Tests that SkBitmaps associated with shortcut item icons are populated in // their own map in web_app_info. TEST(WebAppInstallUtils, PopulateShortcutItemIcons) { @@ -951,7 +1025,7 @@ class FileHandlersFromManifestTest : public ::testing::TestWithParam<bool> { public: FileHandlersFromManifestTest() { - feature_list_.InitWithFeatures({blink::features::kFileHandlingIcons}, {}); + feature_list_.InitAndEnableFeature(blink::features::kFileHandlingIcons); WebAppFileHandlerManager::SetIconsSupportedByOsForTesting(GetParam()); } @@ -1137,8 +1211,8 @@ class RegisterOsSettingsTest : public testing::Test { public: RegisterOsSettingsTest() { - feature_list_.InitWithFeatures( - {features::kEnableWebAppUninstallFromOsSettings}, {}); + feature_list_.InitAndEnableFeature( + features::kEnableWebAppUninstallFromOsSettings); } ~RegisterOsSettingsTest() override = default;
diff --git a/chrome/browser/web_applications/web_app_unittest.cc b/chrome/browser/web_applications/web_app_unittest.cc index 2a6074c..be51ba2d 100644 --- a/chrome/browser/web_applications/web_app_unittest.cc +++ b/chrome/browser/web_applications/web_app_unittest.cc
@@ -171,18 +171,18 @@ "!app_id": "empty_app", "!name": "", "additional_search_terms": [ ], + "allowed_launch_protocols": [ ], "app_service_icon_url": "chrome://app-icon/empty_app/32", "app_size_in_bytes": "", - "allowed_launch_protocols": [ ], "background_color": "none", - "dark_mode_theme_color": "none", - "dark_mode_background_color": "none", - "data_size_in_bytes": "", "capture_links": "kUndefined", "chromeos_data": null, "client_data": { "system_web_app_data": null }, + "dark_mode_background_color": "none", + "dark_mode_theme_color": "none", + "data_size_in_bytes": "", "description": "", "disallowed_launch_protocols": [ ], "display_mode": "", @@ -196,12 +196,11 @@ "file_handler_approval_state": "kRequiresPrompt", "file_handler_os_integration_state": "kDisabled", "file_handlers": [ ], - "manifest_icons": [ ], "handle_links": "kUndefined", - "install_time": "1601-01-01 00:00:00.000 UTC", "install_source_for_metrics": "not set", - "is_generated_icon": false, + "install_time": "1601-01-01 00:00:00.000 UTC", "is_from_sync_and_pending_installation": false, + "is_generated_icon": false, "is_locally_installed": true, "is_storage_isolated": false, "is_uninstalling": false, @@ -209,7 +208,10 @@ "last_launch_time": "1601-01-01 00:00:00.000 UTC", "launch_handler": null, "launch_query_params": null, - "management_type_to_external_configuration_map": {}, + "lock_screen_start_url": "", + "management_type_to_external_configuration_map": { + }, + "manifest_icons": [ ], "manifest_id": null, "manifest_update_time": "1601-01-01 00:00:00.000 UTC", "manifest_url": "", @@ -247,12 +249,12 @@ #endif // BUILDFLAG(IS_CHROMEOS_LACROS) EXPECT_EQ(base::JSONReader::Read(R"JSON({ - "!app_id": "eajjdjobhihlgobdfaehiiheinneagde", + "!app_id": "eajjdjobhihlgobdfaehiiheinneagde", "!name": "Name1234", "additional_search_terms": [ "Foo_1234_0" ], - "allowed_launch_protocols": [ ], + "allowed_launch_protocols": [ "web+test_1234_0", "web+test_1234_1" ], "app_service_icon_url": "chrome://app-icon/eajjdjobhihlgobdfaehiiheinneagde/32", - "app_size_in_bytes": "2093990537", + "app_size_in_bytes": "3687618762", "background_color": "rgba(77,188,194,0.9686274509803922)", "capture_links": "kNone", "chromeos_data": null, @@ -261,7 +263,7 @@ }, "dark_mode_background_color": "none", "dark_mode_theme_color": "none", - "data_size_in_bytes": "2659692452", + "data_size_in_bytes": "2102337622", "description": "Description1234", "disallowed_launch_protocols": [ "web+disallowed_1234_0", "web+disallowed_1234_1", "web+disallowed_1234_2", "web+disallowed_1234_3" ], "display_mode": "standalone", @@ -277,14 +279,14 @@ "MONOCHROME": [ ], "index": 0 }, { - "ANY": [ 218 ], - "MASKABLE": [ 183 ], - "MONOCHROME": [ 203 ], + "ANY": [ 118 ], + "MASKABLE": [ 38 ], + "MONOCHROME": [ 228 ], "index": 1 }, { - "ANY": [ 87, 136 ], - "MASKABLE": [ 187, 128 ], - "MONOCHROME": [ 78, 130 ], + "ANY": [ 80, 47 ], + "MASKABLE": [ 240, 164 ], + "MONOCHROME": [ 138, 107 ], "index": 2 } ], "file_handler_approval_state": "kRequiresPrompt", @@ -390,8 +392,8 @@ "launch_type": "kSingleClient", "name": "2591174844 file" } ], - "handle_links": "kAuto", - "install_source_for_metrics": 13, + "handle_links": "kUndefined", + "install_source_for_metrics": 2, "install_time": "1970-01-10 21:57:36.131 UTC", "is_from_sync_and_pending_installation": false, "is_generated_icon": true, @@ -400,28 +402,25 @@ "is_uninstalling": false, "last_badging_time": "1970-01-13 20:12:59.451 UTC", "last_launch_time": "1970-01-04 17:38:34.900 UTC", - "launch_handler": null, + "launch_handler": { + "route_to": "kExistingClientNavigate" + }, "launch_query_params": "986688382", + "lock_screen_start_url": "https://example.com/scope1234/lock_screen_start_url3206632378", "management_type_to_external_configuration_map": { - "Default": { - "install_urls": [ - "https://example.com/installer1_1234/" - ], - "is_placeholder": false - }, - "SubApp": { - "install_urls": [ - "https://example.com/installer1_1234/" - ], - "is_placeholder": false - }, - "WebAppStore": { - "install_urls": [ - "https://example.com/installer2_1234/" - ], - "is_placeholder": false - } - }, + "Default": { + "install_urls": [ "https://example.com/installer1_1234/" ], + "is_placeholder": true + }, + "SubApp": { + "install_urls": [ "https://example.com/installer2_1234/" ], + "is_placeholder": false + }, + "WebAppStore": { + "install_urls": [ "https://example.com/installer1_1234/" ], + "is_placeholder": true + } + }, "manifest_icons": [ { "purpose": "kAny", "square_size_px": 256, @@ -432,10 +431,10 @@ "url": "https://example.com/icon944292860" } ], "manifest_id": null, - "manifest_update_time": "1970-01-22 23:19:09.029 UTC", + "manifest_update_time": "1970-01-21 01:09:01.170 UTC", "manifest_url": "https://example.com/manifest1234.json", - "note_taking_new_note_url": "https://example.com/scope1234/new_note3206632378", - "parent_app_id": "2353265476", + "note_taking_new_note_url": "", + "parent_app_id": "1112833914", "protocol_handlers": [ { "protocol": "web+test24741963850", "url": "https://example.com/24741963850" @@ -460,105 +459,47 @@ "icons": { "ANY": [ ], "MASKABLE": [ { - "square_size_px": 20, - "url": "https://example.com/shortcuts/icon358829003342" - }, { - "square_size_px": 11, - "url": "https://example.com/shortcuts/icon358829003341" - }, { - "square_size_px": 4, - "url": "https://example.com/shortcuts/icon358829003340" + "square_size_px": 9, + "url": "https://example.com/shortcuts/icon302299027120" } ], - "MONOCHROME": [ ] + "MONOCHROME": [ { + "square_size_px": 18, + "url": "https://example.com/shortcuts/icon302299027121" + } ] }, - "name": "shortcut35882900334", - "url": "https://example.com/scope1234/shortcut35882900334" + "name": "shortcut30229902712", + "url": "https://example.com/scope1234/shortcut30229902712" }, { "icons": { "ANY": [ { - "square_size_px": 41, - "url": "https://example.com/shortcuts/icon358829003334" + "square_size_px": 14, + "url": "https://example.com/shortcuts/icon302299027111" + } ], + "MASKABLE": [ { + "square_size_px": 29, + "url": "https://example.com/shortcuts/icon302299027112" }, { + "square_size_px": 7, + "url": "https://example.com/shortcuts/icon302299027110" + } ], + "MONOCHROME": [ ] + }, + "name": "shortcut30229902711", + "url": "https://example.com/scope1234/shortcut30229902711" + }, { + "icons": { + "ANY": [ { "square_size_px": 0, - "url": "https://example.com/shortcuts/icon358829003330" + "url": "https://example.com/shortcuts/icon302299027100" } ], - "MASKABLE": [ { - "square_size_px": 32, - "url": "https://example.com/shortcuts/icon358829003333" - } ], + "MASKABLE": [ ], "MONOCHROME": [ { - "square_size_px": 23, - "url": "https://example.com/shortcuts/icon358829003332" - }, { "square_size_px": 16, - "url": "https://example.com/shortcuts/icon358829003331" + "url": "https://example.com/shortcuts/icon302299027101" } ] }, - "name": "shortcut35882900333", - "url": "https://example.com/scope1234/shortcut35882900333" - }, { - "icons": { - "ANY": [ { - "square_size_px": 11, - "url": "https://example.com/shortcuts/icon358829003321" - } ], - "MASKABLE": [ { - "square_size_px": 21, - "url": "https://example.com/shortcuts/icon358829003322" - }, { - "square_size_px": 7, - "url": "https://example.com/shortcuts/icon358829003320" - } ], - "MONOCHROME": [ ] - }, - "name": "shortcut35882900332", - "url": "https://example.com/scope1234/shortcut35882900332" - }, { - "icons": { - "ANY": [ { - "square_size_px": 4, - "url": "https://example.com/shortcuts/icon358829003310" - } ], - "MASKABLE": [ { - "square_size_px": 34, - "url": "https://example.com/shortcuts/icon358829003313" - } ], - "MONOCHROME": [ { - "square_size_px": 44, - "url": "https://example.com/shortcuts/icon358829003314" - }, { - "square_size_px": 25, - "url": "https://example.com/shortcuts/icon358829003312" - }, { - "square_size_px": 10, - "url": "https://example.com/shortcuts/icon358829003311" - } ] - }, - "name": "shortcut35882900331", - "url": "https://example.com/scope1234/shortcut35882900331" - }, { - "icons": { - "ANY": [ { - "square_size_px": 33, - "url": "https://example.com/shortcuts/icon358829003303" - }, { - "square_size_px": 26, - "url": "https://example.com/shortcuts/icon358829003302" - } ], - "MASKABLE": [ { - "square_size_px": 11, - "url": "https://example.com/shortcuts/icon358829003301" - } ], - "MONOCHROME": [ { - "square_size_px": 45, - "url": "https://example.com/shortcuts/icon358829003304" - }, { - "square_size_px": 7, - "url": "https://example.com/shortcuts/icon358829003300" - } ] - }, - "name": "shortcut35882900330", - "url": "https://example.com/scope1234/shortcut35882900330" + "name": "shortcut30229902710", + "url": "https://example.com/scope1234/shortcut30229902710" } ], "sources": [ "SubApp", "WebAppStore", "Sync", "Default" ], "start_url": "https://example.com/scope1234/start1234",
diff --git a/chrome/browser/web_applications/web_app_utils.cc b/chrome/browser/web_applications/web_app_utils.cc index fc40cb91..5b7c85a2 100644 --- a/chrome/browser/web_applications/web_app_utils.cc +++ b/chrome/browser/web_applications/web_app_utils.cc
@@ -4,29 +4,47 @@ #include "chrome/browser/web_applications/web_app_utils.h" +#include <algorithm> +#include <bitset> +#include <iterator> +#include <set> +#include <type_traits> #include <utility> #include "base/base64.h" +#include "base/bind.h" +#include "base/check.h" +#include "base/check_op.h" #include "base/containers/contains.h" -#include "base/feature_list.h" +#include "base/containers/flat_set.h" +#include "base/containers/flat_tree.h" #include "base/files/file_path.h" +#include "base/strings/string_piece_forward.h" #include "base/strings/string_util.h" #include "base/strings/utf_string_conversions.h" +#include "base/values.h" #include "build/build_config.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/web_applications/os_integration/os_integration_manager.h" #include "chrome/browser/web_applications/web_app.h" +#include "chrome/browser/web_applications/web_app_constants.h" #include "chrome/browser/web_applications/web_app_icon_manager.h" #include "chrome/browser/web_applications/web_app_provider.h" -#include "chrome/browser/web_applications/web_app_registry_update.h" +#include "chrome/browser/web_applications/web_app_registrar.h" #include "chrome/browser/web_applications/web_app_sync_bridge.h" #include "chrome/common/chrome_constants.h" -#include "chrome/common/chrome_features.h" #include "chrome/grit/generated_resources.h" +#include "components/custom_handlers/protocol_handler.h" #include "components/grit/components_resources.h" #include "components/site_engagement/content/site_engagement_service.h" #include "components/strings/grit/components_strings.h" +#include "content/public/common/alternative_error_page_override_info.mojom-forward.h" +#include "content/public/common/alternative_error_page_override_info.mojom.h" +#include "mojo/public/cpp/bindings/struct_ptr.h" #include "skia/ext/skia_utils_base.h" +#include "third_party/abseil-cpp/absl/types/optional.h" +#include "third_party/skia/include/core/SkBitmap.h" +#include "third_party/skia/include/core/SkColor.h" #include "ui/base/l10n/l10n_util.h" #include "ui/gfx/codec/png_codec.h" #include "url/gurl.h" @@ -479,4 +497,12 @@ return provider->registrar().IsLocallyInstalled(app_id); } +bool IsInScope(const GURL& url, const GURL& scope) { + if (!scope.is_valid()) + return false; + + return base::StartsWith(url.spec(), scope.spec(), + base::CompareCase::SENSITIVE); +} + } // namespace web_app
diff --git a/chrome/browser/web_applications/web_app_utils.h b/chrome/browser/web_applications/web_app_utils.h index 4ef9128f..50900bb2 100644 --- a/chrome/browser/web_applications/web_app_utils.h +++ b/chrome/browser/web_applications/web_app_utils.h
@@ -5,15 +5,18 @@ #ifndef CHROME_BROWSER_WEB_APPLICATIONS_WEB_APP_UTILS_H_ #define CHROME_BROWSER_WEB_APPLICATIONS_WEB_APP_UTILS_H_ +#include <stddef.h> #include <string> +#include <tuple> #include <vector> -#include "base/callback.h" +#include "base/callback_forward.h" +#include "build/build_config.h" +#include "build/buildflag.h" #include "build/chromeos_buildflags.h" #include "chrome/browser/web_applications/web_app.h" #include "chrome/browser/web_applications/web_app_id.h" #include "components/services/app_service/public/cpp/file_handler.h" -#include "content/public/common/alternative_error_page_override_info.mojom.h" class GURL; class Profile; @@ -160,6 +163,9 @@ // Check if |url|'s path is an installed web app. bool HasAppSettingsPage(Profile* profile, const GURL& url); +// Returns whether `url` is in scope `scope`. False if scope is invalid. +bool IsInScope(const GURL& url, const GURL& scope); + #if BUILDFLAG(IS_CHROMEOS) // The kLacrosPrimary and kWebAppsCrosapi features are each independently // sufficient to enable the web apps Crosapi (used for Lacros web app
diff --git a/chrome/build/linux.pgo.txt b/chrome/build/linux.pgo.txt index c237c170..6487ec61 100644 --- a/chrome/build/linux.pgo.txt +++ b/chrome/build/linux.pgo.txt
@@ -1 +1 @@ -chrome-linux-main-1653257309-efa8e931c3f435bcf0a6b5f3d59546fe559d64c8.profdata +chrome-linux-main-1653285310-05ab8e44ff839714d80ecd7b81dd58d047710853.profdata
diff --git a/chrome/build/mac-arm.pgo.txt b/chrome/build/mac-arm.pgo.txt index df95975d..674037c 100644 --- a/chrome/build/mac-arm.pgo.txt +++ b/chrome/build/mac-arm.pgo.txt
@@ -1 +1 @@ -chrome-mac-arm-main-1653257309-a96b1a463206393066c30bdc173870125e250990.profdata +chrome-mac-arm-main-1653285310-33ae798904d1454f1b7f7317369b87c48fe902e3.profdata
diff --git a/chrome/build/mac.pgo.txt b/chrome/build/mac.pgo.txt index e2c4051b..dd487bc 100644 --- a/chrome/build/mac.pgo.txt +++ b/chrome/build/mac.pgo.txt
@@ -1 +1 @@ -chrome-mac-main-1653257309-f8c7b5e83e2b2faf432dfc9230022c4890b9dbb6.profdata +chrome-mac-main-1653285310-8776e0cabafaab2134539e8077bc208d5b83c1de.profdata
diff --git a/chrome/build/win32.pgo.txt b/chrome/build/win32.pgo.txt index 3084c61..5874648 100644 --- a/chrome/build/win32.pgo.txt +++ b/chrome/build/win32.pgo.txt
@@ -1 +1 @@ -chrome-win32-main-1653257309-dec949c51dcbaf1801f91da9e0e9d1f750465f3d.profdata +chrome-win32-main-1653296201-d65cbd52699822181f14833c5d6cb9010b3469a2.profdata
diff --git a/chrome/build/win64.pgo.txt b/chrome/build/win64.pgo.txt index d2d31c4..1a7f4a7d 100644 --- a/chrome/build/win64.pgo.txt +++ b/chrome/build/win64.pgo.txt
@@ -1 +1 @@ -chrome-win64-main-1653257309-ddaa0d9f1ab247ab4b678de6ff0cc424c2d08e4c.profdata +chrome-win64-main-1653296201-52b223a5b458bfbdd58f2891cbdd48ac7b1b0506.profdata
diff --git a/chrome/common/chrome_features.cc b/chrome/common/chrome_features.cc index ff727a14..202a0e5c5 100644 --- a/chrome/common/chrome_features.cc +++ b/chrome/common/chrome_features.cc
@@ -383,13 +383,6 @@ base::FEATURE_ENABLED_BY_DEFAULT}; #endif -#if BUILDFLAG(IS_ANDROID) -// Under this flag tab preloading at startup will be elided (i.e., not -// performed). -const base::Feature kElideTabPreloadAtStartup = { - "ElideTabPreloadAtStartup", base::FEATURE_ENABLED_BY_DEFAULT}; -#endif - // Enables all registered system web apps, regardless of their respective // feature flags. const base::Feature kEnableAllSystemWebApps{"EnableAllSystemWebApps", @@ -625,9 +618,11 @@ "IncognitoBrandConsistencyForAndroid", base::FEATURE_DISABLED_BY_DEFAULT}; #endif +#if BUILDFLAG(IS_ANDROID) // When enabled, users will see a warning when downloading from Incognito. const base::Feature kIncognitoDownloadsWarning{ "IncognitoDownloadsWarning", base::FEATURE_DISABLED_BY_DEFAULT}; +#endif // When enabled, users will see updated UI in Incognito NTP const base::Feature kIncognitoNtpRevamp{"IncognitoNtpRevamp",
diff --git a/chrome/common/chrome_features.h b/chrome/common/chrome_features.h index 3ab6dea..54d3797f 100644 --- a/chrome/common/chrome_features.h +++ b/chrome/common/chrome_features.h
@@ -260,11 +260,6 @@ extern const base::Feature kElidePrioritizationOfPreNativeBootstrapTasks; #endif -#if BUILDFLAG(IS_ANDROID) -COMPONENT_EXPORT(CHROME_FEATURES) -extern const base::Feature kElideTabPreloadAtStartup; -#endif - COMPONENT_EXPORT(CHROME_FEATURES) extern const base::Feature kEnableAllSystemWebApps; @@ -437,8 +432,10 @@ extern const base::Feature kIncognitoBrandConsistencyForAndroid; #endif +#if BUILDFLAG(IS_ANDROID) COMPONENT_EXPORT(CHROME_FEATURES) extern const base::Feature kIncognitoDownloadsWarning; +#endif COMPONENT_EXPORT(CHROME_FEATURES) extern const base::Feature kIncognitoNtpRevamp;
diff --git a/chrome/common/extensions/api/file_manager_private.idl b/chrome/common/extensions/api/file_manager_private.idl index e026cd5..de18d77d 100644 --- a/chrome/common/extensions/api/file_manager_private.idl +++ b/chrome/common/extensions/api/file_manager_private.idl
@@ -1043,6 +1043,9 @@ // cancel the task. callback StartCopyCallback = void(long copyId); +// |taskId| ID of the task that was started. Can be used to cancel ongoing task. +callback IOTaskIdCallback = void(long taskId); + // |sizeStats| Name/value pairs of size stats. Will be undefined if stats could // not be determined. callback GetSizeStatsCallback = void(optional MountPointSizeStats sizeStats); @@ -1502,6 +1505,7 @@ [nocompile] static void getRecentFiles(SourceRestriction restriction, RecentFileType fileType, + boolean invalidateCache, GetRecentFilesCallback callback); // Requests the root directory of the volume with the ID specified in @@ -1650,7 +1654,8 @@ static void startIOTask( IOTaskType type, [instanceof=Entry] object[] entries, - IOTaskParams params); + IOTaskParams params, + optional IOTaskIdCallback callback); // Cancels an I/O task by id. Task ids are communicated to the Files App in // each I/O task's progress status.
diff --git a/chrome/common/extensions/api/file_manager_private_internal.idl b/chrome/common/extensions/api/file_manager_private_internal.idl index 1e75ae3..c7af1499 100644 --- a/chrome/common/extensions/api/file_manager_private_internal.idl +++ b/chrome/common/extensions/api/file_manager_private_internal.idl
@@ -36,6 +36,7 @@ callback GetDisallowedTransfersCallback = void(EntryDescription[] entries); callback StartCopyCallback = void(long copyId); + callback IOTaskIdCallback = void(long taskId); callback ZipSelectionCallback = void(long zipId, double totalBytes); callback ValidatePathNameLengthCallback = void(boolean result); callback GetDirectorySizeCallback = void(double size); @@ -112,6 +113,7 @@ GetVolumeRootCallback callback); static void getRecentFiles(fileManagerPrivate.SourceRestriction restriction, fileManagerPrivate.RecentFileType file_type, + boolean invalidate_cache, GetRecentFilesCallback callback); static void sharePathsWithCrostini(DOMString vmName, DOMString[] urls, boolean persist, @@ -146,6 +148,7 @@ optional SimpleCallback callback); static void startIOTask(fileManagerPrivate.IOTaskType type, DOMString[] urls, - IOTaskParams params); + IOTaskParams params, + optional IOTaskIdCallback callback); }; };
diff --git a/chrome/installer/setup/install_worker.cc b/chrome/installer/setup/install_worker.cc index b87def5..9a70296 100644 --- a/chrome/installer/setup/install_worker.cc +++ b/chrome/installer/setup/install_worker.cc
@@ -564,7 +564,7 @@ // languages is a superset of Chrome's set of translations with this one // exception: what Chrome calls "en-us", Omaha calls "en". sigh. std::wstring language(GetCurrentTranslation()); - if (base::LowerCaseEqualsASCII(language, "en-us")) + if (base::EqualsCaseInsensitiveASCII(language, "en-us")) language.resize(2); list->AddSetRegValueWorkItem(root, clients_key, KEY_WOW64_32KEY, google_update::kRegLangField, language,
diff --git a/chrome/renderer/autofill/autofill_renderer_browsertest.cc b/chrome/renderer/autofill/autofill_renderer_browsertest.cc index ca947383..8c05963 100644 --- a/chrome/renderer/autofill/autofill_renderer_browsertest.cc +++ b/chrome/renderer/autofill/autofill_renderer_browsertest.cc
@@ -98,11 +98,13 @@ const FormFieldData& field, const gfx::RectF& bounding_box) override {} - void AskForValuesToFill(int32_t id, + void AskForValuesToFill(int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) override {} + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) override { + } void HidePopup() override {}
diff --git a/chrome/renderer/autofill/form_autocomplete_browsertest.cc b/chrome/renderer/autofill/form_autocomplete_browsertest.cc index 7b16d85d..b345ff2 100644 --- a/chrome/renderer/autofill/form_autocomplete_browsertest.cc +++ b/chrome/renderer/autofill/form_autocomplete_browsertest.cc
@@ -96,11 +96,12 @@ select_control_changed_ = std::make_unique<FormFieldData>(field); } - void AskForValuesToFill(int32_t id, + void AskForValuesToFill(int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_field) override {} + bool autoselect_first_field, + TouchToFillEligible touch_to_fill_eliible) override {} void HidePopup() override {}
diff --git a/chrome/renderer/resources/extensions/file_manager_private_custom_bindings.js b/chrome/renderer/resources/extensions/file_manager_private_custom_bindings.js index 5c6b8fba..0cb6741 100644 --- a/chrome/renderer/resources/extensions/file_manager_private_custom_bindings.js +++ b/chrome/renderer/resources/extensions/file_manager_private_custom_bindings.js
@@ -253,9 +253,9 @@ }); apiFunctions.setHandleRequest('getRecentFiles', function( - restriction, file_type, callback) { - fileManagerPrivateInternal.getRecentFiles(restriction, file_type, function( - entryDescriptions) { + restriction, file_type, invalidate_cache, callback) { + fileManagerPrivateInternal.getRecentFiles(restriction, file_type, + invalidate_cache, function(entryDescriptions) { callback(entryDescriptions.map(function(description) { return GetExternalFileEntry(description); })); @@ -367,14 +367,16 @@ urls, added, callback); }); - apiFunctions.setHandleRequest('startIOTask', function(type, entries, params) { - const urls = entries.map(entry => getEntryURL(entry)); - let newParams = {}; - if (params.destinationFolder) { - newParams.destinationFolderUrl = getEntryURL(params.destinationFolder); - } - fileManagerPrivateInternal.startIOTask(type, urls, newParams); - }); + apiFunctions.setHandleRequest( + 'startIOTask', function(type, entries, params, callback) { + const urls = entries.map(entry => getEntryURL(entry)); + let newParams = {}; + if (params.destinationFolder) { + newParams.destinationFolderUrl = + getEntryURL(params.destinationFolder); + } + fileManagerPrivateInternal.startIOTask(type, urls, newParams, callback); + }); }); bindingUtil.registerEventArgumentMassager(
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn index 77e062d4..328f6ab 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn
@@ -2150,7 +2150,7 @@ "../browser/ui/views/hats/hats_browsertest.cc", "../browser/ui/views/incognito_clear_browsing_data_dialog_browsertest.cc", "../browser/ui/views/privacy_sandbox/privacy_sandbox_dialog_view_browsertest.cc", - "../browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_view_browsertest.cc", + "../browser/ui/views/privacy_sandbox/privacy_sandbox_notice_bubble_browsertest.cc", "../browser/ui/views/reader_mode/reader_mode_icon_view_browsertest.cc", "../browser/ui/views/sharing/remote_copy_browsertest.cc", "../browser/ui/views/sharing/shared_clipboard_browsertest.cc",
diff --git a/chrome/test/chromedriver/chrome/frame_tracker.cc b/chrome/test/chromedriver/chrome/frame_tracker.cc index 2e48918..8b729a05 100644 --- a/chrome/test/chromedriver/chrome/frame_tracker.cc +++ b/chrome/test/chromedriver/chrome/frame_tracker.cc
@@ -22,8 +22,8 @@ FrameTracker::~FrameTracker() {} -Status FrameTracker::GetContextIdForFrame( - const std::string& frame_id, int* context_id) { +Status FrameTracker::GetContextIdForFrame(const std::string& frame_id, + std::string* context_id) { if (frame_to_context_map_.count(frame_id) == 0) { return Status(kNoSuchExecutionContext, "frame does not have execution context"); @@ -105,7 +105,7 @@ std::string frame_id; bool is_default = true; - absl::optional<int> context_id = context->GetDict().FindInt("id"); + const std::string* context_id = context->GetDict().FindString("uniqueId"); if (!context_id) { std::string json; base::JSONWriter::Write(*context, &json); @@ -131,14 +131,22 @@ if (is_default && !frame_id.empty()) frame_to_context_map_[frame_id] = *context_id; } else if (method == "Runtime.executionContextDestroyed") { - absl::optional<int> execution_context_id = - params.GetDict().FindInt("executionContextId"); - if (!execution_context_id) - return Status(kUnknownError, method + " missing 'executionContextId'"); - for (auto entry : frame_to_context_map_) { - if (entry.second == *execution_context_id) { - frame_to_context_map_.erase(entry.first); - break; + const base::Value::Dict* context = params.GetDict().FindDict("context"); + // TODO(nechaev): Interpret the missing 'context' as an error + // after https://crbug.com/chromedriver/4120 is fixed. + if (context) { + const std::string* context_id = context->FindString("uniqueId"); + if (!context_id) { + std::string json; + base::JSONWriter::Write(*context, &json); + return Status(kUnknownError, + method + " has invalid 'context': " + json); + } + for (auto entry : frame_to_context_map_) { + if (entry.second == *context_id) { + frame_to_context_map_.erase(entry.first); + break; + } } } } else if (method == "Runtime.executionContextsCleared") { @@ -153,6 +161,9 @@ } else if (method == "Page.frameDetached") { if (const std::string* frame_id = params.GetDict().FindString("frameId")) { attached_frames_.erase(*frame_id); + // TODO(nechaev): Remove the following line + // after https://crbug.com/chromedriver/4120 is fixed. + frame_to_context_map_.erase(*frame_id); } else { return Status(kUnknownError, "missing frameId in Page.frameDetached event");
diff --git a/chrome/test/chromedriver/chrome/frame_tracker.h b/chrome/test/chromedriver/chrome/frame_tracker.h index f467dc5..c64cafe 100644 --- a/chrome/test/chromedriver/chrome/frame_tracker.h +++ b/chrome/test/chromedriver/chrome/frame_tracker.h
@@ -33,7 +33,8 @@ ~FrameTracker() override; - Status GetContextIdForFrame(const std::string& frame_id, int* context_id); + Status GetContextIdForFrame(const std::string& frame_id, + std::string* context_id); WebView* GetTargetForFrame(const std::string& frame_id); bool IsKnownFrame(const std::string& frame_id) const; void DeleteTargetForFrame(const std::string& frame_id); @@ -45,7 +46,7 @@ const base::DictionaryValue& params) override; private: - std::map<std::string, int> frame_to_context_map_; + std::map<std::string, std::string> frame_to_context_map_; std::map<std::string, std::unique_ptr<WebView>> frame_to_target_map_; std::unordered_set<std::string> attached_frames_; raw_ptr<WebView> web_view_;
diff --git a/chrome/test/chromedriver/chrome/frame_tracker_unittest.cc b/chrome/test/chromedriver/chrome/frame_tracker_unittest.cc index dd49da9..b044b8f0 100644 --- a/chrome/test/chromedriver/chrome/frame_tracker_unittest.cc +++ b/chrome/test/chromedriver/chrome/frame_tracker_unittest.cc
@@ -14,12 +14,13 @@ TEST(FrameTracker, GetContextIdForFrame) { StubDevToolsClient client; FrameTracker tracker(&client); - int context_id = -1; + std::string context_id; ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsError()); - ASSERT_EQ(-1, context_id); + ASSERT_EQ("", context_id); const char context[] = - "{\"id\":100,\"auxData\":{\"frameId\":\"f\",\"isDefault\":true}}"; + "{\"uniqueId\":\"100\",\"auxData\":{\"frameId\":\"f\",\"isDefault\":true}" + "}"; base::DictionaryValue params; params.GetDict().Set("context", std::move(*base::JSONReader::ReadDeprecated(context))); @@ -28,9 +29,9 @@ .code()); ASSERT_EQ(kNoSuchExecutionContext, tracker.GetContextIdForFrame("foo", &context_id).code()); - ASSERT_EQ(-1, context_id); + ASSERT_EQ("", context_id); ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsOk()); - ASSERT_EQ(100, context_id); + ASSERT_EQ("100", context_id); base::DictionaryValue nav_params; nav_params.GetDict().SetByDottedPath("frame.parentId", "1"); @@ -47,11 +48,11 @@ TEST(FrameTracker, AuxData) { StubDevToolsClient client; FrameTracker tracker(&client); - int context_id = -1; + std::string context_id; ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsError()); - ASSERT_EQ(-1, context_id); + ASSERT_EQ("", context_id); - const char context[] = "{\"id\":100,\"auxData\":{}}"; + const char context[] = "{\"uniqueId\":\"100\",\"auxData\":{}}"; base::DictionaryValue params; params.GetDict().Set("context", std::move(*base::JSONReader::ReadDeprecated(context))); @@ -62,9 +63,9 @@ .code()); ASSERT_EQ(kNoSuchExecutionContext, tracker.GetContextIdForFrame("foo", &context_id).code()); - ASSERT_EQ(-1, context_id); + ASSERT_EQ("", context_id); ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsOk()); - ASSERT_EQ(100, context_id); + ASSERT_EQ("100", context_id); } TEST(FrameTracker, CanUpdateFrameContextId) { @@ -72,23 +73,23 @@ FrameTracker tracker(&client); const char context[] = - "{\"id\":1,\"auxData\":{\"frameId\":\"f\",\"isDefault\":true}}"; + "{\"uniqueId\":\"1\",\"auxData\":{\"frameId\":\"f\",\"isDefault\":true}}"; base::DictionaryValue params; params.GetDict().Set("context", std::move(*base::JSONReader::ReadDeprecated(context))); ASSERT_EQ(kOk, tracker.OnEvent(&client, "Runtime.executionContextCreated", params) .code()); - int context_id = -1; + std::string context_id; ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsOk()); - ASSERT_EQ(1, context_id); + ASSERT_EQ("1", context_id); - params.GetDict().SetByDottedPath("context.id", 2); + params.GetDict().SetByDottedPath("context.uniqueId", "2"); ASSERT_EQ(kOk, tracker.OnEvent(&client, "Runtime.executionContextCreated", params) .code()); ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsOk()); - ASSERT_EQ(2, context_id); + ASSERT_EQ("2", context_id); } TEST(FrameTracker, DontTrackContentScriptContexts) { @@ -96,22 +97,22 @@ FrameTracker tracker(&client); const char context[] = - "{\"id\":1,\"auxData\":{\"frameId\":\"f\",\"isDefault\":true}}"; + "{\"uniqueId\":\"1\",\"auxData\":{\"frameId\":\"f\",\"isDefault\":true}}"; base::DictionaryValue params; params.GetDict().Set("context", std::move(*base::JSONReader::ReadDeprecated(context))); ASSERT_EQ(kOk, tracker.OnEvent(&client, "Runtime.executionContextCreated", params) .code()); - int context_id = -1; + std::string context_id; ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsOk()); - ASSERT_EQ(1, context_id); + ASSERT_EQ("1", context_id); - params.GetDict().SetByDottedPath("context.id", 2); + params.GetDict().SetByDottedPath("context.uniqueId", "2"); params.GetDict().SetByDottedPath("context.auxData.isDefault", false); ASSERT_EQ(kOk, tracker.OnEvent(&client, "Runtime.executionContextCreated", params) .code()); ASSERT_TRUE(tracker.GetContextIdForFrame("f", &context_id).IsOk()); - ASSERT_EQ(1, context_id); + ASSERT_EQ("1", context_id); }
diff --git a/chrome/test/chromedriver/chrome/web_view_impl.cc b/chrome/test/chromedriver/chrome/web_view_impl.cc index 2f5af109..0efeb33 100644 --- a/chrome/test/chromedriver/chrome/web_view_impl.cc +++ b/chrome/test/chromedriver/chrome/web_view_impl.cc
@@ -47,9 +47,10 @@ Status GetContextIdForFrame(WebViewImpl* web_view, const std::string& frame, - int* context_id) { + std::string* context_id) { + DCHECK(context_id); if (frame.empty() || frame == web_view->GetId()) { - *context_id = 0; + context_id->clear(); return Status(kOk); } Status status = @@ -587,7 +588,7 @@ awaitPromise, result); } - int context_id; + std::string context_id; Status status = GetContextIdForFrame(this, frame, &context_id); if (status.IsError()) return status; @@ -680,7 +681,7 @@ return target->GetFrameByFunction(frame, function, args, out_frame); } - int context_id; + std::string context_id; Status status = GetContextIdForFrame(this, frame, &context_id); if (status.IsError()) return status; @@ -1136,7 +1137,7 @@ int* backend_node_id) { if (!element.is_dict()) return Status(kUnknownError, "'element' is not a dictionary"); - int context_id; + std::string context_id; Status status = GetContextIdForFrame(this, frame, &context_id); if (status.IsError()) return status; @@ -1535,7 +1536,7 @@ namespace internal { Status EvaluateScript(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& expression, EvaluateScriptReturnType return_type, const base::TimeDelta& timeout, @@ -1544,8 +1545,9 @@ base::DictionaryValue params; base::Value::Dict& dict = params.GetDict(); dict.Set("expression", expression); - if (context_id) - dict.Set("contextId", context_id); + if (!context_id.empty()) { + dict.Set("uniqueContextId", context_id); + } dict.Set("returnByValue", return_type == ReturnByValue); dict.Set("awaitPromise", awaitPromise); base::Value cmd_result; @@ -1575,7 +1577,7 @@ } Status EvaluateScriptAndGetObject(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& expression, const base::TimeDelta& timeout, const bool awaitPromise, @@ -1599,7 +1601,7 @@ } Status EvaluateScriptAndGetValue(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& expression, const base::TimeDelta& timeout, const bool awaitPromise, @@ -1650,7 +1652,7 @@ } Status GetBackendNodeIdFromFunction(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& function, const base::ListValue& args, bool* found_node, @@ -1715,7 +1717,7 @@ } Status GetFrameIdFromFunction(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& function, const base::ListValue& args, bool* found_node,
diff --git a/chrome/test/chromedriver/chrome/web_view_impl.h b/chrome/test/chromedriver/chrome/web_view_impl.h index ffe361f..a996845b 100644 --- a/chrome/test/chromedriver/chrome/web_view_impl.h +++ b/chrome/test/chromedriver/chrome/web_view_impl.h
@@ -255,21 +255,21 @@ ReturnByObject }; Status EvaluateScript(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& expression, EvaluateScriptReturnType return_type, const base::TimeDelta& timeout, const bool awaitPromise, std::unique_ptr<base::DictionaryValue>* result); Status EvaluateScriptAndGetObject(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& expression, const base::TimeDelta& timeout, const bool awaitPromise, bool* got_object, std::string* object_id); Status EvaluateScriptAndGetValue(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& expression, const base::TimeDelta& timeout, const bool awaitPromise, @@ -277,14 +277,14 @@ Status ParseCallFunctionResult(const base::Value& temp_result, std::unique_ptr<base::Value>* result); Status GetBackendNodeIdFromFunction(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& function, const base::ListValue& args, bool* found_node, int* backend_node_id, bool w3c_compliant); Status GetFrameIdFromFunction(DevToolsClient* client, - int context_id, + const std::string& context_id, const std::string& function, const base::ListValue& args, bool* found_node,
diff --git a/chrome/test/chromedriver/chrome/web_view_impl_unittest.cc b/chrome/test/chromedriver/chrome/web_view_impl_unittest.cc index 000e9c5..d45a0c5 100644 --- a/chrome/test/chromedriver/chrome/web_view_impl_unittest.cc +++ b/chrome/test/chromedriver/chrome/web_view_impl_unittest.cc
@@ -57,7 +57,7 @@ FakeDevToolsClient client; client.set_result(command_result); Status status = internal::EvaluateScript( - &client, 0, std::string(), internal::ReturnByValue, + &client, "context", std::string(), internal::ReturnByValue, base::TimeDelta::Max(), false, &result); ASSERT_EQ(kUnknownError, status.code()); ASSERT_FALSE(result); @@ -70,7 +70,7 @@ FakeDevToolsClient client; client.set_status(Status(kUnknownError)); Status status = internal::EvaluateScript( - &client, 0, std::string(), internal::ReturnByValue, + &client, "context", std::string(), internal::ReturnByValue, base::TimeDelta::Max(), false, &result); ASSERT_EQ(kUnknownError, status.code()); ASSERT_FALSE(result); @@ -95,7 +95,7 @@ dict.GetDict().SetByDottedPath("result.key", 100); FakeDevToolsClient client; client.set_result(dict); - ASSERT_TRUE(internal::EvaluateScript(&client, 0, std::string(), + ASSERT_TRUE(internal::EvaluateScript(&client, "context", std::string(), internal::ReturnByValue, base::TimeDelta::Max(), false, &result) .IsOk()); @@ -109,9 +109,9 @@ base::DictionaryValue dict; dict.GetDict().SetByDottedPath("result.value", 1); client.set_result(dict); - ASSERT_TRUE(internal::EvaluateScriptAndGetValue(&client, 0, std::string(), - base::TimeDelta::Max(), false, - &result) + ASSERT_TRUE(internal::EvaluateScriptAndGetValue( + &client, "context", std::string(), base::TimeDelta::Max(), + false, &result) .IsError()); } @@ -122,7 +122,8 @@ dict.GetDict().SetByDottedPath("result.type", "undefined"); client.set_result(dict); Status status = internal::EvaluateScriptAndGetValue( - &client, 0, std::string(), base::TimeDelta::Max(), false, &result); + &client, "context", std::string(), base::TimeDelta::Max(), false, + &result); ASSERT_EQ(kOk, status.code()); ASSERT_TRUE(result && result->is_none()); } @@ -135,7 +136,8 @@ dict.GetDict().SetByDottedPath("result.value", 1); client.set_result(dict); Status status = internal::EvaluateScriptAndGetValue( - &client, 0, std::string(), base::TimeDelta::Max(), false, &result); + &client, "context", std::string(), base::TimeDelta::Max(), false, + &result); ASSERT_EQ(kOk, status.code()); ASSERT_TRUE(result && result->is_int()); ASSERT_EQ(1, result->GetInt()); @@ -149,8 +151,8 @@ bool got_object; std::string object_id; ASSERT_TRUE(internal::EvaluateScriptAndGetObject( - &client, 0, std::string(), base::TimeDelta::Max(), false, - &got_object, &object_id) + &client, "context", std::string(), base::TimeDelta::Max(), + false, &got_object, &object_id) .IsOk()); ASSERT_FALSE(got_object); ASSERT_TRUE(object_id.empty()); @@ -164,8 +166,8 @@ bool got_object; std::string object_id; ASSERT_TRUE(internal::EvaluateScriptAndGetObject( - &client, 0, std::string(), base::TimeDelta::Max(), false, - &got_object, &object_id) + &client, "context", std::string(), base::TimeDelta::Max(), + false, &got_object, &object_id) .IsOk()); ASSERT_TRUE(got_object); ASSERT_STREQ("id", object_id.c_str());
diff --git a/chrome/test/chromedriver/element_util.cc b/chrome/test/chromedriver/element_util.cc index acc461d..1b73c355 100644 --- a/chrome/test/chromedriver/element_util.cc +++ b/chrome/test/chromedriver/element_util.cc
@@ -529,8 +529,7 @@ "document.contentType", false, &contentType); if (status.IsError()) return status; - if (base::LowerCaseEqualsASCII(contentType->GetString(), - "text/xml")) + if (base::EqualsCaseInsensitiveASCII(contentType->GetString(), "text/xml")) *is_xml_document = true; else *is_xml_document = false; @@ -567,7 +566,7 @@ return status; if (result->is_string()) { *is_equal = - base::LowerCaseEqualsASCII(result->GetString(), attribute_value); + base::EqualsCaseInsensitiveASCII(result->GetString(), attribute_value); } else { *is_equal = false; }
diff --git a/chrome/test/data/extensions/api_test/automation/sites/add_remove_event_listeners.html b/chrome/test/data/extensions/api_test/automation/sites/add_remove_event_listeners.html index cbd9bc3..4c123ec 100644 --- a/chrome/test/data/extensions/api_test/automation/sites/add_remove_event_listeners.html +++ b/chrome/test/data/extensions/api_test/automation/sites/add_remove_event_listeners.html
@@ -8,17 +8,11 @@ <title>Automation Tests - Add Remove Event Listeners</title> </head> <body> - <button id="remove">remove</button> - <button id="close">close</button> + <button></button> <script> - const removeButton = document.getElementById('remove'); - removeButton.addEventListener('click', () => { - removeButton.remove(); - }); - - const closeButton = document.getElementById('close'); - closeButton.addEventListener('click', () => { - window.close(); + const button = document.querySelector('button'); + button.addEventListener('click', () => { + button.setAttribute('aria-hidden', true); }); </script> </body>
diff --git a/chrome/test/data/extensions/api_test/automation/tests/desktop/add_remove_event_listeners.js b/chrome/test/data/extensions/api_test/automation/tests/desktop/add_remove_event_listeners.js index 5d9c5436..af7258ce 100644 --- a/chrome/test/data/extensions/api_test/automation/tests/desktop/add_remove_event_listeners.js +++ b/chrome/test/data/extensions/api_test/automation/tests/desktop/add_remove_event_listeners.js
@@ -50,28 +50,17 @@ desktop.removeEventListener( chrome.automation.EventType.FOCUS, focusHandler); - // This does get the current desktop as well, prior to disabling. Doing this - // checks that repeated calls still work prior to the disable coming - // through. + // This sends an enableDesktop call, which should be processed after the + // disableDesktop request. const newDesktop = await new Promise(r => chrome.automation.getDesktop(r)); - // Both |desktop| and |newDesktop| should be valid and refer to the + // Finally, both |desktop| and |newDesktop| should be valid and refer to the // same tree. assertTrue(!!desktop); assertTrue(!!newDesktop); assertEq(newDesktop, desktop); assertEq(chrome.automation.RoleType.DESKTOP, newDesktop.role); - // Finally, the disabling above (from removing the event listeners) comes - // some time later. Wait for it so that it does not impact other tests. - await new Promise(r => { - setInterval(() => { - if (desktop.role === undefined) { - r(); - } - }, 100); - }); - chrome.test.succeed(); }, @@ -79,16 +68,8 @@ const desktop = await new Promise(r => chrome.automation.getDesktop(r)); assertTrue(!!desktop); - const button = await new Promise(r => { - setInterval(() => { - let node; - if (node = findAutomationNode(desktop, n => n.name === 'remove')) { - r(node); - } - }, 100); - }); + const button = desktop.find({role: chrome.automation.RoleType.BUTTON}); assertTrue(!!button); - assertEq('remove', button.name); // Adding a listener should have no effect. const focusHandler = () => {}; @@ -113,55 +94,6 @@ // The tree is completely cleared. assertEq(undefined, desktop.role); chrome.test.succeed(); - }, - - // Note that these tests run on the *same* webpage, so the above test already - // removed/hide one of the buttons. - async function testWindowClose() { - const desktop = await new Promise(r => chrome.automation.getDesktop(r)); - assertTrue(!!desktop); - - const button = await new Promise(r => { - setInterval(() => { - let node; - if (node = findAutomationNode(desktop, n => n.name === 'close')) { - r(node); - } - }, 100); - }); - assertTrue(!!button); - assertEq('close', button.name); - - // Adding a listener should have no effect. - const focusHandler = () => {}; - button.addEventListener(chrome.automation.EventType.FOCUS, focusHandler); - assertEq(chrome.automation.RoleType.DESKTOP, desktop.role); - - // The click/do default action triggers the window to close. - button.doDefault(); - - // We can't add event listeners to observe the deletions as to not trigger - // adds, so poll for the change. - await new Promise(r => { - const checkForButton = () => { - if (button.role === undefined) { - r(); - clearInterval(id); - } - }; - const id = setInterval(checkForButton, 10); - }); - - // The tree is completely cleared after some time. - await new Promise(r => { - setInterval(() => { - if (desktop.role === undefined) { - r(); - } - }, 100); - }); - - chrome.test.succeed(); } ];
diff --git a/chrome/test/data/extensions/api_test/file_browser/recent_test/test.js b/chrome/test/data/extensions/api_test/file_browser/recent_test/test.js index 89f4d77..6c296bb5 100644 --- a/chrome/test/data/extensions/api_test/file_browser/recent_test/test.js +++ b/chrome/test/data/extensions/api_test/file_browser/recent_test/test.js
@@ -46,7 +46,7 @@ chrome.test.runTests([ function testGetRecentFiles() { chrome.fileManagerPrivate.getRecentFiles( - 'native_source', 'all', chrome.test.callbackPass(entries => { + 'native_source', 'all', false, chrome.test.callbackPass(entries => { chrome.test.assertTrue( exists(entries, 'all-justice.jpg'), 'all-justice.jpg not found'); @@ -60,7 +60,7 @@ }, function testGetRecentAudioFiles() { chrome.fileManagerPrivate.getRecentFiles( - 'native_source', 'audio', chrome.test.callbackPass(entries => { + 'native_source', 'audio', false, chrome.test.callbackPass(entries => { chrome.test.assertFalse( exists(entries, 'all-justice.jpg'), 'all-justice.jpg unexpectedly found'); @@ -74,7 +74,7 @@ }, function testGetRecentImageFiles() { chrome.fileManagerPrivate.getRecentFiles( - 'native_source', 'image', chrome.test.callbackPass(entries => { + 'native_source', 'image', false, chrome.test.callbackPass(entries => { chrome.test.assertTrue( exists(entries, 'all-justice.jpg'), 'all-justice.jpg not found'); @@ -88,7 +88,7 @@ }, function testGetRecentVideoFiles() { chrome.fileManagerPrivate.getRecentFiles( - 'native_source', 'video', chrome.test.callbackPass(entries => { + 'native_source', 'video', false, chrome.test.callbackPass(entries => { chrome.test.assertFalse( exists(entries, 'all-justice.jpg'), 'all-justice.jpg unexpectedly found');
diff --git a/chrome/test/data/webui/settings/cr_settings_browsertest.js b/chrome/test/data/webui/settings/cr_settings_browsertest.js index d1c3bbb..c29a3215 100644 --- a/chrome/test/data/webui/settings/cr_settings_browsertest.js +++ b/chrome/test/data/webui/settings/cr_settings_browsertest.js
@@ -519,8 +519,16 @@ runMochaSuite('PrivacyGuidePage'); }); +// TODO(crbug.com/1328037): Flaky on Linux Tests(dbg). +GEN('#if BUILDFLAG(IS_LINUX) && !defined(NDEBUG)'); +GEN('#define MAYBE_PrivacyGuideFragmentMetricsTests \\'); +GEN(' DISABLED_PrivacyGuideFragmentMetricsTests'); +GEN('#else'); +GEN('#define MAYBE_PrivacyGuideFragmentMetricsTests \\'); +GEN(' PrivacyGuideFragmentMetricsTests'); +GEN('#endif'); TEST_F( - 'CrSettingsPrivacyGuidePageTest', 'PrivacyGuideFragmentMetricsTests', + 'CrSettingsPrivacyGuidePageTest', 'MAYBE_PrivacyGuideFragmentMetricsTests', function() { runMochaSuite('PrivacyGuideFragmentMetrics'); });
diff --git a/chrome/updater/test/integration_test_commands.h b/chrome/updater/test/integration_test_commands.h index 39a797bb..eff3830a 100644 --- a/chrome/updater/test/integration_test_commands.h +++ b/chrome/updater/test/integration_test_commands.h
@@ -94,8 +94,6 @@ virtual void ExpectLastStarted() const = 0; virtual void UninstallApp(const std::string& app_id) const = 0; - virtual void RunOfflineInstall() = 0; - protected: friend class base::RefCountedThreadSafe<IntegrationTestCommands>;
diff --git a/chrome/updater/test/integration_test_commands_system.cc b/chrome/updater/test/integration_test_commands_system.cc index 8a22b04..e9baada 100644 --- a/chrome/updater/test/integration_test_commands_system.cc +++ b/chrome/updater/test/integration_test_commands_system.cc
@@ -270,10 +270,6 @@ RunCommand("uninstall_app", {Param("app_id", app_id)}); } - void RunOfflineInstall() override { - updater::test::RunOfflineInstall(updater_scope_); - } - private: ~IntegrationTestCommandsSystem() override = default;
diff --git a/chrome/updater/test/integration_test_commands_user.cc b/chrome/updater/test/integration_test_commands_user.cc index 421e5f1..be1c375 100644 --- a/chrome/updater/test/integration_test_commands_user.cc +++ b/chrome/updater/test/integration_test_commands_user.cc
@@ -234,10 +234,6 @@ updater::test::UninstallApp(updater_scope_, app_id); } - void RunOfflineInstall() override { - updater::test::RunOfflineInstall(updater_scope_); - } - private: ~IntegrationTestCommandsUser() override = default;
diff --git a/chrome/updater/test/integration_tests.cc b/chrome/updater/test/integration_tests.cc index 7cca93b..3f8db104 100644 --- a/chrome/updater/test/integration_tests.cc +++ b/chrome/updater/test/integration_tests.cc
@@ -301,8 +301,6 @@ void ExpectLastStarted() { test_commands_->ExpectLastStarted(); } - void RunOfflineInstall() { test_commands_->RunOfflineInstall(); } - scoped_refptr<IntegrationTestCommands> test_commands_; private: @@ -753,13 +751,6 @@ Uninstall(); } -TEST_F(IntegrationTest, OfflineInstall) { - Install(); - ExpectInstalled(); - RunOfflineInstall(); - Uninstall(); -} - #endif // BUILDFLAG(IS_WIN) || !defined(COMPONENT_BUILD) } // namespace test
diff --git a/chrome/updater/test/integration_tests_impl.h b/chrome/updater/test/integration_tests_impl.h index 29d6a7f..1f332f6 100644 --- a/chrome/updater/test/integration_tests_impl.h +++ b/chrome/updater/test/integration_tests_impl.h
@@ -216,8 +216,6 @@ void UninstallApp(UpdaterScope scope, const std::string& app_id); -void RunOfflineInstall(UpdaterScope scope); - } // namespace test } // namespace updater
diff --git a/chrome/updater/test/integration_tests_linux.cc b/chrome/updater/test/integration_tests_linux.cc index 8f23697..c1add23 100644 --- a/chrome/updater/test/integration_tests_linux.cc +++ b/chrome/updater/test/integration_tests_linux.cc
@@ -102,9 +102,5 @@ NOTREACHED(); } -void RunOfflineInstall(UpdaterScope scope) { - NOTREACHED(); -} - } // namespace test } // namespace updater
diff --git a/chrome/updater/test/integration_tests_mac.mm b/chrome/updater/test/integration_tests_mac.mm index f8e5212..5c583ffe 100644 --- a/chrome/updater/test/integration_tests_mac.mm +++ b/chrome/updater/test/integration_tests_mac.mm
@@ -418,9 +418,5 @@ base::FilePath(FILE_PATH_LITERAL("NONE"))); } -void RunOfflineInstall(UpdaterScope scope) { - // TODO(crbug.com/1286574). -} - } // namespace test } // namespace updater
diff --git a/chrome/updater/test/integration_tests_win.cc b/chrome/updater/test/integration_tests_win.cc index 0f38438..c42a017 100644 --- a/chrome/updater/test/integration_tests_win.cc +++ b/chrome/updater/test/integration_tests_win.cc
@@ -13,11 +13,9 @@ #include <vector> #include "base/command_line.h" -#include "base/containers/contains.h" #include "base/containers/flat_map.h" #include "base/files/file_path.h" #include "base/files/file_util.h" -#include "base/files/scoped_temp_dir.h" #include "base/json/json_writer.h" #include "base/logging.h" #include "base/path_service.h" @@ -31,7 +29,6 @@ #include "base/task/task_traits.h" #include "base/task/thread_pool.h" #include "base/test/bind.h" -#include "base/test/test_timeouts.h" #include "base/time/time.h" #include "base/timer/elapsed_timer.h" #include "base/values.h" @@ -54,10 +51,6 @@ #include "chrome/updater/util.h" #include "chrome/updater/win/setup/setup_util.h" #include "chrome/updater/win/task_scheduler.h" -#include "chrome/updater/win/test/test_executables.h" -#include "chrome/updater/win/test/test_strings.h" -#include "chrome/updater/win/ui/l10n_util.h" -#include "chrome/updater/win/ui/resources/updater_installer_strings.h" #include "chrome/updater/win/win_constants.h" #include "chrome/updater/win/win_util.h" #include "components/crx_file/crx_verifier.h" @@ -340,63 +333,6 @@ VLOG(2) << "Sleep complete."; } -class WindowEnumerator { - public: - WindowEnumerator(HWND parent, - base::RepeatingCallback<bool(HWND hwnd)> filter, - base::RepeatingCallback<void(HWND hwnd)> action) - : parent_(parent), filter_(filter), action_(action) {} - - WindowEnumerator(const WindowEnumerator&) = delete; - WindowEnumerator& operator=(const WindowEnumerator&) = delete; - - void Run() const { - ::EnumChildWindows(parent_, &OnWindowProc, reinterpret_cast<LPARAM>(this)); - } - - static std::wstring GetWindowClass(HWND hwnd) { - constexpr int kMaxWindowClassNameLength = 256; - wchar_t buffer[kMaxWindowClassNameLength + 1] = {0}; - int name_len = ::GetClassName(hwnd, buffer, std::size(buffer)); - if (name_len <= 0 || name_len > kMaxWindowClassNameLength) - return std::wstring(); - - return std::wstring(&buffer[0], name_len); - } - - static bool IsSystemDialog(HWND hwnd) { - constexpr wchar_t kSystemDialogClass[] = L"#32770"; - return GetWindowClass(hwnd) == kSystemDialogClass; - } - - static std::wstring GetWindowText(HWND hwnd) { - const int num_chars = ::GetWindowTextLength(hwnd); - if (!num_chars) - return std::wstring(); - std::vector<wchar_t> text(num_chars + 1); - if (!::GetWindowText(hwnd, &text.front(), text.size())) - return std::wstring(); - return std::wstring(text.begin(), text.end()); - } - - private: - bool OnWindow(HWND hwnd) const { - if (filter_.Run(hwnd)) - action_.Run(hwnd); - - // Returns true to keep enumerating. - return true; - } - - static BOOL CALLBACK OnWindowProc(HWND hwnd, LPARAM lparam) { - return reinterpret_cast<WindowEnumerator*>(lparam)->OnWindow(hwnd); - } - - const HWND parent_; - base::RepeatingCallback<bool(HWND hwnd)> filter_; - base::RepeatingCallback<void(HWND hwnd)> action_; -}; - } // namespace base::FilePath GetSetupExecutablePath() { @@ -1041,128 +977,5 @@ ASSERT_EQ(key.DeleteKey(base::SysUTF8ToWide(app_id).c_str()), ERROR_SUCCESS); } -void RunOfflineInstall(UpdaterScope scope) { - const char kManifestFormat[] = - "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" - "<response protocol=\"3.0\">" - " <app appid=\"{CDABE316-39CD-43BA-8440-6D1E0547AEE6}\" status=\"ok\">" - " <updatecheck status=\"ok\">" - " <manifest version=\"1.2.3.4\">" - " <packages>" - " <package hash_sha256=\"sha256hash_foobar\"" - " name=\"%s\"" - " required=\"true\"" - " size=\"%lld\"/>" - " </packages>" - " <actions>" - " <action event=\"install\" needsadmin=\"false\"" - " run=\"%s\"" - " arguments=\"--%s=%s\"/>" - " </actions>" - " </manifest>" - " </updatecheck>" - " <data index=\"verboselogging\" name=\"install\" status=\"ok\">" - " {\"distribution\": { \"verbose_logging\": true}}" - " </data>" - " </app>" - "</response>"; - - // Create a unique name for a shared event to be waited for in this process - // and signaled by the app installer to confirm that app installer is run. - const std::wstring event_name = - base::StrCat({kTestProcessExecutableName, L"-", - base::NumberToWString(::GetCurrentProcessId())}); - NamedObjectAttributes attr; - GetNamedObjectAttributes(event_name.c_str(), scope, &attr); - - base::WaitableEvent event(base::win::ScopedHandle( - ::CreateEvent(&attr.sa, FALSE, FALSE, attr.name.c_str()))); - ASSERT_NE(event.handle(), nullptr); - - base::FilePath exe_dir; - ASSERT_TRUE(base::PathService::Get(base::DIR_EXE, &exe_dir)); - base::FilePath exe_path = exe_dir.Append(updater::kTestProcessExecutableName); - ASSERT_TRUE(base::PathExists(exe_path)); - - base::ScopedTempDir temp_dir; - EXPECT_TRUE(temp_dir.CreateUniqueTempDir()); - const base::FilePath& offline_dir = temp_dir.GetPath(); - - // Create manifest file. - const std::string exe_name = base::SysWideToUTF8(kTestProcessExecutableName); - base::FilePath manifest_path = - offline_dir.Append(FILE_PATH_LITERAL("OfflineManifest.gup")); - int64_t exe_size = 0; - EXPECT_TRUE(base::GetFileSize(exe_path, &exe_size)); - const std::string manifest = - base::StringPrintf(kManifestFormat, - exe_name.c_str(), // `name` in <package>. - exe_size, // `size` in <package>. - exe_name.c_str(), // `run` in <action>. - kTestEventToSignal, // `arguments` in <action>. - base::SysWideToUTF8(attr.name).c_str()); - EXPECT_TRUE(base::WriteFile(manifest_path, manifest)); - - // Copy app installer. - ASSERT_TRUE( - base::CopyFile(exe_path, offline_dir.Append(exe_path.BaseName()))); - - // Trigger offline install. - const absl::optional<base::FilePath> updater_exe = - GetInstalledExecutablePath(scope); - ASSERT_TRUE(updater_exe.has_value()); - base::CommandLine offline_install_cmd(updater_exe.value()); - - offline_install_cmd.AppendSwitch(kEnableLoggingSwitch); - offline_install_cmd.AppendSwitchASCII(kLoggingModuleSwitch, - kLoggingModuleSwitchValue); - if (scope == UpdaterScope::kSystem) - offline_install_cmd.AppendSwitch(kSystemSwitch); - - offline_install_cmd.AppendSwitchASCII( - updater::kHandoffSwitch, - "appguid={CDABE316-39CD-43BA-8440-6D1E0547AEE6}&lang=en&installdataindex=" - "verboselogging"); - offline_install_cmd.AppendSwitchASCII( - updater::kSessionIdSwitch, "{E85204C6-6F2F-40BF-9E6C-4952208BB977}"); - offline_install_cmd.AppendSwitchNative(updater::kOfflineDirSwitch, - offline_dir.value()); - - base::Process process = base::LaunchProcess(offline_install_cmd, {}); - EXPECT_TRUE(process.IsValid()); - - // Dismiss the installation completion dialog, then wait for the process exit. - WaitFor(base::BindRepeating([]() { - // Enumerate the top-level dialogs to find the setup dialog. - WindowEnumerator( - ::GetDesktopWindow(), base::BindRepeating([](HWND hwnd) { - return WindowEnumerator::IsSystemDialog(hwnd) && - base::Contains( - WindowEnumerator::GetWindowText(hwnd), - GetLocalizedStringF( - IDS_INSTALLER_DISPLAY_NAME_BASE, - GetLocalizedString(IDS_FRIENDLY_COMPANY_NAME_BASE))); - }), - base::BindRepeating([](HWND hwnd) { - // Enumerates the dialog items to search for installation complete - // message. Once found, close the dialog. - WindowEnumerator( - hwnd, base::BindRepeating([](HWND hwnd) { - return base::Contains( - WindowEnumerator::GetWindowText(hwnd), - GetLocalizedString(IDS_BUNDLE_INSTALLED_SUCCESSFULLY_BASE)); - }), - base::BindRepeating([](HWND hwnd) { - ::PostMessage(::GetParent(hwnd), WM_CLOSE, 0, 0); - })) - .Run(); - })) - .Run(); - return !IsUpdaterRunning(); - })); - - EXPECT_TRUE(event.TimedWait(TestTimeouts::action_timeout())); -} - } // namespace test } // namespace updater
diff --git a/chromecast/media/cma/backend/alsa/BUILD.gn b/chromecast/media/cma/backend/alsa/BUILD.gn index ed3dc90..2a2a9797 100644 --- a/chromecast/media/cma/backend/alsa/BUILD.gn +++ b/chromecast/media/cma/backend/alsa/BUILD.gn
@@ -46,6 +46,8 @@ sources = [ "alsa_volume_control.cc", "alsa_volume_control.h", + "scoped_alsa_mixer.cc", + "scoped_alsa_mixer.h", ] libs = [ "asound" ]
diff --git a/chromecast/media/cma/backend/alsa/alsa_volume_control.cc b/chromecast/media/cma/backend/alsa/alsa_volume_control.cc index d6cb1009..fac9b76 100644 --- a/chromecast/media/cma/backend/alsa/alsa_volume_control.cc +++ b/chromecast/media/cma/backend/alsa/alsa_volume_control.cc
@@ -8,6 +8,7 @@ #include "base/bind.h" #include "base/callback_helpers.h" +#include "base/check.h" #include "base/command_line.h" #include "base/location.h" #include "base/logging.h" @@ -15,6 +16,7 @@ #include "base/task/current_thread.h" #include "chromecast/base/chromecast_switches.h" #include "chromecast/base/metrics/cast_metrics_helper.h" +#include "chromecast/media/cma/backend/alsa/scoped_alsa_mixer.h" #include "media/base/media_switches.h" #define ALSA_ASSERT(func, ...) \ @@ -36,76 +38,6 @@ } // namespace -class AlsaVolumeControl::ScopedAlsaMixer { - public: - ScopedAlsaMixer(::media::AlsaWrapper* alsa, - const std::string& mixer_device_name, - const std::string& mixer_element_name) - : alsa_(alsa), - mixer_device_name_(mixer_device_name), - mixer_element_name_(mixer_element_name) { - DCHECK(alsa_); - Refresh(); - } - - ~ScopedAlsaMixer() { - if (mixer) { - alsa_->MixerClose(mixer); - } - } - - void Refresh() { - if (mixer) { - alsa_->MixerClose(mixer); - DVLOG(2) << "Reopening mixer element \"" << mixer_element_name_ - << "\" on device \"" << mixer_device_name_ << "\""; - } else { - LOG(INFO) << "Opening mixer element \"" << mixer_element_name_ - << "\" on device \"" << mixer_device_name_ << "\""; - } - - int alsa_err = alsa_->MixerOpen(&mixer, 0); - if (alsa_err < 0) { - LOG(ERROR) << "MixerOpen error: " << alsa_->StrError(alsa_err); - mixer = nullptr; - return; - } - alsa_err = alsa_->MixerAttach(mixer, mixer_device_name_.c_str()); - if (alsa_err < 0) { - LOG(ERROR) << "MixerAttach error: " << alsa_->StrError(alsa_err); - alsa_->MixerClose(mixer); - mixer = nullptr; - return; - } - ALSA_ASSERT(MixerElementRegister, mixer, NULL, NULL); - alsa_err = alsa_->MixerLoad(mixer); - if (alsa_err < 0) { - LOG(ERROR) << "MixerLoad error: " << alsa_->StrError(alsa_err); - alsa_->MixerClose(mixer); - mixer = nullptr; - return; - } - snd_mixer_selem_id_t* sid = NULL; - ALSA_ASSERT(MixerSelemIdMalloc, &sid); - alsa_->MixerSelemIdSetIndex(sid, 0); - alsa_->MixerSelemIdSetName(sid, mixer_element_name_.c_str()); - element = alsa_->MixerFindSelem(mixer, sid); - if (!element) { - LOG(ERROR) << "Simple mixer control element \"" << mixer_element_name_ - << "\" not found."; - } - alsa_->MixerSelemIdFree(sid); - } - - snd_mixer_elem_t* element = nullptr; - snd_mixer_t* mixer = nullptr; - - private: - ::media::AlsaWrapper* const alsa_; - const std::string mixer_device_name_; - const std::string mixer_element_name_; -}; - // static std::string AlsaVolumeControl::GetVolumeElementName() { std::string mixer_element_name = @@ -270,7 +202,8 @@ mute_mixer_ptr_ = mute_mixer_.get(); alsa_->MixerElemSetCallback( - mute_mixer_->element, &AlsaVolumeControl::VolumeOrMuteChangeCallback); + mute_mixer_->element, + &AlsaVolumeControl::VolumeOrMuteChangeCallback); alsa_->MixerElemSetCallbackPrivate(mute_mixer_->element, reinterpret_cast<void*>(this)); RefreshMixerFds(mute_mixer_.get());
diff --git a/chromecast/media/cma/backend/alsa/alsa_volume_control.h b/chromecast/media/cma/backend/alsa/alsa_volume_control.h index 72656104..16261f37 100644 --- a/chromecast/media/cma/backend/alsa/alsa_volume_control.h +++ b/chromecast/media/cma/backend/alsa/alsa_volume_control.h
@@ -17,6 +17,7 @@ namespace chromecast { namespace media { +class ScopedAlsaMixer; // SystemVolumeControl implementation for ALSA. class AlsaVolumeControl : public SystemVolumeControl, @@ -41,8 +42,6 @@ void CheckPowerSave(); private: - class ScopedAlsaMixer; - static std::string GetVolumeElementName(); static std::string GetVolumeDeviceName(); static std::string GetMuteElementName(::media::AlsaWrapper* alsa,
diff --git a/chromecast/media/cma/backend/alsa/scoped_alsa_mixer.cc b/chromecast/media/cma/backend/alsa/scoped_alsa_mixer.cc new file mode 100644 index 0000000..1703304 --- /dev/null +++ b/chromecast/media/cma/backend/alsa/scoped_alsa_mixer.cc
@@ -0,0 +1,79 @@ +// Copyright 2022 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 "chromecast/media/cma/backend/alsa/scoped_alsa_mixer.h" + +#include "base/check.h" +#include "base/logging.h" + +#define ALSA_ASSERT(func, ...) \ + do { \ + int err = alsa_->func(__VA_ARGS__); \ + LOG_ASSERT(err >= 0) << #func " error: " << alsa_->StrError(err); \ + } while (0) + +namespace chromecast { +namespace media { + +ScopedAlsaMixer::ScopedAlsaMixer(::media::AlsaWrapper* alsa, + const std::string& mixer_device_name, + const std::string& mixer_element_name) + : alsa_(alsa), + mixer_device_name_(mixer_device_name), + mixer_element_name_(mixer_element_name) { + DCHECK(alsa_); + Refresh(); +} + +ScopedAlsaMixer::~ScopedAlsaMixer() { + if (mixer) { + alsa_->MixerClose(mixer); + } +} + +void ScopedAlsaMixer::Refresh() { + if (mixer) { + alsa_->MixerClose(mixer); + DVLOG(2) << "Reopening mixer element \"" << mixer_element_name_ + << "\" on device \"" << mixer_device_name_ << "\""; + } else { + LOG(INFO) << "Opening mixer element \"" << mixer_element_name_ + << "\" on device \"" << mixer_device_name_ << "\""; + } + + int alsa_err = alsa_->MixerOpen(&mixer, 0); + if (alsa_err < 0) { + LOG(ERROR) << "MixerOpen error: " << alsa_->StrError(alsa_err); + mixer = nullptr; + return; + } + alsa_err = alsa_->MixerAttach(mixer, mixer_device_name_.c_str()); + if (alsa_err < 0) { + LOG(ERROR) << "MixerAttach error: " << alsa_->StrError(alsa_err); + alsa_->MixerClose(mixer); + mixer = nullptr; + return; + } + ALSA_ASSERT(MixerElementRegister, mixer, nullptr, nullptr); + alsa_err = alsa_->MixerLoad(mixer); + if (alsa_err < 0) { + LOG(ERROR) << "MixerLoad error: " << alsa_->StrError(alsa_err); + alsa_->MixerClose(mixer); + mixer = nullptr; + return; + } + snd_mixer_selem_id_t* sid = nullptr; + ALSA_ASSERT(MixerSelemIdMalloc, &sid); + alsa_->MixerSelemIdSetIndex(sid, 0); + alsa_->MixerSelemIdSetName(sid, mixer_element_name_.c_str()); + element = alsa_->MixerFindSelem(mixer, sid); + if (!element) { + LOG(ERROR) << "Simple mixer control element \"" << mixer_element_name_ + << "\" not found."; + } + alsa_->MixerSelemIdFree(sid); +} + +} // namespace media +} // namespace chromecast
diff --git a/chromecast/media/cma/backend/alsa/scoped_alsa_mixer.h b/chromecast/media/cma/backend/alsa/scoped_alsa_mixer.h new file mode 100644 index 0000000..75f3be7 --- /dev/null +++ b/chromecast/media/cma/backend/alsa/scoped_alsa_mixer.h
@@ -0,0 +1,39 @@ +// Copyright 2022 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 CHROMECAST_MEDIA_CMA_BACKEND_ALSA_SCOPED_ALSA_MIXER_H_ +#define CHROMECAST_MEDIA_CMA_BACKEND_ALSA_SCOPED_ALSA_MIXER_H_ + +#include <string> + +#include "media/audio/alsa/alsa_wrapper.h" + +namespace chromecast { +namespace media { + +class ScopedAlsaMixer { + public: + ScopedAlsaMixer(::media::AlsaWrapper* alsa, + const std::string& mixer_device_name, + const std::string& mixer_element_name); + ~ScopedAlsaMixer(); + ScopedAlsaMixer(const ScopedAlsaMixer&) = delete; + ScopedAlsaMixer& operator=(const ScopedAlsaMixer&) = delete; + + void Refresh(); + + snd_mixer_elem_t* element = nullptr; + snd_mixer_t* mixer = nullptr; + + private: + ::media::AlsaWrapper* const alsa_; + + const std::string mixer_device_name_; + const std::string mixer_element_name_; +}; + +} // namespace media +} // namespace chromecast + +#endif // CHROMECAST_MEDIA_CMA_BACKEND_ALSA_SCOPED_ALSA_MIXER_H_
diff --git a/chromeos/ash/components/dbus/concierge/concierge_client.cc b/chromeos/ash/components/dbus/concierge/concierge_client.cc index b3c5ecb..e563231 100644 --- a/chromeos/ash/components/dbus/concierge/concierge_client.cc +++ b/chromeos/ash/components/dbus/concierge/concierge_client.cc
@@ -139,17 +139,16 @@ CallMethod(concierge::kListVmDisksMethod, request, std::move(callback)); } - void StartTerminaVm( + void StartVm( const concierge::StartVmRequest& request, DBusMethodCallback<concierge::StartVmResponse> callback) override { CallMethod(concierge::kStartVmMethod, request, std::move(callback)); } - void StartTerminaVmWithFd( - base::ScopedFD fd, - const vm_tools::concierge::StartVmRequest& request, - DBusMethodCallback<vm_tools::concierge::StartVmResponse> callback) - override { + void StartVmWithFd(base::ScopedFD fd, + const vm_tools::concierge::StartVmRequest& request, + DBusMethodCallback<vm_tools::concierge::StartVmResponse> + callback) override { CallMethodWithFd(concierge::kStartVmMethod, request, std::move(fd), std::move(callback)); }
diff --git a/chromeos/ash/components/dbus/concierge/concierge_client.h b/chromeos/ash/components/dbus/concierge/concierge_client.h index 6c2e7cbe..d2445721 100644 --- a/chromeos/ash/components/dbus/concierge/concierge_client.h +++ b/chromeos/ash/components/dbus/concierge/concierge_client.h
@@ -167,14 +167,14 @@ // Starts a Termina VM if there is not already one running. // |callback| is called after the method call finishes. - virtual void StartTerminaVm( + virtual void StartVm( const vm_tools::concierge::StartVmRequest& request, DBusMethodCallback<vm_tools::concierge::StartVmResponse> callback) = 0; // Starts a Termina VM if there is not already one running. // |fd| references an extra image for concierge to use. // |callback| is called after the method call finishes. - virtual void StartTerminaVmWithFd( + virtual void StartVmWithFd( base::ScopedFD fd, const vm_tools::concierge::StartVmRequest& request, DBusMethodCallback<vm_tools::concierge::StartVmResponse> callback) = 0;
diff --git a/chromeos/ash/components/dbus/concierge/fake_concierge_client.cc b/chromeos/ash/components/dbus/concierge/fake_concierge_client.cc index 8296574..d6fb7de 100644 --- a/chromeos/ash/components/dbus/concierge/fake_concierge_client.cc +++ b/chromeos/ash/components/dbus/concierge/fake_concierge_client.cc
@@ -183,10 +183,10 @@ FROM_HERE, base::BindOnce(std::move(callback), list_vm_disks_response_)); } -void FakeConciergeClient::StartTerminaVm( +void FakeConciergeClient::StartVm( const vm_tools::concierge::StartVmRequest& request, DBusMethodCallback<vm_tools::concierge::StartVmResponse> callback) { - start_termina_vm_call_count_++; + start_vm_call_count_++; base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( FROM_HERE, base::BindOnce(std::move(callback), start_vm_response_), send_start_vm_response_delay_); @@ -218,11 +218,11 @@ std::move(vm_started_signal))); } -void FakeConciergeClient::StartTerminaVmWithFd( +void FakeConciergeClient::StartVmWithFd( base::ScopedFD fd, const vm_tools::concierge::StartVmRequest& request, DBusMethodCallback<vm_tools::concierge::StartVmResponse> callback) { - StartTerminaVm(std::move(request), std::move(callback)); + StartVm(std::move(request), std::move(callback)); } void FakeConciergeClient::NotifyTremplinStarted(
diff --git a/chromeos/ash/components/dbus/concierge/fake_concierge_client.h b/chromeos/ash/components/dbus/concierge/fake_concierge_client.h index 7345e91..f5398eb 100644 --- a/chromeos/ash/components/dbus/concierge/fake_concierge_client.h +++ b/chromeos/ash/components/dbus/concierge/fake_concierge_client.h
@@ -74,14 +74,13 @@ void ListVmDisks(const vm_tools::concierge::ListVmDisksRequest& request, DBusMethodCallback<vm_tools::concierge::ListVmDisksResponse> callback) override; - void StartTerminaVm(const vm_tools::concierge::StartVmRequest& request, - DBusMethodCallback<vm_tools::concierge::StartVmResponse> - callback) override; - void StartTerminaVmWithFd( - base::ScopedFD fd, - const vm_tools::concierge::StartVmRequest& request, - DBusMethodCallback<vm_tools::concierge::StartVmResponse> callback) - override; + void StartVm(const vm_tools::concierge::StartVmRequest& request, + DBusMethodCallback<vm_tools::concierge::StartVmResponse> + callback) override; + void StartVmWithFd(base::ScopedFD fd, + const vm_tools::concierge::StartVmRequest& request, + DBusMethodCallback<vm_tools::concierge::StartVmResponse> + callback) override; void StopVm(const vm_tools::concierge::StopVmRequest& request, DBusMethodCallback<vm_tools::concierge::StopVmResponse> callback) override; @@ -171,9 +170,7 @@ return import_disk_image_call_count_; } int list_vm_disks_call_count() const { return list_vm_disks_call_count_; } - int start_termina_vm_call_count() const { - return start_termina_vm_call_count_; - } + int start_vm_call_count() const { return start_vm_call_count_; } int stop_vm_call_count() const { return stop_vm_call_count_; } int get_vm_info_call_count() const { return get_vm_info_call_count_; } int get_vm_enterprise_reporting_info_call_count() const { @@ -364,7 +361,7 @@ int import_disk_image_call_count_ = 0; int disk_image_status_call_count_ = 0; int list_vm_disks_call_count_ = 0; - int start_termina_vm_call_count_ = 0; + int start_vm_call_count_ = 0; int stop_vm_call_count_ = 0; int get_vm_info_call_count_ = 0; int get_vm_enterprise_reporting_info_call_count_ = 0;
diff --git a/components/android_autofill/browser/android_autofill_manager.cc b/components/android_autofill/browser/android_autofill_manager.cc index aba3742c..945ddfc 100644 --- a/components/android_autofill/browser/android_autofill_manager.cc +++ b/components/android_autofill/browser/android_autofill_manager.cc
@@ -94,10 +94,12 @@ const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) { + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { if (auto* provider = GetAutofillProvider()) { provider->OnAskForValuesToFill(this, query_id, form, field, bounding_box, - autoselect_first_suggestion); + autoselect_first_suggestion, + touch_to_fill_eligible); } }
diff --git a/components/android_autofill/browser/android_autofill_manager.h b/components/android_autofill/browser/android_autofill_manager.h index d99d684..a19fa3f3 100644 --- a/components/android_autofill/browser/android_autofill_manager.h +++ b/components/android_autofill/browser/android_autofill_manager.h
@@ -99,11 +99,13 @@ const FormFieldData& field, const gfx::RectF& bounding_box) override; - void OnAskForValuesToFillImpl(int query_id, - const FormData& form, - const FormFieldData& field, - const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) override; + void OnAskForValuesToFillImpl( + int query_id, + const FormData& form, + const FormFieldData& field, + const gfx::RectF& bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) override; void OnFocusOnFormFieldImpl(const FormData& form, const FormFieldData& field,
diff --git a/components/android_autofill/browser/autofill_provider.h b/components/android_autofill/browser/autofill_provider.h index dca4a6b..685d1b9 100644 --- a/components/android_autofill/browser/autofill_provider.h +++ b/components/android_autofill/browser/autofill_provider.h
@@ -34,12 +34,14 @@ static bool is_download_manager_disabled_for_testing(); static void set_is_download_manager_disabled_for_testing(); - virtual void OnAskForValuesToFill(AndroidAutofillManager* manager, - int32_t id, - const FormData& form, - const FormFieldData& field, - const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) = 0; + virtual void OnAskForValuesToFill( + AndroidAutofillManager* manager, + int32_t query_id, + const FormData& form, + const FormFieldData& field, + const gfx::RectF& bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) = 0; virtual void OnTextFieldDidChange(AndroidAutofillManager* manager, const FormData& form,
diff --git a/components/android_autofill/browser/autofill_provider_android.cc b/components/android_autofill/browser/autofill_provider_android.cc index f8b9fe77..01768e8 100644 --- a/components/android_autofill/browser/autofill_provider_android.cc +++ b/components/android_autofill/browser/autofill_provider_android.cc
@@ -102,16 +102,17 @@ void AutofillProviderAndroid::OnAskForValuesToFill( AndroidAutofillManager* manager, - int32_t id, + int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool /*unused_autoselect_first_suggestion*/) { + bool /*unused_autoselect_first_suggestion*/, + TouchToFillEligible /*unused_touch_to_fill_eligible*/) { // The id isn't passed to Java side because Android API guarantees the // response is always for current session, so we just use the current id // in response, see OnAutofillAvailable. DCHECK_CURRENTLY_ON(BrowserThread::UI); - id_ = id; + id_ = query_id; // Focus or field value change will also trigger the query, so it should be // ignored if the form is same.
diff --git a/components/android_autofill/browser/autofill_provider_android.h b/components/android_autofill/browser/autofill_provider_android.h index b8c405a2..873d77f7 100644 --- a/components/android_autofill/browser/autofill_provider_android.h +++ b/components/android_autofill/browser/autofill_provider_android.h
@@ -49,11 +49,12 @@ // AutofillProvider: void OnAskForValuesToFill( AndroidAutofillManager* manager, - int32_t id, + int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool /*unused_autoselect_first_suggestion*/) override; + bool /*unused_autoselect_first_suggestion*/, + TouchToFillEligible /*unused_touch_to_fill_eligible*/) override; void OnTextFieldDidChange(AndroidAutofillManager* manager, const FormData& form, const FormFieldData& field,
diff --git a/components/android_autofill/browser/autofill_provider_unittest.cc b/components/android_autofill/browser/autofill_provider_unittest.cc index f4ae486..b205f866 100644 --- a/components/android_autofill/browser/autofill_provider_unittest.cc +++ b/components/android_autofill/browser/autofill_provider_unittest.cc
@@ -25,7 +25,8 @@ void SimulateOnAskForValuesToFillImpl() { OnAskForValuesToFillImpl(0, FormData(), FormFieldData(), gfx::RectF(), - /*autoselect_first_suggestion=*/false); + /*autoselect_first_suggestion=*/false, + TouchToFillEligible(false)); } }; @@ -38,12 +39,14 @@ private: // AutofillProvider - void OnAskForValuesToFill(AndroidAutofillManager* manager, - int32_t id, - const FormData& form, - const FormFieldData& field, - const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) override { + void OnAskForValuesToFill( + AndroidAutofillManager* manager, + int32_t query_id, + const FormData& form, + const FormFieldData& field, + const gfx::RectF& bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) override { manager_ = manager; } void OnServerQueryRequestError(AndroidAutofillManager* manager,
diff --git a/components/android_autofill/browser/test_autofill_provider.h b/components/android_autofill/browser/test_autofill_provider.h index dcb28fa..666b67e 100644 --- a/components/android_autofill/browser/test_autofill_provider.h +++ b/components/android_autofill/browser/test_autofill_provider.h
@@ -20,12 +20,14 @@ ~TestAutofillProvider() override = default; // AutofillProvider: - void OnAskForValuesToFill(AndroidAutofillManager* manager, - int32_t id, - const FormData& form, - const FormFieldData& field, - const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) override {} + void OnAskForValuesToFill( + AndroidAutofillManager* manager, + int32_t query_id, + const FormData& form, + const FormFieldData& field, + const gfx::RectF& bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) override {} void OnTextFieldDidChange(AndroidAutofillManager* manager, const FormData& form, const FormFieldData& field,
diff --git a/components/autofill/content/browser/content_autofill_driver.cc b/components/autofill/content/browser/content_autofill_driver.cc index 7e13122..2d864b4 100644 --- a/components/autofill/content/browser/content_autofill_driver.cc +++ b/components/autofill/content/browser/content_autofill_driver.cc
@@ -331,13 +331,15 @@ } void ContentAutofillDriver::AskForValuesToFillImpl( - int32_t id, + int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) { - autofill_manager_->OnAskForValuesToFill(id, form, field, bounding_box, - autoselect_first_suggestion); + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { + autofill_manager_->OnAskForValuesToFill(query_id, form, field, bounding_box, + autoselect_first_suggestion, + touch_to_fill_eligible); } void ContentAutofillDriver::HidePopupImpl() { @@ -478,20 +480,21 @@ } void ContentAutofillDriver::AskForValuesToFill( - int32_t id, + int32_t query_id, const FormData& raw_form, const FormFieldData& raw_field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) { + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { if (!bad_message::CheckFrameNotPrerendering(render_frame_host_)) return; FormData form = raw_form; FormFieldData field = raw_field; SetFrameAndFormMetaData(form, &field); GetAutofillRouter().AskForValuesToFill( - this, id, form, field, + this, query_id, form, field, TransformBoundingBoxToViewportCoordinates(bounding_box), - autoselect_first_suggestion); + autoselect_first_suggestion, touch_to_fill_eligible); } void ContentAutofillDriver::HidePopup() {
diff --git a/components/autofill/content/browser/content_autofill_driver.h b/components/autofill/content/browser/content_autofill_driver.h index 03159d93..28c1099 100644 --- a/components/autofill/content/browser/content_autofill_driver.h +++ b/components/autofill/content/browser/content_autofill_driver.h
@@ -221,11 +221,12 @@ void SelectControlDidChange(const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box) override; - void AskForValuesToFill(int32_t id, + void AskForValuesToFill(int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) override; + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) override; void HidePopup() override; void FocusNoLongerOnForm(bool had_interacted_form) override; void FocusOnFormField(const FormData& form, @@ -255,11 +256,12 @@ void SelectControlDidChangeImpl(const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box); - void AskForValuesToFillImpl(int32_t id, + void AskForValuesToFillImpl(int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion); + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible); void HidePopupImpl(); void FocusNoLongerOnFormImpl(bool had_interacted_form); void FocusOnFormFieldImpl(const FormData& form,
diff --git a/components/autofill/content/browser/content_autofill_driver_factory_unittest.cc b/components/autofill/content/browser/content_autofill_driver_factory_unittest.cc index 75dab6a4..cb88436 100644 --- a/components/autofill/content/browser/content_autofill_driver_factory_unittest.cc +++ b/components/autofill/content/browser/content_autofill_driver_factory_unittest.cc
@@ -49,7 +49,7 @@ MOCK_METHOD(void, TriggerReparse, (), (override)); MOCK_METHOD(void, FillOrPreviewForm, - (int32_t id, + (int32_t query_id, const FormData& form, mojom::RendererFormDataAction action), (override));
diff --git a/components/autofill/content/browser/content_autofill_driver_unittest.cc b/components/autofill/content/browser/content_autofill_driver_unittest.cc index 3bee7721..4beff3e 100644 --- a/components/autofill/content/browser/content_autofill_driver_unittest.cc +++ b/components/autofill/content/browser/content_autofill_driver_unittest.cc
@@ -166,14 +166,14 @@ // mojom::AutofillAgent: void TriggerReparse() override {} - void FillOrPreviewForm(int32_t id, + void FillOrPreviewForm(int32_t query_id, const FormData& form, mojom::RendererFormDataAction action) override { if (action == mojom::RendererFormDataAction::kPreview) { - preview_form_id_ = id; + preview_form_id_ = query_id; preview_form_form_ = form; } else { - fill_form_id_ = id; + fill_form_id_ = query_id; fill_form_form_ = form; } CallDone();
diff --git a/components/autofill/content/browser/content_autofill_router.cc b/components/autofill/content/browser/content_autofill_router.cc index 229be2e..4f366501 100644 --- a/components/autofill/content/browser/content_autofill_router.cc +++ b/components/autofill/content/browser/content_autofill_router.cc
@@ -349,14 +349,16 @@ void ContentAutofillRouter::AskForValuesToFill( ContentAutofillDriver* source, - int32_t id, + int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) { + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { if (!base::FeatureList::IsEnabled(features::kAutofillAcrossIframes)) { - source->AskForValuesToFillImpl(id, form, field, bounding_box, - autoselect_first_suggestion); + source->AskForValuesToFillImpl(query_id, form, field, bounding_box, + autoselect_first_suggestion, + touch_to_fill_eligible); return; } @@ -372,8 +374,9 @@ AFCHECK(target, return ); SetLastQueriedSource(source); SetLastQueriedTarget(target); - target->AskForValuesToFillImpl(id, browser_form, field, bounding_box, - autoselect_first_suggestion); + target->AskForValuesToFillImpl(query_id, browser_form, field, bounding_box, + autoselect_first_suggestion, + touch_to_fill_eligible); } void ContentAutofillRouter::HidePopup(ContentAutofillDriver* source) {
diff --git a/components/autofill/content/browser/content_autofill_router.h b/components/autofill/content/browser/content_autofill_router.h index ddeb5dbd..b4ce114 100644 --- a/components/autofill/content/browser/content_autofill_router.h +++ b/components/autofill/content/browser/content_autofill_router.h
@@ -189,11 +189,12 @@ const FormFieldData& field, const gfx::RectF& bounding_box); void AskForValuesToFill(ContentAutofillDriver* source_driver, - int32_t id, + int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion); + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible); void HidePopup(ContentAutofillDriver* source_driver); void FocusNoLongerOnForm(ContentAutofillDriver* source_driver, bool had_interacted_form);
diff --git a/components/autofill/content/common/mojom/autofill_agent.mojom b/components/autofill/content/common/mojom/autofill_agent.mojom index 0e35c55b..65a019d 100644 --- a/components/autofill/content/common/mojom/autofill_agent.mojom +++ b/components/autofill/content/common/mojom/autofill_agent.mojom
@@ -16,8 +16,10 @@ // Instructs the renderer to fill or preview the active form with the given // form data. Refer to AutofillDriver.AskForValuesToFill for comments - // about the |id|. - FillOrPreviewForm(int32 id, FormData form, RendererFormDataAction action); + // about the |query_id|. + FillOrPreviewForm(int32 query_id, + FormData form, + RendererFormDataAction action); // Sends the heuristic and server field type predictions to the renderer. FieldTypePredictionsAvailable(array<FormDataPredictions> forms);
diff --git a/components/autofill/content/common/mojom/autofill_driver.mojom b/components/autofill/content/common/mojom/autofill_driver.mojom index d92cc1b..5fa1c41 100644 --- a/components/autofill/content/common/mojom/autofill_driver.mojom +++ b/components/autofill/content/common/mojom/autofill_driver.mojom
@@ -52,12 +52,16 @@ // Queries the browser for Autofill suggestions for a form input field. // For autofill this means asking the user which values to fill. - // |id| is the request ID which is used to map responses correctly. - AskForValuesToFill(int32 id, - FormData form, - FormFieldData field, - gfx.mojom.RectF bounding_box, - bool autoselect_first_suggestion); + // |query_id| is the request ID which is used to map responses correctly. + // |touch_to_fill_eligible| indicates if the Touch To Fill surface could + // be used for showing suggestions (e.g. when the user taps an input element + // but not on text change). + AskForValuesToFill(int32 query_id, + FormData form, + FormFieldData field, + gfx.mojom.RectF bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible); // Instructs the browser to hide the Autofill popup if it is open. HidePopup();
diff --git a/components/autofill/content/renderer/autofill_agent.cc b/components/autofill/content/renderer/autofill_agent.cc index abbaee56..f8448c6 100644 --- a/components/autofill/content/renderer/autofill_agent.cc +++ b/components/autofill/content/renderer/autofill_agent.cc
@@ -176,13 +176,14 @@ void SelectFieldOptionsDidChange(const FormData& form) override { DeferMsg(&mojom::AutofillDriver::SelectFieldOptionsDidChange, form); } - void AskForValuesToFill(int32_t id, + void AskForValuesToFill(int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) override { - DeferMsg(&mojom::AutofillDriver::AskForValuesToFill, id, form, field, - bounding_box, autoselect_first_suggestion); + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) override { + DeferMsg(&mojom::AutofillDriver::AskForValuesToFill, query_id, form, field, + bounding_box, autoselect_first_suggestion, touch_to_fill_eligible); } void HidePopup() override { DeferMsg(&mojom::AutofillDriver::HidePopup); } void FocusNoLongerOnForm(bool had_interacted_form) override { @@ -209,12 +210,6 @@ base::WeakPtrFactory<DeferringAutofillDriver> weak_ptr_factory_{this}; }; -AutofillAgent::ShowSuggestionsOptions::ShowSuggestionsOptions() - : autofill_on_empty_values(false), - requires_caret_at_end(false), - show_full_suggestion_list(false), - autoselect_first_suggestion(false) {} - AutofillAgent::AutofillAgent(content::RenderFrame* render_frame, PasswordAutofillAgent* password_autofill_agent, PasswordGenerationAgent* password_generation_agent, @@ -443,9 +438,7 @@ return; } - ShowSuggestionsOptions options; - options.requires_caret_at_end = true; - ShowSuggestions(element, options); + ShowSuggestions(element, {.requires_caret_at_end = true}); FormData form; FormFieldData field; @@ -465,21 +458,17 @@ if (event.windows_key_code == ui::VKEY_DOWN || event.windows_key_code == ui::VKEY_UP) { - ShowSuggestionsOptions options; - options.autofill_on_empty_values = true; - options.requires_caret_at_end = true; - options.autoselect_first_suggestion = - ShouldAutoselectFirstSuggestionOnArrowDown(); - ShowSuggestions(element, options); + ShowSuggestions(element, + {.autofill_on_empty_values = true, + .requires_caret_at_end = true, + .autoselect_first_suggestion = + ShouldAutoselectFirstSuggestionOnArrowDown()}); } } void AutofillAgent::OpenTextDataListChooser(const WebInputElement& element) { DCHECK(IsOwnedByFrame(element, render_frame())); - - ShowSuggestionsOptions options; - options.autofill_on_empty_values = true; - ShowSuggestions(element, options); + ShowSuggestions(element, {.autofill_on_empty_values = true}); } // Notifies the AutofillDriver about changes in the <datalist> options in @@ -538,14 +527,14 @@ } // mojom::AutofillAgent: -void AutofillAgent::FillOrPreviewForm(int32_t id, +void AutofillAgent::FillOrPreviewForm(int32_t query_id, const FormData& form, mojom::RendererFormDataAction action) { // If |element_| is null or not focused, a Autofill was triggered from another // frame. In this case, set |element_| to some form field as if Autofill had // been triggered from that field. This is necessary because currently // AutofillAgent's relies on |elemet_| in many places. - if (id == kCrossFrameFill && !form.fields.empty() && + if (query_id == kCrossFrameFill && !form.fields.empty() && (element_.IsNull() || !element_.Focused())) { WebDocument document = render_frame()->GetWebFrame()->GetDocument(); element_ = form_util::FindFormControlElementByUniqueRendererId( @@ -555,8 +544,9 @@ if (element_.IsNull()) return; - if (id != autofill_query_id_ && id != kCrossFrameFill && - (action == mojom::RendererFormDataAction::kPreview || id != kNoQueryId)) { + if (query_id != autofill_query_id_ && query_id != kCrossFrameFill && + (action == mojom::RendererFormDataAction::kPreview || + query_id != kNoQueryId)) { return; } @@ -571,7 +561,7 @@ was_last_action_fill_ = true; // If this is a re-fill, replace the triggering element if it's invalid. - if (id == kNoQueryId) + if (query_id == kNoQueryId) ReplaceElementIfNowInvalid(form); query_node_autofill_state_ = element_.GetAutofillState(); @@ -835,7 +825,8 @@ return; } - QueryAutofillSuggestions(element, options.autoselect_first_suggestion); + QueryAutofillSuggestions(element, options.autoselect_first_suggestion, + options.touch_to_fill_eligible); } void AutofillAgent::SetQueryPasswordSuggestion(bool query) { @@ -902,7 +893,8 @@ void AutofillAgent::QueryAutofillSuggestions( const WebFormControlElement& element, - bool autoselect_first_suggestion) { + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { blink::WebLocalFrame* frame = element.GetDocument().GetFrame(); if (!frame) return; @@ -947,9 +939,9 @@ } is_popup_possibly_visible_ = true; - GetAutofillDriver().AskForValuesToFill(autofill_query_id_, form, field, - field.bounds, - autoselect_first_suggestion); + GetAutofillDriver().AskForValuesToFill( + autofill_query_id_, form, field, field.bounds, + autoselect_first_suggestion, touch_to_fill_eligible); } void AutofillAgent::DoFillFieldWithValue(const std::u16string& value, @@ -1137,16 +1129,15 @@ password_autofill_agent_->TryToShowTouchToFill(element); #endif - ShowSuggestionsOptions options; - options.autofill_on_empty_values = true; - // Even if the user has not edited an input element, it may still contain a - // value: A default value filled by the website. In that case, we don't want - // to elide suggestions that don't have a common prefix with the default - // value. - options.show_full_suggestion_list = - element.IsAutofilled() || !element.UserHasEditedTheField(); - - ShowSuggestions(element, options); + ShowSuggestions( + element, {.autofill_on_empty_values = true, + // Even if the user has not edited an input element, it may + // still contain a value: A default value filled by the website. + // In that case, we don't want to elide suggestions that don't + // have a common prefix with the default value. + .show_full_suggestion_list = + element.IsAutofilled() || !element.UserHasEditedTheField(), + .touch_to_fill_eligible = TouchToFillEligible(true)}); SendPotentiallySubmittedFormToBrowser(); } @@ -1176,6 +1167,12 @@ SendPotentiallySubmittedFormToBrowser(); } +void AutofillAgent::JavaScriptChangedAutofilledValue( + const blink::WebFormControlElement& element, + const blink::WebString& old_value) { + // TODO(crbug.com/1314360): Send event to browser. +} + void AutofillAgent::OnProvisionallySaveForm( const WebFormElement& form, const WebFormControlElement& element,
diff --git a/components/autofill/content/renderer/autofill_agent.h b/components/autofill/content/renderer/autofill_agent.h index 5fb4867b..33ffacbf 100644 --- a/components/autofill/content/renderer/autofill_agent.h +++ b/components/autofill/content/renderer/autofill_agent.h
@@ -92,7 +92,7 @@ // mojom::AutofillAgent: void TriggerReparse() override; - void FillOrPreviewForm(int32_t id, + void FillOrPreviewForm(int32_t query_id, const FormData& form, mojom::RendererFormDataAction action) override; void FieldTypePredictionsAvailable( @@ -162,25 +162,26 @@ // Flags passed to ShowSuggestions. struct ShowSuggestionsOptions { - // All fields are default initialized to false. - ShowSuggestionsOptions(); - // Specifies that suggestions should be shown when |element| contains no // text. - bool autofill_on_empty_values; + bool autofill_on_empty_values{false}; // Specifies that suggestions should be shown when the caret is not // after the last character in the element. - bool requires_caret_at_end; + bool requires_caret_at_end{false}; // Specifies that all autofill suggestions should be shown and none should // be elided because of the current value of |element| (relevant for inline // autocomplete). - bool show_full_suggestion_list; + bool show_full_suggestion_list{false}; // Specifies that the first suggestion must be auto-selected when the // dropdown is shown. Enabled when the user presses ARROW_DOWN on a field. - bool autoselect_first_suggestion; + bool autoselect_first_suggestion{false}; + + // Specifies that suggestions are triggered in a way it makes sense to + // prompt the Touch To Fill surface first (e.g. on click). + TouchToFillEligible touch_to_fill_eligible{false}; }; // content::RenderFrameObserver: @@ -213,6 +214,9 @@ void DataListOptionsChanged(const blink::WebInputElement& element) override; void UserGestureObserved() override; void AjaxSucceeded() override; + void JavaScriptChangedAutofilledValue( + const blink::WebFormControlElement& element, + const blink::WebString& old_value) override; void DidCompleteFocusChangeInFrame() override; void DidReceiveLeftMouseDownOrGestureTapInNode( const blink::WebNode& node) override; @@ -245,7 +249,8 @@ // Queries the browser for Autocomplete and Autofill suggestions for the given // |element|. void QueryAutofillSuggestions(const blink::WebFormControlElement& element, - bool autoselect_first_suggestion); + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible); // Sets the selected value of the the field identified by |field_id| to // |suggested_value|.
diff --git a/components/autofill/content/renderer/autofill_agent_browsertest.cc b/components/autofill/content/renderer/autofill_agent_browsertest.cc index ed4149a..0ce0d307 100644 --- a/components/autofill/content/renderer/autofill_agent_browsertest.cc +++ b/components/autofill/content/renderer/autofill_agent_browsertest.cc
@@ -86,11 +86,12 @@ (override)); MOCK_METHOD(void, AskForValuesToFill, - (int32_t id, + (int32_t query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion), + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible), (override)); MOCK_METHOD(void, HidePopup, (), (override)); MOCK_METHOD(void,
diff --git a/components/autofill/core/browser/autofill_manager.cc b/components/autofill/core/browser/autofill_manager.cc index 3c934b2..96330f1 100644 --- a/components/autofill/core/browser/autofill_manager.cc +++ b/components/autofill/core/browser/autofill_manager.cc
@@ -309,16 +309,18 @@ observer.OnSelectControlDidChange(); } -void AutofillManager::OnAskForValuesToFill(int query_id, - const FormData& form, - const FormFieldData& field, - const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) { +void AutofillManager::OnAskForValuesToFill( + int query_id, + const FormData& form, + const FormFieldData& field, + const gfx::RectF& bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { if (!IsValidFormData(form) || !IsValidFormFieldData(field)) return; OnAskForValuesToFillImpl(query_id, form, field, bounding_box, - autoselect_first_suggestion); + autoselect_first_suggestion, touch_to_fill_eligible); } void AutofillManager::OnFocusOnFormField(const FormData& form,
diff --git a/components/autofill/core/browser/autofill_manager.h b/components/autofill/core/browser/autofill_manager.h index 15b4146..64b4d0c0 100644 --- a/components/autofill/core/browser/autofill_manager.h +++ b/components/autofill/core/browser/autofill_manager.h
@@ -135,11 +135,15 @@ // Invoked when the |form| needs to be autofilled, the |bounding_box| is // a window relative value of |field|. // |bounding_box| are viewport coordinates. + // |touch_to_fill_eligible| indicates if the Touch To Fill surface could be + // used for showing suggestion. Note that it doesn't guarantee the given form + // input field is eligible for autofilling. void OnAskForValuesToFill(int query_id, const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion); + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible); // Invoked when |form|'s |field| has focus. // |bounding_box| are viewport coordinates. @@ -313,11 +317,13 @@ const FormFieldData& field, const gfx::RectF& bounding_box) = 0; - virtual void OnAskForValuesToFillImpl(int query_id, - const FormData& form, - const FormFieldData& field, - const gfx::RectF& bounding_box, - bool autoselect_first_suggestion) = 0; + virtual void OnAskForValuesToFillImpl( + int query_id, + const FormData& form, + const FormFieldData& field, + const gfx::RectF& bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) = 0; virtual void OnFocusOnFormFieldImpl(const FormData& form, const FormFieldData& field,
diff --git a/components/autofill/core/browser/autofill_manager_unittest.cc b/components/autofill/core/browser/autofill_manager_unittest.cc index 12aed8d..32c4f3988 100644 --- a/components/autofill/core/browser/autofill_manager_unittest.cc +++ b/components/autofill/core/browser/autofill_manager_unittest.cc
@@ -119,7 +119,8 @@ const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box, - bool autoselect_first_suggestion), + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible), (override)); MOCK_METHOD(void, OnFocusOnFormFieldImpl,
diff --git a/components/autofill/core/browser/browser_autofill_manager.cc b/components/autofill/core/browser/browser_autofill_manager.cc index ef0f6fa..3dd8b4b 100644 --- a/components/autofill/core/browser/browser_autofill_manager.cc +++ b/components/autofill/core/browser/browser_autofill_manager.cc
@@ -949,7 +949,8 @@ const FormData& form, const FormFieldData& field, const gfx::RectF& transformed_box, - bool autoselect_first_suggestion) { + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { if (base::FeatureList::IsEnabled(features::kAutofillDisableFilling)) { return; } @@ -1052,7 +1053,7 @@ field.form_control_type, weak_ptr_factory_.GetWeakPtr(), context); return; } - + // TODO(crbug.com/1247698): Try to show TTF if |touch_to_fill_eligible|. // Send Autofill suggestions (could be an empty list). single_field_form_fill_router_->CancelPendingQueries(this); external_delegate_->OnSuggestionsReturned(query_id, suggestions,
diff --git a/components/autofill/core/browser/browser_autofill_manager.h b/components/autofill/core/browser/browser_autofill_manager.h index 980d3bc..bffd1f37 100644 --- a/components/autofill/core/browser/browser_autofill_manager.h +++ b/components/autofill/core/browser/browser_autofill_manager.h
@@ -362,11 +362,13 @@ void OnTextFieldDidScrollImpl(const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box) override {} - void OnAskForValuesToFillImpl(int query_id, - const FormData& form, - const FormFieldData& field, - const gfx::RectF& transformed_box, - bool autoselect_first_suggestion) override; + void OnAskForValuesToFillImpl( + int query_id, + const FormData& form, + const FormFieldData& field, + const gfx::RectF& transformed_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) override; void OnSelectControlDidChangeImpl(const FormData& form, const FormFieldData& field, const gfx::RectF& bounding_box) override;
diff --git a/components/autofill/core/browser/browser_autofill_manager_unittest.cc b/components/autofill/core/browser/browser_autofill_manager_unittest.cc index c36cc3dc..ba343e8 100644 --- a/components/autofill/core/browser/browser_autofill_manager_unittest.cc +++ b/components/autofill/core/browser/browser_autofill_manager_unittest.cc
@@ -481,7 +481,7 @@ const FormFieldData& field) { browser_autofill_manager_->OnAskForValuesToFill( query_id, form, field, gfx::RectF(), - /*autoselect_first_suggestion=*/false); + /*autoselect_first_suggestion=*/false, TouchToFillEligible(false)); } void GetAutofillSuggestions(const FormData& form,
diff --git a/components/autofill/core/browser/metrics/autofill_metrics_unittest.cc b/components/autofill/core/browser/metrics/autofill_metrics_unittest.cc index b25b657..5f616e93 100644 --- a/components/autofill/core/browser/metrics/autofill_metrics_unittest.cc +++ b/components/autofill/core/browser/metrics/autofill_metrics_unittest.cc
@@ -4076,8 +4076,7 @@ { // Simulate activating the autofill popup for the phone field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample("Autofill.AddressSuggestionsCount", 2, 1); } @@ -4087,8 +4086,7 @@ // No new metric should be logged, since we're still on the same page. test::CreateTestFormField("Email", "email", "b", "email", &field); base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectTotalCount("Autofill.AddressSuggestionsCount", 0); } @@ -4099,8 +4097,7 @@ { // Simulate activating the autofill popup for the email field after typing. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample("Autofill.AddressSuggestionsCount", 1, 1); } @@ -4113,8 +4110,7 @@ // Simulate activating the autofill popup for the email field after a fill. form.fields[0].is_autofilled = true; base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectTotalCount("Autofill.AddressSuggestionsCount", 1); } } @@ -4150,9 +4146,7 @@ { // Simulate activating the autofill popup for the phone field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); - + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample("Autofill.AddressSuggestionsCount", 2, 1); } @@ -4193,8 +4187,7 @@ // Simulate an Autofill query on a credit card field. { base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledCreditCardSuggestions")); } @@ -4291,8 +4284,7 @@ // Simulate submitting the credit card form. { base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); EXPECT_EQ(1, @@ -4419,8 +4411,7 @@ // Simulate an Autofill query on a profile field. { base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledProfileSuggestions")); } @@ -4472,8 +4463,7 @@ // Simulate submitting the profile form. { base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); EXPECT_EQ(1, @@ -4563,32 +4553,24 @@ // Simulate an Autofill query on a credit card field. A poll should be logged. base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledCreditCardSuggestions")); // Simulate a second query on the same field. There should still only be one // logged poll. - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledCreditCardSuggestions")); // Simulate a query to another field. There should be a second poll logged. - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[1], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[1]); EXPECT_EQ(2, user_action_tester.GetActionCount( "Autofill_PolledCreditCardSuggestions")); // Simulate a query back to the initial field. There should be a third poll // logged. - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); EXPECT_EQ(3, user_action_tester.GetActionCount( "Autofill_PolledCreditCardSuggestions")); } @@ -4643,9 +4625,7 @@ // Simulate an Autofill query on a credit card field (HTTP, non-secure // form). base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[1], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[1]); histogram_tester.ExpectUniqueSample( "Autofill.QueriedCreditCardFormIsSecure", false, 1); // Reset the main frame origin to secure for other tests @@ -4665,9 +4645,7 @@ // Simulate an Autofill query on a credit card field (HTTPS form). base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[1], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[1]); histogram_tester.ExpectUniqueSample( "Autofill.QueriedCreditCardFormIsSecure", true, 1); } @@ -4705,32 +4683,24 @@ // Simulate an Autofill query on a profile field. A poll should be logged. base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledProfileSuggestions")); // Simulate a second query on the same field. There should still only be poll // logged. - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledProfileSuggestions")); // Simulate a query to another field. There should be a second poll logged. - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[1], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[1]); EXPECT_EQ(2, user_action_tester.GetActionCount( "Autofill_PolledProfileSuggestions")); // Simulate a query back to the initial field. There should be a third poll // logged. - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); EXPECT_EQ(3, user_action_tester.GetActionCount( "Autofill_PolledProfileSuggestions")); } @@ -4800,8 +4770,7 @@ { // Simulate activating the autofill popup for the credit card field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample("Autofill.FormEvents.CreditCard", FORM_EVENT_INTERACTED_ONCE, 1); histogram_tester.ExpectUniqueSample( @@ -4816,10 +4785,8 @@ { // Simulate activating the autofill popup for the credit card field twice. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); - autofill_manager().OnAskForValuesToFill( - 1, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field, /*query_id=*/0); + autofill_manager().OnAskForValuesToFillTest(form, field, /*query_id=*/1); histogram_tester.ExpectUniqueSample("Autofill.FormEvents.CreditCard", FORM_EVENT_INTERACTED_ONCE, 1); histogram_tester.ExpectUniqueSample( @@ -5009,8 +4976,7 @@ { // Simulate new popup being shown. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); histogram_tester.ExpectBucketCount("Autofill.FormEvents.CreditCard", FORM_EVENT_SUGGESTIONS_SHOWN, 1); @@ -5041,8 +5007,7 @@ { // Simulating two popups in the same page load. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); histogram_tester.ExpectBucketCount("Autofill.FormEvents.CreditCard", @@ -5074,8 +5039,7 @@ { // Simulating same popup being refreshed. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(false /* is_new_popup */, form, field); histogram_tester.ExpectBucketCount("Autofill.FormEvents.CreditCard", @@ -5114,8 +5078,7 @@ // Simulating two popups in the same page load. Suggestions shown should be // logged, but suggestions shown with virtual card should not. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); histogram_tester.ExpectBucketCount("Autofill.FormEvents.CreditCard", @@ -5822,8 +5785,7 @@ // Simulating submission with suggestion shown, but not selected. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -5866,8 +5828,7 @@ // Simulating submission with suggestion shown, but not selected. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -5914,8 +5875,7 @@ // Simulating submission with suggestion shown, but not selected. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -5963,8 +5923,7 @@ // Simulating submission with suggestion shown, but not selected. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -6012,8 +5971,7 @@ // Simulating submission with suggestion shown, but not selected. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -6061,8 +6019,7 @@ // Simulating submission with suggestion shown and selected. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid("10000000-0000-0000-0000-000000000001"); autofill_manager().FillOrPreviewForm( mojom::RendererFormDataAction::kFill, 0, form, form.fields.back(), @@ -6122,8 +6079,7 @@ // Simulating submission with no filled data. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -6166,8 +6122,7 @@ { // Simulating submission with no filled data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); @@ -6200,8 +6155,7 @@ // Simulating submission with suggestion shown. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -6246,8 +6200,7 @@ // triggered. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); // Trigger UploadFormDataAsyncCallback. @@ -6291,8 +6244,7 @@ { // Simulating submission with filled local data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid("10000000-0000-0000-0000-000000000001"); // local card autofill_manager().FillOrPreviewForm( mojom::RendererFormDataAction::kFill, 0, form, form.fields.front(), @@ -6339,8 +6291,7 @@ // Simulating submission with filled virtual card data by selecting the // option based on the enrolled masked card. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid("10000000-0000-0000-0000-000000000002"); // masked card autofill_manager().FillOrPreviewVirtualCardInformation( mojom::RendererFormDataAction::kFill, guid, kDefaultPageID, form, @@ -6387,8 +6338,7 @@ { // Simulating submission with filled server data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid( "10000000-0000-0000-0000-000000000003"); // full server card autofill_manager().FillOrPreviewForm( @@ -6491,8 +6441,7 @@ { // Simulating multiple submissions. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); @@ -6722,8 +6671,7 @@ { // Simulating submission with no filled data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -6748,8 +6696,7 @@ // Simulating submission with suggestion shown. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -6773,8 +6720,7 @@ { // Simulating submission with filled local data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid("10000000-0000-0000-0000-000000000001"); // local card autofill_manager().FillOrPreviewForm( mojom::RendererFormDataAction::kFill, 0, form, form.fields.front(), @@ -6804,8 +6750,7 @@ // Simulating submission with filled virtual card data by selecting the // option based on the enrolled masked card. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid("10000000-0000-0000-0000-000000000002"); // masked card autofill_manager().FillOrPreviewVirtualCardInformation( mojom::RendererFormDataAction::kFill, guid, kDefaultPageID, form, @@ -6835,8 +6780,7 @@ { // Simulating submission with filled server data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); // Full server card. std::string guid("10000000-0000-0000-0000-000000000003"); autofill_manager().FillOrPreviewForm( @@ -6901,8 +6845,7 @@ { // Simulating multiple submissions. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, @@ -7077,8 +7020,7 @@ // Simulating activating the autofill popup for the credit card field, new // popup being shown and filling a local card suggestion. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); std::string guid("10000000-0000-0000-0000-000000000001"); // local card autofill_manager().FillOrPreviewForm( @@ -7127,8 +7069,7 @@ // submitting the form. Verify that all related form events are correctly // logged to offer sub-histogram. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); // Select the masked server card with the linked offer. autofill_manager().FillOrPreviewForm( @@ -7175,8 +7116,7 @@ // submitting the form. Verify that all related form events are correctly // logged to offer sub-histogram. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); // Select another card, and still log to offer // sub-histogram because user has another masked server card with offer. @@ -7241,8 +7181,7 @@ // Simulating activating the autofill popup for the credit card field, // new popup being shown and filling a local card suggestion. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); // Select the card with linked offer, though metrics should not record it // since the offer is expired. @@ -7318,8 +7257,7 @@ // sub-histogram. Making suggestions reappear tests confirmation of a fix // for crbug/1198751. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); // Select the masked server card with the linked offer. autofill_manager().FillOrPreviewForm( @@ -7331,8 +7269,7 @@ // Simulate user showing suggestions but then submitting form with // previously filled card info. - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); @@ -7381,8 +7318,7 @@ // failing the CVC check and submitting the form anyways. Verify that all // related form events are correctly logged to offer sub-histogram. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); // Select the masked server card with the linked offer, but fail the CVC // check. @@ -7443,8 +7379,7 @@ base::HistogramTester histogram_tester; // Show suggestions and select the card with offer. - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); autofill_manager().FillOrPreviewForm( mojom::RendererFormDataAction::kFill, 0, form, form.fields.back(), @@ -7454,8 +7389,7 @@ "6011000990139424"); // Show suggestions again, and select a local card instead. - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); guid = "10000000-0000-0000-0000-000000000001"; autofill_manager().FillOrPreviewForm( @@ -7612,8 +7546,7 @@ { // Simulate activating the autofill popup for the street field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample("Autofill.FormEvents.Address", FORM_EVENT_INTERACTED_ONCE, 1); @@ -7638,10 +7571,8 @@ { // Simulate activating the autofill popup for the street field twice. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); - autofill_manager().OnAskForValuesToFill( - 1, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field, /*query_id=*/0); + autofill_manager().OnAskForValuesToFillTest(form, field, /*query_id=*/1); histogram_tester.ExpectUniqueSample("Autofill.FormEvents.Address", FORM_EVENT_INTERACTED_ONCE, 1); // Check if FormEvent UKM is logged properly @@ -8025,8 +7956,7 @@ { // Simulating submission with no filled data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -8052,8 +7982,7 @@ // autofill manager is reset before UploadFormDataAsyncCallback is // triggered. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); // Trigger UploadFormDataAsyncCallback. @@ -8080,8 +8009,7 @@ // Simulating submission with suggestion shown. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -8100,8 +8028,7 @@ { // Simulating submission with filled local data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid(kTestGuid); // local profile autofill_manager().FillOrPreviewForm( mojom::RendererFormDataAction::kFill, 0, form, form.fields.front(), @@ -8124,8 +8051,7 @@ { // Simulating multiple submissions. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, @@ -8211,8 +8137,7 @@ { // Simulating submission with no filled data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -8232,8 +8157,7 @@ // Simulating submission with suggestion shown. base::HistogramTester histogram_tester; autofill_manager().DidShowSuggestions(true /* is_new_popup */, form, field); - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); histogram_tester.ExpectBucketCount( @@ -8252,8 +8176,7 @@ { // Simulating submission with filled local data. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); std::string guid(kTestGuid); // local profile autofill_manager().FillOrPreviewForm( mojom::RendererFormDataAction::kFill, 0, form, form.fields.front(), @@ -8277,8 +8200,7 @@ { // Simulating multiple submissions. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, SubmissionSource::FORM_SUBMISSION); autofill_manager().OnFormSubmitted(form, /*known_success=*/false, @@ -8357,8 +8279,7 @@ autofill_manager().AddSeenForm(form, field_types, field_types); base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectBucketCount("Autofill.FormEvents.Address.PhoneOnly", FORM_EVENT_INTERACTED_ONCE, 1); } @@ -8397,8 +8318,7 @@ { // Simulate activating the autofill popup for the credit card field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample( "Autofill.FormEvents.CreditCard.WithNoData", FORM_EVENT_INTERACTED_ONCE, 1); @@ -8416,8 +8336,7 @@ { // Simulate activating the autofill popup for the credit card field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample( "Autofill.FormEvents.CreditCard.WithOnlyLocalData", FORM_EVENT_INTERACTED_ONCE, 1); @@ -8435,8 +8354,7 @@ { // Simulate activating the autofill popup for the credit card field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample( "Autofill.FormEvents.CreditCard.WithOnlyServerData", FORM_EVENT_INTERACTED_ONCE, 1); @@ -8454,8 +8372,7 @@ { // Simulate activating the autofill popup for the credit card field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample( "Autofill.FormEvents.CreditCard.WithOnlyServerData", FORM_EVENT_INTERACTED_ONCE, 1); @@ -8473,8 +8390,7 @@ { // Simulate activating the autofill popup for the credit card field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample( "Autofill.FormEvents.CreditCard.WithBothServerAndLocalData", FORM_EVENT_INTERACTED_ONCE, 1); @@ -8512,8 +8428,7 @@ { // Simulate activating the autofill popup for the street field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample( "Autofill.FormEvents.Address.WithNoData", FORM_EVENT_INTERACTED_ONCE, 1); @@ -8527,8 +8442,7 @@ { // Simulate activating the autofill popup for the street field. base::HistogramTester histogram_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); histogram_tester.ExpectUniqueSample( "Autofill.FormEvents.Address.WithOnlyLocalData", FORM_EVENT_INTERACTED_ONCE, 1); @@ -10331,8 +10245,7 @@ // Simulate an Autofill query on a credit card field. { base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledCreditCardSuggestions")); } @@ -10393,8 +10306,7 @@ // Simulate an Autofill query on a credit card field. { base::UserActionTester user_action_tester; - autofill_manager().OnAskForValuesToFill( - 0, form, field, gfx::RectF(), /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, field); EXPECT_EQ(1, user_action_tester.GetActionCount( "Autofill_PolledCreditCardSuggestions")); } @@ -11607,9 +11519,7 @@ // Simulate interacting with the form. if (user_interacted_with_form) { - autofill_manager().OnAskForValuesToFill( - /*query_id=*/0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); } // Simulate seeing a suggestion. @@ -11750,9 +11660,7 @@ /*removed_forms=*/{}); // Simulate interacting with the form. - autofill_manager().OnAskForValuesToFill( - /*query_id=*/0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); // Don't simulate a suggestion but simulate the user typing. autofill_manager().OnTextFieldDidChange(form, form.fields[0], gfx::RectF(), @@ -11835,9 +11743,7 @@ // Simulate page load. autofill_manager().OnFormsSeen(/*updated_forms=*/{form_}, /*removed_forms=*/{}); - autofill_manager().OnAskForValuesToFill( - 0, form_, form_.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form_, form_.fields[0]); // Simulate form submission. autofill_manager().OnFormSubmitted(form_, false, @@ -11866,9 +11772,7 @@ personal_data().ClearProfiles(); autofill_manager().OnFormsSeen(/*updated_forms=*/{form_}, /*removed_forms=*/{}); - autofill_manager().OnAskForValuesToFill( - 0, form_, form_.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form_, form_.fields[0]); // Simulate user typing the address. autofill_manager().OnTextFieldDidChange(form_, form_.fields[0], gfx::RectF(), @@ -11901,9 +11805,7 @@ // Simulate that suggestion is shown but user does not accept it. autofill_manager().OnFormsSeen(/*updated_forms=*/{form_}, /*removed_forms=*/{}); - autofill_manager().OnAskForValuesToFill( - 0, form_, form_.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form_, form_.fields[0]); autofill_manager().DidShowSuggestions( /*has_autofill_suggestions=*/true, form_, form_.fields[0]); @@ -11938,9 +11840,7 @@ // Simulate that suggestion is shown and user accepts it. autofill_manager().OnFormsSeen(/*updated_forms=*/{form_}, /*removed_forms=*/{}); - autofill_manager().OnAskForValuesToFill( - 0, form_, form_.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form_, form_.fields[0]); autofill_manager().DidShowSuggestions( /*has_autofill_suggestions=*/true, form_, form_.fields[0]); autofill_manager().FillOrPreviewForm( @@ -11978,9 +11878,7 @@ // Simulate that suggestion is shown and user accepts it. autofill_manager().OnFormsSeen(/*updated_forms=*/{form_}, /*removed_forms=*/{}); - autofill_manager().OnAskForValuesToFill( - 0, form_, form_.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form_, form_.fields[0]); autofill_manager().DidShowSuggestions( /*has_autofill_suggestions=*/true, form_, form_.fields[0]); autofill_manager().FillOrPreviewForm( @@ -12168,9 +12066,7 @@ // Simulate having seen this form on page load. autofill_manager().AddSeenForm(form, heuristic_types, server_types); - autofill_manager().OnAskForValuesToFill( - 0, form, form.fields[0], gfx::RectF(), - /*autoselect_first_suggestion=*/false); + autofill_manager().OnAskForValuesToFillTest(form, form.fields[0]); autofill_manager().DidShowSuggestions( /*has_autofill_suggestions=*/true, form, form.fields[0]);
diff --git a/components/autofill/core/browser/test_browser_autofill_manager.cc b/components/autofill/core/browser/test_browser_autofill_manager.cc index ce32b148..73d1b9f 100644 --- a/components/autofill/core/browser/test_browser_autofill_manager.cc +++ b/components/autofill/core/browser/test_browser_autofill_manager.cc
@@ -150,6 +150,18 @@ return submitted_form_signature_; } +void TestBrowserAutofillManager::OnAskForValuesToFillTest( + const FormData& form, + const FormFieldData& field, + int query_id, + const gfx::RectF& bounding_box, + bool autoselect_first_suggestion, + TouchToFillEligible touch_to_fill_eligible) { + BrowserAutofillManager::OnAskForValuesToFill( + query_id, form, field, bounding_box, autoselect_first_suggestion, + touch_to_fill_eligible); +} + void TestBrowserAutofillManager::SetAutofillProfileEnabled( bool autofill_profile_enabled) { autofill_profile_enabled_ = autofill_profile_enabled;
diff --git a/components/autofill/core/browser/test_browser_autofill_manager.h b/components/autofill/core/browser/test_browser_autofill_manager.h index 4612f7a..e60192e6 100644 --- a/components/autofill/core/browser/test_browser_autofill_manager.h +++ b/components/autofill/core/browser/test_browser_autofill_manager.h
@@ -70,6 +70,15 @@ const std::string GetSubmittedFormSignature(); + // Helper to skip irrelevant params. + void OnAskForValuesToFillTest( + const FormData& form, + const FormFieldData& field, + int query_id = 0, + const gfx::RectF& bounding_box = {}, + bool autoselect_first_suggestion = false, + TouchToFillEligible touch_to_fill_eligible = TouchToFillEligible(false)); + void SetAutofillProfileEnabled(bool profile_enabled); void SetAutofillCreditCardEnabled(bool credit_card_enabled);
diff --git a/components/autofill/core/common/BUILD.gn b/components/autofill/core/common/BUILD.gn index 1df8b62..0660e3a 100644 --- a/components/autofill/core/common/BUILD.gn +++ b/components/autofill/core/common/BUILD.gn
@@ -4,6 +4,7 @@ static_library("common") { sources = [ + "aliases.h", "autofill_clock.cc", "autofill_clock.h", "autofill_constants.cc",
diff --git a/components/autofill/core/common/aliases.h b/components/autofill/core/common/aliases.h new file mode 100644 index 0000000..dfd1a0c6 --- /dev/null +++ b/components/autofill/core/common/aliases.h
@@ -0,0 +1,20 @@ +// Copyright 2022 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef COMPONENTS_AUTOFILL_CORE_COMMON_ALIASES_H_ +#define COMPONENTS_AUTOFILL_CORE_COMMON_ALIASES_H_ + +#include "base/types/strong_alias.h" + +namespace autofill { + +// TODO(crbug.com/1326518): Use strong aliases for other primitives in mojom +// files. + +using TouchToFillEligible = + base::StrongAlias<struct TouchToFillEligibleTag, bool>; + +} // namespace autofill + +#endif // COMPONENTS_AUTOFILL_CORE_COMMON_ALIASES_H_
diff --git a/components/autofill/core/common/mojom/BUILD.gn b/components/autofill/core/common/mojom/BUILD.gn index 7a7eaa7b..f076b75e 100644 --- a/components/autofill/core/common/mojom/BUILD.gn +++ b/components/autofill/core/common/mojom/BUILD.gn
@@ -72,6 +72,11 @@ mojom = "autofill.mojom.PasswordGenerationUIData" cpp = "::autofill::password_generation::PasswordGenerationUIData" }, + { + mojom = "autofill.mojom.TouchToFillEligible" + cpp = "::autofill::TouchToFillEligible" + copyable_pass_by_value = true + }, ] traits_headers = [ "autofill_types_mojom_traits.h" ] traits_sources = [ "autofill_types_mojom_traits.cc" ]
diff --git a/components/autofill/core/common/mojom/autofill_types.mojom b/components/autofill/core/common/mojom/autofill_types.mojom index d135727..5cb2482 100644 --- a/components/autofill/core/common/mojom/autofill_types.mojom +++ b/components/autofill/core/common/mojom/autofill_types.mojom
@@ -309,3 +309,8 @@ kFill, // The renderer should fill the form data. kPreview, // The renderer should preview the form data. }; + +// autofill::TouchToFillEligible +struct TouchToFillEligible { + bool eligible; +};
diff --git a/components/autofill/core/common/mojom/autofill_types_mojom_traits.cc b/components/autofill/core/common/mojom/autofill_types_mojom_traits.cc index 8c64af0..808cf396 100644 --- a/components/autofill/core/common/mojom/autofill_types_mojom_traits.cc +++ b/components/autofill/core/common/mojom/autofill_types_mojom_traits.cc
@@ -311,4 +311,12 @@ data.ReadConfirmPasswordRendererId(&out->confirm_password_renderer_id); } +bool StructTraits<autofill::mojom::TouchToFillEligibleDataView, + autofill::TouchToFillEligible>:: + Read(autofill::mojom::TouchToFillEligibleDataView data, + autofill::TouchToFillEligible* out) { + *out = autofill::TouchToFillEligible(data.eligible()); + return true; +} + } // namespace mojo
diff --git a/components/autofill/core/common/mojom/autofill_types_mojom_traits.h b/components/autofill/core/common/mojom/autofill_types_mojom_traits.h index ec8fa9db..c551782 100644 --- a/components/autofill/core/common/mojom/autofill_types_mojom_traits.h +++ b/components/autofill/core/common/mojom/autofill_types_mojom_traits.h
@@ -11,6 +11,7 @@ #include <vector> #include "base/i18n/rtl.h" +#include "components/autofill/core/common/aliases.h" #include "components/autofill/core/common/form_data.h" #include "components/autofill/core/common/form_data_predictions.h" #include "components/autofill/core/common/form_field_data.h" @@ -539,6 +540,15 @@ autofill::ParsingResult* out); }; +template <> +struct StructTraits<autofill::mojom::TouchToFillEligibleDataView, + autofill::TouchToFillEligible> { + static bool eligible(autofill::TouchToFillEligible r) { return r.value(); } + + static bool Read(autofill::mojom::TouchToFillEligibleDataView data, + autofill::TouchToFillEligible* out); +}; + } // namespace mojo #endif // COMPONENTS_AUTOFILL_CORE_COMMON_MOJOM_AUTOFILL_TYPES_MOJOM_TRAITS_H_
diff --git a/components/autofill/ios/browser/autofill_agent.mm b/components/autofill/ios/browser/autofill_agent.mm index 867fe9f..c195f976 100644 --- a/components/autofill/ios/browser/autofill_agent.mm +++ b/components/autofill/ios/browser/autofill_agent.mm
@@ -333,7 +333,8 @@ // -showAutofillPopup:popupDelegate:. autofillManager->OnAskForValuesToFill(++_lastQueryID, form, field, gfx::RectF(), - /*autoselect_first_suggestion=*/false); + /*autoselect_first_suggestion=*/false, + autofill::TouchToFillEligible(false)); } - (void)checkIfSuggestionsAvailableForForm:
diff --git a/components/cronet/android/BUILD.gn b/components/cronet/android/BUILD.gn index 2fb476e..96a5a63f 100644 --- a/components/cronet/android/BUILD.gn +++ b/components/cronet/android/BUILD.gn
@@ -274,6 +274,7 @@ "java/src/org/chromium/net/impl/CronetEngineBase.java", "java/src/org/chromium/net/impl/CronetEngineBuilderImpl.java", "java/src/org/chromium/net/impl/CronetExceptionImpl.java", + "java/src/org/chromium/net/impl/CronetLogger.java", "java/src/org/chromium/net/impl/NetworkExceptionImpl.java", "java/src/org/chromium/net/impl/Preconditions.java", "java/src/org/chromium/net/impl/QuicExceptionImpl.java",
diff --git a/components/cronet/android/java/src/org/chromium/net/impl/CronetLogger.java b/components/cronet/android/java/src/org/chromium/net/impl/CronetLogger.java new file mode 100644 index 0000000..bca44c9f --- /dev/null +++ b/components/cronet/android/java/src/org/chromium/net/impl/CronetLogger.java
@@ -0,0 +1,188 @@ +// Copyright 2022 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.net.impl; + +import org.chromium.net.ExperimentalCronetEngine; + +/** + * Base class for implementing a CronetLogger. + */ +public abstract class CronetLogger { + public static enum CronetSource { + // Safe default, don't use explicitly. + CRONET_SOURCE_UNSPECIFIED, + // The library is bundled with the application. + CRONET_SOURCE_STATICALLY_LINKED, + // The library is loaded from GooglePlayServices + CRONET_SOURCE_PLAY_SERVICES, + // The application is using the fallback implementation + CRONET_SOURCE_FALLBACK, + } + + public abstract void logCronetEngineCreation(int cronetEngineId, + ExperimentalCronetEngine.Builder builder, CronetVersion version, CronetSource source); + + public abstract void logCronetTrafficInfo(int cronetEngineId, CronetTrafficInfo trafficInfo); + + /** + * This aggregates the information about request and response traffic for a + * particular CronetEngine + */ + public static class CronetTrafficInfo { + private final int mRequestHeaderSizeInBytes; + private final int mRequestBodySizeInBytes; + private final int mResponseHeaderSizeInBytes; + private final int mResponseBodySizeInBytes; + private final int mResponseStatusCode; + private final int mHeadersLatencyInMillis; + private final int mTotalLatencyInMillis; + private final String mNegotiatedProtocol; + private final boolean mWasConnectionMigrationAttempted; + private final boolean mDidConnectionMigrationSucceed; + + public CronetTrafficInfo(int requestHeaderSizeInBytes, int requestBodySizeInBytes, + int responseHeaderSizeInBytes, int responseBodySizeInBytes, int responseStatusCode, + int headersLatencyInMillis, int totalLatencyInMillis, String negotiatedProtocol, + boolean wasConnectionMigrationAttempted, boolean didConnectionMigrationSucceed) { + mRequestHeaderSizeInBytes = requestHeaderSizeInBytes; + mRequestBodySizeInBytes = requestBodySizeInBytes; + mResponseHeaderSizeInBytes = responseHeaderSizeInBytes; + mResponseBodySizeInBytes = responseBodySizeInBytes; + mResponseStatusCode = responseStatusCode; + mHeadersLatencyInMillis = headersLatencyInMillis; + mTotalLatencyInMillis = totalLatencyInMillis; + mNegotiatedProtocol = negotiatedProtocol; + mWasConnectionMigrationAttempted = wasConnectionMigrationAttempted; + mDidConnectionMigrationSucceed = didConnectionMigrationSucceed; + } + + /** + * @return The total size of headers sent in bytes + */ + public int getRequestHeaderSizeInBytes() { + return mRequestHeaderSizeInBytes; + } + + /** + * @return The total size of request body sent, if any, in bytes + */ + public int getRequestBodySizeInBytes() { + return mRequestBodySizeInBytes; + } + + /** + * @return The total size of headers received in bytes + */ + public int getResponseHeaderSizeInBytes() { + return mResponseHeaderSizeInBytes; + } + + /** + * @return The total size of response body, if any, received in bytes + */ + public int getResponseBodySizeInBytes() { + return mResponseBodySizeInBytes; + } + + /** + * @return The response status code of the request + */ + public int getResponseStatusCode() { + return mResponseStatusCode; + } + + /** + * The time it took from starting the request to receiving the full set of + * response headers. + * + * @return The time to get response headers in milliseconds + */ + public int getHeadersLatencyInMillis() { + return mHeadersLatencyInMillis; + } + + /** + * The time it took from starting the request to receiving the entire + * response. + * + * @return The time to get total response in milliseconds + */ + public int getTotalLatencyInMillis() { + return mTotalLatencyInMillis; + } + + /** + * @return The negotiated protocol used for the traffic + */ + public String getNegotiatedProtocol() { + return mNegotiatedProtocol; + } + + /** + * @return True if the connection migration was attempted, else False + */ + public boolean wasConnectionMigrationAttempted() { + return mWasConnectionMigrationAttempted; + } + + /** + * @return True if the connection migration was attempted and succeeded, else False + */ + public boolean didConnectionMigrationSucceed() { + return mDidConnectionMigrationSucceed; + } + } + + /** + * Holds information about the cronet version used for a cronetEngine. + */ + public static class CronetVersion { + private final int mMajorVersion; + private final int mMinorVersion; + private final int mBuildVersion; + private final int mPatchVersion; + + /** + * Pass the cronet version string here and + * it would be split. The string comes in the format + * MAJOR.MINOR.BUILD.PATCH + */ + public CronetVersion(String version) { + String[] splitVersion = version.split("\\."); + mMajorVersion = Integer.parseInt(splitVersion[0]); + mMinorVersion = Integer.parseInt(splitVersion[1]); + mBuildVersion = Integer.parseInt(splitVersion[2]); + mPatchVersion = Integer.parseInt(splitVersion[3]); + } + + /** + * @return the MAJOR version of cronet used for the traffic + */ + public int getMajorVersion() { + return mMajorVersion; + } + + /** + * @return the MINOR version of cronet used for the traffic + */ + public int getMinorVersion() { + return mMinorVersion; + } + + /** + * @return the BUILD version of cronet used for the traffic + */ + public int getBuildVersion() { + return mBuildVersion; + } + + /** + * @return the PATCH version of cronet used for the traffic + */ + public int getPatchVersion() { + return mPatchVersion; + } + } +} \ No newline at end of file
diff --git a/components/page_load_metrics/browser/page_load_metrics_forward_observer.cc b/components/page_load_metrics/browser/page_load_metrics_forward_observer.cc index af20d10..f43eabc 100644 --- a/components/page_load_metrics/browser/page_load_metrics_forward_observer.cc +++ b/components/page_load_metrics/browser/page_load_metrics_forward_observer.cc
@@ -217,13 +217,11 @@ void PageLoadMetricsForwardObserver::OnFirstInputInPage( const mojom::PageLoadTiming& timing) {} +// OnLoadingBehaviorObserved is called through PageLoadTracker::UpdateMetrics. +// So, the event is always forwarded at the PageLoadTracker layer. void PageLoadMetricsForwardObserver::OnLoadingBehaviorObserved( content::RenderFrameHost* rfh, - int behavior_flags) { - if (!parent_observer_) - return; - parent_observer_->OnLoadingBehaviorObserved(rfh, behavior_flags); -} + int behavior_flags) {} void PageLoadMetricsForwardObserver::OnFeaturesUsageObserved( content::RenderFrameHost* rfh,
diff --git a/components/password_manager/core/browser/form_parsing/form_parser.cc b/components/password_manager/core/browser/form_parsing/form_parser.cc index bdddb29..e3d58f3 100644 --- a/components/password_manager/core/browser/form_parsing/form_parser.cc +++ b/components/password_manager/core/browser/form_parsing/form_parser.cc
@@ -64,16 +64,18 @@ return AutocompleteFlag::kNone; const base::StringPiece& field_type = tokens.back(); - if (base::LowerCaseEqualsASCII(field_type, kAutocompleteUsername)) + if (base::EqualsCaseInsensitiveASCII(field_type, kAutocompleteUsername)) return AutocompleteFlag::kUsername; - if (base::LowerCaseEqualsASCII(field_type, kAutocompleteCurrentPassword)) + if (base::EqualsCaseInsensitiveASCII(field_type, + kAutocompleteCurrentPassword)) return AutocompleteFlag::kCurrentPassword; - if (base::LowerCaseEqualsASCII(field_type, kAutocompleteNewPassword)) + if (base::EqualsCaseInsensitiveASCII(field_type, kAutocompleteNewPassword)) return AutocompleteFlag::kNewPassword; - if (base::LowerCaseEqualsASCII(field_type, kAutocompleteWebAuthn)) + if (base::EqualsCaseInsensitiveASCII(field_type, kAutocompleteWebAuthn)) return AutocompleteFlag::kWebAuthn; - if (base::LowerCaseEqualsASCII(field_type, kAutocompleteOneTimePassword) || + if (base::EqualsCaseInsensitiveASCII(field_type, + kAutocompleteOneTimePassword) || base::StartsWith(field_type, kAutocompleteCreditCardPrefix, base::CompareCase::SENSITIVE)) { return AutocompleteFlag::kNonPassword;
diff --git a/components/signin/core/browser/signin_internals_util.h b/components/signin/core/browser/signin_internals_util.h index 09e80e8..9851505 100644 --- a/components/signin/core/browser/signin_internals_util.h +++ b/components/signin/core/browser/signin_internals_util.h
@@ -18,11 +18,9 @@ extern const char kSigninPrefPrefix[]; extern const char kTokenPrefPrefix[]; -// Helper enums to access fields from SigninStatus (declared below). -enum { - SIGNIN_FIELDS_BEGIN = 0, - UNTIMED_FIELDS_BEGIN_UNTYPED = SIGNIN_FIELDS_BEGIN -}; +// Helper constants to access fields from SigninStatus (declared below). +constexpr int SIGNIN_FIELDS_BEGIN = 0; +constexpr int UNTIMED_FIELDS_BEGIN_UNTYPED = SIGNIN_FIELDS_BEGIN; enum UntimedSigninStatusField { UNTIMED_FIELDS_BEGIN = UNTIMED_FIELDS_BEGIN_UNTYPED, @@ -32,10 +30,8 @@ UNTIMED_FIELDS_END }; -enum { - UNTIMED_FIELDS_COUNT = UNTIMED_FIELDS_END - UNTIMED_FIELDS_BEGIN, - TIMED_FIELDS_BEGIN_UNTYPED = UNTIMED_FIELDS_END -}; +constexpr int UNTIMED_FIELDS_COUNT = UNTIMED_FIELDS_END - UNTIMED_FIELDS_BEGIN; +constexpr int TIMED_FIELDS_BEGIN_UNTYPED = UNTIMED_FIELDS_END; enum TimedSigninStatusField { TIMED_FIELDS_BEGIN = TIMED_FIELDS_BEGIN_UNTYPED, @@ -44,11 +40,9 @@ TIMED_FIELDS_END }; -enum { - TIMED_FIELDS_COUNT = TIMED_FIELDS_END - TIMED_FIELDS_BEGIN, - SIGNIN_FIELDS_END = TIMED_FIELDS_END, - SIGNIN_FIELDS_COUNT = SIGNIN_FIELDS_END - SIGNIN_FIELDS_BEGIN -}; +constexpr int TIMED_FIELDS_COUNT = TIMED_FIELDS_END - TIMED_FIELDS_BEGIN; +constexpr int SIGNIN_FIELDS_END = TIMED_FIELDS_END; +constexpr int SIGNIN_FIELDS_COUNT = SIGNIN_FIELDS_END - SIGNIN_FIELDS_BEGIN; // Returns the name of a SigninStatus field. std::string SigninStatusFieldToString(UntimedSigninStatusField field);
diff --git a/content/browser/devtools/protocol/page_handler.cc b/content/browser/devtools/protocol/page_handler.cc index 2bd35a87..1e2eca9 100644 --- a/content/browser/devtools/protocol/page_handler.cc +++ b/content/browser/devtools/protocol/page_handler.cc
@@ -1277,9 +1277,18 @@ } Response PageHandler::SetWebLifecycleState(const std::string& state) { - WebContentsImpl* web_contents = GetWebContents(); - if (!web_contents) + if (!host_) return Response::ServerError("Not attached to a page"); + + // Inactive pages(e.g., a prerendered or back-forward cached page) should not + // affect the state. + if (!host_->IsActive()) + return Response::ServerError("Not attached to an active page"); + + if (host_->GetParentOrOuterDocument()) + return Response::ServerError("This is only supported for top-level frames"); + + WebContents* web_contents = WebContents::FromRenderFrameHost(host_); if (state == Page::SetWebLifecycleState::StateEnum::Frozen) { // TODO(fmeawad): Instead of forcing a visibility change, only allow // freezing a page if it was already hidden.
diff --git a/content/browser/loader/file_url_loader_factory.cc b/content/browser/loader/file_url_loader_factory.cc index 1a5106b..e1894ae6 100644 --- a/content/browser/loader/file_url_loader_factory.cc +++ b/content/browser/loader/file_url_loader_factory.cc
@@ -518,7 +518,7 @@ #if BUILDFLAG(IS_WIN) base::FilePath shortcut_target; if (link_following_policy == LinkFollowingPolicy::kFollow && - base::LowerCaseEqualsASCII(path.Extension(), ".lnk") && + base::EqualsCaseInsensitiveASCII(path.Extension(), ".lnk") && base::win::ResolveShortcut(path, &shortcut_target, nullptr)) { // Follow Windows shortcuts redirect_data_ = std::make_unique<RedirectData>();
diff --git a/content/browser/renderer_host/pending_beacon_host.cc b/content/browser/renderer_host/pending_beacon_host.cc index 118132b8..43e6e79 100644 --- a/content/browser/renderer_host/pending_beacon_host.cc +++ b/content/browser/renderer_host/pending_beacon_host.cc
@@ -4,6 +4,8 @@ #include "content/browser/renderer_host/pending_beacon_host.h" +#include "content/browser/renderer_host/pending_beacon_service.h" + namespace content { PendingBeaconHost::PendingBeaconHost(RenderFrameHost* rfh, @@ -31,4 +33,25 @@ DOCUMENT_USER_DATA_KEY_IMPL(PendingBeaconHost); +Beacon::Beacon(const base::UnguessableToken& id, + const GURL& url, + blink::mojom::BeaconMethod method, + base::TimeDelta timeout, + mojo::PendingReceiver<blink::mojom::PendingBeacon> receiver) + : receiver_(this, std::move(receiver)), + id_(id), + url_(url), + method_(method), + timeout_(timeout) {} + +Beacon::~Beacon() = default; + +void Beacon::Deactivate() { + // Beacons are not deleted on deactivation; they'll be cleaned up when the + // document that owns the beacon is either hidden or discarded. + // TODO(crbug.com/1293679): Clean up beacons when their owning document is + // discarded or hidden. + active_ = false; +} + } // namespace content
diff --git a/content/browser/renderer_host/pending_beacon_host.h b/content/browser/renderer_host/pending_beacon_host.h index 74c46b1..76a27454 100644 --- a/content/browser/renderer_host/pending_beacon_host.h +++ b/content/browser/renderer_host/pending_beacon_host.h
@@ -8,7 +8,6 @@ #include "base/memory/raw_ptr.h" #include "base/time/time.h" #include "base/unguessable_token.h" -#include "content/browser/renderer_host/pending_beacon_service.h" #include "content/common/content_export.h" #include "content/public/browser/document_user_data.h" #include "mojo/public/cpp/bindings/pending_receiver.h" @@ -17,6 +16,8 @@ namespace content { +class PendingBeaconService; + // Holds a set of IDs (i.e. UnguessableTokens) for a document's // pending beacons. This class is responsible for triggering the sending // of beacons when a document is either discarded or hidden. @@ -55,6 +56,34 @@ DOCUMENT_USER_DATA_KEY_DECL(); }; +class Beacon : public blink::mojom::PendingBeacon { + public: + // Browser-side pending beacon constructor. Parameters correspond to the + // renderer-side PendingBeacon class, except for 'id' which is a + // browser-side identifier to distinguish which beacons belong to which + // documents. This will be used to determine if a beacon should be sent when + // a particular document is discarded or hidden (each document has a + // `PendingBeaconHost` which keeps a vector of IDs for the beacons it owns). + // API explainer can be found at: + // https://github.com/darrenw/docs/blob/main/explainers/beacon_api.md + explicit Beacon(const base::UnguessableToken& id, + const GURL& url, + blink::mojom::BeaconMethod method, + base::TimeDelta timeout, + mojo::PendingReceiver<blink::mojom::PendingBeacon> receiver); + ~Beacon() override; + void Deactivate() override; + + private: + mojo::Receiver<blink::mojom::PendingBeacon> receiver_; + + const base::UnguessableToken id_; + const GURL url_; + [[maybe_unused]] const blink::mojom::BeaconMethod method_; + [[maybe_unused]] const base::TimeDelta timeout_; + bool active_ = true; +}; + } // namespace content #endif // CONTENT_BROWSER_RENDERER_HOST_PENDING_BEACON_HOST_H_ \ No newline at end of file
diff --git a/content/browser/renderer_host/pending_beacon_service.cc b/content/browser/renderer_host/pending_beacon_service.cc index af9a911..ccd80ef 100644 --- a/content/browser/renderer_host/pending_beacon_service.cc +++ b/content/browser/renderer_host/pending_beacon_service.cc
@@ -3,7 +3,9 @@ // found in the LICENSE file. #include "content/browser/renderer_host/pending_beacon_service.h" + #include "base/time/time.h" +#include "content/browser/renderer_host/pending_beacon_host.h" #include "mojo/public/cpp/bindings/pending_remote.h" #include "third_party/blink/public/mojom/frame/pending_beacon.mojom.h" @@ -27,26 +29,4 @@ beacons_.emplace_back(std::move(beacon)); } -void PendingBeaconService::Beacon::Deactivate() { - // Beacons are not deleted on deactivation; they'll be cleaned up when the - // document that owns the beacon is either hidden or discarded. - // TODO(crbug.com/1293679): Clean up beacons when their owning document is - // discarded or hidden. - active_ = false; -} - -PendingBeaconService::Beacon::Beacon( - const base::UnguessableToken& id, - const GURL& url, - blink::mojom::BeaconMethod method, - base::TimeDelta timeout, - mojo::PendingReceiver<blink::mojom::PendingBeacon> receiver) - : receiver_(this, std::move(receiver)), - id_(id), - url_(url), - method_(method), - timeout_(timeout) {} - -PendingBeaconService::Beacon::~Beacon() = default; - } // namespace content
diff --git a/content/browser/renderer_host/pending_beacon_service.h b/content/browser/renderer_host/pending_beacon_service.h index 652771fd..5e3c681 100644 --- a/content/browser/renderer_host/pending_beacon_service.h +++ b/content/browser/renderer_host/pending_beacon_service.h
@@ -8,6 +8,7 @@ #include "base/memory/singleton.h" #include "base/time/time.h" #include "base/unguessable_token.h" +#include "content/browser/renderer_host/pending_beacon_host.h" #include "content/common/content_export.h" #include "mojo/public/cpp/bindings/pending_receiver.h" #include "mojo/public/cpp/bindings/receiver.h" @@ -34,37 +35,6 @@ ~PendingBeaconService(); private: - class Beacon : public blink::mojom::PendingBeacon { - public: - // Browser-side pending beacon constructor. Parameters correspond to the - // renderer-side PendingBeacon class, except for 'id' which is a - // browser-side identifier to distinguish which beacons belong to which - // documents. This will be used to determine if a beacon should be sent when - // a particular document is discarded or hidden (each document has a - // `PendingBeaconHost` which keeps a vector of IDs for the beacons it owns). - // API explainer can be found at: - // https://github.com/darrenw/docs/blob/main/explainers/beacon_api.md - explicit Beacon( - const base::UnguessableToken& id, - const GURL& url, - blink::mojom::BeaconMethod method, - base::TimeDelta timeout, - mojo::PendingReceiver<blink::mojom::PendingBeacon> receiver); - ~Beacon() override; - void Deactivate() override; - - private: - mojo::Receiver<blink::mojom::PendingBeacon> receiver_; - - const base::UnguessableToken id_; - const GURL url_; - [[maybe_unused]] const blink::mojom::BeaconMethod method_; - [[maybe_unused]] const base::TimeDelta timeout_; - bool active_ = true; - - friend class PendingBeaconService; - }; - PendingBeaconService(); std::vector<std::unique_ptr<Beacon>> beacons_;
diff --git a/docs/clang_format.md b/docs/clang_format.md index 13dfe1de..2c55bf1 100644 --- a/docs/clang_format.md +++ b/docs/clang_format.md
@@ -44,6 +44,7 @@ * [Sublime Text](https://www.chromium.org/developers/sublime-text#TOC-Format-selection-or-area-around-cursor-using-clang-format) * [llvm's guidelines for vim, emacs, and bbedit](http://clang.llvm.org/docs/ClangFormat.html) +* [Visual Studio Code](https://chromium.googlesource.com/chromium/src/+/HEAD/docs/vscode.md#useful-extensions) * For vim, `:so tools/vim/clang-format.vim` and then hit cmd-shift-i (mac) ctrl-shift-i (elsewhere) to indent the current line or current selection.
diff --git a/extensions/renderer/api/automation/automation_internal_custom_bindings.cc b/extensions/renderer/api/automation/automation_internal_custom_bindings.cc index 654086a..ea44b0bf 100644 --- a/extensions/renderer/api/automation/automation_internal_custom_bindings.cc +++ b/extensions/renderer/api/automation/automation_internal_custom_bindings.cc
@@ -1867,12 +1867,7 @@ if (tree_id == accessibility_focused_tree_id_) accessibility_focused_tree_id_ = ui::AXTreeIDUnknown(); - auto it = tree_id_to_tree_wrapper_map_.find(tree_id); - if (it == tree_id_to_tree_wrapper_map_.end()) - return; - - TreeEventListenersChanged(it->second.get(), /* is_deleting=*/true); - tree_id_to_tree_wrapper_map_.erase(it); + tree_id_to_tree_wrapper_map_.erase(tree_id); } void AutomationInternalCustomBindings::AddTreeChangeObserver( @@ -2973,9 +2968,8 @@ } void AutomationInternalCustomBindings::TreeEventListenersChanged( - AutomationAXTreeWrapper* tree_wrapper, - bool is_deleting) { - if (!is_deleting && tree_wrapper->EventListenerCount() != 0) { + AutomationAXTreeWrapper* tree_wrapper) { + if (tree_wrapper->EventListenerCount() != 0) { trees_with_event_listeners_.insert(tree_wrapper->GetTreeID()); return; }
diff --git a/extensions/renderer/api/automation/automation_internal_custom_bindings.h b/extensions/renderer/api/automation/automation_internal_custom_bindings.h index 979fb89..e0231a20 100644 --- a/extensions/renderer/api/automation/automation_internal_custom_bindings.h +++ b/extensions/renderer/api/automation/automation_internal_custom_bindings.h
@@ -271,8 +271,7 @@ bool* offscreen = nullptr, bool clip_bounds = true) const; - void TreeEventListenersChanged(AutomationAXTreeWrapper* tree_wrapper, - bool is_deleting = false); + void TreeEventListenersChanged(AutomationAXTreeWrapper* tree_wrapper); std::map<ui::AXTreeID, std::unique_ptr<AutomationAXTreeWrapper>> tree_id_to_tree_wrapper_map_;
diff --git a/ios/chrome/browser/chrome_url_util.mm b/ios/chrome/browser/chrome_url_util.mm index 3a87262..ec79b99 100644 --- a/ios/chrome/browser/chrome_url_util.mm +++ b/ios/chrome/browser/chrome_url_util.mm
@@ -22,7 +22,8 @@ bool UrlIsExternalFileReference(const GURL& url) { return url.SchemeIs(kChromeUIScheme) && - base::LowerCaseEqualsASCII(url.host(), kChromeUIExternalFileHost); + base::EqualsCaseInsensitiveASCII(url.host(), + kChromeUIExternalFileHost); } bool UrlHasChromeScheme(const GURL& url) {
diff --git a/media/audio/alsa/alsa_wrapper.cc b/media/audio/alsa/alsa_wrapper.cc index b24630d..a5ac06a 100644 --- a/media/audio/alsa/alsa_wrapper.cc +++ b/media/audio/alsa/alsa_wrapper.cc
@@ -350,6 +350,10 @@ return snd_mixer_selem_has_playback_switch(elem); } +int AlsaWrapper::MixerSelemHasPlaybackVolume(snd_mixer_elem_t* elem) { + return snd_mixer_selem_has_playback_volume(elem); +} + void AlsaWrapper::MixerSelemIdSetIndex(snd_mixer_selem_id_t* obj, unsigned int val) { snd_mixer_selem_id_set_index(obj, val); @@ -367,6 +371,12 @@ return snd_mixer_selem_set_playback_switch(elem, channel, value); } +int AlsaWrapper::MixerSelemSetPlaybackSwitchAll( + snd_mixer_elem_t* elem, + int value) { + return snd_mixer_selem_set_playback_switch_all(elem, value); +} + int AlsaWrapper::MixerSelemSetPlaybackVolumeAll(snd_mixer_elem_t* elem, long value) { return snd_mixer_selem_set_playback_volume_all(elem, value);
diff --git a/media/audio/alsa/alsa_wrapper.h b/media/audio/alsa/alsa_wrapper.h index 970327f..11e0f20 100644 --- a/media/audio/alsa/alsa_wrapper.h +++ b/media/audio/alsa/alsa_wrapper.h
@@ -143,12 +143,15 @@ long* min, long* max); virtual int MixerSelemHasPlaybackSwitch(snd_mixer_elem_t* elem); + virtual int MixerSelemHasPlaybackVolume(snd_mixer_elem_t* elem); virtual void MixerSelemIdSetIndex(snd_mixer_selem_id_t* obj, unsigned int val); virtual void MixerSelemIdSetName(snd_mixer_selem_id_t* obj, const char* val); virtual int MixerSelemSetPlaybackSwitch(snd_mixer_elem_t* elem, snd_mixer_selem_channel_id_t channel, int value); + virtual int MixerSelemSetPlaybackSwitchAll(snd_mixer_elem_t* elem, + int value); virtual int MixerSelemSetPlaybackVolumeAll(snd_mixer_elem_t* elem, long value); virtual int MixerSelemIdMalloc(snd_mixer_selem_id_t** ptr);
diff --git a/net/http/http_cache_transaction.cc b/net/http/http_cache_transaction.cc index 56379bb..2007ceb0 100644 --- a/net/http/http_cache_transaction.cc +++ b/net/http/http_cache_transaction.cc
@@ -90,6 +90,12 @@ EXTERNALLY_CONDITIONALIZED_MAX }; +void RecordPervasivePayloadIndex(const char* histogram_name, int index) { + if (index != -1) { + base::UmaHistogramExactLinear(histogram_name, index, 101); + } +} + } // namespace #define CACHE_STATUS_HISTOGRAMS(type) \ @@ -668,8 +674,13 @@ if (hex_result != request_->checksum) { DVLOG(2) << "Pervasive payload checksum mismatch for \"" << request_->url << "\": got " << hex_result << ", expected " << request_->checksum; + RecordPervasivePayloadIndex("Network.CacheTransparency.MismatchedChecksums", + request_->pervasive_payloads_index_for_logging); return false; } + RecordPervasivePayloadIndex( + "Network.CacheTransparency.SingleKeyedCacheIsUsed", + request_->pervasive_payloads_index_for_logging); return true; } @@ -1528,6 +1539,9 @@ } if (response_.single_keyed_cache_entry_unusable) { + RecordPervasivePayloadIndex("Network.CacheTransparency.MarkedUnusable", + request_->pervasive_payloads_index_for_logging); + // We've read the single keyed entry and it turned out to be unusable. Let's // retry reading from the split cache. if (effective_load_flags_ & LOAD_USE_SINGLE_KEYED_CACHE) {
diff --git a/net/http/http_request_info.cc b/net/http/http_request_info.cc index faf3191..dba2c9b6 100644 --- a/net/http/http_request_info.cc +++ b/net/http/http_request_info.cc
@@ -15,7 +15,8 @@ privacy_mode(PRIVACY_MODE_DISABLED), secure_dns_policy(SecureDnsPolicy::kAllow), reporting_upload_depth(0), - idempotency(net::DEFAULT_IDEMPOTENCY) {} + idempotency(net::DEFAULT_IDEMPOTENCY), + pervasive_payloads_index_for_logging(-1) {} HttpRequestInfo::HttpRequestInfo(const HttpRequestInfo& other) = default;
diff --git a/net/http/http_request_info.h b/net/http/http_request_info.h index 444a9b83..e10fcd4 100644 --- a/net/http/http_request_info.h +++ b/net/http/http_request_info.h
@@ -89,6 +89,10 @@ // that the request is idempotent. net::Idempotency idempotency; + // Index of the requested URL in Cache Transparency's pervasive payload list. + // Only used for logging purposes. + int pervasive_payloads_index_for_logging; + // Checksum of the request body and selected headers, in upper-case // hexadecimal. Only non-empty if the USE_SINGLE_KEYED_CACHE load flag is set. std::string checksum;
diff --git a/net/url_request/url_request.h b/net/url_request/url_request.h index ce6d47e7..0aeb701 100644 --- a/net/url_request/url_request.h +++ b/net/url_request/url_request.h
@@ -792,6 +792,14 @@ void SetIdempotency(Idempotency idempotency) { idempotency_ = idempotency; } Idempotency GetIdempotency() const { return idempotency_; } + int pervasive_payloads_index_for_logging() const { + return pervasive_payloads_index_for_logging_; + } + + void set_pervasive_payloads_index_for_logging(int index) { + pervasive_payloads_index_for_logging_ = index; + } + const std::string& expected_response_checksum() const { return expected_response_checksum_; } @@ -1041,6 +1049,11 @@ ResponseHeadersCallback early_response_headers_callback_; ResponseHeadersCallback response_headers_callback_; + // The index of the request URL in Cache Transparency's Pervasive Payloads + // List. This is only used for logging purposes. It is initialized as -1 to + // signify that the index has not been set. + int pervasive_payloads_index_for_logging_ = -1; + // A SHA-256 checksum of the response and selected headers, stored as // upper-case hexadecimal. This is only used if the // LOAD_USE_SINGLE_KEYED_CACHE flag is set. On failure to match the cache
diff --git a/net/url_request/url_request_http_job.cc b/net/url_request/url_request_http_job.cc index 33d77d31..e889bb0 100644 --- a/net/url_request/url_request_http_job.cc +++ b/net/url_request/url_request_http_job.cc
@@ -278,6 +278,8 @@ net::MutableNetworkTrafficAnnotationTag(request_->traffic_annotation()); request_info_.socket_tag = request_->socket_tag(); request_info_.idempotency = request_->GetIdempotency(); + request_info_.pervasive_payloads_index_for_logging = + request_->pervasive_payloads_index_for_logging(); request_info_.checksum = request_->expected_response_checksum(); #if BUILDFLAG(ENABLE_REPORTING) request_info_.reporting_upload_depth = request_->reporting_upload_depth();
diff --git a/services/network/public/cpp/content_security_policy/content_security_policy.cc b/services/network/public/cpp/content_security_policy/content_security_policy.cc index d5f266c..9b57873 100644 --- a/services/network/public/cpp/content_security_policy/content_security_policy.cc +++ b/services/network/public/cpp/content_security_policy/content_security_policy.cc
@@ -1399,65 +1399,65 @@ } CSPDirectiveName ToCSPDirectiveName(const std::string& name) { - if (base::LowerCaseEqualsASCII(name, "base-uri")) + if (base::EqualsCaseInsensitiveASCII(name, "base-uri")) return CSPDirectiveName::BaseURI; - if (base::LowerCaseEqualsASCII(name, "block-all-mixed-content")) + if (base::EqualsCaseInsensitiveASCII(name, "block-all-mixed-content")) return CSPDirectiveName::BlockAllMixedContent; - if (base::LowerCaseEqualsASCII(name, "child-src")) + if (base::EqualsCaseInsensitiveASCII(name, "child-src")) return CSPDirectiveName::ChildSrc; - if (base::LowerCaseEqualsASCII(name, "connect-src")) + if (base::EqualsCaseInsensitiveASCII(name, "connect-src")) return CSPDirectiveName::ConnectSrc; - if (base::LowerCaseEqualsASCII(name, "default-src")) + if (base::EqualsCaseInsensitiveASCII(name, "default-src")) return CSPDirectiveName::DefaultSrc; - if (base::LowerCaseEqualsASCII(name, "fenced-frame-src")) + if (base::EqualsCaseInsensitiveASCII(name, "fenced-frame-src")) return CSPDirectiveName::FencedFrameSrc; - if (base::LowerCaseEqualsASCII(name, "frame-ancestors")) + if (base::EqualsCaseInsensitiveASCII(name, "frame-ancestors")) return CSPDirectiveName::FrameAncestors; - if (base::LowerCaseEqualsASCII(name, "frame-src")) + if (base::EqualsCaseInsensitiveASCII(name, "frame-src")) return CSPDirectiveName::FrameSrc; - if (base::LowerCaseEqualsASCII(name, "font-src")) + if (base::EqualsCaseInsensitiveASCII(name, "font-src")) return CSPDirectiveName::FontSrc; - if (base::LowerCaseEqualsASCII(name, "form-action")) + if (base::EqualsCaseInsensitiveASCII(name, "form-action")) return CSPDirectiveName::FormAction; - if (base::LowerCaseEqualsASCII(name, "img-src")) + if (base::EqualsCaseInsensitiveASCII(name, "img-src")) return CSPDirectiveName::ImgSrc; - if (base::LowerCaseEqualsASCII(name, "manifest-src")) + if (base::EqualsCaseInsensitiveASCII(name, "manifest-src")) return CSPDirectiveName::ManifestSrc; - if (base::LowerCaseEqualsASCII(name, "media-src")) + if (base::EqualsCaseInsensitiveASCII(name, "media-src")) return CSPDirectiveName::MediaSrc; - if (base::LowerCaseEqualsASCII(name, "object-src")) + if (base::EqualsCaseInsensitiveASCII(name, "object-src")) return CSPDirectiveName::ObjectSrc; - if (base::LowerCaseEqualsASCII(name, "prefetch-src")) + if (base::EqualsCaseInsensitiveASCII(name, "prefetch-src")) return CSPDirectiveName::PrefetchSrc; - if (base::LowerCaseEqualsASCII(name, "report-uri")) + if (base::EqualsCaseInsensitiveASCII(name, "report-uri")) return CSPDirectiveName::ReportURI; - if (base::LowerCaseEqualsASCII(name, "require-trusted-types-for")) + if (base::EqualsCaseInsensitiveASCII(name, "require-trusted-types-for")) return CSPDirectiveName::RequireTrustedTypesFor; - if (base::LowerCaseEqualsASCII(name, "sandbox")) + if (base::EqualsCaseInsensitiveASCII(name, "sandbox")) return CSPDirectiveName::Sandbox; - if (base::LowerCaseEqualsASCII(name, "script-src")) + if (base::EqualsCaseInsensitiveASCII(name, "script-src")) return CSPDirectiveName::ScriptSrc; - if (base::LowerCaseEqualsASCII(name, "script-src-attr")) + if (base::EqualsCaseInsensitiveASCII(name, "script-src-attr")) return CSPDirectiveName::ScriptSrcAttr; - if (base::LowerCaseEqualsASCII(name, "script-src-elem")) + if (base::EqualsCaseInsensitiveASCII(name, "script-src-elem")) return CSPDirectiveName::ScriptSrcElem; - if (base::LowerCaseEqualsASCII(name, "style-src")) + if (base::EqualsCaseInsensitiveASCII(name, "style-src")) return CSPDirectiveName::StyleSrc; - if (base::LowerCaseEqualsASCII(name, "style-src-attr")) + if (base::EqualsCaseInsensitiveASCII(name, "style-src-attr")) return CSPDirectiveName::StyleSrcAttr; - if (base::LowerCaseEqualsASCII(name, "style-src-elem")) + if (base::EqualsCaseInsensitiveASCII(name, "style-src-elem")) return CSPDirectiveName::StyleSrcElem; - if (base::LowerCaseEqualsASCII(name, "treat-as-public-address")) + if (base::EqualsCaseInsensitiveASCII(name, "treat-as-public-address")) return CSPDirectiveName::TreatAsPublicAddress; - if (base::LowerCaseEqualsASCII(name, "trusted-types")) + if (base::EqualsCaseInsensitiveASCII(name, "trusted-types")) return CSPDirectiveName::TrustedTypes; - if (base::LowerCaseEqualsASCII(name, "upgrade-insecure-requests")) + if (base::EqualsCaseInsensitiveASCII(name, "upgrade-insecure-requests")) return CSPDirectiveName::UpgradeInsecureRequests; - if (base::LowerCaseEqualsASCII(name, "worker-src")) + if (base::EqualsCaseInsensitiveASCII(name, "worker-src")) return CSPDirectiveName::WorkerSrc; - if (base::LowerCaseEqualsASCII(name, "report-to")) + if (base::EqualsCaseInsensitiveASCII(name, "report-to")) return CSPDirectiveName::ReportTo; - if (base::LowerCaseEqualsASCII(name, "navigate-to")) + if (base::EqualsCaseInsensitiveASCII(name, "navigate-to")) return CSPDirectiveName::NavigateTo; return CSPDirectiveName::Unknown;
diff --git a/services/network/public/cpp/features.cc b/services/network/public/cpp/features.cc index e4b8796a..00b86bc9 100644 --- a/services/network/public/cpp/features.cc +++ b/services/network/public/cpp/features.cc
@@ -268,13 +268,17 @@ const base::Feature kCacheTransparency{"CacheTransparency", base::FEATURE_DISABLED_BY_DEFAULT}; +// Load Pervasive Payloads List for Cache Transparency. +const base::Feature kPervasivePayloadsList{"PervasivePayloadsList", + base::FEATURE_DISABLED_BY_DEFAULT}; + // The list of pervasive payloads. A comma separated list starting with a // version number, followed one or more pairs of URL and checksum. The version // number is an integer. The URL is the canonical URL as returned by // GURL::spec(). The checksum is the SHA-256 of the payload and selected headers // converted to uppercase hexadecimal. constexpr base::FeatureParam<std::string> kCacheTransparencyPervasivePayloads{ - &kCacheTransparency, "pervasive-payloads", ""}; + &kPervasivePayloadsList, "pervasive-payloads", ""}; // Read as much of the net::URLRequest as there is space in the Mojo data pipe. const base::Feature kOptimizeNetworkBuffers{"OptimizeNetworkBuffers",
diff --git a/services/network/public/cpp/features.h b/services/network/public/cpp/features.h index a39b128..10bbcd0 100644 --- a/services/network/public/cpp/features.h +++ b/services/network/public/cpp/features.h
@@ -113,6 +113,9 @@ extern const base::Feature kCacheTransparency; COMPONENT_EXPORT(NETWORK_CPP) +extern const base::Feature kPervasivePayloadsList; + +COMPONENT_EXPORT(NETWORK_CPP) extern const base::FeatureParam<std::string> kCacheTransparencyPervasivePayloads;
diff --git a/services/network/url_loader.cc b/services/network/url_loader.cc index 559ed70..c2d3f893 100644 --- a/services/network/url_loader.cc +++ b/services/network/url_loader.cc
@@ -432,10 +432,28 @@ return enabled_; } + bool PervasivePayloadsEnabled() const { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + return pervasive_payloads_enabled_; + } + + absl::optional<int> GetIndexForURL(const GURL& url) const { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + + if (!pervasive_payloads_enabled_ || !url.is_valid()) + return absl::nullopt; + + auto it = map_.find(url.spec()); + if (it == map_.end()) { + return absl::nullopt; + } + return std::distance(map_.begin(), it); + } + absl::optional<std::string> GetChecksumForURL(const GURL& url) const { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - if (!url.is_valid()) + if (!enabled_ || !url.is_valid()) return absl::nullopt; auto it = map_.find(url.spec()); @@ -449,7 +467,11 @@ using PervasivePayloadsMap = base::flat_map<std::string, std::string>; CacheTransparencySettings() - : enabled_(base::FeatureList::IsEnabled(features::kCacheTransparency)), + : enabled_( + base::FeatureList::IsEnabled(features::kCacheTransparency) && + base::FeatureList::IsEnabled(features::kPervasivePayloadsList)), + pervasive_payloads_enabled_( + base::FeatureList::IsEnabled(features::kPervasivePayloadsList)), map_(CreateMap()) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); } @@ -458,7 +480,7 @@ PervasivePayloadsMap CreateMap() { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - if (!enabled_) + if (!pervasive_payloads_enabled_) return PervasivePayloadsMap(); const std::string comma_separated = @@ -497,7 +519,8 @@ } SEQUENCE_CHECKER(sequence_checker_); - const bool enabled_ GUARDED_BY_CONTEXT(sequence_checker_) = false; + const bool enabled_ GUARDED_BY_CONTEXT(sequence_checker_); + const bool pervasive_payloads_enabled_ GUARDED_BY_CONTEXT(sequence_checker_); const PervasivePayloadsMap map_ GUARDED_BY_CONTEXT(sequence_checker_); // This is normally leaked to avoid running a destructor. It's only @@ -544,6 +567,16 @@ return false; } +// These values are persisted to logs. Entries should not be renumbered and +// numeric values should never be reused. +enum class CacheTransparencyCacheNotUsedReason { + kTryingSingleKeyedCache = 0, + kIncompatibleRequestType = 1, + kIncompatibleRequestLoadFlags = 2, + kIncompatibleRequestHeaders = 3, + kMaxValue = kIncompatibleRequestHeaders, +}; + } // namespace URLLoader::MaybeSyncURLLoaderClient::MaybeSyncURLLoaderClient( @@ -764,27 +797,46 @@ int request_load_flags = request.load_flags; + if (CacheTransparencySettings::Get().PervasivePayloadsEnabled()) { + auto index = CacheTransparencySettings::Get().GetIndexForURL(request.url); + if (index.has_value()) { + url_request_->set_pervasive_payloads_index_for_logging(index.value()); + base::UmaHistogramExactLinear("Network.CacheTransparency.URLMatched", + index.value(), 101); + } + } + if (CacheTransparencySettings::Get().enabled() && ThirdPartyCookiesEnabled()) { auto checksum = CacheTransparencySettings::Get().GetChecksumForURL(request.url); if (checksum.has_value()) { + CacheTransparencyCacheNotUsedReason cache_not_used_reason = + CacheTransparencyCacheNotUsedReason::kTryingSingleKeyedCache; DVLOG(2) << "Found pervasive payload: " << request.url.spec(); if (request.method != net::HttpRequestHeaders::kGetMethod) { DVLOG(2) << "Not using single-keyed-cache; method is " << request.method; + cache_not_used_reason = + CacheTransparencyCacheNotUsedReason::kIncompatibleRequestType; } else if (HasFlagsIncompatibleWithSingleKeyedCache(request_load_flags)) { DVLOG(2) << "Not using single-keyed-cache; flags are " << request_load_flags; + cache_not_used_reason = + CacheTransparencyCacheNotUsedReason::kIncompatibleRequestLoadFlags; } else if (HasHeadersIncompatibleWithSingleKeyedCache(request.headers)) { DVLOG(2) << "Not using single-keyed-cache; headers are\n" << request.headers.ToString(); + cache_not_used_reason = + CacheTransparencyCacheNotUsedReason::kIncompatibleRequestHeaders; } else { DVLOG(2) << "Trying single-keyed cache"; request_load_flags |= net::LOAD_USE_SINGLE_KEYED_CACHE; url_request_->set_expected_response_checksum(checksum.value()); } + base::UmaHistogramEnumeration("Network.CacheTransparency.CacheNotUsed", + cache_not_used_reason); } }
diff --git a/services/network/url_loader_unittest.cc b/services/network/url_loader_unittest.cc index 3966a4f..1b59124d 100644 --- a/services/network/url_loader_unittest.cc +++ b/services/network/url_loader_unittest.cc
@@ -7313,8 +7313,10 @@ params["pervasive-payloads"] = base::StrCat( {"1,", pervasive_payload_url_.spec(), ",87F6EE26BD9CFC440B4C805AAE79E0A5671F61C00B5E0AF54B8199EAF64AAAC3"}); - cache_transparency_feature_.InitAndEnableFeatureWithParameters( - features::kCacheTransparency, params); + pervasive_payloads_feature_.InitAndEnableFeatureWithParameters( + features::kPervasivePayloadsList, params); + cache_transparency_feature_.InitAndEnableFeature( + features::kCacheTransparency); split_cache_feature_.InitAndEnableFeature( net::features::kSplitCacheByNetworkIsolationKey); @@ -7398,6 +7400,7 @@ private: static constexpr char kPervasivePayload[] = "/pervasive.js"; + base::test::ScopedFeatureList pervasive_payloads_feature_; base::test::ScopedFeatureList cache_transparency_feature_; base::test::ScopedFeatureList split_cache_feature_; GURL pervasive_payload_url_;
diff --git a/testing/buildbot/chromium.chromiumos.json b/testing/buildbot/chromium.chromiumos.json index 72dbc147..5461117 100644 --- a/testing/buildbot/chromium.chromiumos.json +++ b/testing/buildbot/chromium.chromiumos.json
@@ -5865,21 +5865,21 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "isolate_profile_data": true, "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5078.0", + "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -5892,7 +5892,7 @@ }, "test": "interactive_ui_tests", "test_id_prefix": "ninja://chrome/test:interactive_ui_tests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "isolate_profile_data": true, @@ -6030,21 +6030,21 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "isolate_profile_data": true, "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -6056,7 +6056,7 @@ }, "test": "lacros_chrome_browsertests", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "args": [ @@ -6176,21 +6176,21 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "isolate_profile_data": true, "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -6202,7 +6202,7 @@ }, "test": "lacros_chrome_browsertests_run_in_series", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests_run_in_series/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "isolate_profile_data": true,
diff --git a/testing/buildbot/chromium.fyi.json b/testing/buildbot/chromium.fyi.json index 413263c..54538c8 100644 --- a/testing/buildbot/chromium.fyi.json +++ b/testing/buildbot/chromium.fyi.json
@@ -87946,21 +87946,21 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "isolate_profile_data": true, "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5078.0", + "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com", @@ -87968,7 +87968,7 @@ }, "test": "interactive_ui_tests", "test_id_prefix": "ninja://chrome/test:interactive_ui_tests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "isolate_profile_data": true, @@ -88081,28 +88081,28 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "isolate_profile_data": true, "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" }, "test": "lacros_chrome_browsertests", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "args": [ @@ -88202,28 +88202,28 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "isolate_profile_data": true, "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "service_account": "chromium-tester@chops-service-accounts.iam.gserviceaccount.com" }, "test": "lacros_chrome_browsertests_run_in_series", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests_run_in_series/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "isolate_profile_data": true, @@ -89561,20 +89561,20 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5078.0", + "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -89588,7 +89588,7 @@ }, "test": "interactive_ui_tests", "test_id_prefix": "ninja://chrome/test:interactive_ui_tests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "merge": { @@ -89726,20 +89726,20 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -89752,7 +89752,7 @@ }, "test": "lacros_chrome_browsertests", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "args": [ @@ -89872,20 +89872,20 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -89898,7 +89898,7 @@ }, "test": "lacros_chrome_browsertests_run_in_series", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests_run_in_series/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "merge": { @@ -91394,20 +91394,20 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5078.0", + "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -91421,7 +91421,7 @@ }, "test": "interactive_ui_tests", "test_id_prefix": "ninja://chrome/test:interactive_ui_tests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "merge": { @@ -91559,20 +91559,20 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -91585,7 +91585,7 @@ }, "test": "lacros_chrome_browsertests", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "args": [ @@ -91705,20 +91705,20 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.lacros_chrome_browsertests.skew.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5078.0", + "name": "lacros_chrome_browsertests_run_in_series Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -91731,7 +91731,7 @@ }, "test": "lacros_chrome_browsertests_run_in_series", "test_id_prefix": "ninja://chrome/test:lacros_chrome_browsertests_run_in_series/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" }, { "merge": { @@ -92466,20 +92466,20 @@ { "args": [ "--test-launcher-filter-file=../../testing/buildbot/filters/linux-lacros.interactive_ui_tests.filter", - "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome" + "--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome" ], "merge": { "args": [], "script": "//testing/merge_scripts/standard_gtest_merge.py" }, - "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5078.0", + "name": "interactive_ui_tests Lacros version skew testing ash 104.0.5079.0", "swarming": { "can_use_on_swarming_builders": true, "cipd_packages": [ { "cipd_package": "chromium/testing/linux-ash-chromium/x86_64/ash.zip", - "location": "lacros_version_skew_tests_v104.0.5078.0", - "revision": "version:104.0.5078.0" + "location": "lacros_version_skew_tests_v104.0.5079.0", + "revision": "version:104.0.5079.0" } ], "dimension_sets": [ @@ -92492,7 +92492,7 @@ }, "test": "interactive_ui_tests", "test_id_prefix": "ninja://chrome/test:interactive_ui_tests/", - "variant_id": "Lacros version skew testing ash 104.0.5078.0" + "variant_id": "Lacros version skew testing ash 104.0.5079.0" } ] },
diff --git a/testing/buildbot/filters/pixel_tests.filter b/testing/buildbot/filters/pixel_tests.filter index 9d1fdc48..660f425 100644 --- a/testing/buildbot/filters/pixel_tests.filter +++ b/testing/buildbot/filters/pixel_tests.filter
@@ -53,7 +53,7 @@ PermissionRequestChipDialogBrowserTest.* *PermissionPromptBubbleViewBrowserTest.* PrivacySandboxDialogViewBrowserTest.* -PrivacySandboxNoticeBubbleViewBrowserTest.* +PrivacySandboxNoticeBubbleBrowserTest.* PromptForScanningModalDialogTest.* QRCodeGeneratorBubbleBrowserTest.* RelaunchRecommendedBubbleViewDialogTest.*
diff --git a/testing/buildbot/variants.pyl b/testing/buildbot/variants.pyl index ec5839c5..8b52509 100644 --- a/testing/buildbot/variants.pyl +++ b/testing/buildbot/variants.pyl
@@ -22,15 +22,15 @@ }, 'LACROS_VERSION_SKEW_CANARY': { 'args': [ - '--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5078.0/test_ash_chrome', + '--ash-chrome-path-override=../../lacros_version_skew_tests_v104.0.5079.0/test_ash_chrome', ], - 'identifier': 'Lacros version skew testing ash 104.0.5078.0', + 'identifier': 'Lacros version skew testing ash 104.0.5079.0', 'swarming': { 'cipd_packages': [ { 'cipd_package': 'chromium/testing/linux-ash-chromium/x86_64/ash.zip', - 'location': 'lacros_version_skew_tests_v104.0.5078.0', - 'revision': 'version:104.0.5078.0', + 'location': 'lacros_version_skew_tests_v104.0.5079.0', + 'revision': 'version:104.0.5079.0', }, ], },
diff --git a/testing/variations/fieldtrial_testing_config.json b/testing/variations/fieldtrial_testing_config.json index 746ac78..81b7058 100644 --- a/testing/variations/fieldtrial_testing_config.json +++ b/testing/variations/fieldtrial_testing_config.json
@@ -8777,7 +8777,7 @@ ], "experiments": [ { - "name": "Enabled,max_queue_time:75ms,_V2" + "name": "Enabled,max_queue_time:75ms,_V4" } ] }
diff --git a/third_party/blink/public/web/web_autofill_client.h b/third_party/blink/public/web/web_autofill_client.h index 5a7c10a8..c57df434 100644 --- a/third_party/blink/public/web/web_autofill_client.h +++ b/third_party/blink/public/web/web_autofill_client.h
@@ -38,6 +38,7 @@ class WebInputElement; class WebKeyboardEvent; class WebNode; +class WebString; class WebAutofillClient { public: @@ -62,6 +63,11 @@ virtual void DidAssociateFormControlsDynamically() {} virtual void AjaxSucceeded() {} + // Called when |element| is in autofilled state and the value has been changed + // by JavaScript. |old_value| contains the value before being changed. + virtual void JavaScriptChangedAutofilledValue( + const WebFormControlElement& element, + const WebString& old_value) {} virtual void DidCompleteFocusChangeInFrame() {} virtual void DidReceiveLeftMouseDownOrGestureTapInNode(const WebNode&) {}
diff --git a/third_party/blink/renderer/core/animation/css_length_interpolation_type.cc b/third_party/blink/renderer/core/animation/css_length_interpolation_type.cc index 7072b6b..7fa18338 100644 --- a/third_party/blink/renderer/core/animation/css_length_interpolation_type.cc +++ b/third_party/blink/renderer/core/animation/css_length_interpolation_type.cc
@@ -137,8 +137,8 @@ StyleResolverState& state) const { ComputedStyle& style = *state.Style(); float zoom = EffectiveZoom(style); - CSSToLengthConversionData conversion_data = state.CssToLengthConversionData(); - conversion_data.SetZoom(zoom); + CSSToLengthConversionData conversion_data = + state.CssToLengthConversionData().CopyWithAdjustedZoom(zoom); Length length = To<InterpolableLength>(interpolable_value) .CreateLength(conversion_data, value_range_); if (LengthPropertyFunctions::SetLength(CssProperty(), style, length)) {
diff --git a/third_party/blink/renderer/core/css/build.gni b/third_party/blink/renderer/core/css/build.gni index ea4f7d2..a4a8f4f 100644 --- a/third_party/blink/renderer/core/css/build.gni +++ b/third_party/blink/renderer/core/css/build.gni
@@ -707,6 +707,7 @@ "css_style_declaration_test.cc", "css_style_sheet_test.cc", "css_syntax_string_parser_test.cc", + "css_to_length_conversion_data_test.cc", "css_value_clamping_utils_test.cc", "cssom/computed_style_property_map_test.cc", "cssom/cross_thread_style_value_test.cc",
diff --git a/third_party/blink/renderer/core/css/css_container_values.cc b/third_party/blink/renderer/core/css/css_container_values.cc index 1f352d5d..6128db22 100644 --- a/third_party/blink/renderer/core/css/css_container_values.cc +++ b/third_party/blink/renderer/core/css/css_container_values.cc
@@ -18,7 +18,10 @@ width_(width), height_(height), writing_mode_(style.GetWritingMode()), - font_sizes_(&style, document.documentElement()->GetComputedStyle()) {} + font_sizes_(CSSToLengthConversionData::FontSizes( + &style, + document.documentElement()->GetComputedStyle()) + .Unzoomed()) {} float CSSContainerValues::EmSize() const { return font_sizes_.Em(); @@ -29,11 +32,11 @@ } float CSSContainerValues::ExSize() const { - return font_sizes_.Ex() / font_sizes_.Zoom(); + return font_sizes_.Ex(); } float CSSContainerValues::ChSize() const { - return font_sizes_.Ch() / font_sizes_.Zoom(); + return font_sizes_.Ch(); } } // namespace blink
diff --git a/third_party/blink/renderer/core/css/css_to_length_conversion_data.cc b/third_party/blink/renderer/core/css/css_to_length_conversion_data.cc index ab6fd70..d2fcee6 100644 --- a/third_party/blink/renderer/core/css/css_to_length_conversion_data.cc +++ b/third_party/blink/renderer/core/css/css_to_length_conversion_data.cc
@@ -102,18 +102,31 @@ DCHECK(font_data); if (!font_data || !font_data->GetFontMetrics().HasXHeight()) return em_ / 2.0f; - return font_data->GetFontMetrics().XHeight(); + // Font-metrics-based units already account for `zoom`. Therefore we need + // to unzoom using `zoom` first, if the zoom is adjusted. + float unzoom = (zoom_adjust_.has_value() ? zoom_ : 1.0f); + return font_data->GetFontMetrics().XHeight() / unzoom * + zoom_adjust_.value_or(1.0f); } float CSSToLengthConversionData::FontSizes::Ch() const { DCHECK(font_); const SimpleFontData* font_data = font_->PrimaryFont(); DCHECK(font_data); - return font_data ? font_data->GetFontMetrics().ZeroWidth() : 0; + // Font-metrics-based units already account for `zoom`. Therefore we need + // to unzoom using `zoom` first, if the zoom is adjusted. + float unzoom = (zoom_adjust_.has_value() ? zoom_ : 1.0f); + return font_data ? (font_data->GetFontMetrics().ZeroWidth() / unzoom * + zoom_adjust_.value_or(1.0f)) + : 0; } -float CSSToLengthConversionData::FontSizes::Zoom() const { - return zoom_ ? zoom_ : 1; +CSSToLengthConversionData::FontSizes +CSSToLengthConversionData::FontSizes::CopyWithAdjustedZoom( + float new_zoom) const { + FontSizes font_sizes = *this; + font_sizes.zoom_adjust_ = new_zoom; + return font_sizes; } CSSToLengthConversionData::ViewportSize::ViewportSize( @@ -188,7 +201,10 @@ font_sizes_(font_sizes), viewport_size_(viewport_size), container_sizes_(container_sizes), - zoom_(ClampTo<float>(zoom, std::numeric_limits<float>::denorm_min())) {} + zoom_(ClampTo<float>(zoom, std::numeric_limits<float>::denorm_min())) { + if (zoom_ != font_sizes_.zoom_) + font_sizes_ = font_sizes.CopyWithAdjustedZoom(zoom_); +} CSSToLengthConversionData::CSSToLengthConversionData( const ComputedStyle* style, @@ -553,19 +569,17 @@ case CSSPrimitiveValue::UnitType::kContainerMax: return value * ContainerMaxPercent() * Zoom(); - // We do not apply the zoom factor when we are computing the value of the - // font-size property. The zooming for font sizes is much more complicated, - // since we have to worry about enforcing the minimum font size preference - // as well as enforcing the implicit "smart minimum." + // Note that functions for font-relative units already account for the + // zoom factor. case CSSPrimitiveValue::UnitType::kEms: case CSSPrimitiveValue::UnitType::kQuirkyEms: - return value * EmFontSize() * Zoom(); + return value * EmFontSize(); case CSSPrimitiveValue::UnitType::kExs: return value * ExFontSize(); case CSSPrimitiveValue::UnitType::kRems: - return value * RemFontSize() * Zoom(); + return value * RemFontSize(); case CSSPrimitiveValue::UnitType::kChs: return value * ChFontSize();
diff --git a/third_party/blink/renderer/core/css/css_to_length_conversion_data.h b/third_party/blink/renderer/core/css/css_to_length_conversion_data.h index ca8ce3b..eb106aa2 100644 --- a/third_party/blink/renderer/core/css/css_to_length_conversion_data.h +++ b/third_party/blink/renderer/core/css/css_to_length_conversion_data.h
@@ -55,21 +55,27 @@ DISALLOW_NEW(); public: - FontSizes() : em_(0), rem_(0), font_(nullptr), zoom_(1) {} + FontSizes() = default; FontSizes(float em, float rem, const Font*, float zoom); FontSizes(const ComputedStyle*, const ComputedStyle* root_style); - float Em() const { return em_; } - float Rem() const { return rem_; } - float Zoom() const; + FontSizes Unzoomed() const { return CopyWithAdjustedZoom(1.0f); } + + float Em() const { return em_ * zoom_adjust_.value_or(zoom_); } + float Rem() const { return rem_ * zoom_adjust_.value_or(zoom_); } float Ex() const; float Ch() const; private: - float em_; - float rem_; - const Font* font_; - float zoom_; + friend class CSSToLengthConversionData; + + FontSizes CopyWithAdjustedZoom(float new_zoom) const; + + float em_ = 0; + float rem_ = 0; + const Font* font_ = nullptr; + float zoom_ = 1; + absl::optional<float> zoom_adjust_; }; class CORE_EXPORT ViewportSize { @@ -172,7 +178,6 @@ float RemFontSize() const; float ExFontSize() const; float ChFontSize() const; - float FontSizeZoom() const { return font_sizes_.Zoom(); } // Accessing these marks the style as having viewport units double ViewportWidthPercent() const; @@ -226,6 +231,9 @@ viewport_size_, container_sizes_, new_zoom); } + CSSToLengthConversionData Unzoomed() const { + return CopyWithAdjustedZoom(1.0f); + } double ZoomedComputedPixels(double value, CSSPrimitiveValue::UnitType) const;
diff --git a/third_party/blink/renderer/core/css/css_to_length_conversion_data_test.cc b/third_party/blink/renderer/core/css/css_to_length_conversion_data_test.cc new file mode 100644 index 0000000..1f42c87 --- /dev/null +++ b/third_party/blink/renderer/core/css/css_to_length_conversion_data_test.cc
@@ -0,0 +1,114 @@ +// Copyright 2022 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/core/css/css_to_length_conversion_data.h" +#include "third_party/abseil-cpp/absl/types/optional.h" +#include "third_party/blink/renderer/core/css/css_primitive_value.h" +#include "third_party/blink/renderer/core/css/css_test_helpers.h" +#include "third_party/blink/renderer/core/dom/document.h" +#include "third_party/blink/renderer/core/dom/element.h" +#include "third_party/blink/renderer/core/dom/node_computed_style.h" +#include "third_party/blink/renderer/core/html/html_div_element.h" +#include "third_party/blink/renderer/core/style/computed_style.h" +#include "third_party/blink/renderer/core/testing/page_test_base.h" +#include "third_party/blink/renderer/platform/geometry/length.h" + +namespace blink { + +class CSSToLengthConversionDataTest : public PageTestBase { + public: + void SetUp() override { + PageTestBase::SetUp(); + LoadAhem(); + } + + // Set up a page with "Ahem 10px" as :root, and "Ahem 20px" at some <div>, + // then return a CSSToLengthConversionData constructed from that. + // + // css_zoom - The zoom to apply to :root. + // data_zoom - The zoom to pass to the CSSToLengthConversionData constructor. + CSSToLengthConversionData ConversionData( + absl::optional<float> css_zoom = absl::nullopt, + absl::optional<float> data_zoom = absl::nullopt) { + Element* root = GetDocument().documentElement(); + DCHECK(root); + if (css_zoom.has_value()) { + root->SetInlineStyleProperty(CSSPropertyID::kZoom, + String::Format("%f", *css_zoom)); + } + root->SetInlineStyleProperty(CSSPropertyID::kFontSize, "10px"); + root->SetInlineStyleProperty(CSSPropertyID::kFontFamily, "Ahem"); + auto* div = MakeGarbageCollected<HTMLDivElement>(GetDocument()); + div->SetInlineStyleProperty(CSSPropertyID::kFontSize, "20px"); + GetDocument().body()->AppendChild(div); + UpdateAllLifecyclePhasesForTest(); + return CSSToLengthConversionData( + div->GetComputedStyle(), root->GetComputedStyle(), + GetDocument().GetLayoutView(), + CSSToLengthConversionData::ContainerSizes(), + data_zoom.value_or(div->GetComputedStyle()->EffectiveZoom())); + } + + float Convert(const CSSToLengthConversionData& data, String value) { + auto* primitive_value = DynamicTo<CSSPrimitiveValue>( + css_test_helpers::ParseValue(GetDocument(), "<length>", value)); + DCHECK(primitive_value); + return primitive_value->ConvertToLength(data).Pixels(); + } +}; + +TEST_F(CSSToLengthConversionDataTest, Normal) { + CSSToLengthConversionData data = ConversionData(); + EXPECT_FLOAT_EQ(1.0f, Convert(data, "1px")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1em")); + EXPECT_FLOAT_EQ(16.0f, Convert(data, "1ex")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1ch")); + EXPECT_FLOAT_EQ(10.0f, Convert(data, "1rem")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1em")); + EXPECT_FLOAT_EQ(36.0f, Convert(data, "calc(1em + 1ex)")); +} + +TEST_F(CSSToLengthConversionDataTest, Zoomed) { + CSSToLengthConversionData data = ConversionData(2.0f); + EXPECT_FLOAT_EQ(2.0f, Convert(data, "1px")); + EXPECT_FLOAT_EQ(40.0f, Convert(data, "1em")); + EXPECT_FLOAT_EQ(32.0f, Convert(data, "1ex")); + EXPECT_FLOAT_EQ(40.0f, Convert(data, "1ch")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1rem")); + EXPECT_FLOAT_EQ(72.0f, Convert(data, "calc(1em + 1ex)")); +} + +TEST_F(CSSToLengthConversionDataTest, AdjustedZoom) { + CSSToLengthConversionData data = ConversionData().CopyWithAdjustedZoom(2.0f); + EXPECT_FLOAT_EQ(2.0f, Convert(data, "1px")); + EXPECT_FLOAT_EQ(40.0f, Convert(data, "1em")); + EXPECT_FLOAT_EQ(32.0f, Convert(data, "1ex")); + EXPECT_FLOAT_EQ(40.0f, Convert(data, "1ch")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1rem")); + EXPECT_FLOAT_EQ(72.0f, Convert(data, "calc(1em + 1ex)")); +} + +TEST_F(CSSToLengthConversionDataTest, DifferentZoom) { + // The zoom used to calculate fonts is different from the requested + // zoom in the CSSToLengthConversionData constructor. + CSSToLengthConversionData data = ConversionData(1.0f, 2.0f); + EXPECT_FLOAT_EQ(2.0f, Convert(data, "1px")); + EXPECT_FLOAT_EQ(40.0f, Convert(data, "1em")); + EXPECT_FLOAT_EQ(32.0f, Convert(data, "1ex")); + EXPECT_FLOAT_EQ(40.0f, Convert(data, "1ch")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1rem")); + EXPECT_FLOAT_EQ(72.0f, Convert(data, "calc(1em + 1ex)")); +} + +TEST_F(CSSToLengthConversionDataTest, Unzoomed) { + CSSToLengthConversionData data = ConversionData(2.0f).Unzoomed(); + EXPECT_FLOAT_EQ(1.0f, Convert(data, "1px")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1em")); + EXPECT_FLOAT_EQ(16.0f, Convert(data, "1ex")); + EXPECT_FLOAT_EQ(20.0f, Convert(data, "1ch")); + EXPECT_FLOAT_EQ(10.0f, Convert(data, "1rem")); + EXPECT_FLOAT_EQ(36.0f, Convert(data, "calc(1em + 1ex)")); +} + +} // namespace blink
diff --git a/third_party/blink/renderer/core/css/media_values.cc b/third_party/blink/renderer/core/css/media_values.cc index e860739..f0325a5 100644 --- a/third_party/blink/renderer/core/css/media_values.cc +++ b/third_party/blink/renderer/core/css/media_values.cc
@@ -261,10 +261,9 @@ DCHECK(frame->GetDocument()); const ComputedStyle* style = frame->GetDocument()->GetComputedStyle(); DCHECK(style); - CSSToLengthConversionData::FontSizes font_sizes(style, style); // Font metrics are based on the used font which is scaled to match the size // of CSS pixels. Need to scale back to CSS pixels. - return font_sizes.Ex() / font_sizes.Zoom(); + return CSSToLengthConversionData::FontSizes(style, style).Unzoomed().Ex(); } float MediaValues::CalculateChSize(LocalFrame* frame) { @@ -272,10 +271,9 @@ DCHECK(frame->GetDocument()); const ComputedStyle* style = frame->GetDocument()->GetComputedStyle(); DCHECK(style); - CSSToLengthConversionData::FontSizes font_sizes(style, style); // Font metrics are based on the used font which is scaled to match the size // of CSS pixels. Need to scale back to CSS pixels. - return font_sizes.Ch() / font_sizes.Zoom(); + return CSSToLengthConversionData::FontSizes(style, style).Unzoomed().Ch(); } const String MediaValues::CalculateMediaType(LocalFrame* frame) {
diff --git a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc index 374e818..c17170da 100644 --- a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc
@@ -6620,12 +6620,13 @@ const CSSValue& second = list.Item(1); auto* first_primitive_value = DynamicTo<CSSPrimitiveValue>(first); if (first_primitive_value && first_primitive_value->IsLength()) { + CSSToLengthConversionData unzoomed_conversion_data = + state.CssToLengthConversionData().Unzoomed(); // <length>{2} size = gfx::SizeF( - first_primitive_value->ComputeLength<float>( - state.CssToLengthConversionData().CopyWithAdjustedZoom(1.0)), + first_primitive_value->ComputeLength<float>(unzoomed_conversion_data), To<CSSPrimitiveValue>(second).ComputeLength<float>( - state.CssToLengthConversionData().CopyWithAdjustedZoom(1.0))); + unzoomed_conversion_data)); } else { // <page-size> <orientation> size = GetPageSizeFromName(To<CSSIdentifierValue>(first)); @@ -6647,7 +6648,7 @@ // <length> page_size_type = PageSizeType::kFixed; float width = first_primitive_value->ComputeLength<float>( - state.CssToLengthConversionData().CopyWithAdjustedZoom(1.0)); + state.CssToLengthConversionData().Unzoomed()); size = gfx::SizeF(width, width); } else { const auto& ident = To<CSSIdentifierValue>(first);
diff --git a/third_party/blink/renderer/core/css/resolver/cascade_map.cc b/third_party/blink/renderer/core/css/resolver/cascade_map.cc index 033f19d..12457bd7 100644 --- a/third_party/blink/renderer/core/css/resolver/cascade_map.cc +++ b/third_party/blink/renderer/core/css/resolver/cascade_map.cc
@@ -65,6 +65,10 @@ return find_origin(native_properties_.Buffer()[index], origin); } +CascadePriority& CascadeMap::Top(CascadePriorityList& list) { + return list.Top(backing_vector_); +} + const CascadePriority* CascadeMap::FindRevertLayer( const CSSPropertyName& name, CascadePriority revert_from) const {
diff --git a/third_party/blink/renderer/core/css/resolver/cascade_map.h b/third_party/blink/renderer/core/css/resolver/cascade_map.h index 962fee4..8ffce0d 100644 --- a/third_party/blink/renderer/core/css/resolver/cascade_map.h +++ b/third_party/blink/renderer/core/css/resolver/cascade_map.h
@@ -23,6 +23,8 @@ STACK_ALLOCATED(); public: + class CascadePriorityList; + // Get the CascadePriority for the given CSSPropertyName. If there is no // entry for the given name, CascadePriority() is returned. CascadePriority At(const CSSPropertyName&) const; @@ -50,6 +52,8 @@ // layers below the given priority. const CascadePriority* FindRevertLayer(const CSSPropertyName&, CascadePriority) const; + // Similar to Find(), if you already have the right CascadePriorityList. + CascadePriority& Top(CascadePriorityList&); // Adds an entry to the map if the incoming priority is greater than or equal // to the current priority for the same name. Entries must be added in non- // decreasing lexicographical order of (origin, tree scope, layer). @@ -168,6 +172,7 @@ using CustomMap = HashMap<CSSPropertyName, CascadePriorityList>; const CustomMap& GetCustomMap() const { return custom_properties_; } + CustomMap& GetCustomMap() { return custom_properties_; } private: uint64_t high_priority_ = 0;
diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc index efaeda2..87c44bf5 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc
@@ -437,24 +437,11 @@ static float ComputeFontSize(const CSSToLengthConversionData& conversion_data, const CSSPrimitiveValue& primitive_value, const FontDescription::Size& parent_size) { - if (primitive_value.IsLength()) { - float result = primitive_value.ComputeLength<float>(conversion_data); - float font_size_zoom = conversion_data.FontSizeZoom(); - // TODO(crbug.com/408777): Only accounting for numeric literal value here - // will leave calc() without zoom correction. - if (primitive_value.IsNumericLiteralValue() && font_size_zoom != 1) { - CSSPrimitiveValue::UnitType type = - To<CSSNumericLiteralValue>(&primitive_value)->GetType(); - if (type == CSSPrimitiveValue::UnitType::kChs || - type == CSSPrimitiveValue::UnitType::kExs) { - return result / font_size_zoom; - } - } - return result; - } + if (primitive_value.IsLength()) + return primitive_value.ComputeLength<float>(conversion_data); if (primitive_value.IsCalculated()) { return To<CSSMathFunctionValue>(primitive_value) - .ToCalcValue(conversion_data) + .ToCalcValue(conversion_data.Unzoomed()) ->Evaluate(parent_size.value); } NOTREACHED(); @@ -2090,7 +2077,7 @@ primitive_value->IsCalculatedPercentageWithLength()) { // Instead of the actual zoom, use 1 to avoid potential rounding errors Length length = primitive_value->ConvertToLength( - css_to_length_conversion_data.CopyWithAdjustedZoom(1)); + css_to_length_conversion_data.Unzoomed()); return *CSSPrimitiveValue::CreateFromLength(length, 1); }
diff --git a/third_party/blink/renderer/core/css/resolver/style_cascade.cc b/third_party/blink/renderer/core/css/resolver/style_cascade.cc index 3463360..c97d6e4c 100644 --- a/third_party/blink/renderer/core/css/resolver/style_cascade.cc +++ b/third_party/blink/renderer/core/css/resolver/style_cascade.cc
@@ -479,10 +479,6 @@ // (e.g. in AnalyzeMatchResult()) and actually apply them. We need to do this // in a second phase so that we know which ones actually won the cascade // before we start applying, as some properties can affect others. -// -// TODO(sesse): See if we can make this more efficient by iterating -// directly over the BackingVector instead. In particular, that would -// remove the Find() calls into map_. void StyleCascade::ApplyMatchResult(CascadeResolver& resolver) { // We only need to apply the resolver part of the filter here; // the rest have been applied in the previous pass. @@ -507,8 +503,8 @@ LookupAndApplyDeclaration(property, p, resolver); } - for (const auto& [name, priority_list] : map_.GetCustomMap()) { - CascadePriority* p = map_.Find(name); + for (auto& [name, priority_list] : map_.GetCustomMap()) { + CascadePriority* p = &map_.Top(priority_list); CascadePriority priority = *p; if (priority.GetGeneration() >= resolver.generation_) { continue;
diff --git a/third_party/blink/renderer/core/css/rule_set.cc b/third_party/blink/renderer/core/css/rule_set.cc index 3951516f..2d8ccd1 100644 --- a/third_party/blink/renderer/core/css/rule_set.cc +++ b/third_party/blink/renderer/core/css/rule_set.cc
@@ -148,13 +148,13 @@ } void RuleSet::AddToRuleSet(const AtomicString& key, - PendingRuleMap& map, + RuleMap& map, const RuleData* rule_data) { - Member<HeapLinkedStack<Member<const RuleData>>>& rules = + Member<HeapVector<Member<const RuleData>>>& rules = map.insert(key, nullptr).stored_value->value; if (!rules) - rules = MakeGarbageCollected<HeapLinkedStack<Member<const RuleData>>>(); - rules->Push(rule_data); + rules = MakeGarbageCollected<HeapVector<Member<const RuleData>>>(); + rules->push_back(rule_data); } static void ExtractSelectorValues(const CSSSelector* selector, @@ -288,17 +288,20 @@ // Prefer rule sets in order of most likely to apply infrequently. if (!id.IsEmpty()) { - AddToRuleSet(id, EnsurePendingRules()->id_rules, rule_data); + need_compaction_ = true; + AddToRuleSet(id, id_rules_, rule_data); return true; } if (!class_name.IsEmpty()) { - AddToRuleSet(class_name, EnsurePendingRules()->class_rules, rule_data); + need_compaction_ = true; + AddToRuleSet(class_name, class_rules_, rule_data); return true; } if (!attr_name.IsEmpty()) { - AddToRuleSet(attr_name, EnsurePendingRules()->attr_rules, rule_data); + need_compaction_ = true; + AddToRuleSet(attr_name, attr_rules_, rule_data); if (attr_name == html_names::kStyleAttr) { has_bucket_for_style_attr_ = true; } @@ -310,10 +313,10 @@ // and have a relation of ShadowPseudo between them. Therefore we should // never be a situation where ExtractSelectorValues finds id and // className in addition to custom pseudo. + need_compaction_ = true; DCHECK(id.IsEmpty()); DCHECK(class_name.IsEmpty()); - AddToRuleSet(custom_pseudo_element_name, - EnsurePendingRules()->ua_shadow_pseudo_element_rules, + AddToRuleSet(custom_pseudo_element_name, ua_shadow_pseudo_element_rules_, rule_data); return true; } @@ -348,6 +351,7 @@ case CSSSelector::kPseudoPlaceholder: case CSSSelector::kPseudoFileSelectorButton: if (it->FollowsPart()) { + need_compaction_ = true; part_pseudo_rules_.push_back(rule_data); } else if (it->FollowsSlotted()) { slotted_pseudo_element_rules_.push_back(rule_data); @@ -355,8 +359,8 @@ const auto& name = pseudo_type == CSSSelector::kPseudoFileSelectorButton ? shadow_element_names::kPseudoFileUploadButton : shadow_element_names::kPseudoInputPlaceholder; - AddToRuleSet(name, EnsurePendingRules()->ua_shadow_pseudo_element_rules, - rule_data); + need_compaction_ = true; + AddToRuleSet(name, ua_shadow_pseudo_element_rules_, rule_data); } return true; case CSSSelector::kPseudoHost: @@ -371,7 +375,8 @@ } if (!tag_name.IsEmpty()) { - AddToRuleSet(tag_name, EnsurePendingRules()->tag_rules, rule_data); + need_compaction_ = true; + AddToRuleSet(tag_name, tag_rules_, rule_data); return true; } @@ -437,38 +442,37 @@ } void RuleSet::AddPageRule(StyleRulePage* rule) { - EnsurePendingRules(); // So that page_rules_.ShrinkToFit() gets called. + need_compaction_ = true; page_rules_.push_back(rule); } void RuleSet::AddFontFaceRule(StyleRuleFontFace* rule) { - EnsurePendingRules(); // So that font_face_rules_.ShrinkToFit() gets called. + need_compaction_ = true; font_face_rules_.push_back(rule); } void RuleSet::AddKeyframesRule(StyleRuleKeyframes* rule) { - EnsurePendingRules(); // So that keyframes_rules_.ShrinkToFit() gets called. + need_compaction_ = true; keyframes_rules_.push_back(rule); } void RuleSet::AddPropertyRule(StyleRuleProperty* rule) { - EnsurePendingRules(); // So that property_rules_.ShrinkToFit() gets called. + need_compaction_ = true; property_rules_.push_back(rule); } void RuleSet::AddCounterStyleRule(StyleRuleCounterStyle* rule) { - EnsurePendingRules(); // So that counter_style_rules_.ShrinkToFit() gets - // called. + need_compaction_ = true; counter_style_rules_.push_back(rule); } void RuleSet::AddFontPaletteValuesRule(StyleRuleFontPaletteValues* rule) { - EnsurePendingRules(); + need_compaction_ = true; font_palette_values_rules_.push_back(rule); } void RuleSet::AddScrollTimelineRule(StyleRuleScrollTimeline* rule) { - EnsurePendingRules(); // So that property_rules_.ShrinkToFit() gets called. + need_compaction_ = true; scroll_timeline_rules_.push_back(rule); } @@ -618,28 +622,9 @@ return cascade_layer->GetOrAddSubLayer(name); } -void RuleSet::CompactPendingRules(PendingRuleMap& pending_map, - CompactRuleMap& compact_map) { - for (auto& item : pending_map) { - HeapLinkedStack<Member<const RuleData>>* pending_rules = - item.value.Release(); - Member<HeapVector<Member<const RuleData>>>& rules = - compact_map.insert(item.key, nullptr).stored_value->value; - if (!rules) { - rules = MakeGarbageCollected<HeapVector<Member<const RuleData>>>(); - rules->ReserveInitialCapacity(pending_rules->size()); - } else { - rules->ReserveCapacity(pending_rules->size()); - } - // Since pending_rules is a stack, we need to insert in the reversed - // ordering so that the resulting vector is sorted by rule position - wtf_size_t num_pending_rules = pending_rules->size(); - rules->Grow(rules->size() + num_pending_rules); - for (auto iter = rules->rbegin(); !pending_rules->IsEmpty(); ++iter) { - DCHECK(iter != rules->rend()); - *iter = pending_rules->Peek(); - pending_rules->Pop(); - } +void RuleSet::CompactRuleMap(RuleMap& map) { + for (auto& [key, value] : map) { + value->ShrinkToFit(); } } @@ -665,7 +650,6 @@ const HeapVector<Member<const RuleData>>* list, const AtomicString& key, const AtomicString& value) const { - DCHECK(!pending_rules_); DCHECK_EQ(attr_rules_.find(key)->value, list); if (list->size() < GetMinimumRulesetSizeForSubstringMatcher()) { // Too small to build up a tree, so always check. @@ -688,7 +672,7 @@ } void RuleSet::CreateSubstringMatchers( - CompactRuleMap& attr_map, + RuleMap& attr_map, RuleSet::SubstringMatcherMap& substring_matcher_map) { for (const auto& [/*AtomicString*/ attr, /*Member<RuleSet>*/ ruleset] : attr_map) { @@ -744,15 +728,13 @@ } void RuleSet::CompactRules() { - DCHECK(pending_rules_); - PendingRuleMaps* pending_rules = pending_rules_.Release(); - CompactPendingRules(pending_rules->id_rules, id_rules_); - CompactPendingRules(pending_rules->class_rules, class_rules_); - CompactPendingRules(pending_rules->attr_rules, attr_rules_); + DCHECK(need_compaction_); + CompactRuleMap(id_rules_); + CompactRuleMap(class_rules_); + CompactRuleMap(attr_rules_); CreateSubstringMatchers(attr_rules_, attr_substring_matchers_); - CompactPendingRules(pending_rules->tag_rules, tag_rules_); - CompactPendingRules(pending_rules->ua_shadow_pseudo_element_rules, - ua_shadow_pseudo_element_rules_); + CompactRuleMap(tag_rules_); + CompactRuleMap(ua_shadow_pseudo_element_rules_); link_pseudo_class_rules_.ShrinkToFit(); cue_pseudo_rules_.ShrinkToFit(); focus_pseudo_class_rules_.ShrinkToFit(); @@ -776,6 +758,7 @@ #if EXPENSIVE_DCHECKS_ARE_ON() AssertRuleListsSorted(); #endif + need_compaction_ = false; } #if EXPENSIVE_DCHECKS_ARE_ON() @@ -885,14 +868,6 @@ visitor->Trace(style_scope_); } -void RuleSet::PendingRuleMaps::Trace(Visitor* visitor) const { - visitor->Trace(id_rules); - visitor->Trace(class_rules); - visitor->Trace(attr_rules); - visitor->Trace(tag_rules); - visitor->Trace(ua_shadow_pseudo_element_rules); -} - void RuleSet::LayerInterval::Trace(Visitor* visitor) const { visitor->Trace(layer); } @@ -921,7 +896,6 @@ visitor->Trace(property_rules_); visitor->Trace(counter_style_rules_); visitor->Trace(scroll_timeline_rules_); - visitor->Trace(pending_rules_); visitor->Trace(implicit_outer_layer_); visitor->Trace(layer_intervals_); #ifndef NDEBUG
diff --git a/third_party/blink/renderer/core/css/rule_set.h b/third_party/blink/renderer/core/css/rule_set.h index 05b5e501..c4103d6c 100644 --- a/third_party/blink/renderer/core/css/rule_set.h +++ b/third_party/blink/renderer/core/css/rule_set.h
@@ -244,20 +244,17 @@ const HeapVector<Member<const RuleData>>* IdRules( const AtomicString& key) const { - DCHECK(!pending_rules_); auto it = id_rules_.find(key); return it != id_rules_.end() ? it->value : nullptr; } const HeapVector<Member<const RuleData>>* ClassRules( const AtomicString& key) const { - DCHECK(!pending_rules_); auto it = class_rules_.find(key); return it != class_rules_.end() ? it->value : nullptr; } bool HasAnyAttrRules() const { return !attr_rules_.IsEmpty(); } const HeapVector<Member<const RuleData>>* AttrRules( const AtomicString& key) const { - DCHECK(!pending_rules_); auto it = attr_rules_.find(key); return it != attr_rules_.end() ? it->value : nullptr; } @@ -266,61 +263,48 @@ const AtomicString& value) const; const HeapVector<Member<const RuleData>>* TagRules( const AtomicString& key) const { - DCHECK(!pending_rules_); auto it = tag_rules_.find(key); return it != tag_rules_.end() ? it->value : nullptr; } const HeapVector<Member<const RuleData>>* UAShadowPseudoElementRules( const AtomicString& key) const { - DCHECK(!pending_rules_); auto it = ua_shadow_pseudo_element_rules_.find(key); return it != ua_shadow_pseudo_element_rules_.end() ? it->value : nullptr; } const HeapVector<Member<const RuleData>>* LinkPseudoClassRules() const { - DCHECK(!pending_rules_); return &link_pseudo_class_rules_; } const HeapVector<Member<const RuleData>>* CuePseudoRules() const { - DCHECK(!pending_rules_); return &cue_pseudo_rules_; } const HeapVector<Member<const RuleData>>* FocusPseudoClassRules() const { - DCHECK(!pending_rules_); return &focus_pseudo_class_rules_; } const HeapVector<Member<const RuleData>>* FocusVisiblePseudoClassRules() const { - DCHECK(!pending_rules_); return &focus_visible_pseudo_class_rules_; } const HeapVector<Member<const RuleData>>* SpatialNavigationInterestPseudoClassRules() const { - DCHECK(!pending_rules_); return &spatial_navigation_interest_class_rules_; } const HeapVector<Member<const RuleData>>* UniversalRules() const { - DCHECK(!pending_rules_); return &universal_rules_; } const HeapVector<Member<const RuleData>>* ShadowHostRules() const { - DCHECK(!pending_rules_); return &shadow_host_rules_; } const HeapVector<Member<const RuleData>>* PartPseudoRules() const { - DCHECK(!pending_rules_); return &part_pseudo_rules_; } const HeapVector<Member<const RuleData>>* VisitedDependentRules() const { - DCHECK(!pending_rules_); return &visited_dependent_rules_; } const HeapVector<Member<const RuleData>>* SelectorFragmentAnchorRules() const { - DCHECK(!pending_rules_); return &selector_fragment_anchor_rules_; } const HeapVector<Member<StyleRulePage>>& PageRules() const { - DCHECK(!pending_rules_); return page_rules_; } const HeapVector<Member<StyleRuleFontFace>>& FontFaceRules() const { @@ -344,7 +328,6 @@ return scroll_timeline_rules_; } const HeapVector<Member<const RuleData>>* SlottedPseudoElementRules() const { - DCHECK(!pending_rules_); return &slotted_pseudo_element_rules_; } @@ -357,9 +340,8 @@ unsigned RuleCount() const { return rule_count_; } void CompactRulesIfNeeded() { - if (!pending_rules_) - return; - CompactRules(); + if (need_compaction_) + CompactRules(); } bool HasSlottedRules() const { @@ -403,15 +385,12 @@ FRIEND_TEST_ALL_PREFIXES(RuleSetTest, RuleCountNotIncreasedByInvalidRuleData); friend class RuleSetCascadeLayerTest; - using PendingRuleMap = - HeapHashMap<AtomicString, - Member<HeapLinkedStack<Member<const RuleData>>>>; - using CompactRuleMap = + using RuleMap = HeapHashMap<AtomicString, Member<HeapVector<Member<const RuleData>>>>; using SubstringMatcherMap = HashMap<AtomicString, std::unique_ptr<base::SubstringSetMatcher>>; - void AddToRuleSet(const AtomicString& key, PendingRuleMap&, const RuleData*); + void AddToRuleSet(const AtomicString& key, RuleMap&, const RuleData*); void AddPageRule(StyleRulePage*); void AddViewportRule(StyleRuleViewport*); void AddFontFaceRule(StyleRuleFontFace*); @@ -440,30 +419,11 @@ void SortKeyframesRulesIfNeeded(); void CompactRules(); - static void CompactPendingRules(PendingRuleMap&, CompactRuleMap&); + static void CompactRuleMap(RuleMap&); static void CreateSubstringMatchers( - CompactRuleMap& attr_map, + RuleMap& attr_map, SubstringMatcherMap& substring_matcher_map); - class PendingRuleMaps : public GarbageCollected<PendingRuleMaps> { - public: - PendingRuleMaps() = default; - - PendingRuleMap id_rules; - PendingRuleMap class_rules; - PendingRuleMap attr_rules; - PendingRuleMap tag_rules; - PendingRuleMap ua_shadow_pseudo_element_rules; - - void Trace(Visitor*) const; - }; - - PendingRuleMaps* EnsurePendingRules() { - if (!pending_rules_) - pending_rules_ = MakeGarbageCollected<PendingRuleMaps>(); - return pending_rules_.Get(); - } - #if DCHECK_IS_ON() void AssertRuleListsSorted() const; #endif @@ -481,9 +441,9 @@ // May return nullptr for the implicit outer layer. const CascadeLayer* GetLayerForTest(const RuleData&) const; - CompactRuleMap id_rules_; - CompactRuleMap class_rules_; - CompactRuleMap attr_rules_; + RuleMap id_rules_; + RuleMap class_rules_; + RuleMap attr_rules_; // A structure for quickly rejecting an entire attribute rule set // (from attr_rules_). If we have many rules in the same bucket, // we build up a case-insensitive substring-matching structure of all @@ -506,8 +466,8 @@ // doing a simple match.) Check GetMinimumRulesetSizeForSubstringMatcher() // before looking up for a cheaper test. SubstringMatcherMap attr_substring_matchers_; - CompactRuleMap tag_rules_; - CompactRuleMap ua_shadow_pseudo_element_rules_; + RuleMap tag_rules_; + RuleMap ua_shadow_pseudo_element_rules_; HeapVector<Member<const RuleData>> link_pseudo_class_rules_; HeapVector<Member<const RuleData>> cue_pseudo_rules_; HeapVector<Member<const RuleData>> focus_pseudo_class_rules_; @@ -536,7 +496,7 @@ bool has_bucket_for_style_attr_ = false; unsigned rule_count_ = 0; - Member<PendingRuleMaps> pending_rules_; + bool need_compaction_ = false; // nullptr if the stylesheet doesn't explicitly declare any layer. Member<CascadeLayer> implicit_outer_layer_;
diff --git a/third_party/blink/renderer/core/html/forms/html_input_element.cc b/third_party/blink/renderer/core/html/forms/html_input_element.cc index e0f40b15..bb76480b 100644 --- a/third_party/blink/renderer/core/html/forms/html_input_element.cc +++ b/third_party/blink/renderer/core/html/forms/html_input_element.cc
@@ -1181,9 +1181,8 @@ needs_to_update_view_value_ = false; } -void HTMLInputElement::setValue(const String& value, - ExceptionState& exception_state, - TextFieldEventBehavior event_behavior) { +void HTMLInputElement::setValueForBinding(const String& value, + ExceptionState& exception_state) { // FIXME: Remove type check. if (type() == input_type_names::kFile && !value.IsEmpty()) { exception_state.ThrowDOMException(DOMExceptionCode::kInvalidStateError, @@ -1192,7 +1191,17 @@ "to the empty string."); return; } - setValue(value, event_behavior); + + if (GetAutofillState() != WebAutofillState::kAutofilled) { + setValue(value); + } else { + String old_value = this->value(); + setValue(value); + if (Page* page = GetDocument().GetPage()) { + page->GetChromeClient().JavaScriptChangedAutofilledValue(*this, + old_value); + } + } } void HTMLInputElement::setValue(const String& value,
diff --git a/third_party/blink/renderer/core/html/forms/html_input_element.h b/third_party/blink/renderer/core/html/forms/html_input_element.h index d662e8c..3f41dadd 100644 --- a/third_party/blink/renderer/core/html/forms/html_input_element.h +++ b/third_party/blink/renderer/core/html/forms/html_input_element.h
@@ -141,13 +141,11 @@ String value() const override; void setValue( const String&, - ExceptionState&, - TextFieldEventBehavior = TextFieldEventBehavior::kDispatchNoEvent); - void setValue( - const String&, TextFieldEventBehavior = TextFieldEventBehavior::kDispatchNoEvent, TextControlSetValueSelection = TextControlSetValueSelection::kSetSelectionToEnd) override; + String valueForBinding() const { return value(); } + void setValueForBinding(const String&, ExceptionState&); void SetValueForUser(const String&); // Update the value, and clear hasDirtyValue() flag. void SetNonDirtyValue(const String&);
diff --git a/third_party/blink/renderer/core/html/forms/html_input_element.idl b/third_party/blink/renderer/core/html/forms/html_input_element.idl index 36b3b91..ef1ddd0 100644 --- a/third_party/blink/renderer/core/html/forms/html_input_element.idl +++ b/third_party/blink/renderer/core/html/forms/html_input_element.idl
@@ -62,7 +62,7 @@ [CEReactions, Reflect] attribute DOMString step; [CEReactions] attribute DOMString type; [CEReactions, Reflect=value] attribute DOMString defaultValue; - [CEReactions, RaisesException=Setter] attribute [TreatNullAs=EmptyString] DOMString value; + [CEReactions, ImplementedAs=valueForBinding, RaisesException=Setter] attribute [TreatNullAs=EmptyString] DOMString value; [CEReactions, RaisesException=Setter, CallWith=ScriptState] attribute object? valueAsDate; [RaisesException=Setter] attribute unrestricted double valueAsNumber; // Note: The spec has valueLow and valueHigh for two-valued range controls.
diff --git a/third_party/blink/renderer/core/html/forms/html_select_element.cc b/third_party/blink/renderer/core/html/forms/html_select_element.cc index 38c1170..5f87c64 100644 --- a/third_party/blink/renderer/core/html/forms/html_select_element.cc +++ b/third_party/blink/renderer/core/html/forms/html_select_element.cc
@@ -283,6 +283,19 @@ return ""; } +void HTMLSelectElement::setValueForBinding(const String& value) { + if (GetAutofillState() != WebAutofillState::kAutofilled) { + setValue(value); + } else { + String old_value = this->value(); + setValue(value); + if (Page* page = GetDocument().GetPage()) { + page->GetChromeClient().JavaScriptChangedAutofilledValue(*this, + old_value); + } + } +} + void HTMLSelectElement::setValue(const String& value, bool send_events) { HTMLOptionElement* option = nullptr; // Find the option with value() matching the given parameter and make it the
diff --git a/third_party/blink/renderer/core/html/forms/html_select_element.h b/third_party/blink/renderer/core/html/forms/html_select_element.h index d31cc92..a480111 100644 --- a/third_party/blink/renderer/core/html/forms/html_select_element.h +++ b/third_party/blink/renderer/core/html/forms/html_select_element.h
@@ -94,6 +94,8 @@ String value() const; void setValue(const String&, bool send_events = false); + String valueForBinding() const { return value(); } + void setValueForBinding(const String&); String SuggestedValue() const; void SetSuggestedValue(const String&);
diff --git a/third_party/blink/renderer/core/html/forms/html_select_element.idl b/third_party/blink/renderer/core/html/forms/html_select_element.idl index d5fde8e..8a920f9 100644 --- a/third_party/blink/renderer/core/html/forms/html_select_element.idl +++ b/third_party/blink/renderer/core/html/forms/html_select_element.idl
@@ -47,7 +47,7 @@ readonly attribute HTMLCollection selectedOptions; attribute long selectedIndex; - attribute DOMString value; + [ImplementedAs=valueForBinding] attribute DOMString value; readonly attribute boolean willValidate; readonly attribute ValidityState validity;
diff --git a/third_party/blink/renderer/core/html/forms/html_select_menu_element.cc b/third_party/blink/renderer/core/html/forms/html_select_menu_element.cc index c9aa532..0dea95f 100644 --- a/third_party/blink/renderer/core/html/forms/html_select_menu_element.cc +++ b/third_party/blink/renderer/core/html/forms/html_select_menu_element.cc
@@ -22,6 +22,8 @@ #include "third_party/blink/renderer/core/html/html_slot_element.h" #include "third_party/blink/renderer/core/html_names.h" #include "third_party/blink/renderer/core/inspector/console_message.h" +#include "third_party/blink/renderer/core/page/chrome_client.h" +#include "third_party/blink/renderer/core/page/page.h" #include "third_party/blink/renderer/platform/instrumentation/use_counter.h" #include "third_party/blink/renderer/platform/keyboard_codes.h" #include "third_party/blink/renderer/platform/text/platform_locale.h" @@ -302,6 +304,19 @@ return ""; } +void HTMLSelectMenuElement::setValueForBinding(const String& value) { + if (GetAutofillState() != WebAutofillState::kAutofilled) { + setValue(value); + } else { + String old_value = this->value(); + setValue(value); + if (Page* page = GetDocument().GetPage()) { + page->GetChromeClient().JavaScriptChangedAutofilledValue(*this, + old_value); + } + } +} + void HTMLSelectMenuElement::setValue(const String& value, bool send_events) { // Find the option with innerText matching the given parameter and make it the // current selection.
diff --git a/third_party/blink/renderer/core/html/forms/html_select_menu_element.h b/third_party/blink/renderer/core/html/forms/html_select_menu_element.h index 69563df..6fab653e 100644 --- a/third_party/blink/renderer/core/html/forms/html_select_menu_element.h +++ b/third_party/blink/renderer/core/html/forms/html_select_menu_element.h
@@ -36,6 +36,8 @@ HTMLOptionElement* selectedOption() const; String value() const; void setValue(const String&, bool send_events = false); + String valueForBinding() const { return value(); } + void setValueForBinding(const String&); bool open() const; // For ValidityState
diff --git a/third_party/blink/renderer/core/html/forms/html_select_menu_element.idl b/third_party/blink/renderer/core/html/forms/html_select_menu_element.idl index 5286ed1d..2225e39 100644 --- a/third_party/blink/renderer/core/html/forms/html_select_menu_element.idl +++ b/third_party/blink/renderer/core/html/forms/html_select_menu_element.idl
@@ -7,7 +7,7 @@ readonly attribute boolean open; [SameObject] readonly attribute HTMLOptionElement? selectedOption; - attribute DOMString value; + [ImplementedAs=valueForBinding] attribute DOMString value; // TODO(crbug.com/1121840) Fill this out. // Open question: do we want to replicate the interface of // <select> as closely as possible?
diff --git a/third_party/blink/renderer/core/html/forms/html_text_area_element.cc b/third_party/blink/renderer/core/html/forms/html_text_area_element.cc index 779fc2a..e03f4843 100644 --- a/third_party/blink/renderer/core/html/forms/html_text_area_element.cc +++ b/third_party/blink/renderer/core/html/forms/html_text_area_element.cc
@@ -439,6 +439,19 @@ return value_; } +void HTMLTextAreaElement::setValueForBinding(const String& value) { + if (GetAutofillState() != WebAutofillState::kAutofilled) { + setValue(value); + } else { + String old_value = this->value(); + setValue(value); + if (Page* page = GetDocument().GetPage()) { + page->GetChromeClient().JavaScriptChangedAutofilledValue(*this, + old_value); + } + } +} + void HTMLTextAreaElement::setValue(const String& value, TextFieldEventBehavior event_behavior, TextControlSetValueSelection selection) {
diff --git a/third_party/blink/renderer/core/html/forms/html_text_area_element.h b/third_party/blink/renderer/core/html/forms/html_text_area_element.h index 2aa3e15..7767b9e 100644 --- a/third_party/blink/renderer/core/html/forms/html_text_area_element.h +++ b/third_party/blink/renderer/core/html/forms/html_text_area_element.h
@@ -50,6 +50,8 @@ TextFieldEventBehavior = TextFieldEventBehavior::kDispatchNoEvent, TextControlSetValueSelection = TextControlSetValueSelection::kSetSelectionToEnd) override; + String valueForBinding() const { return value(); } + void setValueForBinding(const String&); String defaultValue() const; void setDefaultValue(const String&); int textLength() const { return value().length(); }
diff --git a/third_party/blink/renderer/core/html/forms/html_text_area_element.idl b/third_party/blink/renderer/core/html/forms/html_text_area_element.idl index 591be34..ef4c28ff 100644 --- a/third_party/blink/renderer/core/html/forms/html_text_area_element.idl +++ b/third_party/blink/renderer/core/html/forms/html_text_area_element.idl
@@ -40,7 +40,7 @@ readonly attribute DOMString type; [CEReactions] attribute DOMString defaultValue; - [CEReactions] attribute [TreatNullAs=EmptyString] DOMString value; + [CEReactions, ImplementedAs=valueForBinding] attribute [TreatNullAs=EmptyString] DOMString value; readonly attribute unsigned long textLength; readonly attribute boolean willValidate;
diff --git a/third_party/blink/renderer/core/layout/ng/inline/ng_line_breaker.cc b/third_party/blink/renderer/core/layout/ng/inline/ng_line_breaker.cc index b1de07f9..0294527 100644 --- a/third_party/blink/renderer/core/layout/ng/inline/ng_line_breaker.cc +++ b/third_party/blink/renderer/core/layout/ng/inline/ng_line_breaker.cc
@@ -536,8 +536,7 @@ ResetRewindLoopDetector(); } -void NGLineBreaker::NextLine( - NGLineInfo* line_info) { +void NGLineBreaker::NextLine(NGLineInfo* line_info) { PrepareNextLine(line_info); BreakLine(line_info); if (UNLIKELY(HasHyphen())) @@ -578,8 +577,7 @@ ComputeLineLocation(line_info); } -void NGLineBreaker::BreakLine( - NGLineInfo* line_info) { +void NGLineBreaker::BreakLine(NGLineInfo* line_info) { DCHECK(!line_info->IsLastLine()); const HeapVector<NGInlineItem>& items = Items(); state_ = LineBreakState::kContinue; @@ -1469,6 +1467,7 @@ unsigned last_safe = source_result->PreviousSafeToBreakOffset(end_offset); DCHECK_LE(last_safe, end_offset); + // TODO(abotella): Shouldn't last_safe <= start_offset trigger a reshaping? if (last_safe == end_offset || last_safe <= start_offset) { return ShapeResultView::Create(source_result, start_offset, end_offset); } @@ -1909,9 +1908,8 @@ MoveToNextOf(item); } -void NGLineBreaker::HandleAtomicInline( - const NGInlineItem& item, - NGLineInfo* line_info) { +void NGLineBreaker::HandleAtomicInline(const NGInlineItem& item, + NGLineInfo* line_info) { DCHECK_EQ(item.Type(), NGInlineItem::kAtomicInline); DCHECK(item.Style()); const ComputedStyle& style = *item.Style();
diff --git a/third_party/blink/renderer/core/page/chrome_client.h b/third_party/blink/renderer/core/page/chrome_client.h index 547ebe57..1f0c79f2 100644 --- a/third_party/blink/renderer/core/page/chrome_client.h +++ b/third_party/blink/renderer/core/page/chrome_client.h
@@ -480,6 +480,10 @@ virtual void DidChangeSelectionInSelectControl(HTMLFormControlElement&) {} virtual void SelectFieldOptionsChanged(HTMLFormControlElement&) {} virtual void AjaxSucceeded(LocalFrame*) {} + // Called when |element| is in autofilled state and the value has been changed + // by JavaScript. |old_value| contains the value before being changed. + virtual void JavaScriptChangedAutofilledValue(HTMLFormControlElement&, + const String& old_value) {} // Input method editor related functions. virtual void ShowVirtualKeyboardOnElementFocus(LocalFrame&) {}
diff --git a/third_party/blink/renderer/core/page/chrome_client_impl.cc b/third_party/blink/renderer/core/page/chrome_client_impl.cc index 8d9c6f4c..b05a0d8 100644 --- a/third_party/blink/renderer/core/page/chrome_client_impl.cc +++ b/third_party/blink/renderer/core/page/chrome_client_impl.cc
@@ -1213,6 +1213,16 @@ fill_client->AjaxSucceeded(); } +void ChromeClientImpl::JavaScriptChangedAutofilledValue( + HTMLFormControlElement& element, + const String& old_value) { + Document& doc = element.GetDocument(); + if (auto* fill_client = AutofillClientFromFrame(doc.GetFrame())) { + fill_client->JavaScriptChangedAutofilledValue( + WebFormControlElement(&element), old_value); + } +} + TransformationMatrix ChromeClientImpl::GetDeviceEmulationTransform() const { DCHECK(web_view_); return web_view_->GetDeviceEmulationTransform();
diff --git a/third_party/blink/renderer/core/page/chrome_client_impl.h b/third_party/blink/renderer/core/page/chrome_client_impl.h index 6796e96..6413b206 100644 --- a/third_party/blink/renderer/core/page/chrome_client_impl.h +++ b/third_party/blink/renderer/core/page/chrome_client_impl.h
@@ -258,6 +258,8 @@ void DidChangeSelectionInSelectControl(HTMLFormControlElement&) override; void SelectFieldOptionsChanged(HTMLFormControlElement&) override; void AjaxSucceeded(LocalFrame*) override; + void JavaScriptChangedAutofilledValue(HTMLFormControlElement&, + const String& old_value) override; void ShowVirtualKeyboardOnElementFocus(LocalFrame&) override;
diff --git a/third_party/blink/renderer/core/page/chrome_client_impl_test.cc b/third_party/blink/renderer/core/page/chrome_client_impl_test.cc index d09b6b17..2b4085db 100644 --- a/third_party/blink/renderer/core/page/chrome_client_impl_test.cc +++ b/third_party/blink/renderer/core/page/chrome_client_impl_test.cc
@@ -38,6 +38,7 @@ #include "third_party/blink/public/mojom/choosers/color_chooser.mojom-blink.h" #include "third_party/blink/public/web/web_local_frame.h" #include "third_party/blink/public/web/web_local_frame_client.h" +#include "third_party/blink/public/web/web_testing_support.h" #include "third_party/blink/public/web/web_view.h" #include "third_party/blink/public/web/web_view_client.h" #include "third_party/blink/renderer/core/exported/web_view_impl.h" @@ -57,6 +58,7 @@ #include "third_party/blink/renderer/core/loader/frame_load_request.h" #include "third_party/blink/renderer/core/page/page.h" #include "third_party/blink/renderer/core/page/scoped_page_pauser.h" +#include "third_party/blink/renderer/core/script/classic_script.h" #include "third_party/blink/renderer/core/testing/page_test_base.h" #include "third_party/blink/renderer/platform/language.h" @@ -65,6 +67,20 @@ namespace blink { +namespace { +class FakeChromeClientForAutofill : public EmptyChromeClient { + public: + void JavaScriptChangedAutofilledValue(HTMLFormControlElement&, + const String& old_value) override { + last_old_value_ = old_value; + } + const String& last_old_value() const { return last_old_value_; } + + private: + String last_old_value_; +}; +} // namespace + class ViewCreatingClient : public frame_test_helpers::TestWebViewClient { public: WebView* CreateView(WebLocalFrame* opener, @@ -371,4 +387,64 @@ chooser.ResponseOnOpenFileChooser(FileChooserFileInfoList()); } +class AutofillChromeClientTest : public PageTestBase { + public: + void SetUp() override { + chrome_client_ = MakeGarbageCollected<FakeChromeClientForAutofill>(); + SetupPageWithClients(chrome_client_); + GetFrame().GetSettings()->SetScriptEnabled(true); + } + + void ExecuteScript(const char* script) { + ClassicScript::CreateUnspecifiedScript(script)->RunScript( + GetFrame().DomWindow()); + } + + Persistent<FakeChromeClientForAutofill> chrome_client_; +}; + +TEST_F(AutofillChromeClientTest, NotificationsOfJavaScriptChanges) { + SetHtmlInnerHTML(R"HTML( + <!DOCTYPE HTML> + <form id='form' method='GET' action='https://internal.test/' + target='_blank'> + <input id='text' value='old_text'> + <textarea id='textarea'>old_textarea</textarea> + <select id='select'> + <option value='select_a'>a</option> + <option value='select_b' selected>b</option> + </select> + <selectmenu id='selectmenu'> + <option value='selectmenu_a'>a</option> + <option value='selectmenu_b' selected>b</option> + </select> + <input id='not_autofilled_text' value='old_text'> + </form> + )HTML"); + + for (const char* id : {"text", "textarea", "select", "selectmenu"}) { + To<HTMLFormControlElement>(GetElementById(id)) + ->SetAutofillState(WebAutofillState::kAutofilled); + } + + ExecuteScript("document.getElementById('text').value = 'new_text';"); + EXPECT_EQ(String("old_text"), chrome_client_->last_old_value()); + + ExecuteScript("document.getElementById('textarea').value = 'new_text';"); + EXPECT_EQ(String("old_textarea"), chrome_client_->last_old_value()); + + ExecuteScript("document.getElementById('select').value = 'select_a';"); + EXPECT_EQ(String("select_b"), chrome_client_->last_old_value()); + + ExecuteScript( + "document.getElementById('selectmenu').value = 'selectmenu_a';"); + EXPECT_EQ(String("selectmenu_b"), chrome_client_->last_old_value()); + + // Because this is not in state "autofilled", the chrome client is not + // informed about the change. + ExecuteScript( + "document.getElementById('not_autofilled_text').value = 'new_text';"); + EXPECT_EQ(String("selectmenu_b"), chrome_client_->last_old_value()); +} + } // namespace blink
diff --git a/third_party/blink/renderer/core/script/script_loader.cc b/third_party/blink/renderer/core/script/script_loader.cc index 00d86faf..fc55ee10 100644 --- a/third_party/blink/renderer/core/script/script_loader.cc +++ b/third_party/blink/renderer/core/script/script_loader.cc
@@ -202,10 +202,6 @@ // attribute.</spec> if (MIMETypeRegistry::IsSupportedJavaScriptMIMEType("text/" + language)) return true; - - // Not spec'ed. - if (MIMETypeRegistry::IsLegacySupportedJavaScriptLanguage(language)) - return true; } else if (type.IsEmpty()) { // <spec step="8">the script element has a type attribute and its value is // the empty string, or</spec>
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_device.cc b/third_party/blink/renderer/modules/webgpu/gpu_device.cc index d327e06..c0c7f60 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_device.cc +++ b/third_party/blink/renderer/modules/webgpu/gpu_device.cc
@@ -104,6 +104,7 @@ } GPUDevice::~GPUDevice() { + DestroyAllExternalTextures(); // Clear the callbacks since we can't handle callbacks after finalization. // error_callback_, logging_callback_, and lost_callback_ will be deleted. GetProcs().deviceSetUncapturedErrorCallback(GetHandle(), nullptr, nullptr); @@ -276,6 +277,8 @@ } void GPUDevice::destroy() { + destroyed_ = true; + DestroyAllExternalTextures(); GetProcs().deviceDestroy(GetHandle()); FlushNow(); } @@ -305,10 +308,18 @@ GPUExternalTexture* GPUDevice::importExternalTexture( const GPUExternalTextureDescriptor* descriptor, ExceptionState& exception_state) { + // Ensure the GPUExternalTexture created from a destroyed GPUDevice will be + // expired immediately. + if (destroyed_) + return GPUExternalTexture::CreateExpired(this, descriptor, exception_state); + GPUExternalTexture* externalTexture = GPUExternalTexture::Create(this, descriptor, exception_state); - if (externalTexture) + + // No need to manage expired GPUExternalTexture in GPUDevice. + if (externalTexture && !externalTexture->expired()) { EnsureExternalTextureDestroyed(externalTexture); + } return externalTexture; } @@ -485,16 +496,20 @@ DCHECK(externalTexture); external_textures_pending_destroy_.push_back(externalTexture); - if (has_pending_microtask_) + if (has_destroy_external_texture_microtask_) return; Microtask::EnqueueMicrotask(WTF::Bind( &GPUDevice::DestroyExternalTexturesMicrotask, WrapWeakPersistent(this))); - has_pending_microtask_ = true; + has_destroy_external_texture_microtask_ = true; } void GPUDevice::DestroyExternalTexturesMicrotask() { - has_pending_microtask_ = false; + // GPUDevice.destroy() call has destroyed all pending external textures. + if (!has_destroy_external_texture_microtask_) + return; + + has_destroy_external_texture_microtask_ = false; auto externalTextures = std::move(external_textures_pending_destroy_); for (Member<GPUExternalTexture> externalTexture : externalTextures) { @@ -502,4 +517,15 @@ } } +void GPUDevice::DestroyAllExternalTextures() { + has_destroy_external_texture_microtask_ = false; + + auto externalTexturesPendingDestroy = + std::move(external_textures_pending_destroy_); + for (Member<GPUExternalTexture> externalTexture : + externalTexturesPendingDestroy) { + externalTexture->Destroy(); + } +} + } // namespace blink
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_device.h b/third_party/blink/renderer/modules/webgpu/gpu_device.h index 89cf0c7..023d48b 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_device.h +++ b/third_party/blink/renderer/modules/webgpu/gpu_device.h
@@ -137,14 +137,15 @@ void InjectError(WGPUErrorType type, const char* message); void AddConsoleWarning(const char* message); - void EnsureExternalTextureDestroyed(GPUExternalTexture* externalTexture); - private: using LostProperty = ScriptPromiseProperty<Member<GPUDeviceLostInfo>, ToV8UndefinedGenerator>; + void EnsureExternalTextureDestroyed(GPUExternalTexture* externalTexture); void DestroyExternalTexturesMicrotask(); + void DestroyAllExternalTextures(); + void OnUncapturedError(WGPUErrorType errorType, const char* message); void OnLogging(WGPULoggingType loggingType, const char* message); void OnDeviceLostError(WGPUDeviceLostReason, const char* message); @@ -188,8 +189,11 @@ static constexpr int kMaxAllowedConsoleWarnings = 500; int allowed_console_warnings_remaining_ = kMaxAllowedConsoleWarnings; - bool has_pending_microtask_ = false; + bool has_destroy_external_texture_microtask_ = false; HeapVector<Member<GPUExternalTexture>> external_textures_pending_destroy_; + + // This attribute records that whether GPUDevice is destroyed (via destroy()). + bool destroyed_ = false; }; } // namespace blink
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_external_texture.cc b/third_party/blink/renderer/modules/webgpu/gpu_external_texture.cc index 6af881c3..949cf90 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_external_texture.cc +++ b/third_party/blink/renderer/modules/webgpu/gpu_external_texture.cc
@@ -103,6 +103,85 @@ dstTransferConstants[5] = dst_transfer_fn.e; dstTransferConstants[6] = dst_transfer_fn.f; } + +struct ExternalTextureSource { + scoped_refptr<media::VideoFrame> media_video_frame = nullptr; + media::PaintCanvasVideoRenderer* video_renderer = nullptr; + bool valid = false; +}; + +ExternalTextureSource GetExternalTextureSource( + GPUDevice* deivce, + const GPUExternalTextureDescriptor* webgpu_desc, + ExceptionState& exception_state) { + ExternalTextureSource source; + switch (webgpu_desc->source()->GetContentType()) { + case V8UnionHTMLVideoElementOrVideoFrame::ContentType::kHTMLVideoElement: { + HTMLVideoElement* video = webgpu_desc->source()->GetAsHTMLVideoElement(); + if (!video) { + exception_state.ThrowDOMException(DOMExceptionCode::kOperationError, + "Missing video source"); + return source; + } + + if (video->WouldTaintOrigin()) { + exception_state.ThrowSecurityError( + "Video element is tainted by cross-origin data and may not be " + "loaded."); + return source; + } + + if (auto* wmp = video->GetWebMediaPlayer()) { + source.media_video_frame = wmp->GetCurrentFrame(); + source.video_renderer = wmp->GetPaintCanvasVideoRenderer(); + } + + if (!source.media_video_frame) { + exception_state.ThrowDOMException(DOMExceptionCode::kOperationError, + "Failed to import texture from video " + "element that doesn't have back " + "resource."); + return source; + } + + break; + } + + case V8UnionHTMLVideoElementOrVideoFrame::ContentType::kVideoFrame: { + VideoFrame* frame = webgpu_desc->source()->GetAsVideoFrame(); + + if (!frame) { + exception_state.ThrowDOMException(DOMExceptionCode::kOperationError, + "Missing video frame"); + return source; + } + // Tainted blink::VideoFrames are not supposed to be possible. + DCHECK(!frame->WouldTaintOrigin()); + + source.media_video_frame = frame->frame(); + if (!source.media_video_frame) { + exception_state.ThrowDOMException( + DOMExceptionCode::kOperationError, + "Failed to import texture from video " + "frame that doesn't have back resource"); + return source; + } + + if (!source.media_video_frame->coded_size().width() || + !source.media_video_frame->coded_size().height()) { + exception_state.ThrowDOMException( + DOMExceptionCode::kOperationError, + "Cannot import from zero sized video frame"); + return source; + } + break; + } + } + + source.valid = true; + return source; +} + } // namespace // static @@ -110,87 +189,34 @@ GPUDevice* device, const GPUExternalTextureDescriptor* webgpu_desc, ExceptionState& exception_state) { - scoped_refptr<media::VideoFrame> media_video_frame; - media::PaintCanvasVideoRenderer* video_renderer = nullptr; - switch (webgpu_desc->source()->GetContentType()) { - case V8UnionHTMLVideoElementOrVideoFrame::ContentType::kHTMLVideoElement: { - HTMLVideoElement* video = webgpu_desc->source()->GetAsHTMLVideoElement(); - - if (!video || !video->videoWidth() || !video->videoHeight()) { - exception_state.ThrowDOMException(DOMExceptionCode::kOperationError, - "Missing video source"); - return nullptr; - } - - if (video->WouldTaintOrigin()) { - exception_state.ThrowSecurityError( - "Video element is tainted by cross-origin data and may not be " - "loaded."); - return nullptr; - } - - if (auto* wmp = video->GetWebMediaPlayer()) { - media_video_frame = wmp->GetCurrentFrame(); - video_renderer = wmp->GetPaintCanvasVideoRenderer(); - } - break; - } - - case V8UnionHTMLVideoElementOrVideoFrame::ContentType::kVideoFrame: { - VideoFrame* frame = webgpu_desc->source()->GetAsVideoFrame(); - - if (!frame || !frame->codedWidth() || !frame->codedHeight()) { - exception_state.ThrowDOMException(DOMExceptionCode::kOperationError, - "Missing video source"); - return nullptr; - } - - if (frame->WouldTaintOrigin()) { - exception_state.ThrowSecurityError( - "VideoFrame is tainted by cross-origin data and may not be " - "loaded."); - return nullptr; - } - - media_video_frame = frame->frame(); - break; - } - } - - if (!media_video_frame) { - exception_state.ThrowDOMException(DOMExceptionCode::kOperationError, - "Failed to import texture from video"); - if (!media_video_frame) { - device->AddConsoleWarning( - "Cannot get valid video frame, maybe the" - "HTMLVideoElement is not loaded"); - } - + ExternalTextureSource source = + GetExternalTextureSource(device, webgpu_desc, exception_state); + if (!source.valid) return nullptr; - } - gfx::ColorSpace srcColorSpace = media_video_frame->ColorSpace(); + gfx::ColorSpace srcColorSpace = source.media_video_frame->ColorSpace(); gfx::ColorSpace dstColorSpace; switch (webgpu_desc->colorSpace().AsEnum()) { case V8GPUPredefinedColorSpace::Enum::kSRGB: dstColorSpace = gfx::ColorSpace::CreateSRGB(); } + DCHECK(source.media_video_frame); // TODO(crbug.com/1306753): Use SharedImageProducer and CompositeSharedImage // rather than check 'is_webgpu_compatible'. bool device_support_zero_copy = device->adapter()->features()->FeatureNameSet().Contains( "multi-planar-formats"); - if (media_video_frame->HasTextures() && - (media_video_frame->format() == media::PIXEL_FORMAT_NV12) && + if (source.media_video_frame->HasTextures() && + (source.media_video_frame->format() == media::PIXEL_FORMAT_NV12) && device_support_zero_copy && - media_video_frame->metadata().is_webgpu_compatible) { + source.media_video_frame->metadata().is_webgpu_compatible) { scoped_refptr<WebGPUMailboxTexture> mailbox_texture = WebGPUMailboxTexture::FromVideoFrame( device->GetDawnControlClient(), device->GetHandle(), WGPUTextureUsage::WGPUTextureUsage_TextureBinding, - media_video_frame); + source.media_video_frame); WGPUTextureViewDescriptor view_desc = { .format = WGPUTextureFormat_R8Unorm, @@ -210,7 +236,7 @@ external_texture_desc.colorSpace = AsDawnEnum(webgpu_desc->colorSpace()); float yuvToRgbMatrix[12]; - GetYUVToRGBMatrix(srcColorSpace, media_video_frame->BitDepth(), + GetYUVToRGBMatrix(srcColorSpace, source.media_video_frame->BitDepth(), yuvToRgbMatrix); external_texture_desc.yuvToRgbConversionMatrix = yuvToRgbMatrix; @@ -247,7 +273,7 @@ context_provider_wrapper->ContextProvider()->IsContextLost()) return nullptr; - const auto intrinsic_size = media_video_frame->natural_size(); + const auto intrinsic_size = source.media_video_frame->natural_size(); // Get a recyclable resource for producing WebGPU-compatible shared images. std::unique_ptr<RecyclableCanvasResource> recyclable_canvas_resource = @@ -276,10 +302,10 @@ // DrawVideoFrameIntoResourceProvider() creates local_video_renderer always. // This might affect performance, maybe a cache local_video_renderer could // help. - const auto dest_rect = gfx::Rect(media_video_frame->natural_size()); + const auto dest_rect = gfx::Rect(source.media_video_frame->natural_size()); if (!DrawVideoFrameIntoResourceProvider( - std::move(media_video_frame), resource_provider, - raster_context_provider, dest_rect, video_renderer)) { + std::move(source.media_video_frame), resource_provider, + raster_context_provider, dest_rect, source.video_renderer)) { exception_state.ThrowDOMException(DOMExceptionCode::kOperationError, "Failed to import texture from video"); return nullptr; @@ -327,6 +353,24 @@ return external_texture; } +// static +GPUExternalTexture* GPUExternalTexture::CreateExpired( + GPUDevice* device, + const GPUExternalTextureDescriptor* webgpu_desc, + ExceptionState& exception_state) { + // Validate GPUExternalTextureDescriptor. + ExternalTextureSource source = + GetExternalTextureSource(device, webgpu_desc, exception_state); + if (!source.valid) + return nullptr; + + // Bypass importing video frame into Dawn. + GPUExternalTexture* external_texture = + MakeGarbageCollected<GPUExternalTexture>(device, nullptr, nullptr); + external_texture->Destroy(); + return external_texture; +} + GPUExternalTexture::GPUExternalTexture( GPUDevice* device, WGPUExternalTexture external_texture, @@ -335,11 +379,12 @@ mailbox_texture_(mailbox_texture) {} void GPUExternalTexture::Destroy() { - WGPUTexture texture = mailbox_texture_->GetTexture(); - GetProcs().textureReference(texture); + expired_ = true; + if (!mailbox_texture_) + return; + + GetProcs().textureDestroy(mailbox_texture_->GetTexture()); mailbox_texture_.reset(); - GetProcs().textureDestroy(texture); - GetProcs().textureRelease(texture); } } // namespace blink
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_external_texture.h b/third_party/blink/renderer/modules/webgpu/gpu_external_texture.h index e559cd1..a5c31ee0 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_external_texture.h +++ b/third_party/blink/renderer/modules/webgpu/gpu_external_texture.h
@@ -22,6 +22,10 @@ GPUDevice* device, const GPUExternalTextureDescriptor* webgpu_desc, ExceptionState& exception_state); + static GPUExternalTexture* CreateExpired( + GPUDevice* device, + const GPUExternalTextureDescriptor* webgpu_desc, + ExceptionState& exception_state); explicit GPUExternalTexture( GPUDevice* device, WGPUExternalTexture external_texture, @@ -32,6 +36,8 @@ void Destroy(); + bool expired() const { return expired_; } + private: void setLabelImpl(const String& value) override { std::string utf8_label = value.Utf8(); @@ -39,6 +45,9 @@ } scoped_refptr<WebGPUMailboxTexture> mailbox_texture_; + + // This attribute marks whether GPUExternalTexture will be destroyed. + bool expired_ = false; }; } // namespace blink
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_external_texture.idl b/third_party/blink/renderer/modules/webgpu/gpu_external_texture.idl index 33262786..ba5570ed 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_external_texture.idl +++ b/third_party/blink/renderer/modules/webgpu/gpu_external_texture.idl
@@ -8,5 +8,6 @@ Exposed(Window WebGPU, DedicatedWorker WebGPU), SecureContext ] interface GPUExternalTexture { + readonly attribute boolean expired; }; GPUExternalTexture includes GPUObjectBase;
diff --git a/third_party/blink/renderer/platform/fonts/shaping/shape_result_view.cc b/third_party/blink/renderer/platform/fonts/shaping/shape_result_view.cc index 427bca02..dfca9c1 100644 --- a/third_party/blink/renderer/platform/fonts/shaping/shape_result_view.cc +++ b/third_party/blink/renderer/platform/fonts/shaping/shape_result_view.cc
@@ -472,7 +472,7 @@ unsigned ShapeResultView::PreviousSafeToBreakOffset(unsigned index) const { for (auto it = RunsOrParts().rbegin(); it != RunsOrParts().rend(); ++it) { const auto& part = *it; - unsigned run_start = part.start_index_; + unsigned run_start = part.start_index_ + char_index_offset_; if (index >= run_start) { unsigned offset = index - run_start; if (offset <= part.num_characters_) {
diff --git a/third_party/blink/renderer/platform/fonts/shaping/shape_result_view_test.cc b/third_party/blink/renderer/platform/fonts/shaping/shape_result_view_test.cc index 81113f5..04ecc04 100644 --- a/third_party/blink/renderer/platform/fonts/shaping/shape_result_view_test.cc +++ b/third_party/blink/renderer/platform/fonts/shaping/shape_result_view_test.cc
@@ -468,4 +468,24 @@ EXPECT_EQ(view2->NumGlyphs(), 1u); } +// https://crbug.com/1304876 +// In a text containing only Latin characters and without ligatures (or where +// ligatures are not close to the end of the view), PreviousSafeToBreakOffset in +// some cases used to return the length of the view, rather than a position into +// the view. +TEST_F(ShapeResultViewTest, PreviousSafeOffsetInsideView) { + HarfBuzzShaper shaper("Blah bla test something. "); + scoped_refptr<const ShapeResult> result = + shaper.Shape(&font, TextDirection::kLtr); + + // Used to be 14 - 9 = 5, which is before the start of the view. + auto view1 = ShapeResultView::Create(result.get(), 9, 14); + EXPECT_EQ(view1->PreviousSafeToBreakOffset(14), 14u); + + // Used to be 25 - 9 = 16, which is inside the view's range, but not the last + // safe offset. + auto view2 = ShapeResultView::Create(result.get(), 9, 25); + EXPECT_EQ(view2->PreviousSafeToBreakOffset(24), 24u); +} + } // namespace blink
diff --git a/third_party/blink/renderer/platform/loader/fetch/resource.cc b/third_party/blink/renderer/platform/loader/fetch/resource.cc index ac88afb8..bd4e64a 100644 --- a/third_party/blink/renderer/platform/loader/fetch/resource.cc +++ b/third_party/blink/renderer/platform/loader/fetch/resource.cc
@@ -1164,11 +1164,13 @@ switch (type_) { case ResourceType::kImage: case ResourceType::kCSSStyleSheet: - case ResourceType::kScript: case ResourceType::kFont: case ResourceType::kSVGDocument: case ResourceType::kXSLStyleSheet: return true; + case ResourceType::kScript: + // <script> elements delay the load event in core/script (e.g. in + // ScriptRunner) and no longer need the delaying in platform/loader side. case ResourceType::kRaw: case ResourceType::kLinkPrefetch: case ResourceType::kTextTrack:
diff --git a/third_party/blink/web_tests/TestExpectations b/third_party/blink/web_tests/TestExpectations index 556454f..6f5210d 100644 --- a/third_party/blink/web_tests/TestExpectations +++ b/third_party/blink/web_tests/TestExpectations
@@ -3188,7 +3188,6 @@ crbug.com/626703 virtual/plz-dedicated-worker/external/wpt/service-workers/service-worker/navigation-timing-extended.https.html [ Failure ] crbug.com/626703 external/wpt/preload/preload-resource-match.https.html [ Failure ] crbug.com/626703 virtual/prerender/external/wpt/speculation-rules/prerender/workers.html [ Failure ] -crbug.com/626703 [ Win ] external/wpt/preload/avoid-delaying-onload-link-modulepreload.html [ Failure ] crbug.com/626703 [ Win ] virtual/prerender/external/wpt/speculation-rules/prerender/restriction-presentation-request.https.html [ Failure ] crbug.com/626703 [ Win ] virtual/prerender/external/wpt/speculation-rules/prerender/storage-foundation.https.html [ Failure ] crbug.com/626703 [ Win ] virtual/partitioned-cookies/http/tests/inspector-protocol/network/disabled-cache-navigation.js [ Failure ]
diff --git a/third_party/blink/web_tests/animations/svg/stroke-width-zoom-factor.html b/third_party/blink/web_tests/animations/svg/stroke-width-zoom-factor.html index aaeb4a3..1168859 100644 --- a/third_party/blink/web_tests/animations/svg/stroke-width-zoom-factor.html +++ b/third_party/blink/web_tests/animations/svg/stroke-width-zoom-factor.html
@@ -3,12 +3,17 @@ <title>Make sure stroke-width is zoom agnostic when animating</title> <script src="../../resources/testharness.js"></script> <script src="../../resources/testharnessreport.js"></script> +<script src="../../resources/ahem.js"></script> <div id="target"></div> <script> test(t => { - // Setting the zoom factor should not change the value of strokeWidth. + t.add_cleanup(() => { + if (window.testRunner) + testRunner.setPageZoomFactor(1); + }); + if (window.testRunner) testRunner.setPageZoomFactor(5); @@ -21,5 +26,28 @@ anim.currentTime = 500; assert_equals(getComputedStyle(target).strokeWidth, '12.5px'); -}); +}, 'Zoom does not affect strokeWidth animation (px)'); + +promise_test(async t => { + t.add_cleanup(() => { + target.style = ''; + }); + target.style.fontFamily = 'Ahem'; + target.style.fontSize = '20px'; + + await document.fonts.ready; + + if (window.testRunner) + testRunner.setPageZoomFactor(5); + + const anim = target.animate([ + { strokeWidth: '1ex' }, // 16px + { strokeWidth: '2ex' }, // 32px + ], { + duration: 1000, + }); + + anim.currentTime = 500; + assert_equals(getComputedStyle(target).strokeWidth, '24px'); +}, 'Zoom does not affect strokeWidth animation (ex)'); </script>
diff --git a/third_party/blink/web_tests/external/wpt/css/css-text/shaping/reference/shaping_lig-001-ref.html b/third_party/blink/web_tests/external/wpt/css/css-text/shaping/reference/shaping_lig-001-ref.html new file mode 100644 index 0000000..df71a1d --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-text/shaping/reference/shaping_lig-001-ref.html
@@ -0,0 +1,40 @@ +<!DOCTYPE html> +<html lang="en" > +<head> +<meta charset="utf-8"> +<title>shaping: test for Chromium bug 1304876</title> +<style type="text/css"> +@font-face { + font-family: GentiumPlus; + src: url('/fonts/GentiumPlus-R.woff') format('woff'); + font-weight: normal; + font-style: normal; +} +.test { + font-family: GentiumPlus; + font-size: 18pt; + width: 300px; + border: 1px solid black; + margin: 1em; +} +.line { + display: block; + white-space: nowrap; +} +/* the CSS above is not part of the test */ +</style> +</head> +<body> +<p class="instructions">Test passes if the word "office" is rendered without repeated letters.</p> +<div class="test"> + <div class="line">Sanitary measures in the</div> + <div class="line">office ought be adequately</div> + <div class="line"><b>maintained</b>.</div> +</div> +<div class="test"> + <div class="line">Sanitary measures in the</div> + <div class="line">office ought be adequately</div> + <div class="line"><b>maintained</b>.</div> +</div> +</body> +</html> \ No newline at end of file
diff --git a/third_party/blink/web_tests/external/wpt/css/css-text/shaping/shaping_lig-001.html b/third_party/blink/web_tests/external/wpt/css/css-text/shaping/shaping_lig-001.html new file mode 100644 index 0000000..059b8df --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/css/css-text/shaping/shaping_lig-001.html
@@ -0,0 +1,31 @@ +<!DOCTYPE html> +<html lang="en" > +<head> +<meta charset="utf-8"> +<title>shaping: test for Chromium bug 1304876</title> +<link rel="author" title="Andreu Botella" href="mailto:abotella@igalia.com"> +<link rel="help" href="https://bugs.chromium.org/p/chromium/issues/detail?id=1304876"> +<link rel="match" href="reference/shaping_lig-001-ref.html"> +<style type="text/css"> +@font-face { + font-family: GentiumPlus; + src: url('/fonts/GentiumPlus-R.woff') format('woff'); + font-weight: normal; + font-style: normal; +} +.test { + font-family: GentiumPlus; + font-size: 18pt; + width: 300px; + border: 1px solid black; + margin: 1em; +} +/* the CSS above is not part of the test */ +</style> +</head> +<body> +<p class="instructions">Test passes if the word "office" is rendered without repeated letters.</p> +<div class="test">Sanitary measures in the office ought be adequately <b>maintained</b>.</div> +<div class="test">Sanitary measures in the<br>office ought be adequately <b>maintained</b>.</div> +</body> +</html> \ No newline at end of file
diff --git a/third_party/blink/web_tests/fast/html/script-allowed-types-languages.html b/third_party/blink/web_tests/fast/html/script-allowed-types-languages.html deleted file mode 100644 index 3ee958e..0000000 --- a/third_party/blink/web_tests/fast/html/script-allowed-types-languages.html +++ /dev/null
@@ -1,123 +0,0 @@ -<script> -function log(msg) -{ - document.getElementById('log').appendChild(document.createTextNode(msg + '\n')); -} - -function appendChildText(node, text) -{ - if (node.canHaveChildren == null || node.canHaveChildren) { - node.appendChild(document.createTextNode(text)); - } else { - // IE doesn't allow script nodes to have children. We must use the - // .text property instead. - node.text = text; - } -} - -function createScriptElement(type, language) -{ - var script = document.createElement('script'); - - var typeStr; - if (type == null) { - typeStr = 'unspecified'; - } else { - typeStr = '\\"' + type + '\\"'; - script.setAttribute('type', type); - } - - var languageStr; - if (language == null) { - languageStr = 'unspecified'; - } else { - languageStr = '\\"' + language + '\\"'; - script.setAttribute('language', language); - } - - var text = 'log("Type: ' + typeStr + ', Language: ' + languageStr + '");'; - appendChildText(script, text); - - return script; -} - -function test() -{ - if (window.testRunner) - testRunner.dumpAsText(); - - var types = [ - null, - "", - "text/javascript", - "text/ecmascript", - "text/x-javascript", - "text/x-ecmascript", - "application/javascript", - "application/ecmascript", - "application/x-javascript", - "application/x-ecmascript", - "text/javascript1.0", - "text/javascript1.1", - "text/javascript1.2", - "text/javascript1.3", - "text/javascript1.4", - "text/javascript1.5", - "text/javascript1.6", - "text/javascript1.7", - "text/javascript1.8", - "text/javascript1.9", - "text/jscript", - "text/livescript", - "text/x-ebayScript", - " text/javascript", - "text/javascript ", - " text/javascript ", - " ", - "abcdefg" - ]; - - var languages = [ - "", - "javascript", - "javascript1.0", - "javascript1.1", - "javascript1.2", - "javascript1.3", - "javascript1.4", - "javascript1.5", - "javascript1.6", - "javascript1.7", - "javascript1.8", - "javascript1.9", - "ecmascript", - "livescript", - "jscript", - "ebayScript", - " ", - " javascript", - "javascript ", - " javascript ", - "abcdefg" - ]; - - for (var i = 0; i < types.length; ++i) - document.body.appendChild(createScriptElement(types[i], null)); - - for (var i = 0; i < languages.length; ++i) - document.body.appendChild(createScriptElement(null, languages[i])); - - for (var i = 0; i < languages.length; ++i) - document.body.appendChild(createScriptElement("", languages[i])); - - log('When a type is specified, the language attribute should be ignored.'); - for (var i = 0; i < languages.length; ++i) - document.body.appendChild(createScriptElement("text/javascript", languages[i])); -} -</script> -<body onload="test();"> - <p>This page tests the allowed values for the type and language attributes - of the <script> tag. Below you will see the allowed values.</p> - - <pre id="log"></pre> -</body>
diff --git a/third_party/blink/web_tests/fast/tokenizer/004.html b/third_party/blink/web_tests/fast/tokenizer/004.html deleted file mode 100644 index f405f0f..0000000 --- a/third_party/blink/web_tests/fast/tokenizer/004.html +++ /dev/null
@@ -1,187 +0,0 @@ -<html> -<script> - if (window.testRunner) - testRunner.dumpAsText(); -</script> -<body> -<h3>Variations on type attribute of script tag</h3> -<h4>These scripts should execute</h4> -<ol> - <li>no type attribute <script>document.write("executed");</script></li> - <li>empty string <script type="">document.write("executed");</script></li> - <li>text/javascript <script type="text/javascript">document.write("executed");</script></li> - <li>text/JAVASCRIPT <script type="text/JAVASCRIPT">document.write("executed");</script></li> - <li>TEXT/JAVASCRIPT <script type="TEXT/JAVASCRIPT">document.write("executed");</script></li> - <li>'text/javascript ' <script type="text/javascript ">document.write("executed");</script></li> - <li>' text/javascript ' <script type=" text/javascript ">document.write("executed");</script></li> - <li>text/jscript <script type="text/jscript">document.write("executed");</script></li> - <li>text/ecmascript <script type="text/ecmascript">document.write("executed");</script></li> - <li>text/livescript <script type="text/livescript">document.write("executed");</script></li> - <li>text/javascript1.0 <script type="text/javascript1.0">document.write("executed");</script></li> - <li>text/javascript1.1 <script type="text/javascript1.1">document.write("executed");</script></li> - <li>text/javascript1.2 <script type="text/javascript1.2">document.write("executed");</script></li> - <li>text/javascript1.3 <script type="text/javascript1.3">document.write("executed");</script></li> - <li>text/javascript1.4 <script type="text/javascript1.4">document.write("executed");</script></li> - <li>text/javascript1.5 <script type="text/javascript1.5">document.write("executed");</script></li> - <li>text/x-javascript <script type="text/x-javascript">document.write("executed");</script></li> - <li>text/x-ecmascript <script type="text/x-ecmascript">document.write("executed");</script></li> - <li>application/javascript <script type="application/javascript">document.write("executed");</script></li> - <li>application/ecmascript <script type="application/ecmascript">document.write("executed");</script></li> - <li>application/x-javascript <script type="application/x-javascript">document.write("executed");</script></li> - <li>application/x-ecmascript <script type="application/x-ecmascript">document.write("executed");</script></li> -</ol> -<h4>These scripts should not execute</h4> -<ol> - <li>one space <script type=" ">document.write("executed");</script></li> - <li>text/ <script type="text/">document.write("executed");</script></li> - <li>text/vbscript <script type="text/vbscript">document.write("executed");</script></li> - <li>text/vbs <script type="text/vbs">document.write("executed");</script></li> - <li>text/xml <script type="text/xml">document.write("executed");</script></li> - <li>text/javascript1 <script type="text/javascript1">document.write("executed");</script></li> - <li>text/javascript1.6 <script type="text/javascript1.6">document.write("executed");</script></li> - <li>application/jscript <script type="application/jscript">document.write("executed");</script></li> - <li>application/x-jscript <script type="application/x-jscript">document.write("executed");</script></li> - <li>application/livescript <script type="application/livescript">document.write("executed");</script></li> - <li>application/x-livescript <script type="application/x-livescript">document.write("executed");</script></li> - <li>application/javascript1.2 <script type="application/javascript1.2">document.write("executed");</script></li> - <li>application/x-javascript1.2 <script type="application/x-javascript1.2">document.write("executed");</script></li> - <li>javascript <script type="javascript">document.write("executed");</script></li> - <li>jscript <script type="jscript">document.write("executed");</script></li> - <li>ecmascript <script type="ecmascript">document.write("executed");</script></li> - <li>livescript <script type="livescript">document.write("executed");</script></li> - <li>livescript1.1 <script type="livescript1.1">document.write("executed");</script></li> - <li>JAVASCRIPT <script type="JAVASCRIPT">document.write("executed");</script></li> - <li>JavaScript <script type="JavaScript">document.write("executed");</script></li> - <li>JavaScript 1 <script type="JavaScript 1">document.write("executed");</script></li> - <li>JavaScript 1.0 <script type="JavaScript 1.0">document.write("executed");</script></li> - <li>JavaScript 1.1 <script type="JavaScript 1.1">document.write("executed");</script></li> - <li>JavaScript 1.1.1 <script type="JavaScript 1.1.1">document.write("executed");</script></li> - <li>JavaScript 1.2 <script type="JavaScript 1.2">document.write("executed");</script></li> - <li>JavaScript 1.3 <script type="JavaScript 1.3">document.write("executed");</script></li> - <li>JavaScript 1.4 <script type="JavaScript 1.4">document.write("executed");</script></li> - <li>JavaScript 1.5 <script type="JavaScript 1.5">document.write("executed");</script></li> - <li>JavaScript 1.6 <script type="JavaScript 1.6">document.write("executed");</script></li> - <li>JavaScript 1.7 <script type="JavaScript 1.7">document.write("executed");</script></li> - <li>JavaScript 1.8 <script type="JavaScript 1.8">document.write("executed");</script></li> - <li>JavaScript 1.9 <script type="JavaScript 1.9">document.write("executed");</script></li> - <li>JavaScript 2 <script type="JavaScript 2">document.write("executed");</script></li> - <li>JavaScript 2.1 <script type="JavaScript 2.1">document.write("executed");</script></li> - <li>JavaScript 10 <script type="JavaScript 10">document.write("executed");</script></li> - <li>JavaScript 10.0 <script type="JavaScript 10.0">document.write("executed");</script></li> - <li>_javascript <script type="_javascript">document.write("executed");</script></li> - <li>javascript_ <script type="javascript_">document.write("executed");</script></li> - <li>javascript_1.0 <script type="javascript_1.0">document.write("executed");</script></li> - <li>javascript 1.0 x <script type="javascript 1.0 x">document.write("executed");</script></li> - <li>JavaScript1 <script type="JavaScript1">document.write("executed");</script></li> - <li>JavaScript1.0 <script type="JavaScript1.0">document.write("executed");</script></li> - <li>JavaScript1.1 <script type="JavaScript1.1">document.write("executed");</script></li> - <li>JavaScript1.2 <script type="JavaScript1.2">document.write("executed");</script></li> - <li>JavaScript1.3 <script type="JavaScript1.3">document.write("executed");</script></li> - <li>JavaScript1.4 <script type="JavaScript1.4">document.write("executed");</script></li> - <li>JavaScript1.4.1 <script type="JavaScript1.4.1">document.write("executed");</script></li> - <li>JavaScript1.5 <script type="JavaScript1.5">document.write("executed");</script></li> - <li>JavaScript1.6 <script type="JavaScript1.6">document.write("executed");</script></li> - <li>JavaScript1.7 <script type="JavaScript1.7">document.write("executed");</script></li> - <li>1.0 javascript <script type="1.0 javascript">document.write("executed");</script></li> - <li>' javascript ' <script type=" javascript ">document.write("executed");</script></li> - <li>' javascript1.1 ' <script type=" javascript1.1 ">document.write("executed");</script></li> - <li>' javascript ' <script type=" javascript ">document.write("executed");</script></li> - <li>' javascript 1.0 ' <script type=" javascript 1.0 ">document.write("executed");</script></li> - <li>' javascript 1.0 ' <script type=" javascript 1.0 ">document.write("executed");</script></li> - <li>jscript 1 <script type="jscript 1">document.write("executed");</script></li> - <li>jscript 1.0 <script type="jscript 1.0">document.write("executed");</script></li> - <li>ecmascript 1 <script type="ecmascript 1">document.write("executed");</script></li> - <li>ecmascript 1.0 <script type="ecmascript 1.0">document.write("executed");</script></li> - <li>livescript 1 <script type="livescript 1">document.write("executed");</script></li> - <li>livescript 1.0 <script type="livescript 1.0">document.write("executed");</script></li> - <li>' jscript 1.0 ' <script type=" jscript 1.0 ">document.write("executed");</script></li> - <li>disabled_javascript <script type="disabled_javascript">document.write("executed");</script></li> - <li>xxxjavascriptxxx <script type="xxxjavascriptxxx">document.write("executed");</script></li> - <li>bogus <script type="bogus">document.write("executed");</script></li> -</ol> - -<h3>Variations on language attribute of script tag</h3> -<h4>These scripts should execute</h4> -<ol> - <li>no language attribute <script>document.write("executed");</script></li> - <li>empty string <script language="">document.write("executed");</script></li> - <li>jscript <script language="jscript">document.write("executed");</script></li> - <li>ecmascript <script language="ecmascript">document.write("executed");</script></li> - <li>livescript <script language="livescript">document.write("executed");</script></li> - <li>javascript <script language="javascript">document.write("executed");</script></li> - <li>JAVASCRIPT <script language="JAVASCRIPT">document.write("executed");</script></li> - <li>JavaScript <script language="JavaScript">document.write("executed");</script></li> - <li>JavaScript1.0 <script language="JavaScript1.0">document.write("executed");</script></li> - <li>JavaScript1.1 <script language="JavaScript1.1">document.write("executed");</script></li> - <li>JavaScript1.2 <script language="JavaScript1.2">document.write("executed");</script></li> - <li>JavaScript1.3 <script language="JavaScript1.3">document.write("executed");</script></li> - <li>JavaScript1.4 <script language="JavaScript1.4">document.write("executed");</script></li> - <li>JavaScript1.5 <script language="JavaScript1.5">document.write("executed");</script></li> - <li>JavaScript1.6 <script language="JavaScript1.6">document.write("executed");</script></li> - <li>JavaScript1.7 <script language="JavaScript1.7">document.write("executed");</script></li> -</ol> -<h4>These scripts should not execute</h4> -<ol> - <li>one space <script language=" ">document.write("executed");</script></li> - <li>vbscript <script language="vbscript">document.write("executed");</script></li> - <li>livescript1.1 <script language="livescript1.1">document.write("executed");</script></li> - <li>JavaScript 1 <script language="JavaScript 1">document.write("executed");</script></li> - <li>JavaScript 1.0 <script language="JavaScript 1.0">document.write("executed");</script></li> - <li>JavaScript 1.1 <script language="JavaScript 1.1">document.write("executed");</script></li> - <li>JavaScript 1.1.1 <script language="JavaScript 1.1.1">document.write("executed");</script></li> - <li>JavaScript 1.2 <script language="JavaScript 1.2">document.write("executed");</script></li> - <li>JavaScript 1.3 <script language="JavaScript 1.3">document.write("executed");</script></li> - <li>JavaScript 1.4 <script language="JavaScript 1.4">document.write("executed");</script></li> - <li>JavaScript 1.5 <script language="JavaScript 1.5">document.write("executed");</script></li> - <li>JavaScript 1.6 <script language="JavaScript 1.6">document.write("executed");</script></li> - <li>JavaScript 1.7 <script language="JavaScript 1.7">document.write("executed");</script></li> - <li>JavaScript 1.8 <script language="JavaScript 1.8">document.write("executed");</script></li> - <li>JavaScript 1.9 <script language="JavaScript 1.9">document.write("executed");</script></li> - <li>JavaScript 2 <script language="JavaScript 2">document.write("executed");</script></li> - <li>JavaScript 2.1 <script language="JavaScript 2.1">document.write("executed");</script></li> - <li>JavaScript 10 <script language="JavaScript 10">document.write("executed");</script></li> - <li>JavaScript 10.0 <script language="JavaScript 10.0">document.write("executed");</script></li> - <li>_javascript <script language="_javascript">document.write("executed");</script></li> - <li>javascript_ <script language="javascript_">document.write("executed");</script></li> - <li>javascript_1.0 <script language="javascript_1.0">document.write("executed");</script></li> - <li>javascript 1.0 x <script language="javascript 1.0 x">document.write("executed");</script></li> - <li>JavaScript1 <script language="JavaScript1">document.write("executed");</script></li> - <li>JavaScript1.8 <script language="JavaScript1.8">document.write("executed");</script></li> - <li>JavaScript1.9 <script language="JavaScript1.9">document.write("executed");</script></li> - <li>JavaScript1.4.1 <script language="JavaScript1.4.1">document.write("executed");</script></li> - <li>1.0 javascript <script language="1.0 javascript">document.write("executed");</script></li> - <li>' javascript ' <script language=" javascript ">document.write("executed");</script></li> - <li>' javascript1.1 ' <script language=" javascript1.1 ">document.write("executed");</script></li> - <li>' javascript ' <script language=" javascript ">document.write("executed");</script></li> - <li>' javascript 1.0 ' <script language=" javascript 1.0 ">document.write("executed");</script></li> - <li>' javascript 1.0 ' <script language=" javascript 1.0 ">document.write("executed");</script></li> - <li>jscript 1 <script language="jscript 1">document.write("executed");</script></li> - <li>jscript 1.0 <script language="jscript 1.0">document.write("executed");</script></li> - <li>ecmascript 1 <script language="ecmascript 1">document.write("executed");</script></li> - <li>ecmascript 1.0 <script language="ecmascript 1.0">document.write("executed");</script></li> - <li>livescript 1 <script language="livescript 1">document.write("executed");</script></li> - <li>livescript 1.0 <script language="livescript 1.0">document.write("executed");</script></li> - <li>' jscript 1.0 ' <script language=" jscript 1.0 ">document.write("executed");</script></li> - <li>disabled_javascript <script language="disabled_javascript">document.write("executed");</script></li> - <li>xxxjavascriptxxx <script language="xxxjavascriptxxx">document.write("executed");</script></li> - <li>bogus <script language="bogus">document.write("executed");</script></li> -</ol> - -<h3>Variations on combined type and language attributes of script tag</h3> -<h4>These scripts should execute</h4> -<ol> - <li>empty string type, "javascript" language <script type="" language="javascript">document.write("executed");</script></li> - <li>empty string language, "text/javascript" type <script type="text/javascript" language="">document.write("executed");</script></li> - <li>"javascript" language, "text/javascript" type <script type="text/javascript" language="javascript">document.write("executed");</script></li> - <li>"bogus" language, "text/javascript" type <script type="text/javascript" language="bogus">document.write("executed");</script></li> - <li>"livescript" language, "text/javascript" type <script type="text/javascript" language="livescript">document.write("executed");</script></li> - <li>"javascript1.2" language, "text/javascript" type <script type="text/javascript" language="javascript1.2">document.write("executed");</script></li> - <li>empty string type, "bogus" language <script type="" language="bogus">document.write("executed");</script></li> -</ol> -<h4>These scripts should not execute</h4> -<ol> - <li>"javascript" language, "bogus" type <script type="bogus" language="javascript">document.write("executed");</script></li> - <li>empty string language, "bogus" type <script type="bogus" language="">document.write("executed");</script></li> -</ol> -</body> -</html>
diff --git a/third_party/blink/web_tests/http/tests/inspector-protocol/fenced-frame/setWebLifecycleState-fenced-frame.https.js b/third_party/blink/web_tests/http/tests/inspector-protocol/fenced-frame/setWebLifecycleState-fenced-frame.https.js new file mode 100644 index 0000000..3ad1545 --- /dev/null +++ b/third_party/blink/web_tests/http/tests/inspector-protocol/fenced-frame/setWebLifecycleState-fenced-frame.https.js
@@ -0,0 +1,26 @@ +(async function(testRunner) { + const {session, dp} = await testRunner.startURL( + 'resources/page-with-fenced-frame.php', + 'Tests that Page.setWebLifecycleState() in a fenced frame is not allowed.'); + await dp.Page.enable(); + await dp.Runtime.enable(); + + dp.Target.setAutoAttach( + {autoAttach: true, waitForDebuggerOnStart: false, flatten: true}); + let {sessionId} = (await dp.Target.onceAttachedToTarget()).params; + + let childSession = session.createChild(sessionId); + let ffdp = childSession.protocol; + + // Wait for FF to finish loading. + await ffdp.Page.enable(); + ffdp.Page.setLifecycleEventsEnabled({enabled: true}); + await ffdp.Page.onceLifecycleEvent(event => event.params.name === 'load'); + + // setWebLifecycleState() in a fenced frame gets an error. + const result = await ffdp.Page.setWebLifecycleState({state: 'frozen'}); + testRunner.log( + 'Page.setWebLifecycleState() from a fenced frame:\n' + + (result.error ? 'PASS: ' + result.error.message : 'FAIL: no error')); + testRunner.completeTest(); +}) \ No newline at end of file
diff --git a/third_party/blink/web_tests/platform/generic/external/wpt/html/semantics/scripting-1/the-script-element/script-type-and-language-js-expected.txt b/third_party/blink/web_tests/platform/generic/external/wpt/html/semantics/scripting-1/the-script-element/script-type-and-language-js-expected.txt deleted file mode 100644 index 43acb10..0000000 --- a/third_party/blink/web_tests/platform/generic/external/wpt/html/semantics/scripting-1/the-script-element/script-type-and-language-js-expected.txt +++ /dev/null
@@ -1,460 +0,0 @@ -This is a testharness.js-based test. -Found 456 tests; 454 PASS, 2 FAIL, 0 TIMEOUT, 0 NOTRUN. -PASS Script should run with type="" -PASS Script shouldn't run with type=" " -PASS Script should run with type="application/ecmascript" -PASS Script should run with type="application/javascript" -PASS Script should run with type="application/x-ecmascript" -PASS Script should run with type="application/x-javascript" -PASS Script should run with type="APPLICATION/ECMASCRIPT" -PASS Script should run with type="APPLICATION/JAVASCRIPT" -PASS Script should run with type="APPLICATION/X-ECMASCRIPT" -PASS Script should run with type="APPLICATION/X-JAVASCRIPT" -PASS Script should run with type="application/ecmascript " -PASS Script should run with type="application/javascript " -PASS Script should run with type="application/x-ecmascript " -PASS Script should run with type="application/x-javascript " -PASS Script should run with type=" application/ecmascript" -PASS Script should run with type=" application/javascript" -PASS Script should run with type=" application/x-ecmascript" -PASS Script should run with type=" application/x-javascript" -PASS Script should run with type="application/ecmascript\t" -PASS Script should run with type="application/javascript\t" -PASS Script should run with type="application/x-ecmascript\t" -PASS Script should run with type="application/x-javascript\t" -PASS Script should run with type="\tapplication/ecmascript" -PASS Script should run with type="\tapplication/javascript" -PASS Script should run with type="\tapplication/x-ecmascript" -PASS Script should run with type="\tapplication/x-javascript" -PASS Script should run with type="application/ecmascript\n" -PASS Script should run with type="application/javascript\n" -PASS Script should run with type="application/x-ecmascript\n" -PASS Script should run with type="application/x-javascript\n" -PASS Script should run with type="\napplication/ecmascript" -PASS Script should run with type="\napplication/javascript" -PASS Script should run with type="\napplication/x-ecmascript" -PASS Script should run with type="\napplication/x-javascript" -PASS Script should run with type="application/ecmascript\r" -PASS Script should run with type="application/javascript\r" -PASS Script should run with type="application/x-ecmascript\r" -PASS Script should run with type="application/x-javascript\r" -PASS Script should run with type="\rapplication/ecmascript" -PASS Script should run with type="\rapplication/javascript" -PASS Script should run with type="\rapplication/x-ecmascript" -PASS Script should run with type="\rapplication/x-javascript" -PASS Script should run with type="application/ecmascript\f" -PASS Script should run with type="application/javascript\f" -PASS Script should run with type="application/x-ecmascript\f" -PASS Script should run with type="application/x-javascript\f" -PASS Script should run with type="\fapplication/ecmascript" -PASS Script should run with type="\fapplication/javascript" -PASS Script should run with type="\fapplication/x-ecmascript" -PASS Script should run with type="\fapplication/x-javascript" -PASS Script shouldn't run with type="application/ecmascript\0" -PASS Script shouldn't run with type="application/javascript\0" -PASS Script shouldn't run with type="application/x-ecmascript\0" -PASS Script shouldn't run with type="application/x-javascript\0" -PASS Script shouldn't run with type="application/ecmascript\0foo" -PASS Script shouldn't run with type="application/javascript\0foo" -PASS Script shouldn't run with type="application/x-ecmascript\0foo" -PASS Script shouldn't run with type="application/x-javascript\0foo" -PASS Script should run with type="text/ecmascript" -PASS Script should run with type="text/javascript" -PASS Script should run with type="text/javascript1.0" -PASS Script should run with type="text/javascript1.1" -PASS Script should run with type="text/javascript1.2" -PASS Script should run with type="text/javascript1.3" -PASS Script should run with type="text/javascript1.4" -PASS Script should run with type="text/javascript1.5" -PASS Script should run with type="text/jscript" -PASS Script should run with type="text/livescript" -PASS Script should run with type="text/x-ecmascript" -PASS Script should run with type="text/x-javascript" -PASS Script should run with type="TEXT/ECMASCRIPT" -PASS Script should run with type="TEXT/JAVASCRIPT" -PASS Script should run with type="TEXT/JAVASCRIPT1.0" -PASS Script should run with type="TEXT/JAVASCRIPT1.1" -PASS Script should run with type="TEXT/JAVASCRIPT1.2" -PASS Script should run with type="TEXT/JAVASCRIPT1.3" -PASS Script should run with type="TEXT/JAVASCRIPT1.4" -PASS Script should run with type="TEXT/JAVASCRIPT1.5" -PASS Script should run with type="TEXT/JSCRIPT" -PASS Script should run with type="TEXT/LIVESCRIPT" -PASS Script should run with type="TEXT/X-ECMASCRIPT" -PASS Script should run with type="TEXT/X-JAVASCRIPT" -PASS Script shouldn't run with type="text/javascript1.6" -PASS Script shouldn't run with type="text/javascript1.7" -PASS Script shouldn't run with type="text/javascript1.8" -PASS Script shouldn't run with type="text/javascript1.9" -PASS Script should run with type="text/ecmascript " -PASS Script should run with type="text/javascript " -PASS Script should run with type="text/javascript1.0 " -PASS Script should run with type="text/javascript1.1 " -PASS Script should run with type="text/javascript1.2 " -PASS Script should run with type="text/javascript1.3 " -PASS Script should run with type="text/javascript1.4 " -PASS Script should run with type="text/javascript1.5 " -PASS Script should run with type="text/jscript " -PASS Script should run with type="text/livescript " -PASS Script should run with type="text/x-ecmascript " -PASS Script should run with type="text/x-javascript " -PASS Script should run with type=" text/ecmascript" -PASS Script should run with type=" text/javascript" -PASS Script should run with type=" text/javascript1.0" -PASS Script should run with type=" text/javascript1.1" -PASS Script should run with type=" text/javascript1.2" -PASS Script should run with type=" text/javascript1.3" -PASS Script should run with type=" text/javascript1.4" -PASS Script should run with type=" text/javascript1.5" -PASS Script should run with type=" text/jscript" -PASS Script should run with type=" text/livescript" -PASS Script should run with type=" text/x-ecmascript" -PASS Script should run with type=" text/x-javascript" -PASS Script should run with type="text/ecmascript\t" -PASS Script should run with type="text/javascript\t" -PASS Script should run with type="text/javascript1.0\t" -PASS Script should run with type="text/javascript1.1\t" -PASS Script should run with type="text/javascript1.2\t" -PASS Script should run with type="text/javascript1.3\t" -PASS Script should run with type="text/javascript1.4\t" -PASS Script should run with type="text/javascript1.5\t" -PASS Script should run with type="text/jscript\t" -PASS Script should run with type="text/livescript\t" -PASS Script should run with type="text/x-ecmascript\t" -PASS Script should run with type="text/x-javascript\t" -PASS Script should run with type="\ttext/ecmascript" -PASS Script should run with type="\ttext/javascript" -PASS Script should run with type="\ttext/javascript1.0" -PASS Script should run with type="\ttext/javascript1.1" -PASS Script should run with type="\ttext/javascript1.2" -PASS Script should run with type="\ttext/javascript1.3" -PASS Script should run with type="\ttext/javascript1.4" -PASS Script should run with type="\ttext/javascript1.5" -PASS Script should run with type="\ttext/jscript" -PASS Script should run with type="\ttext/livescript" -PASS Script should run with type="\ttext/x-ecmascript" -PASS Script should run with type="\ttext/x-javascript" -PASS Script should run with type="text/ecmascript\n" -PASS Script should run with type="text/javascript\n" -PASS Script should run with type="text/javascript1.0\n" -PASS Script should run with type="text/javascript1.1\n" -PASS Script should run with type="text/javascript1.2\n" -PASS Script should run with type="text/javascript1.3\n" -PASS Script should run with type="text/javascript1.4\n" -PASS Script should run with type="text/javascript1.5\n" -PASS Script should run with type="text/jscript\n" -PASS Script should run with type="text/livescript\n" -PASS Script should run with type="text/x-ecmascript\n" -PASS Script should run with type="text/x-javascript\n" -PASS Script should run with type="\ntext/ecmascript" -PASS Script should run with type="\ntext/javascript" -PASS Script should run with type="\ntext/javascript1.0" -PASS Script should run with type="\ntext/javascript1.1" -PASS Script should run with type="\ntext/javascript1.2" -PASS Script should run with type="\ntext/javascript1.3" -PASS Script should run with type="\ntext/javascript1.4" -PASS Script should run with type="\ntext/javascript1.5" -PASS Script should run with type="\ntext/jscript" -PASS Script should run with type="\ntext/livescript" -PASS Script should run with type="\ntext/x-ecmascript" -PASS Script should run with type="\ntext/x-javascript" -PASS Script should run with type="text/ecmascript\r" -PASS Script should run with type="text/javascript\r" -PASS Script should run with type="text/javascript1.0\r" -PASS Script should run with type="text/javascript1.1\r" -PASS Script should run with type="text/javascript1.2\r" -PASS Script should run with type="text/javascript1.3\r" -PASS Script should run with type="text/javascript1.4\r" -PASS Script should run with type="text/javascript1.5\r" -PASS Script should run with type="text/jscript\r" -PASS Script should run with type="text/livescript\r" -PASS Script should run with type="text/x-ecmascript\r" -PASS Script should run with type="text/x-javascript\r" -PASS Script should run with type="\rtext/ecmascript" -PASS Script should run with type="\rtext/javascript" -PASS Script should run with type="\rtext/javascript1.0" -PASS Script should run with type="\rtext/javascript1.1" -PASS Script should run with type="\rtext/javascript1.2" -PASS Script should run with type="\rtext/javascript1.3" -PASS Script should run with type="\rtext/javascript1.4" -PASS Script should run with type="\rtext/javascript1.5" -PASS Script should run with type="\rtext/jscript" -PASS Script should run with type="\rtext/livescript" -PASS Script should run with type="\rtext/x-ecmascript" -PASS Script should run with type="\rtext/x-javascript" -PASS Script should run with type="text/ecmascript\f" -PASS Script should run with type="text/javascript\f" -PASS Script should run with type="text/javascript1.0\f" -PASS Script should run with type="text/javascript1.1\f" -PASS Script should run with type="text/javascript1.2\f" -PASS Script should run with type="text/javascript1.3\f" -PASS Script should run with type="text/javascript1.4\f" -PASS Script should run with type="text/javascript1.5\f" -PASS Script should run with type="text/jscript\f" -PASS Script should run with type="text/livescript\f" -PASS Script should run with type="text/x-ecmascript\f" -PASS Script should run with type="text/x-javascript\f" -PASS Script should run with type="\ftext/ecmascript" -PASS Script should run with type="\ftext/javascript" -PASS Script should run with type="\ftext/javascript1.0" -PASS Script should run with type="\ftext/javascript1.1" -PASS Script should run with type="\ftext/javascript1.2" -PASS Script should run with type="\ftext/javascript1.3" -PASS Script should run with type="\ftext/javascript1.4" -PASS Script should run with type="\ftext/javascript1.5" -PASS Script should run with type="\ftext/jscript" -PASS Script should run with type="\ftext/livescript" -PASS Script should run with type="\ftext/x-ecmascript" -PASS Script should run with type="\ftext/x-javascript" -PASS Script shouldn't run with type="text/ecmascript\0" -PASS Script shouldn't run with type="text/javascript\0" -PASS Script shouldn't run with type="text/javascript1.0\0" -PASS Script shouldn't run with type="text/javascript1.1\0" -PASS Script shouldn't run with type="text/javascript1.2\0" -PASS Script shouldn't run with type="text/javascript1.3\0" -PASS Script shouldn't run with type="text/javascript1.4\0" -PASS Script shouldn't run with type="text/javascript1.5\0" -PASS Script shouldn't run with type="text/jscript\0" -PASS Script shouldn't run with type="text/livescript\0" -PASS Script shouldn't run with type="text/x-ecmascript\0" -PASS Script shouldn't run with type="text/x-javascript\0" -PASS Script shouldn't run with type="text/ecmascript\0foo" -PASS Script shouldn't run with type="text/javascript\0foo" -PASS Script shouldn't run with type="text/javascript1.0\0foo" -PASS Script shouldn't run with type="text/javascript1.1\0foo" -PASS Script shouldn't run with type="text/javascript1.2\0foo" -PASS Script shouldn't run with type="text/javascript1.3\0foo" -PASS Script shouldn't run with type="text/javascript1.4\0foo" -PASS Script shouldn't run with type="text/javascript1.5\0foo" -PASS Script shouldn't run with type="text/jscript\0foo" -PASS Script shouldn't run with type="text/livescript\0foo" -PASS Script shouldn't run with type="text/x-ecmascript\0foo" -PASS Script shouldn't run with type="text/x-javascript\0foo" -PASS Script shouldn't run with type="ecmascript" -PASS Script shouldn't run with type="javascript" -PASS Script shouldn't run with type="javascript1.0" -PASS Script shouldn't run with type="javascript1.1" -PASS Script shouldn't run with type="javascript1.2" -PASS Script shouldn't run with type="javascript1.3" -PASS Script shouldn't run with type="javascript1.4" -PASS Script shouldn't run with type="javascript1.5" -PASS Script shouldn't run with type="jscript" -PASS Script shouldn't run with type="livescript" -PASS Script shouldn't run with type="x-ecmascript" -PASS Script shouldn't run with type="x-javascript" -PASS Script shouldn't run with type="javascript1.6" -PASS Script shouldn't run with type="javascript1.7" -PASS Script shouldn't run with type="javascript1.8" -PASS Script shouldn't run with type="javascript1.9" -PASS Script should run with language="" -PASS Script shouldn't run with language=" " -PASS Script should run with language="ecmascript" -PASS Script should run with language="javascript" -PASS Script should run with language="javascript1.0" -PASS Script should run with language="javascript1.1" -PASS Script should run with language="javascript1.2" -PASS Script should run with language="javascript1.3" -PASS Script should run with language="javascript1.4" -PASS Script should run with language="javascript1.5" -PASS Script should run with language="jscript" -PASS Script should run with language="livescript" -PASS Script should run with language="x-ecmascript" -PASS Script should run with language="x-javascript" -PASS Script should run with language="ECMASCRIPT" -PASS Script should run with language="JAVASCRIPT" -PASS Script should run with language="JAVASCRIPT1.0" -PASS Script should run with language="JAVASCRIPT1.1" -PASS Script should run with language="JAVASCRIPT1.2" -PASS Script should run with language="JAVASCRIPT1.3" -PASS Script should run with language="JAVASCRIPT1.4" -PASS Script should run with language="JAVASCRIPT1.5" -PASS Script should run with language="JSCRIPT" -PASS Script should run with language="LIVESCRIPT" -PASS Script should run with language="X-ECMASCRIPT" -PASS Script should run with language="X-JAVASCRIPT" -FAIL Script shouldn't run with language="javascript1.6" assert_equals: expected false but got true -FAIL Script shouldn't run with language="javascript1.7" assert_equals: expected false but got true -PASS Script shouldn't run with language="javascript1.8" -PASS Script shouldn't run with language="javascript1.9" -PASS Script shouldn't run with language="ecmascript " -PASS Script shouldn't run with language="javascript " -PASS Script shouldn't run with language="javascript1.0 " -PASS Script shouldn't run with language="javascript1.1 " -PASS Script shouldn't run with language="javascript1.2 " -PASS Script shouldn't run with language="javascript1.3 " -PASS Script shouldn't run with language="javascript1.4 " -PASS Script shouldn't run with language="javascript1.5 " -PASS Script shouldn't run with language="jscript " -PASS Script shouldn't run with language="livescript " -PASS Script shouldn't run with language="x-ecmascript " -PASS Script shouldn't run with language="x-javascript " -PASS Script shouldn't run with language=" ecmascript" -PASS Script shouldn't run with language=" javascript" -PASS Script shouldn't run with language=" javascript1.0" -PASS Script shouldn't run with language=" javascript1.1" -PASS Script shouldn't run with language=" javascript1.2" -PASS Script shouldn't run with language=" javascript1.3" -PASS Script shouldn't run with language=" javascript1.4" -PASS Script shouldn't run with language=" javascript1.5" -PASS Script shouldn't run with language=" jscript" -PASS Script shouldn't run with language=" livescript" -PASS Script shouldn't run with language=" x-ecmascript" -PASS Script shouldn't run with language=" x-javascript" -PASS Script shouldn't run with language="ecmascript\t" -PASS Script shouldn't run with language="javascript\t" -PASS Script shouldn't run with language="javascript1.0\t" -PASS Script shouldn't run with language="javascript1.1\t" -PASS Script shouldn't run with language="javascript1.2\t" -PASS Script shouldn't run with language="javascript1.3\t" -PASS Script shouldn't run with language="javascript1.4\t" -PASS Script shouldn't run with language="javascript1.5\t" -PASS Script shouldn't run with language="jscript\t" -PASS Script shouldn't run with language="livescript\t" -PASS Script shouldn't run with language="x-ecmascript\t" -PASS Script shouldn't run with language="x-javascript\t" -PASS Script shouldn't run with language="\tecmascript" -PASS Script shouldn't run with language="\tjavascript" -PASS Script shouldn't run with language="\tjavascript1.0" -PASS Script shouldn't run with language="\tjavascript1.1" -PASS Script shouldn't run with language="\tjavascript1.2" -PASS Script shouldn't run with language="\tjavascript1.3" -PASS Script shouldn't run with language="\tjavascript1.4" -PASS Script shouldn't run with language="\tjavascript1.5" -PASS Script shouldn't run with language="\tjscript" -PASS Script shouldn't run with language="\tlivescript" -PASS Script shouldn't run with language="\tx-ecmascript" -PASS Script shouldn't run with language="\tx-javascript" -PASS Script shouldn't run with language="ecmascript\n" -PASS Script shouldn't run with language="javascript\n" -PASS Script shouldn't run with language="javascript1.0\n" -PASS Script shouldn't run with language="javascript1.1\n" -PASS Script shouldn't run with language="javascript1.2\n" -PASS Script shouldn't run with language="javascript1.3\n" -PASS Script shouldn't run with language="javascript1.4\n" -PASS Script shouldn't run with language="javascript1.5\n" -PASS Script shouldn't run with language="jscript\n" -PASS Script shouldn't run with language="livescript\n" -PASS Script shouldn't run with language="x-ecmascript\n" -PASS Script shouldn't run with language="x-javascript\n" -PASS Script shouldn't run with language="\necmascript" -PASS Script shouldn't run with language="\njavascript" -PASS Script shouldn't run with language="\njavascript1.0" -PASS Script shouldn't run with language="\njavascript1.1" -PASS Script shouldn't run with language="\njavascript1.2" -PASS Script shouldn't run with language="\njavascript1.3" -PASS Script shouldn't run with language="\njavascript1.4" -PASS Script shouldn't run with language="\njavascript1.5" -PASS Script shouldn't run with language="\njscript" -PASS Script shouldn't run with language="\nlivescript" -PASS Script shouldn't run with language="\nx-ecmascript" -PASS Script shouldn't run with language="\nx-javascript" -PASS Script shouldn't run with language="ecmascript\r" -PASS Script shouldn't run with language="javascript\r" -PASS Script shouldn't run with language="javascript1.0\r" -PASS Script shouldn't run with language="javascript1.1\r" -PASS Script shouldn't run with language="javascript1.2\r" -PASS Script shouldn't run with language="javascript1.3\r" -PASS Script shouldn't run with language="javascript1.4\r" -PASS Script shouldn't run with language="javascript1.5\r" -PASS Script shouldn't run with language="jscript\r" -PASS Script shouldn't run with language="livescript\r" -PASS Script shouldn't run with language="x-ecmascript\r" -PASS Script shouldn't run with language="x-javascript\r" -PASS Script shouldn't run with language="\recmascript" -PASS Script shouldn't run with language="\rjavascript" -PASS Script shouldn't run with language="\rjavascript1.0" -PASS Script shouldn't run with language="\rjavascript1.1" -PASS Script shouldn't run with language="\rjavascript1.2" -PASS Script shouldn't run with language="\rjavascript1.3" -PASS Script shouldn't run with language="\rjavascript1.4" -PASS Script shouldn't run with language="\rjavascript1.5" -PASS Script shouldn't run with language="\rjscript" -PASS Script shouldn't run with language="\rlivescript" -PASS Script shouldn't run with language="\rx-ecmascript" -PASS Script shouldn't run with language="\rx-javascript" -PASS Script shouldn't run with language="ecmascript\f" -PASS Script shouldn't run with language="javascript\f" -PASS Script shouldn't run with language="javascript1.0\f" -PASS Script shouldn't run with language="javascript1.1\f" -PASS Script shouldn't run with language="javascript1.2\f" -PASS Script shouldn't run with language="javascript1.3\f" -PASS Script shouldn't run with language="javascript1.4\f" -PASS Script shouldn't run with language="javascript1.5\f" -PASS Script shouldn't run with language="jscript\f" -PASS Script shouldn't run with language="livescript\f" -PASS Script shouldn't run with language="x-ecmascript\f" -PASS Script shouldn't run with language="x-javascript\f" -PASS Script shouldn't run with language="\fecmascript" -PASS Script shouldn't run with language="\fjavascript" -PASS Script shouldn't run with language="\fjavascript1.0" -PASS Script shouldn't run with language="\fjavascript1.1" -PASS Script shouldn't run with language="\fjavascript1.2" -PASS Script shouldn't run with language="\fjavascript1.3" -PASS Script shouldn't run with language="\fjavascript1.4" -PASS Script shouldn't run with language="\fjavascript1.5" -PASS Script shouldn't run with language="\fjscript" -PASS Script shouldn't run with language="\flivescript" -PASS Script shouldn't run with language="\fx-ecmascript" -PASS Script shouldn't run with language="\fx-javascript" -PASS Script shouldn't run with language="ecmascriptxyz" -PASS Script shouldn't run with language="javascriptxyz" -PASS Script shouldn't run with language="javascript1.0xyz" -PASS Script shouldn't run with language="javascript1.1xyz" -PASS Script shouldn't run with language="javascript1.2xyz" -PASS Script shouldn't run with language="javascript1.3xyz" -PASS Script shouldn't run with language="javascript1.4xyz" -PASS Script shouldn't run with language="javascript1.5xyz" -PASS Script shouldn't run with language="jscriptxyz" -PASS Script shouldn't run with language="livescriptxyz" -PASS Script shouldn't run with language="x-ecmascriptxyz" -PASS Script shouldn't run with language="x-javascriptxyz" -PASS Script shouldn't run with language="xyzecmascript" -PASS Script shouldn't run with language="xyzjavascript" -PASS Script shouldn't run with language="xyzjavascript1.0" -PASS Script shouldn't run with language="xyzjavascript1.1" -PASS Script shouldn't run with language="xyzjavascript1.2" -PASS Script shouldn't run with language="xyzjavascript1.3" -PASS Script shouldn't run with language="xyzjavascript1.4" -PASS Script shouldn't run with language="xyzjavascript1.5" -PASS Script shouldn't run with language="xyzjscript" -PASS Script shouldn't run with language="xyzlivescript" -PASS Script shouldn't run with language="xyzx-ecmascript" -PASS Script shouldn't run with language="xyzx-javascript" -PASS Script shouldn't run with language="ecmascript\0" -PASS Script shouldn't run with language="javascript\0" -PASS Script shouldn't run with language="javascript1.0\0" -PASS Script shouldn't run with language="javascript1.1\0" -PASS Script shouldn't run with language="javascript1.2\0" -PASS Script shouldn't run with language="javascript1.3\0" -PASS Script shouldn't run with language="javascript1.4\0" -PASS Script shouldn't run with language="javascript1.5\0" -PASS Script shouldn't run with language="jscript\0" -PASS Script shouldn't run with language="livescript\0" -PASS Script shouldn't run with language="x-ecmascript\0" -PASS Script shouldn't run with language="x-javascript\0" -PASS Script shouldn't run with language="ecmascript\0foo" -PASS Script shouldn't run with language="javascript\0foo" -PASS Script shouldn't run with language="javascript1.0\0foo" -PASS Script shouldn't run with language="javascript1.1\0foo" -PASS Script shouldn't run with language="javascript1.2\0foo" -PASS Script shouldn't run with language="javascript1.3\0foo" -PASS Script shouldn't run with language="javascript1.4\0foo" -PASS Script shouldn't run with language="javascript1.5\0foo" -PASS Script shouldn't run with language="jscript\0foo" -PASS Script shouldn't run with language="livescript\0foo" -PASS Script shouldn't run with language="x-ecmascript\0foo" -PASS Script shouldn't run with language="x-javascript\0foo" -PASS Script shouldn't run with type=javascript (parser-inserted) -PASS Script shouldn't run with type=javascript1.0 (parser-inserted) -PASS Script shouldn't run with type=javascript1.1 (parser-inserted) -PASS Script shouldn't run with type=javascript1.2 (parser-inserted) -PASS Script shouldn't run with type=javascript1.3 (parser-inserted) -PASS Script shouldn't run with type=javascript1.4 (parser-inserted) -PASS Script shouldn't run with type=javascript1.5 (parser-inserted) -PASS Script shouldn't run with type=javascript1.6 (parser-inserted) -PASS Script shouldn't run with type=javascript1.7 (parser-inserted) -PASS Script shouldn't run with type=livescript (parser-inserted) -PASS Script shouldn't run with type=ecmascript (parser-inserted) -PASS Script shouldn't run with type=jscript (parser-inserted) -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/platform/generic/external/wpt/html/semantics/scripting-1/the-script-element/script-type-and-language-js-xhtml-expected.txt b/third_party/blink/web_tests/platform/generic/external/wpt/html/semantics/scripting-1/the-script-element/script-type-and-language-js-xhtml-expected.txt deleted file mode 100644 index 43acb10..0000000 --- a/third_party/blink/web_tests/platform/generic/external/wpt/html/semantics/scripting-1/the-script-element/script-type-and-language-js-xhtml-expected.txt +++ /dev/null
@@ -1,460 +0,0 @@ -This is a testharness.js-based test. -Found 456 tests; 454 PASS, 2 FAIL, 0 TIMEOUT, 0 NOTRUN. -PASS Script should run with type="" -PASS Script shouldn't run with type=" " -PASS Script should run with type="application/ecmascript" -PASS Script should run with type="application/javascript" -PASS Script should run with type="application/x-ecmascript" -PASS Script should run with type="application/x-javascript" -PASS Script should run with type="APPLICATION/ECMASCRIPT" -PASS Script should run with type="APPLICATION/JAVASCRIPT" -PASS Script should run with type="APPLICATION/X-ECMASCRIPT" -PASS Script should run with type="APPLICATION/X-JAVASCRIPT" -PASS Script should run with type="application/ecmascript " -PASS Script should run with type="application/javascript " -PASS Script should run with type="application/x-ecmascript " -PASS Script should run with type="application/x-javascript " -PASS Script should run with type=" application/ecmascript" -PASS Script should run with type=" application/javascript" -PASS Script should run with type=" application/x-ecmascript" -PASS Script should run with type=" application/x-javascript" -PASS Script should run with type="application/ecmascript\t" -PASS Script should run with type="application/javascript\t" -PASS Script should run with type="application/x-ecmascript\t" -PASS Script should run with type="application/x-javascript\t" -PASS Script should run with type="\tapplication/ecmascript" -PASS Script should run with type="\tapplication/javascript" -PASS Script should run with type="\tapplication/x-ecmascript" -PASS Script should run with type="\tapplication/x-javascript" -PASS Script should run with type="application/ecmascript\n" -PASS Script should run with type="application/javascript\n" -PASS Script should run with type="application/x-ecmascript\n" -PASS Script should run with type="application/x-javascript\n" -PASS Script should run with type="\napplication/ecmascript" -PASS Script should run with type="\napplication/javascript" -PASS Script should run with type="\napplication/x-ecmascript" -PASS Script should run with type="\napplication/x-javascript" -PASS Script should run with type="application/ecmascript\r" -PASS Script should run with type="application/javascript\r" -PASS Script should run with type="application/x-ecmascript\r" -PASS Script should run with type="application/x-javascript\r" -PASS Script should run with type="\rapplication/ecmascript" -PASS Script should run with type="\rapplication/javascript" -PASS Script should run with type="\rapplication/x-ecmascript" -PASS Script should run with type="\rapplication/x-javascript" -PASS Script should run with type="application/ecmascript\f" -PASS Script should run with type="application/javascript\f" -PASS Script should run with type="application/x-ecmascript\f" -PASS Script should run with type="application/x-javascript\f" -PASS Script should run with type="\fapplication/ecmascript" -PASS Script should run with type="\fapplication/javascript" -PASS Script should run with type="\fapplication/x-ecmascript" -PASS Script should run with type="\fapplication/x-javascript" -PASS Script shouldn't run with type="application/ecmascript\0" -PASS Script shouldn't run with type="application/javascript\0" -PASS Script shouldn't run with type="application/x-ecmascript\0" -PASS Script shouldn't run with type="application/x-javascript\0" -PASS Script shouldn't run with type="application/ecmascript\0foo" -PASS Script shouldn't run with type="application/javascript\0foo" -PASS Script shouldn't run with type="application/x-ecmascript\0foo" -PASS Script shouldn't run with type="application/x-javascript\0foo" -PASS Script should run with type="text/ecmascript" -PASS Script should run with type="text/javascript" -PASS Script should run with type="text/javascript1.0" -PASS Script should run with type="text/javascript1.1" -PASS Script should run with type="text/javascript1.2" -PASS Script should run with type="text/javascript1.3" -PASS Script should run with type="text/javascript1.4" -PASS Script should run with type="text/javascript1.5" -PASS Script should run with type="text/jscript" -PASS Script should run with type="text/livescript" -PASS Script should run with type="text/x-ecmascript" -PASS Script should run with type="text/x-javascript" -PASS Script should run with type="TEXT/ECMASCRIPT" -PASS Script should run with type="TEXT/JAVASCRIPT" -PASS Script should run with type="TEXT/JAVASCRIPT1.0" -PASS Script should run with type="TEXT/JAVASCRIPT1.1" -PASS Script should run with type="TEXT/JAVASCRIPT1.2" -PASS Script should run with type="TEXT/JAVASCRIPT1.3" -PASS Script should run with type="TEXT/JAVASCRIPT1.4" -PASS Script should run with type="TEXT/JAVASCRIPT1.5" -PASS Script should run with type="TEXT/JSCRIPT" -PASS Script should run with type="TEXT/LIVESCRIPT" -PASS Script should run with type="TEXT/X-ECMASCRIPT" -PASS Script should run with type="TEXT/X-JAVASCRIPT" -PASS Script shouldn't run with type="text/javascript1.6" -PASS Script shouldn't run with type="text/javascript1.7" -PASS Script shouldn't run with type="text/javascript1.8" -PASS Script shouldn't run with type="text/javascript1.9" -PASS Script should run with type="text/ecmascript " -PASS Script should run with type="text/javascript " -PASS Script should run with type="text/javascript1.0 " -PASS Script should run with type="text/javascript1.1 " -PASS Script should run with type="text/javascript1.2 " -PASS Script should run with type="text/javascript1.3 " -PASS Script should run with type="text/javascript1.4 " -PASS Script should run with type="text/javascript1.5 " -PASS Script should run with type="text/jscript " -PASS Script should run with type="text/livescript " -PASS Script should run with type="text/x-ecmascript " -PASS Script should run with type="text/x-javascript " -PASS Script should run with type=" text/ecmascript" -PASS Script should run with type=" text/javascript" -PASS Script should run with type=" text/javascript1.0" -PASS Script should run with type=" text/javascript1.1" -PASS Script should run with type=" text/javascript1.2" -PASS Script should run with type=" text/javascript1.3" -PASS Script should run with type=" text/javascript1.4" -PASS Script should run with type=" text/javascript1.5" -PASS Script should run with type=" text/jscript" -PASS Script should run with type=" text/livescript" -PASS Script should run with type=" text/x-ecmascript" -PASS Script should run with type=" text/x-javascript" -PASS Script should run with type="text/ecmascript\t" -PASS Script should run with type="text/javascript\t" -PASS Script should run with type="text/javascript1.0\t" -PASS Script should run with type="text/javascript1.1\t" -PASS Script should run with type="text/javascript1.2\t" -PASS Script should run with type="text/javascript1.3\t" -PASS Script should run with type="text/javascript1.4\t" -PASS Script should run with type="text/javascript1.5\t" -PASS Script should run with type="text/jscript\t" -PASS Script should run with type="text/livescript\t" -PASS Script should run with type="text/x-ecmascript\t" -PASS Script should run with type="text/x-javascript\t" -PASS Script should run with type="\ttext/ecmascript" -PASS Script should run with type="\ttext/javascript" -PASS Script should run with type="\ttext/javascript1.0" -PASS Script should run with type="\ttext/javascript1.1" -PASS Script should run with type="\ttext/javascript1.2" -PASS Script should run with type="\ttext/javascript1.3" -PASS Script should run with type="\ttext/javascript1.4" -PASS Script should run with type="\ttext/javascript1.5" -PASS Script should run with type="\ttext/jscript" -PASS Script should run with type="\ttext/livescript" -PASS Script should run with type="\ttext/x-ecmascript" -PASS Script should run with type="\ttext/x-javascript" -PASS Script should run with type="text/ecmascript\n" -PASS Script should run with type="text/javascript\n" -PASS Script should run with type="text/javascript1.0\n" -PASS Script should run with type="text/javascript1.1\n" -PASS Script should run with type="text/javascript1.2\n" -PASS Script should run with type="text/javascript1.3\n" -PASS Script should run with type="text/javascript1.4\n" -PASS Script should run with type="text/javascript1.5\n" -PASS Script should run with type="text/jscript\n" -PASS Script should run with type="text/livescript\n" -PASS Script should run with type="text/x-ecmascript\n" -PASS Script should run with type="text/x-javascript\n" -PASS Script should run with type="\ntext/ecmascript" -PASS Script should run with type="\ntext/javascript" -PASS Script should run with type="\ntext/javascript1.0" -PASS Script should run with type="\ntext/javascript1.1" -PASS Script should run with type="\ntext/javascript1.2" -PASS Script should run with type="\ntext/javascript1.3" -PASS Script should run with type="\ntext/javascript1.4" -PASS Script should run with type="\ntext/javascript1.5" -PASS Script should run with type="\ntext/jscript" -PASS Script should run with type="\ntext/livescript" -PASS Script should run with type="\ntext/x-ecmascript" -PASS Script should run with type="\ntext/x-javascript" -PASS Script should run with type="text/ecmascript\r" -PASS Script should run with type="text/javascript\r" -PASS Script should run with type="text/javascript1.0\r" -PASS Script should run with type="text/javascript1.1\r" -PASS Script should run with type="text/javascript1.2\r" -PASS Script should run with type="text/javascript1.3\r" -PASS Script should run with type="text/javascript1.4\r" -PASS Script should run with type="text/javascript1.5\r" -PASS Script should run with type="text/jscript\r" -PASS Script should run with type="text/livescript\r" -PASS Script should run with type="text/x-ecmascript\r" -PASS Script should run with type="text/x-javascript\r" -PASS Script should run with type="\rtext/ecmascript" -PASS Script should run with type="\rtext/javascript" -PASS Script should run with type="\rtext/javascript1.0" -PASS Script should run with type="\rtext/javascript1.1" -PASS Script should run with type="\rtext/javascript1.2" -PASS Script should run with type="\rtext/javascript1.3" -PASS Script should run with type="\rtext/javascript1.4" -PASS Script should run with type="\rtext/javascript1.5" -PASS Script should run with type="\rtext/jscript" -PASS Script should run with type="\rtext/livescript" -PASS Script should run with type="\rtext/x-ecmascript" -PASS Script should run with type="\rtext/x-javascript" -PASS Script should run with type="text/ecmascript\f" -PASS Script should run with type="text/javascript\f" -PASS Script should run with type="text/javascript1.0\f" -PASS Script should run with type="text/javascript1.1\f" -PASS Script should run with type="text/javascript1.2\f" -PASS Script should run with type="text/javascript1.3\f" -PASS Script should run with type="text/javascript1.4\f" -PASS Script should run with type="text/javascript1.5\f" -PASS Script should run with type="text/jscript\f" -PASS Script should run with type="text/livescript\f" -PASS Script should run with type="text/x-ecmascript\f" -PASS Script should run with type="text/x-javascript\f" -PASS Script should run with type="\ftext/ecmascript" -PASS Script should run with type="\ftext/javascript" -PASS Script should run with type="\ftext/javascript1.0" -PASS Script should run with type="\ftext/javascript1.1" -PASS Script should run with type="\ftext/javascript1.2" -PASS Script should run with type="\ftext/javascript1.3" -PASS Script should run with type="\ftext/javascript1.4" -PASS Script should run with type="\ftext/javascript1.5" -PASS Script should run with type="\ftext/jscript" -PASS Script should run with type="\ftext/livescript" -PASS Script should run with type="\ftext/x-ecmascript" -PASS Script should run with type="\ftext/x-javascript" -PASS Script shouldn't run with type="text/ecmascript\0" -PASS Script shouldn't run with type="text/javascript\0" -PASS Script shouldn't run with type="text/javascript1.0\0" -PASS Script shouldn't run with type="text/javascript1.1\0" -PASS Script shouldn't run with type="text/javascript1.2\0" -PASS Script shouldn't run with type="text/javascript1.3\0" -PASS Script shouldn't run with type="text/javascript1.4\0" -PASS Script shouldn't run with type="text/javascript1.5\0" -PASS Script shouldn't run with type="text/jscript\0" -PASS Script shouldn't run with type="text/livescript\0" -PASS Script shouldn't run with type="text/x-ecmascript\0" -PASS Script shouldn't run with type="text/x-javascript\0" -PASS Script shouldn't run with type="text/ecmascript\0foo" -PASS Script shouldn't run with type="text/javascript\0foo" -PASS Script shouldn't run with type="text/javascript1.0\0foo" -PASS Script shouldn't run with type="text/javascript1.1\0foo" -PASS Script shouldn't run with type="text/javascript1.2\0foo" -PASS Script shouldn't run with type="text/javascript1.3\0foo" -PASS Script shouldn't run with type="text/javascript1.4\0foo" -PASS Script shouldn't run with type="text/javascript1.5\0foo" -PASS Script shouldn't run with type="text/jscript\0foo" -PASS Script shouldn't run with type="text/livescript\0foo" -PASS Script shouldn't run with type="text/x-ecmascript\0foo" -PASS Script shouldn't run with type="text/x-javascript\0foo" -PASS Script shouldn't run with type="ecmascript" -PASS Script shouldn't run with type="javascript" -PASS Script shouldn't run with type="javascript1.0" -PASS Script shouldn't run with type="javascript1.1" -PASS Script shouldn't run with type="javascript1.2" -PASS Script shouldn't run with type="javascript1.3" -PASS Script shouldn't run with type="javascript1.4" -PASS Script shouldn't run with type="javascript1.5" -PASS Script shouldn't run with type="jscript" -PASS Script shouldn't run with type="livescript" -PASS Script shouldn't run with type="x-ecmascript" -PASS Script shouldn't run with type="x-javascript" -PASS Script shouldn't run with type="javascript1.6" -PASS Script shouldn't run with type="javascript1.7" -PASS Script shouldn't run with type="javascript1.8" -PASS Script shouldn't run with type="javascript1.9" -PASS Script should run with language="" -PASS Script shouldn't run with language=" " -PASS Script should run with language="ecmascript" -PASS Script should run with language="javascript" -PASS Script should run with language="javascript1.0" -PASS Script should run with language="javascript1.1" -PASS Script should run with language="javascript1.2" -PASS Script should run with language="javascript1.3" -PASS Script should run with language="javascript1.4" -PASS Script should run with language="javascript1.5" -PASS Script should run with language="jscript" -PASS Script should run with language="livescript" -PASS Script should run with language="x-ecmascript" -PASS Script should run with language="x-javascript" -PASS Script should run with language="ECMASCRIPT" -PASS Script should run with language="JAVASCRIPT" -PASS Script should run with language="JAVASCRIPT1.0" -PASS Script should run with language="JAVASCRIPT1.1" -PASS Script should run with language="JAVASCRIPT1.2" -PASS Script should run with language="JAVASCRIPT1.3" -PASS Script should run with language="JAVASCRIPT1.4" -PASS Script should run with language="JAVASCRIPT1.5" -PASS Script should run with language="JSCRIPT" -PASS Script should run with language="LIVESCRIPT" -PASS Script should run with language="X-ECMASCRIPT" -PASS Script should run with language="X-JAVASCRIPT" -FAIL Script shouldn't run with language="javascript1.6" assert_equals: expected false but got true -FAIL Script shouldn't run with language="javascript1.7" assert_equals: expected false but got true -PASS Script shouldn't run with language="javascript1.8" -PASS Script shouldn't run with language="javascript1.9" -PASS Script shouldn't run with language="ecmascript " -PASS Script shouldn't run with language="javascript " -PASS Script shouldn't run with language="javascript1.0 " -PASS Script shouldn't run with language="javascript1.1 " -PASS Script shouldn't run with language="javascript1.2 " -PASS Script shouldn't run with language="javascript1.3 " -PASS Script shouldn't run with language="javascript1.4 " -PASS Script shouldn't run with language="javascript1.5 " -PASS Script shouldn't run with language="jscript " -PASS Script shouldn't run with language="livescript " -PASS Script shouldn't run with language="x-ecmascript " -PASS Script shouldn't run with language="x-javascript " -PASS Script shouldn't run with language=" ecmascript" -PASS Script shouldn't run with language=" javascript" -PASS Script shouldn't run with language=" javascript1.0" -PASS Script shouldn't run with language=" javascript1.1" -PASS Script shouldn't run with language=" javascript1.2" -PASS Script shouldn't run with language=" javascript1.3" -PASS Script shouldn't run with language=" javascript1.4" -PASS Script shouldn't run with language=" javascript1.5" -PASS Script shouldn't run with language=" jscript" -PASS Script shouldn't run with language=" livescript" -PASS Script shouldn't run with language=" x-ecmascript" -PASS Script shouldn't run with language=" x-javascript" -PASS Script shouldn't run with language="ecmascript\t" -PASS Script shouldn't run with language="javascript\t" -PASS Script shouldn't run with language="javascript1.0\t" -PASS Script shouldn't run with language="javascript1.1\t" -PASS Script shouldn't run with language="javascript1.2\t" -PASS Script shouldn't run with language="javascript1.3\t" -PASS Script shouldn't run with language="javascript1.4\t" -PASS Script shouldn't run with language="javascript1.5\t" -PASS Script shouldn't run with language="jscript\t" -PASS Script shouldn't run with language="livescript\t" -PASS Script shouldn't run with language="x-ecmascript\t" -PASS Script shouldn't run with language="x-javascript\t" -PASS Script shouldn't run with language="\tecmascript" -PASS Script shouldn't run with language="\tjavascript" -PASS Script shouldn't run with language="\tjavascript1.0" -PASS Script shouldn't run with language="\tjavascript1.1" -PASS Script shouldn't run with language="\tjavascript1.2" -PASS Script shouldn't run with language="\tjavascript1.3" -PASS Script shouldn't run with language="\tjavascript1.4" -PASS Script shouldn't run with language="\tjavascript1.5" -PASS Script shouldn't run with language="\tjscript" -PASS Script shouldn't run with language="\tlivescript" -PASS Script shouldn't run with language="\tx-ecmascript" -PASS Script shouldn't run with language="\tx-javascript" -PASS Script shouldn't run with language="ecmascript\n" -PASS Script shouldn't run with language="javascript\n" -PASS Script shouldn't run with language="javascript1.0\n" -PASS Script shouldn't run with language="javascript1.1\n" -PASS Script shouldn't run with language="javascript1.2\n" -PASS Script shouldn't run with language="javascript1.3\n" -PASS Script shouldn't run with language="javascript1.4\n" -PASS Script shouldn't run with language="javascript1.5\n" -PASS Script shouldn't run with language="jscript\n" -PASS Script shouldn't run with language="livescript\n" -PASS Script shouldn't run with language="x-ecmascript\n" -PASS Script shouldn't run with language="x-javascript\n" -PASS Script shouldn't run with language="\necmascript" -PASS Script shouldn't run with language="\njavascript" -PASS Script shouldn't run with language="\njavascript1.0" -PASS Script shouldn't run with language="\njavascript1.1" -PASS Script shouldn't run with language="\njavascript1.2" -PASS Script shouldn't run with language="\njavascript1.3" -PASS Script shouldn't run with language="\njavascript1.4" -PASS Script shouldn't run with language="\njavascript1.5" -PASS Script shouldn't run with language="\njscript" -PASS Script shouldn't run with language="\nlivescript" -PASS Script shouldn't run with language="\nx-ecmascript" -PASS Script shouldn't run with language="\nx-javascript" -PASS Script shouldn't run with language="ecmascript\r" -PASS Script shouldn't run with language="javascript\r" -PASS Script shouldn't run with language="javascript1.0\r" -PASS Script shouldn't run with language="javascript1.1\r" -PASS Script shouldn't run with language="javascript1.2\r" -PASS Script shouldn't run with language="javascript1.3\r" -PASS Script shouldn't run with language="javascript1.4\r" -PASS Script shouldn't run with language="javascript1.5\r" -PASS Script shouldn't run with language="jscript\r" -PASS Script shouldn't run with language="livescript\r" -PASS Script shouldn't run with language="x-ecmascript\r" -PASS Script shouldn't run with language="x-javascript\r" -PASS Script shouldn't run with language="\recmascript" -PASS Script shouldn't run with language="\rjavascript" -PASS Script shouldn't run with language="\rjavascript1.0" -PASS Script shouldn't run with language="\rjavascript1.1" -PASS Script shouldn't run with language="\rjavascript1.2" -PASS Script shouldn't run with language="\rjavascript1.3" -PASS Script shouldn't run with language="\rjavascript1.4" -PASS Script shouldn't run with language="\rjavascript1.5" -PASS Script shouldn't run with language="\rjscript" -PASS Script shouldn't run with language="\rlivescript" -PASS Script shouldn't run with language="\rx-ecmascript" -PASS Script shouldn't run with language="\rx-javascript" -PASS Script shouldn't run with language="ecmascript\f" -PASS Script shouldn't run with language="javascript\f" -PASS Script shouldn't run with language="javascript1.0\f" -PASS Script shouldn't run with language="javascript1.1\f" -PASS Script shouldn't run with language="javascript1.2\f" -PASS Script shouldn't run with language="javascript1.3\f" -PASS Script shouldn't run with language="javascript1.4\f" -PASS Script shouldn't run with language="javascript1.5\f" -PASS Script shouldn't run with language="jscript\f" -PASS Script shouldn't run with language="livescript\f" -PASS Script shouldn't run with language="x-ecmascript\f" -PASS Script shouldn't run with language="x-javascript\f" -PASS Script shouldn't run with language="\fecmascript" -PASS Script shouldn't run with language="\fjavascript" -PASS Script shouldn't run with language="\fjavascript1.0" -PASS Script shouldn't run with language="\fjavascript1.1" -PASS Script shouldn't run with language="\fjavascript1.2" -PASS Script shouldn't run with language="\fjavascript1.3" -PASS Script shouldn't run with language="\fjavascript1.4" -PASS Script shouldn't run with language="\fjavascript1.5" -PASS Script shouldn't run with language="\fjscript" -PASS Script shouldn't run with language="\flivescript" -PASS Script shouldn't run with language="\fx-ecmascript" -PASS Script shouldn't run with language="\fx-javascript" -PASS Script shouldn't run with language="ecmascriptxyz" -PASS Script shouldn't run with language="javascriptxyz" -PASS Script shouldn't run with language="javascript1.0xyz" -PASS Script shouldn't run with language="javascript1.1xyz" -PASS Script shouldn't run with language="javascript1.2xyz" -PASS Script shouldn't run with language="javascript1.3xyz" -PASS Script shouldn't run with language="javascript1.4xyz" -PASS Script shouldn't run with language="javascript1.5xyz" -PASS Script shouldn't run with language="jscriptxyz" -PASS Script shouldn't run with language="livescriptxyz" -PASS Script shouldn't run with language="x-ecmascriptxyz" -PASS Script shouldn't run with language="x-javascriptxyz" -PASS Script shouldn't run with language="xyzecmascript" -PASS Script shouldn't run with language="xyzjavascript" -PASS Script shouldn't run with language="xyzjavascript1.0" -PASS Script shouldn't run with language="xyzjavascript1.1" -PASS Script shouldn't run with language="xyzjavascript1.2" -PASS Script shouldn't run with language="xyzjavascript1.3" -PASS Script shouldn't run with language="xyzjavascript1.4" -PASS Script shouldn't run with language="xyzjavascript1.5" -PASS Script shouldn't run with language="xyzjscript" -PASS Script shouldn't run with language="xyzlivescript" -PASS Script shouldn't run with language="xyzx-ecmascript" -PASS Script shouldn't run with language="xyzx-javascript" -PASS Script shouldn't run with language="ecmascript\0" -PASS Script shouldn't run with language="javascript\0" -PASS Script shouldn't run with language="javascript1.0\0" -PASS Script shouldn't run with language="javascript1.1\0" -PASS Script shouldn't run with language="javascript1.2\0" -PASS Script shouldn't run with language="javascript1.3\0" -PASS Script shouldn't run with language="javascript1.4\0" -PASS Script shouldn't run with language="javascript1.5\0" -PASS Script shouldn't run with language="jscript\0" -PASS Script shouldn't run with language="livescript\0" -PASS Script shouldn't run with language="x-ecmascript\0" -PASS Script shouldn't run with language="x-javascript\0" -PASS Script shouldn't run with language="ecmascript\0foo" -PASS Script shouldn't run with language="javascript\0foo" -PASS Script shouldn't run with language="javascript1.0\0foo" -PASS Script shouldn't run with language="javascript1.1\0foo" -PASS Script shouldn't run with language="javascript1.2\0foo" -PASS Script shouldn't run with language="javascript1.3\0foo" -PASS Script shouldn't run with language="javascript1.4\0foo" -PASS Script shouldn't run with language="javascript1.5\0foo" -PASS Script shouldn't run with language="jscript\0foo" -PASS Script shouldn't run with language="livescript\0foo" -PASS Script shouldn't run with language="x-ecmascript\0foo" -PASS Script shouldn't run with language="x-javascript\0foo" -PASS Script shouldn't run with type=javascript (parser-inserted) -PASS Script shouldn't run with type=javascript1.0 (parser-inserted) -PASS Script shouldn't run with type=javascript1.1 (parser-inserted) -PASS Script shouldn't run with type=javascript1.2 (parser-inserted) -PASS Script shouldn't run with type=javascript1.3 (parser-inserted) -PASS Script shouldn't run with type=javascript1.4 (parser-inserted) -PASS Script shouldn't run with type=javascript1.5 (parser-inserted) -PASS Script shouldn't run with type=javascript1.6 (parser-inserted) -PASS Script shouldn't run with type=javascript1.7 (parser-inserted) -PASS Script shouldn't run with type=livescript (parser-inserted) -PASS Script shouldn't run with type=ecmascript (parser-inserted) -PASS Script shouldn't run with type=jscript (parser-inserted) -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/platform/generic/fast/html/script-allowed-types-languages-expected.txt b/third_party/blink/web_tests/platform/generic/fast/html/script-allowed-types-languages-expected.txt deleted file mode 100644 index de825321..0000000 --- a/third_party/blink/web_tests/platform/generic/fast/html/script-allowed-types-languages-expected.txt +++ /dev/null
@@ -1,80 +0,0 @@ -This page tests the allowed values for the type and language attributes of the <script> tag. Below you will see the allowed values. - -Type: unspecified, Language: unspecified -Type: "", Language: unspecified -Type: "text/javascript", Language: unspecified -Type: "text/ecmascript", Language: unspecified -Type: "text/x-javascript", Language: unspecified -Type: "text/x-ecmascript", Language: unspecified -Type: "application/javascript", Language: unspecified -Type: "application/ecmascript", Language: unspecified -Type: "application/x-javascript", Language: unspecified -Type: "application/x-ecmascript", Language: unspecified -Type: "text/javascript1.0", Language: unspecified -Type: "text/javascript1.1", Language: unspecified -Type: "text/javascript1.2", Language: unspecified -Type: "text/javascript1.3", Language: unspecified -Type: "text/javascript1.4", Language: unspecified -Type: "text/javascript1.5", Language: unspecified -Type: "text/jscript", Language: unspecified -Type: "text/livescript", Language: unspecified -Type: " text/javascript", Language: unspecified -Type: "text/javascript ", Language: unspecified -Type: " text/javascript ", Language: unspecified -Type: unspecified, Language: "" -Type: unspecified, Language: "javascript" -Type: unspecified, Language: "javascript1.0" -Type: unspecified, Language: "javascript1.1" -Type: unspecified, Language: "javascript1.2" -Type: unspecified, Language: "javascript1.3" -Type: unspecified, Language: "javascript1.4" -Type: unspecified, Language: "javascript1.5" -Type: unspecified, Language: "javascript1.6" -Type: unspecified, Language: "javascript1.7" -Type: unspecified, Language: "ecmascript" -Type: unspecified, Language: "livescript" -Type: unspecified, Language: "jscript" -Type: "", Language: "" -Type: "", Language: "javascript" -Type: "", Language: "javascript1.0" -Type: "", Language: "javascript1.1" -Type: "", Language: "javascript1.2" -Type: "", Language: "javascript1.3" -Type: "", Language: "javascript1.4" -Type: "", Language: "javascript1.5" -Type: "", Language: "javascript1.6" -Type: "", Language: "javascript1.7" -Type: "", Language: "javascript1.8" -Type: "", Language: "javascript1.9" -Type: "", Language: "ecmascript" -Type: "", Language: "livescript" -Type: "", Language: "jscript" -Type: "", Language: "ebayScript" -Type: "", Language: " " -Type: "", Language: " javascript" -Type: "", Language: "javascript " -Type: "", Language: " javascript " -Type: "", Language: "abcdefg" -When a type is specified, the language attribute should be ignored. -Type: "text/javascript", Language: "" -Type: "text/javascript", Language: "javascript" -Type: "text/javascript", Language: "javascript1.0" -Type: "text/javascript", Language: "javascript1.1" -Type: "text/javascript", Language: "javascript1.2" -Type: "text/javascript", Language: "javascript1.3" -Type: "text/javascript", Language: "javascript1.4" -Type: "text/javascript", Language: "javascript1.5" -Type: "text/javascript", Language: "javascript1.6" -Type: "text/javascript", Language: "javascript1.7" -Type: "text/javascript", Language: "javascript1.8" -Type: "text/javascript", Language: "javascript1.9" -Type: "text/javascript", Language: "ecmascript" -Type: "text/javascript", Language: "livescript" -Type: "text/javascript", Language: "jscript" -Type: "text/javascript", Language: "ebayScript" -Type: "text/javascript", Language: " " -Type: "text/javascript", Language: " javascript" -Type: "text/javascript", Language: "javascript " -Type: "text/javascript", Language: " javascript " -Type: "text/javascript", Language: "abcdefg" -
diff --git a/third_party/blink/web_tests/platform/generic/fast/tokenizer/004-expected.txt b/third_party/blink/web_tests/platform/generic/fast/tokenizer/004-expected.txt deleted file mode 100644 index 33cd2ffe..0000000 --- a/third_party/blink/web_tests/platform/generic/fast/tokenizer/004-expected.txt +++ /dev/null
@@ -1,165 +0,0 @@ -Variations on type attribute of script tag -These scripts should execute -no type attribute executed -empty string executed -text/javascript executed -text/JAVASCRIPT executed -TEXT/JAVASCRIPT executed -'text/javascript ' executed -' text/javascript ' executed -text/jscript executed -text/ecmascript executed -text/livescript executed -text/javascript1.0 executed -text/javascript1.1 executed -text/javascript1.2 executed -text/javascript1.3 executed -text/javascript1.4 executed -text/javascript1.5 executed -text/x-javascript executed -text/x-ecmascript executed -application/javascript executed -application/ecmascript executed -application/x-javascript executed -application/x-ecmascript executed -These scripts should not execute -one space -text/ -text/vbscript -text/vbs -text/xml -text/javascript1 -text/javascript1.6 -application/jscript -application/x-jscript -application/livescript -application/x-livescript -application/javascript1.2 -application/x-javascript1.2 -javascript -jscript -ecmascript -livescript -livescript1.1 -JAVASCRIPT -JavaScript -JavaScript 1 -JavaScript 1.0 -JavaScript 1.1 -JavaScript 1.1.1 -JavaScript 1.2 -JavaScript 1.3 -JavaScript 1.4 -JavaScript 1.5 -JavaScript 1.6 -JavaScript 1.7 -JavaScript 1.8 -JavaScript 1.9 -JavaScript 2 -JavaScript 2.1 -JavaScript 10 -JavaScript 10.0 -_javascript -javascript_ -javascript_1.0 -javascript 1.0 x -JavaScript1 -JavaScript1.0 -JavaScript1.1 -JavaScript1.2 -JavaScript1.3 -JavaScript1.4 -JavaScript1.4.1 -JavaScript1.5 -JavaScript1.6 -JavaScript1.7 -1.0 javascript -' javascript ' -' javascript1.1 ' -' javascript ' -' javascript 1.0 ' -' javascript 1.0 ' -jscript 1 -jscript 1.0 -ecmascript 1 -ecmascript 1.0 -livescript 1 -livescript 1.0 -' jscript 1.0 ' -disabled_javascript -xxxjavascriptxxx -bogus -Variations on language attribute of script tag -These scripts should execute -no language attribute executed -empty string executed -jscript executed -ecmascript executed -livescript executed -javascript executed -JAVASCRIPT executed -JavaScript executed -JavaScript1.0 executed -JavaScript1.1 executed -JavaScript1.2 executed -JavaScript1.3 executed -JavaScript1.4 executed -JavaScript1.5 executed -JavaScript1.6 executed -JavaScript1.7 executed -These scripts should not execute -one space -vbscript -livescript1.1 -JavaScript 1 -JavaScript 1.0 -JavaScript 1.1 -JavaScript 1.1.1 -JavaScript 1.2 -JavaScript 1.3 -JavaScript 1.4 -JavaScript 1.5 -JavaScript 1.6 -JavaScript 1.7 -JavaScript 1.8 -JavaScript 1.9 -JavaScript 2 -JavaScript 2.1 -JavaScript 10 -JavaScript 10.0 -_javascript -javascript_ -javascript_1.0 -javascript 1.0 x -JavaScript1 -JavaScript1.8 -JavaScript1.9 -JavaScript1.4.1 -1.0 javascript -' javascript ' -' javascript1.1 ' -' javascript ' -' javascript 1.0 ' -' javascript 1.0 ' -jscript 1 -jscript 1.0 -ecmascript 1 -ecmascript 1.0 -livescript 1 -livescript 1.0 -' jscript 1.0 ' -disabled_javascript -xxxjavascriptxxx -bogus -Variations on combined type and language attributes of script tag -These scripts should execute -empty string type, "javascript" language executed -empty string language, "text/javascript" type executed -"javascript" language, "text/javascript" type executed -"bogus" language, "text/javascript" type executed -"livescript" language, "text/javascript" type executed -"javascript1.2" language, "text/javascript" type executed -empty string type, "bogus" language executed -These scripts should not execute -"javascript" language, "bogus" type -empty string language, "bogus" type
diff --git a/third_party/blink/web_tests/platform/generic/http/tests/inspector-protocol/fenced-frame/setWebLifecycleState-fenced-frame.https-expected.txt b/third_party/blink/web_tests/platform/generic/http/tests/inspector-protocol/fenced-frame/setWebLifecycleState-fenced-frame.https-expected.txt new file mode 100644 index 0000000..c2f10b7 --- /dev/null +++ b/third_party/blink/web_tests/platform/generic/http/tests/inspector-protocol/fenced-frame/setWebLifecycleState-fenced-frame.https-expected.txt
@@ -0,0 +1,4 @@ +Tests that Page.setWebLifecycleState() in a fenced frame is not allowed. +Page.setWebLifecycleState() from a fenced frame: +PASS: This is only supported for top-level frames +
diff --git a/third_party/blink/web_tests/platform/linux/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt b/third_party/blink/web_tests/platform/linux/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt deleted file mode 100644 index 6e471cab..0000000 --- a/third_party/blink/web_tests/platform/linux/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt +++ /dev/null
@@ -1,4 +0,0 @@ -This is a testharness.js-based test. -FAIL Fetching modulepreload should not block the window's load event assert_equals: resources/dummy.js?pipe=trickle(d5) expected 0 but got 1 -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/platform/mac/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt b/third_party/blink/web_tests/platform/mac/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt deleted file mode 100644 index 6e471cab..0000000 --- a/third_party/blink/web_tests/platform/mac/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt +++ /dev/null
@@ -1,4 +0,0 @@ -This is a testharness.js-based test. -FAIL Fetching modulepreload should not block the window's load event assert_equals: resources/dummy.js?pipe=trickle(d5) expected 0 but got 1 -Harness: the test ran to completion. -
diff --git a/third_party/blink/web_tests/platform/win10/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt b/third_party/blink/web_tests/platform/win10/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt deleted file mode 100644 index 6e471cab..0000000 --- a/third_party/blink/web_tests/platform/win10/external/wpt/preload/avoid-delaying-onload-link-modulepreload-expected.txt +++ /dev/null
@@ -1,4 +0,0 @@ -This is a testharness.js-based test. -FAIL Fetching modulepreload should not block the window's load event assert_equals: resources/dummy.js?pipe=trickle(d5) expected 0 but got 1 -Harness: the test ran to completion. -
diff --git a/third_party/closure_compiler/externs/file_manager_private.js b/third_party/closure_compiler/externs/file_manager_private.js index 05c4695..6679497 100644 --- a/third_party/closure_compiler/externs/file_manager_private.js +++ b/third_party/closure_compiler/externs/file_manager_private.js
@@ -1185,9 +1185,10 @@ * Gets recently modified files across file systems. * @param {string} restriction * @param {string} fileType + * @param {boolean} invalidateCache * @param {function((!Array<!FileEntry>))} callback */ -chrome.fileManagerPrivate.getRecentFiles = function(restriction, fileType, callback) {}; +chrome.fileManagerPrivate.getRecentFiles = function(restriction, fileType, invalidateCache, callback) {}; /** * Requests the root directory of a volume. The ID of the volume must be @@ -1405,8 +1406,10 @@ * @param {!chrome.fileManagerPrivate.IOTaskType} type * @param {!Array<!Entry>} entries * @param {!chrome.fileManagerPrivate.IOTaskParams} params + * @param {(function(number): void)=} callback Returns the task ID. */ -chrome.fileManagerPrivate.startIOTask = function(type, entries, params) {}; +chrome.fileManagerPrivate.startIOTask = function( + type, entries, params, callback) {}; /** * Cancels an I/O task by id. Task ids are communicated to the Files App in
diff --git a/third_party/zlib/chromeconf.h b/third_party/zlib/chromeconf.h index 7c2241a..c365fa9 100644 --- a/third_party/zlib/chromeconf.h +++ b/third_party/zlib/chromeconf.h
@@ -194,7 +194,6 @@ #define arm_cpu_enable_pmull Cr_z_arm_cpu_enable_pmull #define arm_check_features Cr_z_arm_check_features #define armv8_crc32_little Cr_z_armv8_crc32_little -#define armv8_crc32_pmull_little Cr_z_armv8_crc32_pmull_little /* Symbols added by cpu_features.c */ #define cpu_check_features Cr_z_cpu_check_features
diff --git a/third_party/zlib/cpu_features.c b/third_party/zlib/cpu_features.c index 9391d7b4..70f01be 100644 --- a/third_party/zlib/cpu_features.c +++ b/third_party/zlib/cpu_features.c
@@ -18,16 +18,13 @@ /* TODO(cavalcantii): remove checks for x86_flags on deflate. */ #if defined(ARMV8_OS_MACOS) -/* Crypto extensions (crc32/pmull) are a baseline feature in ARMv8.1-A, and - * OSX running on arm64 is new enough that these can be assumed without - * runtime detection. - */ +/* crc32 is a baseline feature in ARMv8.1-A, and macOS running on arm64 is new + * enough that this can be assumed without runtime detection. */ int ZLIB_INTERNAL arm_cpu_enable_crc32 = 1; -int ZLIB_INTERNAL arm_cpu_enable_pmull = 1; #else int ZLIB_INTERNAL arm_cpu_enable_crc32 = 0; -int ZLIB_INTERNAL arm_cpu_enable_pmull = 0; #endif +int ZLIB_INTERNAL arm_cpu_enable_pmull = 0; int ZLIB_INTERNAL x86_cpu_enable_sse2 = 0; int ZLIB_INTERNAL x86_cpu_enable_ssse3 = 0; int ZLIB_INTERNAL x86_cpu_enable_simd = 0;
diff --git a/third_party/zlib/crc32.c b/third_party/zlib/crc32.c index e60c372..142f1e8 100644 --- a/third_party/zlib/crc32.c +++ b/third_party/zlib/crc32.c
@@ -1101,29 +1101,23 @@ const unsigned char FAR *buf; uInt len; { - /* Some bots compile with optimizations disabled, others will emulate - * ARM on x86 and other weird combinations. - */ #if defined(CRC32_ARMV8_CRC32) - if (arm_cpu_enable_crc32) { -#if defined(__aarch64__) - /* PMULL is 64bit only, plus code needs at least a 64 bytes buffer. */ - if (arm_cpu_enable_pmull && (len > Z_CRC32_PMULL_MINIMUM_LENGTH)) { - const size_t chunk_size = len & ~Z_CRC32_PMULL_CHUNKSIZE_MASK; - crc = ~armv8_crc32_pmull_little(buf, chunk_size, ~(uint32_t)crc); - /* Check remaining data. */ - len -= chunk_size; - if (!len) - return crc; - - /* Fall through for the remaining data. */ - buf += chunk_size; - } -#endif - return armv8_crc32_little(buf, len, crc); /* Armv8@32bit or tail. */ + /* We got to verify ARM CPU features, so exploit the common usage pattern + * of calling this function with Z_NULL for an initial valid crc value. + * This allows to cache the result of the feature check and avoid extraneous + * function calls. + * TODO: try to move this to crc32_z if we don't loose performance on ARM. + */ + if (buf == Z_NULL) { + if (!len) /* Assume user is calling crc32(0, NULL, 0); */ + cpu_check_features(); + return 0UL; } + + if (arm_cpu_enable_crc32) + return armv8_crc32_little(crc, buf, len); #endif - return crc32_z(crc, buf, len); /* Armv7 or Armv8 w/o crypto extensions. */ + return crc32_z(crc, buf, len); } /* ========================================================================= */
diff --git a/third_party/zlib/crc32_simd.c b/third_party/zlib/crc32_simd.c index 14a8534..c8e5592 100644 --- a/third_party/zlib/crc32_simd.c +++ b/third_party/zlib/crc32_simd.c
@@ -157,6 +157,8 @@ #elif defined(CRC32_ARMV8_CRC32) /* CRC32 checksums using ARMv8-a crypto instructions. + * + * TODO: implement a version using the PMULL instruction. */ #if defined(__clang__) @@ -176,23 +178,13 @@ * feature for this target (ignoring feature)." This appears to be a harmless * bug in clang. */ -/* XXX: Cannot hook into builtins with XCode for arm64. */ -#if !defined(ARMV8_OS_MACOS) #define __crc32b __builtin_arm_crc32b #define __crc32d __builtin_arm_crc32d #define __crc32w __builtin_arm_crc32w #define __crc32cw __builtin_arm_crc32cw -#endif - -/* We need some extra types for using PMULL. - */ -#if defined(__aarch64__) -#include <arm_neon.h> -#include <arm_acle.h> -#endif #if defined(__aarch64__) -#define TARGET_ARMV8_WITH_CRC __attribute__((target("aes,crc"))) +#define TARGET_ARMV8_WITH_CRC __attribute__((target("crc"))) #else // !defined(__aarch64__) #define TARGET_ARMV8_WITH_CRC __attribute__((target("armv8-a,crc"))) #endif // defined(__aarch64__) @@ -208,10 +200,9 @@ #endif TARGET_ARMV8_WITH_CRC -uint32_t ZLIB_INTERNAL armv8_crc32_little( - const unsigned char *buf, - z_size_t len, - uint32_t crc) +uint32_t ZLIB_INTERNAL armv8_crc32_little(unsigned long crc, + const unsigned char *buf, + z_size_t len) { uint32_t c = (uint32_t) ~crc; @@ -249,178 +240,4 @@ return ~c; } -#if defined(__aarch64__) || defined(ARMV8_OS_MACOS) /* aarch64 specific code. */ - -/* - * crc32_pmull_simd_(): compute the crc32 of the buffer, where the buffer - * length must be at least 64, and a multiple of 16. Based on: - * - * "Fast CRC Computation for Generic Polynomials Using PCLMULQDQ Instruction" - * V. Gopal, E. Ozturk, et al., 2009, http://intel.ly/2ySEwL0 - */ -TARGET_ARMV8_WITH_CRC -static inline uint8x16_t pmull_lo(const uint64x2_t a, const uint64x2_t b) -{ - uint8x16_t r; - __asm__ __volatile__ ("pmull %0.1q, %1.1d, %2.1d \n\t" - : "=w" (r) : "w" (a), "w" (b) ); - return r; -} - -TARGET_ARMV8_WITH_CRC -static inline uint8x16_t pmull_01(const uint64x2_t a, const uint64x2_t b) -{ - uint8x16_t r; - __asm__ __volatile__ ("pmull %0.1q, %1.1d, %2.1d \n\t" - : "=w" (r) : "w" (a), "w" (vgetq_lane_u64(b, 1)) ); - return r; -} - -TARGET_ARMV8_WITH_CRC -static inline uint8x16_t pmull_hi(const uint64x2_t a, const uint64x2_t b) -{ - uint8x16_t r; - __asm__ __volatile__ ("pmull2 %0.1q, %1.2d, %2.2d \n\t" - : "=w" (r) : "w" (a), "w" (b) ); - return r; -} - -TARGET_ARMV8_WITH_CRC -uint32_t ZLIB_INTERNAL armv8_crc32_pmull_little( - const unsigned char *buf, - z_size_t len, - uint32_t crc) -{ - /* - * Definitions of the bit-reflected domain constants k1,k2,k3, etc and - * the CRC32+Barrett polynomials given at the end of the paper. - */ - static const uint64_t zalign(16) k1k2[] = { 0x0154442bd4, 0x01c6e41596 }; - static const uint64_t zalign(16) k3k4[] = { 0x01751997d0, 0x00ccaa009e }; - static const uint64_t zalign(16) k5k0[] = { 0x0163cd6124, 0x0000000000 }; - static const uint64_t zalign(16) poly[] = { 0x01db710641, 0x01f7011641 }; - - uint64x2_t x0, x1, x2, x3, x4, x5, x6, x7, x8, y5, y6, y7, y8; - - /* - * There's at least one block of 64. - */ - x1 = vld1q_u64((const uint64_t *)(buf + 0x00)); - x2 = vld1q_u64((const uint64_t *)(buf + 0x10)); - x3 = vld1q_u64((const uint64_t *)(buf + 0x20)); - x4 = vld1q_u64((const uint64_t *)(buf + 0x30)); - - x1 = veorq_u64(x1, (uint64x2_t) vsetq_lane_u32(crc, vdupq_n_u32(0), 0)); - - x0 = vld1q_u64(k1k2); - - buf += 64; - len -= 64; - - /* - * Parallel fold blocks of 64, if any. - */ - while (len >= 64) - { - x5 = (uint64x2_t) pmull_lo(x1, x0); - x6 = (uint64x2_t) pmull_lo(x2, x0); - x7 = (uint64x2_t) pmull_lo(x3, x0); - x8 = (uint64x2_t) pmull_lo(x4, x0); - - y5 = vld1q_u64((const uint64_t *)(buf + 0x00)); - y6 = vld1q_u64((const uint64_t *)(buf + 0x10)); - y7 = vld1q_u64((const uint64_t *)(buf + 0x20)); - y8 = vld1q_u64((const uint64_t *)(buf + 0x30)); - - x1 = (uint64x2_t) pmull_hi(x1, x0); - x2 = (uint64x2_t) pmull_hi(x2, x0); - x3 = (uint64x2_t) pmull_hi(x3, x0); - x4 = (uint64x2_t) pmull_hi(x4, x0); - - x1 = veorq_u64(x1, x5); - x2 = veorq_u64(x2, x6); - x3 = veorq_u64(x3, x7); - x4 = veorq_u64(x4, x8); - - x1 = veorq_u64(x1, y5); - x2 = veorq_u64(x2, y6); - x3 = veorq_u64(x3, y7); - x4 = veorq_u64(x4, y8); - - buf += 64; - len -= 64; - } - - /* - * Fold into 128-bits. - */ - x0 = vld1q_u64(k3k4); - - x5 = (uint64x2_t) pmull_lo(x1, x0); - x1 = (uint64x2_t) pmull_hi(x1, x0); - x1 = veorq_u64(x1, x2); - x1 = veorq_u64(x1, x5); - - x5 = (uint64x2_t) pmull_lo(x1, x0); - x1 = (uint64x2_t) pmull_hi(x1, x0); - x1 = veorq_u64(x1, x3); - x1 = veorq_u64(x1, x5); - - x5 = (uint64x2_t) pmull_lo(x1, x0); - x1 = (uint64x2_t) pmull_hi(x1, x0); - x1 = veorq_u64(x1, x4); - x1 = veorq_u64(x1, x5); - - /* - * Single fold blocks of 16, if any. - */ - while (len >= 16) - { - x2 = vld1q_u64((const uint64_t *)buf); - - x5 = (uint64x2_t) pmull_lo(x1, x0); - x1 = (uint64x2_t) pmull_hi(x1, x0); - x1 = veorq_u64(x1, x2); - x1 = veorq_u64(x1, x5); - - buf += 16; - len -= 16; - } - - /* - * Fold 128-bits to 64-bits. - */ - static uint32_t zalign(16) mask[] = { ~0u, 0u, ~0u, 0u }; - - x2 = (uint64x2_t) pmull_01(x1, x0); - x1 = (uint64x2_t) vextq_u8(vreinterpretq_u8_u64(x1), vdupq_n_u8(0), 8); - x3 = (uint64x2_t) vld1q_u32(mask); - x1 = veorq_u64(x1, x2); - - x0 = vld1q_u64(k5k0); - - x2 = (uint64x2_t) pmull_01(x2, x0); - x2 = (uint64x2_t) vextq_u8(vreinterpretq_u8_u64(x1), vdupq_n_u8(0), 4); - x1 = vandq_u64(x1, x3); - x1 = (uint64x2_t) pmull_lo(x1, x0); - x1 = veorq_u64(x1, x2); - - /* - * Barret reduce to 32-bits. - */ - x0 = vld1q_u64(poly); - - x2 = vandq_u64(x1, x3); - x2 = (uint64x2_t) pmull_01(x2, x0); - x2 = vandq_u64(x2, x3); - x2 = (uint64x2_t) pmull_lo(x2, x0); - x1 = veorq_u64(x1, x2); - - /* - * Return the crc32. - */ - return vgetq_lane_u32(vreinterpretq_u32_u64(x1), 1); -} -#endif /* aarch64 specific code. */ - #endif
diff --git a/third_party/zlib/crc32_simd.h b/third_party/zlib/crc32_simd.h index 6985cbb..68bc235c 100644 --- a/third_party/zlib/crc32_simd.h +++ b/third_party/zlib/crc32_simd.h
@@ -15,9 +15,10 @@ * crc32_sse42_simd_(): compute the crc32 of the buffer, where the buffer * length must be at least 64, and a multiple of 16. */ -uint32_t ZLIB_INTERNAL crc32_sse42_simd_(const unsigned char* buf, - z_size_t len, - uint32_t crc); +uint32_t ZLIB_INTERNAL crc32_sse42_simd_( + const unsigned char *buf, + z_size_t len, + uint32_t crc); /* * crc32_sse42_simd_ buffer size constraints: see the use in zlib/crc32.c @@ -29,23 +30,7 @@ /* * CRC32 checksums using ARMv8-a crypto instructions. */ -uint32_t ZLIB_INTERNAL armv8_crc32_little(const unsigned char* buf, - z_size_t len, - uint32_t crc); +uint32_t ZLIB_INTERNAL armv8_crc32_little(unsigned long crc, + const unsigned char* buf, + z_size_t len); -/* aarch64 specific code. */ -#if defined(__aarch64__) - -/* 128 is the sweet spot at the time of coding (late 2020). */ -#define Z_CRC32_PMULL_MINIMUM_LENGTH 128 -#define Z_CRC32_PMULL_CHUNKSIZE_MASK 15 - -/* - * CRC32 checksums using ARMv8-a PMULL instructions, where the buffer - * length must be at least 64, and a multiple of 16. - */ -uint32_t ZLIB_INTERNAL armv8_crc32_pmull_little(const unsigned char* buf, - z_size_t len, - uint32_t crc); - -#endif
diff --git a/tools/metrics/histograms/enums.xml b/tools/metrics/histograms/enums.xml index 43f7ff4..4a4b56a 100644 --- a/tools/metrics/histograms/enums.xml +++ b/tools/metrics/histograms/enums.xml
@@ -13437,6 +13437,13 @@ <int value="5" label="Path FileInfo Failed"/> </enum> +<enum name="CacheTransparencyCacheNotUsedReason"> + <int value="0" label="Trying Single Keyed Cache"/> + <int value="1" label="Incompatible Request Type"/> + <int value="2" label="Incompatible Request Load Flags"/> + <int value="3" label="Incompatible Request Headers"/> +</enum> + <enum name="CALayerResult"> <int value="0" label="Success"/> <int value="1" label="Unknown failure"/> @@ -55213,6 +55220,8 @@ <int value="-1638815914" label="enable-experimental-productivity-features"/> <int value="-1637552275" label="NtpRealboxUseGoogleGIcon:disabled"/> <int value="-1636188191" label="IncognitoNtpRevamp:enabled"/> + <int value="-1635872214" + label="AutofillConsiderPlaceholderForParsing:disabled"/> <int value="-1635048938" label="DetectFormSubmissionOnFormClear:disabled"/> <int value="-1634878515" label="ChromeHomeModernLayout:enabled"/> <int value="-1634490190" @@ -58868,6 +58877,8 @@ <int value="761770770" label="OverrideLanguagePrefsForHrefTranslate:disabled"/> <int value="762700519" label="enable-checker-imaging"/> + <int value="763667542" + label="AutofillFillCreditCardAsPerFormatString:enabled"/> <int value="763947368" label="HomepageLocationPolicy:disabled"/> <int value="764508124" label="NavigationNetworkResponseQueue:disabled"/> <int value="765266228" label="TabGroupsCollapse:disabled"/> @@ -58906,6 +58917,7 @@ <int value="781785788" label="ClipboardSuggestionContentHidden:disabled"/> <int value="782167080" label="enable-new-qp-input-view"/> <int value="783270752" label="AndroidHistoryManager:enabled"/> + <int value="783502146" label="AutofillConsiderPlaceholderForParsing:enabled"/> <int value="785273919" label="CompositingBasedThrottling:disabled"/> <int value="787080596" label="DynamicTcmallocTuning:enabled"/> <int value="787385958" label="RegionalLocalesAsDisplayUI:enabled"/> @@ -60091,6 +60103,8 @@ <int value="1594993731" label="BluetoothRevamp:enabled"/> <int value="1595208893" label="AudioWorkletRealtimeThread:enabled"/> <int value="1596407332" label="EnableSavedDesks:enabled"/> + <int value="1596615083" + label="AutofillFillCreditCardAsPerFormatString:disabled"/> <int value="1597880096" label="FocusMode:disabled"/> <int value="1600850069" label="MobileIdentityConsistency:disabled"/> <int value="1600926040" label="TranslateCompactUI:enabled"/> @@ -89531,17 +89545,6 @@ profiling started"/> </enum> -<enum name="StartupTabPreloaderLoadDecisionCause"> - <int value="0" label="DisabledByIntent"/> - <int value="1" label="Incognito"/> - <int value="2" label="IntentIgnored"/> - <int value="3" label="NoUrl"/> - <int value="4" label="NoTabCreator"/> - <int value="5" label="WrongTabCreator"/> - <int value="6" label="DisabledByFeature"/> - <int value="7" label="AllSatisfied"/> -</enum> - <enum name="StartupTemperature"> <int value="0" label="Cold startup (mostly hard faults)"/> <int value="1" label="Warm startup (nearly no hard faults)"/>
diff --git a/tools/metrics/histograms/metadata/android/histograms.xml b/tools/metrics/histograms/metadata/android/histograms.xml index 1d4cf6e..0f592c52 100644 --- a/tools/metrics/histograms/metadata/android/histograms.xml +++ b/tools/metrics/histograms/metadata/android/histograms.xml
@@ -3046,147 +3046,6 @@ </summary> </histogram> -<histogram name="Android.StartupTabPreloader.ActivityStartToLoadDecision" - units="ms" expires_after="2022-11-06"> - <owner>blundell@chromium.org</owner> - <owner>yfriedman@chromium.org</owner> - <summary> - The time in a cold start between the start of the activity and the - triggerpoint for a startup tab being preloaded. Recorded only in startups - for which Android.Startup.Cold.TimeToFirstVisibleContent is being tracked. - </summary> -</histogram> - -<histogram - name="Android.StartupTabPreloader.LoadDecisionToFirstContentfulPaint.{LoadAndMatchResult}" - units="ms" expires_after="2022-09-01"> - <owner>blundell@chromium.org</owner> - <owner>yfriedman@chromium.org</owner> - <summary> - The time in a cold start between the triggerpoint for a startup tab being - preloaded and Android.Startup.Cold.TimeToFirstContentfulPaint being - recorded, recorded in the case where a startup tab preload is determined - {LoadAndMatchResult}. In the case where the ElideTabPreloadAtStartup feature - is enabled, this metric will be segmented to reflect the state that would - have resulted if tab preloading was not disabled by the feature. Recorded - only in startups for which Android.Startup.Cold.TimeToFirstVisibleContent is - being tracked. - </summary> - <token key="LoadAndMatchResult"> - <variant name="LoadAndMatch" - summary="to be viable and the preload is a match for the actual - initial load"/> - <variant name="LoadAndMismatch" - summary="to be viable and the preload is not a match for the actual - initial load"/> - <variant name="LoadPreMatch" - summary="to be viable and first contentful paint is recorded before - it was determined whether the preload was a match for the - actual initial load. Note that it is not expected that this - case occurs in practice, but it is theoretically possible"/> - <variant name="NoLoad" summary="not to be viable"/> - </token> -</histogram> - -<histogram - name="Android.StartupTabPreloader.LoadDecisionToFirstNavigationCommit.{LoadAndMatchResult}" - units="ms" expires_after="2022-09-01"> - <owner>blundell@chromium.org</owner> - <owner>yfriedman@chromium.org</owner> - <summary> - The time in a cold start between the triggerpoint for a startup tab being - preloaded and Android.Startup.Cold.TimeToFirstNavigationCommit being - recorded, recorded in the case where a startup tab preload is determined - {LoadAndMatchResult}. In the case where the ElideTabPreloadAtStartup feature - is enabled, this metric will be segmented to reflect the state that would - have resulted if tab preloading was not disabled by the feature. - </summary> - <token key="LoadAndMatchResult"> - <variant name="LoadAndMatch" - summary="to be viable and the preload is a match for the actual - initial load"/> - <variant name="LoadAndMismatch" - summary="to be viable and the preload is not a match for the actual - initial load"/> - <variant name="LoadPreMatch" - summary="to be viable and first navigation commit is recorded before - it was determined whether the preload was a match for the - actual initial load. Note that it is not expected that this - case occurs in practice, but it is theoretically possible"/> - <variant name="NoLoad" summary="not to be viable"/> - </token> -</histogram> - -<histogram - name="Android.StartupTabPreloader.LoadDecisionToFirstNavigationStart.{LoadDecision}" - units="ms" expires_after="2022-09-01"> - <owner>blundell@chromium.org</owner> - <owner>yfriedman@chromium.org</owner> - <summary> - The time in a cold start between the triggerpoint for a startup tab being - preloaded and first navigation start, recorded in the case where a startup - tab preload is determined {LoadDecision} viable. In the case where the - ElideTabPreloadAtStartup feature is enabled, this metric will be segmented - to reflect the state that would have resulted if tab preloading was not - disabled by the feature. Recorded only for startups in which - Android.Startup.Cold.TimeToFirstNavigationCommit is recorded for ability to - compare with that metric and its derived metrics. - </summary> - <token key="LoadDecision"> - <variant name="Load" summary="to be"/> - <variant name="NoLoad" summary="not to be"/> - </token> -</histogram> - -<histogram - name="Android.StartupTabPreloader.LoadDecisionToFirstVisibleContent.{LoadAndMatchResult}" - units="ms" expires_after="2022-09-01"> - <owner>blundell@chromium.org</owner> - <owner>yfriedman@chromium.org</owner> - <summary> - The time in a cold start between the triggerpoint for a startup tab being - preloaded and Android.Startup.Cold.TimeToFirstVisibleContent being recorded, - recorded in the case where a startup tab preload is determined - {LoadAndMatchResult}. In the case where the ElideTabPreloadAtStartup feature - is enabled, this metric will be segmented to reflect the state that would - have resulted if tab preloading was not disabled by the feature. - </summary> - <token key="LoadAndMatchResult"> - <variant name="LoadAndMatch" - summary="to be viable and the preload is a match for the actual - initial load"/> - <variant name="LoadAndMismatch" - summary="to be viable and the preload is not a match for the actual - initial load"/> - <variant name="LoadPreMatch" - summary="to be viable and first visible content is recorded before it - was determined whether the preload was a match for the - actual initial load. Note that it is not expected that this - case occurs in practice, but it is theoretically possible"/> - <variant name="NoLoad" summary="not to be viable"/> - </token> -</histogram> - -<histogram - name="Android.StartupTabPreloader.LoadDecisionToMatchDecision.{LoadDecision}" - units="ms" expires_after="2022-09-01"> - <owner>blundell@chromium.org</owner> - <owner>yfriedman@chromium.org</owner> - <summary> - The time in a cold start between the triggerpoint for a startup tab being - preloaded and the decision being made on whether the preload is a match for - the information of the actual initial load that needs to occur, recorded in - the case where a startup tab preload is determined {LoadDecision} viable. In - the case where the ElideTabPreloadAtStartup feature is enabled, this metric - will be segmented to reflect the state that would have resulted if tab - preloading was not disabled by the feature. - </summary> - <token key="LoadDecision"> - <variant name="Load" summary="to be"/> - <variant name="NoLoad" summary="not to be"/> - </token> -</histogram> - <histogram name="Android.StrictMode.OverrideUrlLoadingTime" units="ms" expires_after="2022-10-30"> <owner>yfriedman@chromium.org</owner>
diff --git a/tools/metrics/histograms/metadata/network/histograms.xml b/tools/metrics/histograms/metadata/network/histograms.xml index 748bc83..8ddbcb1f 100644 --- a/tools/metrics/histograms/metadata/network/histograms.xml +++ b/tools/metrics/histograms/metadata/network/histograms.xml
@@ -132,6 +132,65 @@ </token> </histogram> +<histogram name="Network.CacheTransparency.CacheNotUsed" + enum="CacheTransparencyCacheNotUsedReason" expires_after="2022-11-01"> + <owner>nidhijaju@chromium.org</owner> + <owner>ricea@chromium.org</owner> + <summary> + Records why a URL does not use the single-keyed cache due to a reason in + //services/network, when a URL request is made. Reasons include different + request type (i.e. not GET), incompatible request load flags, incompatible + request headers, etc. + </summary> +</histogram> + +<histogram name="Network.CacheTransparency.MarkedUnusable" units="list index" + expires_after="2022-11-01"> + <owner>nidhijaju@chromium.org</owner> + <owner>ricea@chromium.org</owner> + <summary> + Records whether a URL in the pervasive payloads list is marked as + "unusable" when the cached response is read. The list index is the + index of the URL in the pervasive payloads list. + </summary> +</histogram> + +<histogram name="Network.CacheTransparency.MismatchedChecksums" + units="list index" expires_after="2022-11-01"> + <owner>nidhijaju@chromium.org</owner> + <owner>ricea@chromium.org</owner> + <summary> + Records whether a URL in the pervasive payloads list has a different + checksum than what is expected when the response checksums are compared in + HttpCache::Transaction. The list index is the index of the URL in the + pervasive payloads list. + </summary> +</histogram> + +<histogram name="Network.CacheTransparency.SingleKeyedCacheIsUsed" + units="list index" expires_after="2022-11-01"> + <owner>nidhijaju@chromium.org</owner> + <owner>ricea@chromium.org</owner> + <summary> + Records whether the single-keyed cache is used for a URL in the pervasive + payloads list (not just when a cache entry is hit because there could be an + "unusable" flag set). This is recorded when the response checksum + matches the expected checksum in HttpCache::Transaction. The list index is + the index of the URL in the pervasive payloads list. + </summary> +</histogram> + +<histogram name="Network.CacheTransparency.URLMatched" units="list index" + expires_after="2022-11-01"> + <owner>nidhijaju@chromium.org</owner> + <owner>ricea@chromium.org</owner> + <summary> + Records whether a requested resource's URL matched with any of the URLs in + the pervasive payloads list when a URL request is made. The list index is + the index of the URL in the pervasive payloads list. + </summary> +</histogram> + <histogram name="Network.Cellular.Apn.UseAttachApnOnSave" enum="Boolean" expires_after="2022-05-18"> <owner>hsuregan@chromium.org</owner>
diff --git a/tools/metrics/histograms/metadata/startup/histograms.xml b/tools/metrics/histograms/metadata/startup/histograms.xml index 57a6214..810df945 100644 --- a/tools/metrics/histograms/metadata/startup/histograms.xml +++ b/tools/metrics/histograms/metadata/startup/histograms.xml
@@ -330,43 +330,6 @@ </summary> </histogram> -<histogram name="Startup.Android.StartupTabPreloader.LoadDecisionReason" - enum="StartupTabPreloaderLoadDecisionCause" expires_after="2022-11-06"> - <owner>blundell@chromium.org</owner> - <owner>yfriedman@chromium.org</owner> - <summary> - Android: Gives the reason for StartupTabPreloader's decision of whether to - load a tab at startup. As reasons for not doing a startup tab preload are - not necessarily orthogonal, gives highest-priority reason (see computation - of metric in the codebase). Recorded when a profile is created, assuming a - StartupTabPreloader has been constructed for intents with a url and either - regular Chrome or a Custom Tab will be loaded. - </summary> -</histogram> - -<histogram name="Startup.Android.StartupTabPreloader.TabLoaded" units="Boolean" - expires_after="2022-11-06"> - <owner>skyostil@chromium.org</owner> - <summary> - Android: Whether or not creation of a profile lead to the - StartupTabPreloader speculatively created a tab. Recorded when a profile is - created, assuming a StartupTabPreloader has been constructed for intents - with a url and either regular Chrome or a Custom Tab will be loaded. - </summary> -</histogram> - -<histogram name="Startup.Android.StartupTabPreloader.TabTaken" units="Boolean" - expires_after="2022-11-06"> - <owner>skyostil@chromium.org</owner> - <summary> - Android: Whether or not a tab speculatively created by the - StartupTabPreloader was subsequently adopted by ChromeTabCreator. Recorded - when a tab is loaded, assuming a StartupTabPreloader has been constructed - for intents with a url for either regular Chrome or a Custom Tab will be - loaded. Warning: this histogram was expired from 2020-11-08 through M95. - </summary> -</histogram> - <histogram name="Startup.Android.ThumbnailFetchedForGTSFirstMeaningfulPaint" units="thumbnails" expires_after="2020-08-02"> <owner>yusufo@chromium.org</owner>
diff --git a/ui/chromeos/styles/cros_colors.json5 b/ui/chromeos/styles/cros_colors.json5 index 0c37fd4..5ab5c77e 100644 --- a/ui/chromeos/styles/cros_colors.json5 +++ b/ui/chromeos/styles/cros_colors.json5
@@ -192,8 +192,8 @@ * Other foundational colors. */ focus_ring_color: { - light: "$color_prominent", - dark: "$color_prominent", + light: "$color_prominent_light", + dark: "$color_prominent_dark", generate_per_mode: true, }, focus_ring_color_inactive: "$icon_color_secondary",
diff --git a/ui/file_manager/file_manager/background/js/BUILD.gn b/ui/file_manager/file_manager/background/js/BUILD.gn index b1581a7..dbc4ca5 100644 --- a/ui/file_manager/file_manager/background/js/BUILD.gn +++ b/ui/file_manager/file_manager/background/js/BUILD.gn
@@ -372,6 +372,9 @@ "//ui/webui/resources/js:assert.m", "//ui/webui/resources/js/cr:event_target.m", ] + visibility += [ + "//ui/file_manager/file_manager/foreground/js:directory_model_unittest.m", + ] } js_library("file_operation_manager") { @@ -380,6 +383,7 @@ ":metadata_proxy", ":trash", ":volume_manager_factory", + "//ui/file_manager/file_manager/common/js:api", "//ui/file_manager/file_manager/common/js:async_util", "//ui/file_manager/file_manager/common/js:file_operation_common", "//ui/file_manager/file_manager/common/js:trash",
diff --git a/ui/file_manager/file_manager/background/js/file_operation_manager.js b/ui/file_manager/file_manager/background/js/file_operation_manager.js index c29e5a1..7d2cf6d 100644 --- a/ui/file_manager/file_manager/background/js/file_operation_manager.js +++ b/ui/file_manager/file_manager/background/js/file_operation_manager.js
@@ -4,6 +4,7 @@ import {assert} from 'chrome://resources/js/assert.m.js'; +import {startIOTask} from '../../common/js/api.js'; import {AsyncUtil} from '../../common/js/async_util.js'; import {FileOperationError, FileOperationProgressEvent} from '../../common/js/file_operation_common.js'; import {TrashEntry, TrashRootEntry} from '../../common/js/trash.js'; @@ -452,8 +453,7 @@ deleteEntries(entries, permanentlyDelete = false) { if (permanentlyDelete) { if (window.isSWA) { - chrome.fileManagerPrivate.startIOTask( - chrome.fileManagerPrivate.IOTaskType.DELETE, entries, {}); + startIOTask(chrome.fileManagerPrivate.IOTaskType.DELETE, entries, {}); return; } }
diff --git a/ui/file_manager/file_manager/background/js/mock_file_operation_manager.js b/ui/file_manager/file_manager/background/js/mock_file_operation_manager.js index 38450c9..8a292ff2 100644 --- a/ui/file_manager/file_manager/background/js/mock_file_operation_manager.js +++ b/ui/file_manager/file_manager/background/js/mock_file_operation_manager.js
@@ -94,13 +94,23 @@ return this.generatedTaskIds.indexOf(id) !== -1; } - hasQueuedTasks() {} - filterSameDirectoryEntry() {} - willUseTrash() {} + /** @return {boolean} */ + hasQueuedTasks() { + throw new Error('Not implemented'); + } + /** @return {Promise} */ + filterSameDirectoryEntry(sourceEntries, targetEntry, isMove) {} + /** @return {boolean} */ + willUseTrash(volumeManager, entries) { + throw new Error('Not implemented'); + } deleteEntries() {} restoreDeleted() {} emptyTrash() {} zipSelection() {} cancelZip() {} - async writeFile() {} + /** @return {!Promise<!FileEntry>} */ + async writeFile(file, destination) { + throw new Error('Not implemented'); + } }
diff --git a/ui/file_manager/file_manager/background/js/mock_volume_manager.js b/ui/file_manager/file_manager/background/js/mock_volume_manager.js index 6016e48f..522aaf1 100644 --- a/ui/file_manager/file_manager/background/js/mock_volume_manager.js +++ b/ui/file_manager/file_manager/background/js/mock_volume_manager.js
@@ -117,9 +117,14 @@ */ getLocationInfo(entry) { if (util.isFakeEntry(entry)) { + const isReadOnly = + entry.rootType === VolumeManagerCommon.RootType.RECENT ? + !util.isRecentsFilterV2Enabled() : + true; return new EntryLocationImpl( this.volumeInfoList.item(0), - /** @type {!FakeEntry} */ (entry).rootType, true, true); + /** @type {!FakeEntry} */ (entry).rootType, /* isRootType= */ true, + isReadOnly); } if (entry.filesystem.name === VolumeManagerCommon.VolumeType.DRIVE) { @@ -223,6 +228,9 @@ return volumeInfo; } + /** + * @return {!Promise<!VolumeInfo>} + */ async mountArchive(fileUrl, password) { throw new Error('Not implemented'); } @@ -235,7 +243,7 @@ throw new Error('Not implemented'); } - configure(volumeInfo) { + async configure(volumeInfo) { throw new Error('Not implemented'); } @@ -247,6 +255,9 @@ throw new Error('Not implemented'); } + /** + * @return {boolean} + */ dispatchEvent(event) { throw new Error('Not implemented'); }
diff --git a/ui/file_manager/file_manager/background/js/volume_manager_impl.js b/ui/file_manager/file_manager/background/js/volume_manager_impl.js index 950c4c5..dee63e3 100644 --- a/ui/file_manager/file_manager/background/js/volume_manager_impl.js +++ b/ui/file_manager/file_manager/background/js/volume_manager_impl.js
@@ -397,10 +397,13 @@ const volumeInfo = this.getVolumeInfo(entry); if (util.isFakeEntry(entry)) { + const isReadOnly = + entry.rootType === VolumeManagerCommon.RootType.RECENT ? + !util.isRecentsFilterV2Enabled() : + true; return new EntryLocationImpl( volumeInfo, assert(entry.rootType), - true /* the entry points a root directory. */, - true /* fake entries are read only. */); + true /* The entry points a root directory. */, isReadOnly); } if (!volumeInfo) {
diff --git a/ui/file_manager/file_manager/common/js/api.js b/ui/file_manager/file_manager/common/js/api.js index ee304bc0..675ddfea 100644 --- a/ui/file_manager/file_manager/common/js/api.js +++ b/ui/file_manager/file_manager/common/js/api.js
@@ -191,3 +191,16 @@ return '#ffffff'; } } + +/** + * Starts an IOTask of `type` and returns a taskId that can be used to cancel + * or identify the ongoing IO operation. + * @param {!chrome.fileManagerPrivate.IOTaskType} type + * @param {!Array<!Entry>} entries + * @param {!chrome.fileManagerPrivate.IOTaskParams} params + * @returns {!Promise<!number>} + */ +export async function startIOTask(type, entries, params) { + return promisify( + chrome.fileManagerPrivate.startIOTask, type, entries, params); +}
diff --git a/ui/file_manager/file_manager/common/js/volume_manager_types.js b/ui/file_manager/file_manager/common/js/volume_manager_types.js index 964deae..8f81cdf 100644 --- a/ui/file_manager/file_manager/common/js/volume_manager_types.js +++ b/ui/file_manager/file_manager/common/js/volume_manager_types.js
@@ -446,6 +446,14 @@ VolumeManagerCommon.PHOTOS_DOCUMENTS_PROVIDER_VOLUME_ID = 'documents_provider:com.google.android.apps.photos.photoprovider/com.google.android.apps.photos'; +/** + * ID of the MediaDocumentsProvider. All the files returned by ARC source in + * Recents have this ID prefix in their filesystem. + * @const {string} + */ +VolumeManagerCommon.MEDIA_DOCUMENTS_PROVIDER_ID = + 'com.android.providers.media.documents'; + /** * Creates an CustomEvent object for changing current directory when an archive @@ -460,4 +468,17 @@ {detail: {mountPoint: mountPoint}}); }; +/** + * Checks if a file entry is a Recent entry coming from ARC source. + * @param {?Entry} entry + * @return {boolean} + */ +VolumeManagerCommon.isRecentArcEntry = entry => { + if (!entry) { + return false; + } + return entry.filesystem.name.startsWith( + VolumeManagerCommon.MEDIA_DOCUMENTS_PROVIDER_ID); +}; + export {VolumeManagerCommon};
diff --git a/ui/file_manager/file_manager/common/js/volume_manager_types_unittest.m.js b/ui/file_manager/file_manager/common/js/volume_manager_types_unittest.m.js index 468c92d51..b549024 100644 --- a/ui/file_manager/file_manager/common/js/volume_manager_types_unittest.m.js +++ b/ui/file_manager/file_manager/common/js/volume_manager_types_unittest.m.js
@@ -2,7 +2,9 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. -import {assertTrue} from 'chrome://test/chai_assert.js'; +import {assertFalse, assertTrue} from 'chrome://test/chai_assert.js'; + +import {MockFileEntry, MockFileSystem} from './mock_entry.js'; import {VolumeManagerCommon} from './volume_manager_types.js'; // Test that every volumeType has a rootType, and that it maps back to the same @@ -55,3 +57,17 @@ assertTrue(volumeType !== undefined); }); } + +// Tests that IsRecentArcEntry() should return true/false if an entry belongs/ +// doesn't belong to recent. +export function testIsRecentArcEntry() { + assertFalse(VolumeManagerCommon.isRecentArcEntry(null)); + const otherEntry = MockFileEntry.create( + new MockFileSystem('download:Downloads'), 'test.txt'); + assertFalse(VolumeManagerCommon.isRecentArcEntry(otherEntry)); + const recentEntry = MockFileEntry.create( + new MockFileSystem( + 'com.android.providers.media.documents:documents_root'), + 'Documents/abc.pdf'); + assertTrue(VolumeManagerCommon.isRecentArcEntry(recentEntry)); +}
diff --git a/ui/file_manager/file_manager/foreground/js/BUILD.gn b/ui/file_manager/file_manager/foreground/js/BUILD.gn index c605af9..d28685b 100644 --- a/ui/file_manager/file_manager/foreground/js/BUILD.gn +++ b/ui/file_manager/file_manager/foreground/js/BUILD.gn
@@ -446,6 +446,20 @@ ] } +js_unittest("directory_model_unittest.m") { + deps = [ + ":directory_contents", + ":directory_model", + "metadata:mock_metadata", + "//chrome/test/data/webui:chai_assert", + "//ui/file_manager/file_manager/background/js:mock_file_operation_manager", + "//ui/file_manager/file_manager/background/js:mock_volume_manager", + "//ui/file_manager/file_manager/common/js:mock_chrome", + "//ui/file_manager/file_manager/common/js:volume_manager_types", + "//ui/webui/resources/js:load_time_data.m", + ] +} + js_library("navigation_uma") { deps = [ "//ui/file_manager/file_manager/common/js:metrics", @@ -622,6 +636,7 @@ ":webui_command_extender", "ui:directory_tree", "ui:files_confirm_dialog", + "//ui/file_manager/file_manager/common/js:api", "//ui/file_manager/file_manager/common/js:dialog_type", "//ui/file_manager/file_manager/common/js:file_operation_common", "//ui/file_manager/file_manager/common/js:file_type", @@ -742,6 +757,7 @@ "ui:directory_tree", "ui:drag_selector", "ui:list_container", + "//ui/file_manager/file_manager/common/js:api", "//ui/file_manager/file_manager/common/js:file_type", "//ui/file_manager/file_manager/common/js:progress_center_common", "//ui/file_manager/file_manager/common/js:util", @@ -1329,6 +1345,7 @@ ":banner_controller_unittest.m", ":banner_util_unittest.m", ":directory_contents_unittest.m", + ":directory_model_unittest.m", ":file_list_model_unittest.m", ":file_manager_commands_unittest.m", ":file_tasks_unittest.m",
diff --git a/ui/file_manager/file_manager/foreground/js/directory_contents.js b/ui/file_manager/file_manager/foreground/js/directory_contents.js index ea1f3f99..b20cbb6a 100644 --- a/ui/file_manager/file_manager/foreground/js/directory_contents.js +++ b/ui/file_manager/file_manager/foreground/js/directory_contents.js
@@ -37,8 +37,13 @@ * @param {function()} successCallback Called when the scan is completed * successfully. * @param {function(DOMError)} errorCallback Called an error occurs. + * @param {boolean=} invalidateCache True to invalidate the backend scanning + * result cache. This param only works if the corresponding backend + * scanning supports cache. */ - async scan(entriesCallback, successCallback, errorCallback) {} + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) {} /** * Request cancelling of the running scan. When the cancelling is done, @@ -65,7 +70,9 @@ * Starts to read the entries in the directory. * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { if (!this.entry_ || !this.entry_.createReader) { // If entry is not specified or if entry doesn't implement createReader, // we cannot read it. @@ -113,7 +120,9 @@ * Starts to search on Drive File System. * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { // Let's give another search a chance to cancel us before we begin. setTimeout(() => { // Check cancelled state before read the entries. @@ -193,7 +202,9 @@ * Starts the file name search. * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { util.readEntriesRecursively(assert(this.entry_), (entries) => { const matchEntries = entries.filter( entry => entry.name.toLowerCase().indexOf(this.query_) >= 0); @@ -222,7 +233,9 @@ * Starts to metadata-search on Drive File System. * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { chrome.fileManagerPrivate.searchDriveMetadata( {query: '', types: this.searchType_, maxResults: 100}, results => { if (chrome.runtime.lastError) { @@ -282,9 +295,12 @@ /** * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { chrome.fileManagerPrivate.getRecentFiles( - this.sourceRestriction_, this.recentFileType_, entries => { + this.sourceRestriction_, this.recentFileType_, invalidateCache, + entries => { if (chrome.runtime.lastError) { console.error(chrome.runtime.lastError.message); errorCallback( @@ -320,11 +336,13 @@ * hierarchy. We need to list files under the root directory to provide * flatten view. A file will not be shown in multiple directories in * media-view hierarchy since no folders will be added in media documents - * provider. We can list all files without duplication by just retrieveing + * provider. We can list all files without duplication by just retrieving * files in directories recursively. * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { // To provide flatten view of files, this media-view scanner retrieves files // in directories inside the media's root entry recursively. util.readEntriesRecursively( @@ -351,7 +369,9 @@ /** * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { chrome.fileManagerPrivate.mountCrostini(() => { if (chrome.runtime.lastError) { console.error( @@ -390,7 +410,9 @@ /** * @override */ - async scan(entriesCallback, successCallback, errorCallback) { + async scan( + entriesCallback, successCallback, errorCallback, + invalidateCache = false) { try { await mountGuest(this.guest_id_); successCallback(); @@ -790,8 +812,11 @@ * * @param {boolean} refresh True to refresh metadata, or false to use cached * one. + * @param {boolean} invalidateCache True to invalidate the backend scanning + * result cache. This param only works if the corresponding backend + * scanning supports cache. */ - scan(refresh) { + scan(refresh, invalidateCache) { /** * Invoked when the scanning is completed successfully. * @this {DirectoryContents} @@ -818,7 +843,7 @@ this.scanner_ = this.scannerFactory_(); this.scanner_.scan( this.onNewEntries_.bind(this, refresh), completionCallback.bind(this), - errorCallback.bind(this)); + errorCallback.bind(this), invalidateCache); } /**
diff --git a/ui/file_manager/file_manager/foreground/js/directory_model.js b/ui/file_manager/file_manager/foreground/js/directory_model.js index e1c10eb6..a18a988 100644 --- a/ui/file_manager/file_manager/foreground/js/directory_model.js +++ b/ui/file_manager/file_manager/foreground/js/directory_model.js
@@ -114,6 +114,12 @@ this.fileWatcher_.addEventListener( 'watcher-directory-changed', this.onWatcherDirectoryChanged_.bind(this)); + // For non-watchable directory (e.g. FakeEntry), we need to subscribe to + // the IOTask and manually refresh. + if (util.isRecentsFilterV2Enabled()) { + chrome.fileManagerPrivate.onIOTaskProgressStatus.addListener( + this.updateFileListAfterIOTask_.bind(this)); + } util.addEventListenerToBackgroundComponent( fileOperationManager, 'entries-changed', this.onEntriesChanged_.bind(this)); @@ -368,7 +374,7 @@ }); } else { // Invokes force refresh if the detailed information isn't provided. - // This can occur very frequently (e.g. when copying files into Downlaods) + // This can occur very frequently (e.g. when copying files into Downloads) // and rescan is heavy operation, so we keep some interval for each // rescan. this.rescanAggregator_.run(); @@ -484,9 +490,12 @@ * Schedule rescan with short delay. * @param {boolean} refresh True to refresh metadata, or false to use cached * one. + * @param {boolean=} invalidateCache True to invalidate the backend scanning + * result cache. This param only works if the corresponding backend + * scanning supports cache. */ - rescanSoon(refresh) { - this.scheduleRescan(SHORT_RESCAN_INTERVAL, refresh); + rescanSoon(refresh, invalidateCache = false) { + this.scheduleRescan(SHORT_RESCAN_INTERVAL, refresh, invalidateCache); } /** @@ -494,9 +503,12 @@ * notification. * @param {boolean} refresh True to refresh metadata, or false to use cached * one. + * @param {boolean=} invalidateCache True to invalidate the backend scanning + * result cache. This param only works if the corresponding backend + * scanning supports cache. */ - rescanLater(refresh) { - this.scheduleRescan(SIMULTANEOUS_RESCAN_INTERVAL, refresh); + rescanLater(refresh, invalidateCache = false) { + this.scheduleRescan(SIMULTANEOUS_RESCAN_INTERVAL, refresh, invalidateCache); } /** @@ -506,8 +518,11 @@ * @param {number} delay Delay in ms after which the rescan will be performed. * @param {boolean} refresh True to refresh metadata, or false to use cached * one. + * @param {boolean=} invalidateCache True to invalidate the backend scanning + * result cache. This param only works if the corresponding backend + * scanning supports cache. */ - scheduleRescan(delay, refresh) { + scheduleRescan(delay, refresh, invalidateCache = false) { if (this.rescanTime_) { if (this.rescanTime_ <= Date.now() + delay) { return; @@ -521,7 +536,7 @@ this.rescanTimeoutId_ = setTimeout(() => { this.rescanTimeoutId_ = null; if (sequence === this.changeDirectorySequence_) { - this.rescan(refresh); + this.rescan(refresh, invalidateCache); } }, delay); } @@ -548,8 +563,11 @@ * * @param {boolean} refresh True to refresh metadata, or false to use cached * one. + * @param {boolean=} invalidateCache True to invalidate the backend scanning + * result cache. This param only works if the corresponding backend + * scanning supports cache. */ - rescan(refresh) { + rescan(refresh, invalidateCache = false) { this.clearRescanTimeout_(); if (this.runningScan_) { this.pendingRescan_ = true; @@ -571,7 +589,8 @@ }; this.scan_( - dirContents, refresh, successCallback, () => {}, () => {}, () => {}); + dirContents, refresh, invalidateCache, successCallback, () => {}, + () => {}, () => {}); } /** @@ -678,7 +697,7 @@ dispatchSimpleEvent(this, 'scan-started'); fileList.splice(0, fileList.length); this.scan_( - this.currentDirContents_, false, onDone, onFailed, onUpdated, + this.currentDirContents_, false, true, onDone, onFailed, onUpdated, onCancelled); } @@ -747,6 +766,7 @@ * the scan will be run. * @param {boolean} refresh True to refresh metadata, or false to use cached * one. + * @param {boolean} invalidateCache True to invalidate scanning result cache. * @param {function()} successCallback Callback on success. * @param {function(DOMError)} failureCallback Callback on failure. * @param {function()} updatedCallback Callback on update. Only on the last @@ -755,10 +775,8 @@ * @private */ scan_( - dirContents, refresh, successCallback, failureCallback, updatedCallback, - cancelledCallback) { - const self = this; - + dirContents, refresh, invalidateCache, successCallback, failureCallback, + updatedCallback, cancelledCallback) { /** * Runs pending scan if there is one. * @@ -837,7 +855,7 @@ dirContents.addEventListener('scan-updated', updatedCallback); dirContents.addEventListener('scan-failed', onFailure); dirContents.addEventListener('scan-cancelled', onCancelled); - dirContents.scan(refresh); + dirContents.scan(refresh, invalidateCache); } /** @@ -1593,4 +1611,33 @@ this.onClearSearch_ = null; } } + + /** + * Update the file list when curtain IO task is finished. Fake directory + * entries like RecentEntry is not watchable, to keep the file list + * refresh, we need to explicitly subscribe to the IO task status event, and + * manually refresh. + * @param {!chrome.fileManagerPrivate.ProgressStatus} event + * @private + */ + updateFileListAfterIOTask_(event) { + /** @type {!Set<!chrome.fileManagerPrivate.IOTaskType>} */ + const eventTypesRequireRefresh = new Set([ + chrome.fileManagerPrivate.IOTaskType.DELETE, + chrome.fileManagerPrivate.IOTaskType.MOVE, + ]); + /** @type {!Set<?VolumeManagerCommon.RootType>} */ + const rootTypesRequireRefresh = + new Set([VolumeManagerCommon.RootType.RECENT]); + + const currentRootType = this.getCurrentRootType(); + if (!rootTypesRequireRefresh.has(currentRootType)) { + return; + } + const isIOTaskFinished = + event.state === chrome.fileManagerPrivate.IOTaskState.SUCCESS; + if (isIOTaskFinished && eventTypesRequireRefresh.has(event.type)) { + this.rescanLater(/* refresh= */ false, /* invalidateCache= */ true); + } + } }
diff --git a/ui/file_manager/file_manager/foreground/js/directory_model_unittest.m.js b/ui/file_manager/file_manager/foreground/js/directory_model_unittest.m.js new file mode 100644 index 0000000..60358bf --- /dev/null +++ b/ui/file_manager/file_manager/foreground/js/directory_model_unittest.m.js
@@ -0,0 +1,130 @@ +// Copyright 2022 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 {loadTimeData} from 'chrome://resources/js/load_time_data.m.js'; +import {assertFalse, assertTrue} from 'chrome://test/chai_assert.js'; + +import {MockFileOperationManager} from '../../background/js/mock_file_operation_manager.js'; +import {MockVolumeManager} from '../../background/js/mock_volume_manager.js'; +import {installMockChrome} from '../../common/js/mock_chrome.js'; +import {VolumeManagerCommon} from '../../common/js/volume_manager_types.js'; + +import {FileFilter} from './directory_contents.js'; +import {DirectoryModel} from './directory_model.js'; +import {MockMetadataModel} from './metadata/mock_metadata.js'; + +/** + * @type {?function(!chrome.fileManagerPrivate.ProgressStatus):void} + */ +let onIOTaskProgressStatusCallback; + +/** + * Initializes the test environment. + */ +export function setUp() { + // Mock loadTimeData strings. + loadTimeData.resetForTesting({ + DRIVE_DIRECTORY_LABEL: 'Google Drive', + DRIVE_OFFLINE_COLLECTION_LABEL: 'Offline', + DRIVE_SHARED_WITH_ME_COLLECTION_LABEL: 'Shared with me', + DOWNLOADS_DIRECTORY_LABEL: 'Downloads', + FILTERS_IN_RECENTS_V2_ENABLED: true, + }); + + /** + * Mock chrome APIs. + * @type {!Object} + */ + const mockChrome = { + fileManagerPrivate: { + SourceRestriction: { + ANY_SOURCE: 'any_source', + }, + RecentFileType: { + ALL: 'all', + }, + SearchType: { + EXCLUDE_DIRECTORIES: 'EXCLUDE_DIRECTORIES', + SHARED_WITH_ME: 'SHARED_WITH_ME', + OFFLINE: 'OFFLINE', + ALL: 'ALL', + }, + DriveConnectionStateType: { + OFFLINE: 'OFFLINE', + }, + onIOTaskProgressStatus: { + /** + * @param {?function(!chrome.fileManagerPrivate.ProgressStatus):void} + * callback + */ + addListener(callback) { + onIOTaskProgressStatusCallback = callback; + } + }, + IOTaskType: { + DELETE: 'delete', + COPY: 'copy', + }, + IOTaskState: { + SUCCESS: 'success', + }, + onDirectoryChanged: {addListener(callback) {}}, + getRecentFiles: () => {}, + }, + }; + + // Install mock chrome APIs. + installMockChrome(mockChrome); +} + +/** + * Mock DirectoryModel's dependencies and return a DirectoryModel instance. + * + * @returns {!DirectoryModel} + */ +function getDirectoryModel() { + const volumeManager = new MockVolumeManager(); + MockVolumeManager.installMockSingleton(volumeManager); + const fileFilter = new FileFilter(volumeManager); + const metadataModel = new MockMetadataModel({}); + const fileOperationManager = new MockFileOperationManager(); + return new DirectoryModel( + false, fileFilter, metadataModel, volumeManager, fileOperationManager); +} + +/** + * Tests that the directory will be re-scanned after the delete operation. + */ +export function testRecanAfterDeletionForRecents() { + const deleteEvent = /** @type {chrome.fileManagerPrivate.ProgressStatus} */ ({ + type: chrome.fileManagerPrivate.IOTaskType.DELETE, + state: chrome.fileManagerPrivate.IOTaskState.SUCCESS, + }); + const otherEvent = /** @type {chrome.fileManagerPrivate.ProgressStatus} */ ({ + type: chrome.fileManagerPrivate.IOTaskType.COPY, + state: chrome.fileManagerPrivate.IOTaskState.SUCCESS, + }); + + const directoryModel = getDirectoryModel(); + let isRescanCalled = false; + directoryModel.rescanLater = () => { + isRescanCalled = true; + }; + + // Current directory is not Recent. + directoryModel.getCurrentRootType = () => + VolumeManagerCommon.RootType.DOWNLOADS; + onIOTaskProgressStatusCallback(deleteEvent); + assertFalse(isRescanCalled); + onIOTaskProgressStatusCallback(otherEvent); + assertFalse(isRescanCalled); + + // Current directory is Recent. + directoryModel.getCurrentRootType = () => VolumeManagerCommon.RootType.RECENT; + onIOTaskProgressStatusCallback(deleteEvent); + assertTrue(isRescanCalled); + isRescanCalled = false; + onIOTaskProgressStatusCallback(otherEvent); + assertFalse(isRescanCalled); +}
diff --git a/ui/file_manager/file_manager/foreground/js/file_manager_commands.js b/ui/file_manager/file_manager/foreground/js/file_manager_commands.js index 0ef796cb..ef60c664 100644 --- a/ui/file_manager/file_manager/foreground/js/file_manager_commands.js +++ b/ui/file_manager/file_manager/foreground/js/file_manager_commands.js
@@ -9,7 +9,7 @@ import {contextMenuHandler} from 'chrome://resources/js/cr/ui/context_menu_handler.m.js'; import {List} from 'chrome://resources/js/cr/ui/list.m.js'; -import {getHoldingSpaceState} from '../../common/js/api.js'; +import {getHoldingSpaceState, startIOTask} from '../../common/js/api.js'; import {DialogType} from '../../common/js/dialog_type.js'; import {FileOperationProgressEvent} from '../../common/js/file_operation_common.js'; import {FileType} from '../../common/js/file_type.js'; @@ -1613,7 +1613,10 @@ fileManager.volumeManager.getLocationInfo(parentEntry) : null; const volumeIsNotReadOnly = !!locationInfo && !locationInfo.isReadOnly; + // ARC doesn't support rename for now. http://b/232152680 + const isRecentArcEntry = VolumeManagerCommon.isRecentArcEntry(entries[0]); event.canExecute = entries.length === 1 && volumeIsNotReadOnly && + !isRecentArcEntry && CommandUtil.hasCapability(fileManager, entries, 'canRename'); event.command.setHidden(false); } @@ -2081,7 +2084,7 @@ const selectionEntries = fileManager.getSelection().entries; if (util.isExtractArchiveEnabled()) { - chrome.fileManagerPrivate.startIOTask( + startIOTask( chrome.fileManagerPrivate.IOTaskType.EXTRACT, selectionEntries, {destinationFolder: /** @type {!DirectoryEntry} */ (dirEntry)}); } @@ -2132,7 +2135,7 @@ const selectionEntries = fileManager.getSelection().entries; if (window.isSWA) { - chrome.fileManagerPrivate.startIOTask( + startIOTask( chrome.fileManagerPrivate.IOTaskType.ZIP, selectionEntries, {destinationFolder: /** @type {!DirectoryEntry} */ (dirEntry)}); } else {
diff --git a/ui/file_manager/file_manager/foreground/js/file_manager_commands_unittest.m.js b/ui/file_manager/file_manager/foreground/js/file_manager_commands_unittest.m.js index e1773c22..88390d2 100644 --- a/ui/file_manager/file_manager/foreground/js/file_manager_commands_unittest.m.js +++ b/ui/file_manager/file_manager/foreground/js/file_manager_commands_unittest.m.js
@@ -6,6 +6,7 @@ import {assertArrayEquals, assertEquals, assertFalse, assertNotEquals, assertTrue} from 'chrome://test/chai_assert.js'; import {MockVolumeManager} from '../../background/js/mock_volume_manager.js'; +import {FakeEntryImpl} from '../../common/js/files_app_entry_types.js'; import {installMockChrome} from '../../common/js/mock_chrome.js'; import {MockDirectoryEntry, MockEntry} from '../../common/js/mock_entry.js'; import {waitUntil} from '../../common/js/test_error_reporting.js'; @@ -363,3 +364,67 @@ done(); } + +/** + * Tests that rename command should be disabled for Recent entry. + */ +export async function testRenameCommand(done) { + loadTimeData.resetForTesting({}); + + // Check: `rename` command exists. + const command = CommandHandler.getCommand('rename'); + assertNotEquals(command, undefined); + + // Mock volume manager. + const volumeManager = new MockVolumeManager(); + + // Create `documents_root` volume. + const documentsRootVolumeInfo = volumeManager.createVolumeInfo( + VolumeManagerCommon.VolumeType.MEDIA_VIEW, + 'com.android.providers.media.documents:documents_root', 'Documents'); + + // Mock file entries. + const recentEntry = + new FakeEntryImpl('Recent', VolumeManagerCommon.RootType.RECENT); + const pdfEntry = MockDirectoryEntry.create( + documentsRootVolumeInfo.fileSystem, 'Documents/abc.pdf'); + + // Mock `Event`. + const event = { + canExecute: true, + target: { + entry: pdfEntry, + }, + command: { + hidden: false, + setHidden: (hidden) => { + event.command.hidden = hidden; + }, + }, + }; + + // The current selection for testing. + const currentSelection = { + entries: [pdfEntry], + iconType: 'none', + totalCount: 1, + }; + + // Mock `FileManager`. + const fileManager = { + directoryModel: { + isOnNative: () => true, + isReadOnly: () => false, + }, + getCurrentDirectoryEntry: () => recentEntry, + getSelection: () => currentSelection, + volumeManager: volumeManager, + }; + + // Check: canExecute is false and command is disabled. + command.canExecute(event, fileManager); + assertFalse(event.canExecute); + assertFalse(event.command.hidden); + + done(); +}
diff --git a/ui/file_manager/file_manager/foreground/js/file_transfer_controller.js b/ui/file_manager/file_manager/foreground/js/file_transfer_controller.js index dda3981..e1eb28b 100644 --- a/ui/file_manager/file_manager/foreground/js/file_transfer_controller.js +++ b/ui/file_manager/file_manager/foreground/js/file_transfer_controller.js
@@ -8,7 +8,7 @@ import {TreeItem} from 'chrome://resources/js/cr/ui/tree.js'; import {queryRequiredElement} from 'chrome://resources/js/util.m.js'; -import {getDirectory, getDisallowedTransfers} from '../../common/js/api.js'; +import {getDirectory, getDisallowedTransfers, startIOTask} from '../../common/js/api.js'; import {FileType} from '../../common/js/file_type.js'; import {ProgressCenterItem, ProgressItemState, ProgressItemType} from '../../common/js/progress_center_common.js'; import {str, strf, util} from '../../common/js/util.js'; @@ -612,17 +612,25 @@ .then(/** * @param {!Array<Entry>} filteredEntries */ - filteredEntries => { + async filteredEntries => { entries = filteredEntries; if (entries.length === 0) { return Promise.reject('ABORT'); } - // Send only the copy operation to IO Queue in the C++. if (window.isSWA) { - chrome.fileManagerPrivate.startIOTask( - toMove ? chrome.fileManagerPrivate.IOTaskType.MOVE : - chrome.fileManagerPrivate.IOTaskType.COPY, - entries, {destinationFolder: destinationEntry}); + const taskType = toMove ? + chrome.fileManagerPrivate.IOTaskType.MOVE : + chrome.fileManagerPrivate.IOTaskType.COPY; + try { + // TODO(crbug/1290197): Start tracking the copy/move + // operation starting here as both the legacy taskId and + // IOTask taskId are available. + await startIOTask( + taskType, entries, + {destinationFolder: destinationEntry}); + } catch (e) { + console.error(`Failed to start ${taskType} io task:`, e); + } return; } @@ -1310,6 +1318,12 @@ return false; } + // Recent isn't read-only, but it doesn't support paste/drop. + if (destinationLocationInfo.rootType === + VolumeManagerCommon.RootType.RECENT) { + return false; + } + if (destinationLocationInfo.volumeInfo && destinationLocationInfo.volumeInfo.error) { return false; @@ -1489,6 +1503,11 @@ destinationLocationInfo.volumeInfo.error) { return new DropEffectAndLabel(DropEffectType.NONE, null); } + // Recent isn't read-only, but it doesn't support drop. + if (destinationLocationInfo.rootType === + VolumeManagerCommon.RootType.RECENT) { + return new DropEffectAndLabel(DropEffectType.NONE, null); + } if (destinationLocationInfo.isReadOnly) { if (destinationLocationInfo.isSpecialSearchRoot) { // The location is a fake entry that corresponds to special search.
diff --git a/ui/file_manager/integration_tests/file_manager/recents.js b/ui/file_manager/integration_tests/file_manager/recents.js index eb6cb896..60b28ca 100644 --- a/ui/file_manager/integration_tests/file_manager/recents.js +++ b/ui/file_manager/integration_tests/file_manager/recents.js
@@ -67,6 +67,17 @@ } /** + * Checks if the #file-filters-in-recents-v2 flag has been enabled or not. + * + * @return {!Promise<boolean>} Flag enabled or not. + */ +async function isFiltersInRecentsV2Enabled() { + const isFiltersInRecentsEnabled = + await sendTestMessage({name: 'isFiltersInRecentsEnabledV2'}); + return isFiltersInRecentsEnabled === 'true'; +} + +/** * Navigate to Recent folder with specific type and verify the breadcrumb path. * * @param {string} appId Files app windowId. @@ -120,9 +131,15 @@ // Check: the file-list should be selected. await remoteCall.waitForElement(appId, '#file-list li[selected]'); - // Test that the delete button isn't visible. + // Test that the delete button's visibility based on v2 flag. const deleteButton = await remoteCall.waitForElement(appId, '#delete-button'); - chrome.test.assertTrue(deleteButton.hidden, 'delete button should be hidden'); + if (await isFiltersInRecentsV2Enabled()) { + chrome.test.assertFalse( + deleteButton.hidden, 'delete button should be visible'); + } else { + chrome.test.assertTrue( + deleteButton.hidden, 'delete button should be hidden'); + } } /**
diff --git a/weblayer/test/stub_autofill_provider.cc b/weblayer/test/stub_autofill_provider.cc index b5558733..2d7bf18 100644 --- a/weblayer/test/stub_autofill_provider.cc +++ b/weblayer/test/stub_autofill_provider.cc
@@ -17,11 +17,12 @@ void StubAutofillProvider::OnAskForValuesToFill( autofill::AndroidAutofillManager* manager, - int32_t id, + int32_t query_id, const autofill::FormData& form, const autofill::FormFieldData& field, const gfx::RectF& bounding_box, - bool /*unused_autoselect_first_suggestion*/) { + bool /*unused_autoselect_first_suggestion*/, + autofill::TouchToFillEligible /*unused_touch_to_fill_eligible*/) { on_received_form_data_.Run(form); }
diff --git a/weblayer/test/stub_autofill_provider.h b/weblayer/test/stub_autofill_provider.h index 2482725..4df9d6cc 100644 --- a/weblayer/test/stub_autofill_provider.h +++ b/weblayer/test/stub_autofill_provider.h
@@ -30,11 +30,12 @@ // AutofillProvider: void OnAskForValuesToFill( autofill::AndroidAutofillManager* manager, - int32_t id, + int32_t query_id, const autofill::FormData& form, const autofill::FormFieldData& field, const gfx::RectF& bounding_box, - bool /*unused_autoselect_first_suggestion*/) override; + bool /*unused_autoselect_first_suggestion*/, + autofill::TouchToFillEligible /*unused_touch_to_fill_eligible*/) override; private: base::RepeatingCallback<void(const autofill::FormData&)>