diff --git a/DEPS b/DEPS index 0f30bb6..10653225 100644 --- a/DEPS +++ b/DEPS
@@ -295,11 +295,11 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling V8 # and whatever else without interference from each other. - 'src_internal_revision': 'd001483ef1f2440291ad1fa8c15b897b7be0e72f', + 'src_internal_revision': 'f8e36dcd08ab67bfc9e717b3ed315fef7e8e6cba', # 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': '1e07a4b16973cf716cb40b72dd969e961f4dd950', + 'skia_revision': '3ba7657e8745bffd1c6263d5555be935afbc0df9', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling V8 # and whatever else without interference from each other. @@ -307,7 +307,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': 'a38ac25bd93c1fdaf393e2513f9c254b493e18bb', + 'angle_revision': '2a18fdbf4c8c20e37734611064d21a83658f6236', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling SwiftShader # and whatever else without interference from each other. @@ -351,7 +351,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling freetype # and whatever else without interference from each other. - 'freetype_revision': '57a873045016c7866a298f5e9faa830e6ec24cf9', + 'freetype_revision': 'e07e56c7f106b600262ab653d696b7b57f320127', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling freetype # and whatever else without interference from each other. @@ -391,7 +391,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': '55154436a9c71fc62179638710b405c99e80ef54', + 'devtools_frontend_revision': 'acd68d2f092a2e674894c9d389c96e39beec1aa2', # 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. @@ -415,7 +415,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling feed # and whatever else without interference from each other. - 'dawn_revision': '156136ebb43d383a3833545598023dd366085166', + 'dawn_revision': '45b5634e70a3a6d61f3704f308d7a419e7db532d', # Three lines of non-changing comments so that # the commit queue can handle CLs rolling feed # and whatever else without interference from each other. @@ -523,7 +523,7 @@ # Three lines of non-changing comments so that # the commit queue can handle CLs rolling llvm-libc # and whatever else without interference from each other. - 'compiler_rt_revision': '9c6d38aa28100761bc2d6dcd2a590a37f8519adf', + 'compiler_rt_revision': '57196dd146582915c955f6d388e31aea93220c51', # If you change this, also update the libc++ revision in # //buildtools/deps_revisions.gni. @@ -1508,7 +1508,7 @@ 'src/clank': { 'url': Var('chrome_git') + '/clank/internal/apps.git' + '@' + - 'c6f37b2a1ac4f90393eff3c734ca926a8e602153', + '7b3b66843fe0c37489709a09bf6e4c57c6087f53', 'condition': 'checkout_android and checkout_src_internal', }, @@ -2867,7 +2867,7 @@ 'dep_type': 'cipd', }, - 'src/third_party/vulkan-deps': '{chromium_git}/vulkan-deps@bf024288c340597e8421df8db06c2de12c25bf31', + 'src/third_party/vulkan-deps': '{chromium_git}/vulkan-deps@5912cbdd295c2bacb5798432a7b1cac9d20c0725', 'src/third_party/glslang/src': '{chromium_git}/external/github.com/KhronosGroup/glslang@93231001597dad1149a5d035af30eda50b9e6b6c', 'src/third_party/spirv-cross/src': '{chromium_git}/external/github.com/KhronosGroup/SPIRV-Cross@b8fcf307f1f347089e3c46eb4451d27f32ebc8d3', 'src/third_party/spirv-headers/src': '{chromium_git}/external/github.com/KhronosGroup/SPIRV-Headers@c9aad99f9276817f18f72a4696239237c83cb775', @@ -2875,8 +2875,8 @@ 'src/third_party/vulkan-headers/src': '{chromium_git}/external/github.com/KhronosGroup/Vulkan-Headers@75ad707a587e1469fb53a901b9b68fe9f6fbc11f', 'src/third_party/vulkan-loader/src': '{chromium_git}/external/github.com/KhronosGroup/Vulkan-Loader@c913466fdc5004584890f89ff91121bdb2ffd4ba', 'src/third_party/vulkan-tools/src': '{chromium_git}/external/github.com/KhronosGroup/Vulkan-Tools@60b640cb931814fcc6dabe4fc61f4738c56579f6', - 'src/third_party/vulkan-utility-libraries/src': '{chromium_git}/external/github.com/KhronosGroup/Vulkan-Utility-Libraries@ae56bd6e65d9faa731150e931cb35f0d895223bc', - 'src/third_party/vulkan-validation-layers/src': '{chromium_git}/external/github.com/KhronosGroup/Vulkan-ValidationLayers@84b023ac42601ff51ea6094dc2c18ca62960b25d', + 'src/third_party/vulkan-utility-libraries/src': '{chromium_git}/external/github.com/KhronosGroup/Vulkan-Utility-Libraries@49ac28931f28bffaa3cd73dc4ad997284d574962', + 'src/third_party/vulkan-validation-layers/src': '{chromium_git}/external/github.com/KhronosGroup/Vulkan-ValidationLayers@f7ceb1d01a292846db77ec87786be84d6fd568d9', 'src/third_party/vulkan_memory_allocator': Var('chromium_git') + '/external/github.com/GPUOpen-LibrariesAndSDKs/VulkanMemoryAllocator.git' + '@' + '56300b29fbfcc693ee6609ddad3fdd5b7a449a21', @@ -2921,7 +2921,7 @@ Var('chromium_git') + '/webpagereplay.git' + '@' + Var('webpagereplay_revision'), 'src/third_party/webrtc': - Var('webrtc_git') + '/src.git' + '@' + '2fe2d5190bd3d8766759e3a7de2b648d5ce96aee', + Var('webrtc_git') + '/src.git' + '@' + '9909b30d5e3c104d4dce7d066fc8422eef1dcc59', # Wuffs' canonical repository is at github.com/google/wuffs, but we use # Skia's mirror of Wuffs, the same as in upstream Skia's DEPS file. @@ -3054,7 +3054,7 @@ 'packages': [ { 'package': 'chromeos_internal/apps/help_app/app', - 'version': 'CTDlv1ivZiL2YbKkLKyrIf6V149_sKW0ZdPI3x804YgC', + 'version': 'nu99RnP4WrMIbyKDSQ4AuIaXEqIGYHZ6_nRK1EPhFZIC', }, ], 'condition': 'checkout_chromeos and checkout_src_internal', @@ -3065,7 +3065,7 @@ 'packages': [ { 'package': 'chromeos_internal/apps/media_app/app', - 'version': 'AdXzD30R0jed2FtB_0vPwg_W4vqaJwxeQ9mMl9ZXqq0C', + 'version': 'zl3WjF8rNKkrpjHL28zwf14BmBHTh-E6TLAkRyIqiywC', }, ], 'condition': 'checkout_chromeos and checkout_src_internal', @@ -4707,7 +4707,7 @@ 'src/ios_internal': { 'url': Var('chrome_git') + '/chrome/ios_internal.git' + '@' + - 'caa545d88ae49b674a6d9542f80c5514d0cfc18e', + 'a5c6f36c55a93150abaf43134d5c40dc42112f9d', 'condition': 'checkout_ios and checkout_src_internal', },
diff --git a/base/android/java/src/org/chromium/base/DeviceInfo.java b/base/android/java/src/org/chromium/base/DeviceInfo.java index 4ca7a9e5..cbe45d9 100644 --- a/base/android/java/src/org/chromium/base/DeviceInfo.java +++ b/base/android/java/src/org/chromium/base/DeviceInfo.java
@@ -68,14 +68,14 @@ } public static String getGmsVersionCode() { - return sGmsVersionCodeForTesting == null - ? getInstance().mIDeviceInfo.gmsVersionCode - : sGmsVersionCodeForTesting; + return getInstance().mIDeviceInfo.gmsVersionCode; } @CalledByNativeForTesting public static void setGmsVersionCodeForTest(@JniType("std::string") String gmsVersionCode) { sGmsVersionCodeForTesting = gmsVersionCode; + // Every time we call getInstance in a test we reconstruct the mIDeviceInfo object, so we + // don't need to set mIDeviceInfo's copy here as it'll just get reconstructed. ResettersForTesting.register(() -> sGmsVersionCodeForTesting = null); } @@ -138,6 +138,9 @@ gmsPackageInfo != null ? String.valueOf(packageVersionCode(gmsPackageInfo)) : "gms versionCode not available."; + if (sGmsVersionCodeForTesting != null) { + mIDeviceInfo.gmsVersionCode = sGmsVersionCodeForTesting; + } Context appContext = ContextUtils.getApplicationContext(); PackageManager pm = appContext.getPackageManager();
diff --git a/base/files/file_util_posix.cc b/base/files/file_util_posix.cc index 84e81af..76681ad4 100644 --- a/base/files/file_util_posix.cc +++ b/base/files/file_util_posix.cc
@@ -1298,7 +1298,7 @@ // |base| must be a subpath of |path|, so all components should match. // If these CHECKs fail, look at the test that base is a parent of // path at the top of this function. - CHECK(ip != path_components.end(), base::NotFatalUntil::M125); + CHECK(ip != path_components.end()); DCHECK(*ip == *ib); }
diff --git a/base/logging.cc b/base/logging.cc index 26ba1a2..b8eee13 100644 --- a/base/logging.cc +++ b/base/logging.cc
@@ -33,7 +33,6 @@ #include "base/functional/callback.h" #include "base/immediate_crash.h" #include "base/no_destructor.h" -#include "base/not_fatal_until.h" #include "base/path_service.h" #include "base/pending_task.h" #include "base/posix/eintr_wrapper.h" @@ -550,13 +549,13 @@ #if BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_WIN) if (settings.log_file) { - CHECK(settings.log_file_path.empty(), base::NotFatalUntil::M127); + CHECK(settings.log_file_path.empty()); g_log_file = settings.log_file; return true; } #endif // BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_WIN) - CHECK(!settings.log_file_path.empty(), base::NotFatalUntil::M127) + CHECK(!settings.log_file_path.empty()) << "LOG_TO_FILE set but no log_file_path!"; if (!g_log_file_name) {
diff --git a/base/memory/shared_memory_tracker.cc b/base/memory/shared_memory_tracker.cc index 576b786..b90dc3d 100644 --- a/base/memory/shared_memory_tracker.cc +++ b/base/memory/shared_memory_tracker.cc
@@ -62,11 +62,8 @@ const SharedMemoryMapping& mapping) { AutoLock hold(usages_lock_); const auto it = usages_.find(mapping.mapped_memory().data()); - // TODO(pbos): When removing this NotFatalUntil, use erase(it) below. We can't - // do that now because if this CHECK is actually failing there'd be a memory - // bug. - CHECK(it != usages_.end(), base::NotFatalUntil::M125); - usages_.erase(mapping.mapped_memory().data()); + CHECK(it != usages_.end()); + usages_.erase(it); } SharedMemoryTracker::SharedMemoryTracker() {
diff --git a/base/message_loop/message_pump_epoll.cc b/base/message_loop/message_pump_epoll.cc index d99f576..008728bb5 100644 --- a/base/message_loop/message_pump_epoll.cc +++ b/base/message_loop/message_pump_epoll.cc
@@ -421,12 +421,12 @@ const int fd = interest->params().fd; auto entry_it = entries_.find(fd); - CHECK(entry_it != entries_.end(), base::NotFatalUntil::M125); + CHECK(entry_it != entries_.end()); EpollEventEntry& entry = entry_it->second; auto& interests = entry.interests; auto* it = std::ranges::find(interests, interest); - CHECK(it != interests.end(), base::NotFatalUntil::M125); + CHECK(it != interests.end()); interests.erase(it); if (interests.empty()) {
diff --git a/base/metrics/statistics_recorder.cc b/base/metrics/statistics_recorder.cc index 93d3804..6f612b3 100644 --- a/base/metrics/statistics_recorder.cc +++ b/base/metrics/statistics_recorder.cc
@@ -374,7 +374,7 @@ EnsureGlobalRecorderWhileLocked(); auto iter = top_->observers_.find(hash); - CHECK(iter != top_->observers_.end(), base::NotFatalUntil::M125); + CHECK(iter != top_->observers_.end()); auto result = iter->second->RemoveObserver(observer); if (result ==
diff --git a/base/sampling_heap_profiler/poisson_allocation_sampler.cc b/base/sampling_heap_profiler/poisson_allocation_sampler.cc index 7cb9296..1bd644d 100644 --- a/base/sampling_heap_profiler/poisson_allocation_sampler.cc +++ b/base/sampling_heap_profiler/poisson_allocation_sampler.cc
@@ -484,7 +484,7 @@ ScopedMuteThreadSamples no_reentrancy_scope; AutoLock lock(mutex_); auto it = std::ranges::find(observers_, observer); - CHECK(it != observers_.end(), base::NotFatalUntil::M125); + CHECK(it != observers_.end()); observers_.erase(it); // Stop the profiler if there are no more observers. Setting/resetting
diff --git a/base/strings/string_util_impl_helpers.h b/base/strings/string_util_impl_helpers.h index b032e133..7bdfd17 100644 --- a/base/strings/string_util_impl_helpers.h +++ b/base/strings/string_util_impl_helpers.h
@@ -497,7 +497,7 @@ result.reserve(total_size); auto iter = parts.begin(); - CHECK(iter != parts.end(), base::NotFatalUntil::M125); + CHECK(iter != parts.end()); result.append(*iter); UNSAFE_TODO(++iter);
diff --git a/base/task/common/checked_lock_impl.cc b/base/task/common/checked_lock_impl.cc index eefd52e..172a754 100644 --- a/base/task/common/checked_lock_impl.cc +++ b/base/task/common/checked_lock_impl.cc
@@ -51,7 +51,7 @@ void RecordRelease(const CheckedLockImpl* const lock) { LockVector* acquired_locks = GetAcquiredLocksOnCurrentThread(); const auto iter_at_lock = std::ranges::find(*acquired_locks, lock); - CHECK(iter_at_lock != acquired_locks->end(), base::NotFatalUntil::M125); + CHECK(iter_at_lock != acquired_locks->end()); acquired_locks->erase(iter_at_lock); }
diff --git a/base/task/sequence_manager/sequence_manager_impl_unittest.cc b/base/task/sequence_manager/sequence_manager_impl_unittest.cc index f91e5562..6bed549 100644 --- a/base/task/sequence_manager/sequence_manager_impl_unittest.cc +++ b/base/task/sequence_manager/sequence_manager_impl_unittest.cc
@@ -4721,8 +4721,7 @@ } ~PostTaskWhenDeleted() { - CHECK(tasks_alive_->find(full_name()) != tasks_alive_->end(), - base::NotFatalUntil::M125); + CHECK(tasks_alive_->contains(full_name())); tasks_alive_->erase(full_name()); tasks_deleted_->push_back(full_name());
diff --git a/base/task/thread_pool/pooled_single_thread_task_runner_manager.cc b/base/task/thread_pool/pooled_single_thread_task_runner_manager.cc index 1290d0ad9..9ecaabd3 100644 --- a/base/task/thread_pool/pooled_single_thread_task_runner_manager.cc +++ b/base/task/thread_pool/pooled_single_thread_task_runner_manager.cc
@@ -857,7 +857,7 @@ } auto worker_iter = std::ranges::find(workers_, worker); - CHECK(worker_iter != workers_.end(), base::NotFatalUntil::M125); + CHECK(worker_iter != workers_.end()); worker_to_destroy = std::move(*worker_iter); workers_.erase(worker_iter); }
diff --git a/base/task/thread_pool/thread_group_impl.cc b/base/task/thread_pool/thread_group_impl.cc index e87bd15..cad8c8e 100644 --- a/base/task/thread_pool/thread_group_impl.cc +++ b/base/task/thread_pool/thread_group_impl.cc
@@ -615,7 +615,7 @@ // Remove the worker from |workers_|. auto worker_iter = std::ranges::find(outer_->workers_, worker); - CHECK(worker_iter != outer_->workers_.end(), base::NotFatalUntil::M125); + CHECK(worker_iter != outer_->workers_.end()); outer_->workers_.erase(worker_iter); }
diff --git a/base/task/thread_pool/worker_thread_set.cc b/base/task/thread_pool/worker_thread_set.cc index 2653d4a..65101fd 100644 --- a/base/task/thread_pool/worker_thread_set.cc +++ b/base/task/thread_pool/worker_thread_set.cc
@@ -59,7 +59,7 @@ DCHECK(!IsEmpty()); DCHECK_NE(worker, *set_.begin()); auto it = set_.find(const_cast<WorkerThread*>(worker)); - CHECK(it != set_.end(), base::NotFatalUntil::M125); + CHECK(it != set_.end()); DCHECK_NE(TimeTicks(), (*it)->GetLastUsedTime()); set_.erase(it); }
diff --git a/base/threading/hang_watcher.cc b/base/threading/hang_watcher.cc index cf3657b9..28a767d6 100644 --- a/base/threading/hang_watcher.cc +++ b/base/threading/hang_watcher.cc
@@ -1104,7 +1104,7 @@ &std::unique_ptr<internal::HangWatchState>::get); // Thread should be registered to get unregistered. - CHECK(it != watch_states_.end(), base::NotFatalUntil::M125); + CHECK(it != watch_states_.end()); watch_states_.erase(it); }
diff --git a/base/threading/thread_id_name_manager.cc b/base/threading/thread_id_name_manager.cc index 2ee7ca1..3cb0db3 100644 --- a/base/threading/thread_id_name_manager.cc +++ b/base/threading/thread_id_name_manager.cc
@@ -128,13 +128,11 @@ AutoLock locked(lock_); auto handle_to_name_iter = thread_handle_to_interned_name_.find(handle); - CHECK(handle_to_name_iter != thread_handle_to_interned_name_.end(), - base::NotFatalUntil::M125); + CHECK(handle_to_name_iter != thread_handle_to_interned_name_.end()); thread_handle_to_interned_name_.erase(handle_to_name_iter); auto id_to_handle_iter = thread_id_to_handle_.find(id); - CHECK(id_to_handle_iter != thread_id_to_handle_.end(), - base::NotFatalUntil::M125); + CHECK(id_to_handle_iter != thread_id_to_handle_.end()); // The given |id| may have been re-used by the system. Make sure the // mapping points to the provided |handle| before removal. if (id_to_handle_iter->second != handle) {
diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn index 4004a5b..706f0f3 100644 --- a/build/config/BUILDCONFIG.gn +++ b/build/config/BUILDCONFIG.gn
@@ -279,6 +279,11 @@ _default_toolchain = "//build/toolchain/aix:$target_cpu" } else if (target_os == "zos") { _default_toolchain = "//build/toolchain/zos:$target_cpu" +} else if (target_os == "emscripten") { + # Because it's too hard to remove all targets from //BUILD.gn that do not work with it. + assert( + false, + "emscripten is not a supported target_os. It is available only as secondary toolchain.") } else { assert(false, "Unsupported target_os: $target_os") }
diff --git a/build/config/compiler/BUILD.gn b/build/config/compiler/BUILD.gn index a83f75b..59942a3 100644 --- a/build/config/compiler/BUILD.gn +++ b/build/config/compiler/BUILD.gn
@@ -206,7 +206,7 @@ # Set to true to use icf, Identical Code Folding. use_icf = (is_posix || is_fuchsia) && !is_debug && !using_sanitizer && !use_clang_coverage && current_os != "zos" && - !(is_android && use_order_profiling) && use_lld + !(is_android && use_order_profiling) && use_lld && !is_wasm } if (is_android) { @@ -723,6 +723,20 @@ ldflags += [ "-fexperimental-relative-c++-abi-vtables" ] } + if (is_wasm) { + ldflags += [ + "-s", + "ALLOW_MEMORY_GROWTH=1", + "-s", + "LLD_REPORT_UNDEFINED=1", + ] + + if (is_official_build) { + cflags += [ "-flto=full" ] + ldflags += [ "-flto=full" ] + } + } + # Add flags for link-time optimization. These flags enable # optimizations/transformations that require whole-program visibility at link # time, so they need to be applied to all translation units, and we may end up @@ -3006,6 +3020,9 @@ # All configs using /DEBUG should include this: configs += [ ":win_pdbaltpath" ] + } else if (is_wasm) { + cflags = [ "-gseparate-dwarf" ] + ldflags = [ "-gseparate-dwarf" ] } else { cflags = [] if (is_apple && enable_dsyms) {
diff --git a/build/config/mac/mac_sdk.gni b/build/config/mac/mac_sdk.gni index 4a5abb94..8d97e75 100644 --- a/build/config/mac/mac_sdk.gni +++ b/build/config/mac/mac_sdk.gni
@@ -8,6 +8,7 @@ import("//build/toolchain/rbe.gni") import("//build/toolchain/siso.gni") import("//build/toolchain/toolchain.gni") +import("//build_overrides/build.gni") # Allow Android builds on macOS assert(current_os == "mac" || current_toolchain == default_toolchain ||
diff --git a/build/toolchain/toolchain.gni b/build/toolchain/toolchain.gni index ce642da..44dbc84d 100644 --- a/build/toolchain/toolchain.gni +++ b/build/toolchain/toolchain.gni
@@ -5,10 +5,6 @@ # Toolchain-related configuration that may be needed outside the context of the # toolchain() rules themselves. -import("//build/config/cast.gni") -import("//build/config/chrome_build.gni") -import("//build_overrides/build.gni") - declare_args() { # If this is set to true, we use the revision in the llvm repo to determine # the CLANG_REVISION to use, instead of the version hard-coded into @@ -36,17 +32,6 @@ toolchain_allows_use_partition_alloc_as_malloc = true } -if (generate_linker_map) { - assert(is_official_build || is_castos || is_cast_android, - "Linker map files should only be generated when is_official_build = " + - "true or is_castos = true or is_cast_android = true") - assert(current_os == "android" || current_os == "linux" || - target_os == "android" || target_os == "linux" || - target_os == "chromeos", - "Linker map files should only be generated for Android, Linux, " + - "or ChromeOS.") -} - declare_args() { if (llvm_android_mainline) { # https://crbug.com/1481060 clang_version = "17"
diff --git a/build/toolchain/wasm/BUILD.gn b/build/toolchain/wasm/BUILD.gn index 51d5066..4b4d65c8 100644 --- a/build/toolchain/wasm/BUILD.gn +++ b/build/toolchain/wasm/BUILD.gn
@@ -4,12 +4,16 @@ import("//build/toolchain/gcc_toolchain.gni") +declare_args() { + # Path to emsdk directory. + emscripten_path = "//third_party/emsdk/upstream/emscripten/" +} + # This WASM toolchain is NOT to be used to build any Chromium code, # i.e. tests and samples are currently fine. # Usage of this toolchain requires getting explicit approval from # build/OWNERS. gcc_toolchain("wasm") { - emscripten_path = "//third_party/emsdk/upstream/emscripten/" _suffix = "" if (host_os == "win") { _suffix = ".bat" @@ -43,5 +47,8 @@ use_custom_libcxx_for_host = false } executable_extension = ".html" - link_outputs = [ "{{output_dir}}/{{target_output_name}}.wasm" ] + link_outputs = [ + "{{output_dir}}/{{target_output_name}}.wasm", + "{{output_dir}}/{{target_output_name}}.wasm.debug.wasm", + ] }
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabAnimationHostView.java b/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabAnimationHostView.java index c1f5f53..d3833dc 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabAnimationHostView.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabAnimationHostView.java
@@ -38,10 +38,8 @@ /** Host view for the new background tab animation. */ public class NewBackgroundTabAnimationHostView extends FrameLayout { /* package */ static final long CROSS_FADE_DURATION_MS = 150L; - private static final long PATH_ARC_DURATION_MS = 300L; - private static final long NEW_PATH_ARC_DURATION_MS = 400L; - private static final long LINK_SCALE_DURATION_MS = 160L; - private static final long NEW_LINK_SCALE_DURATION_MS = 192L; + private static final long PATH_ARC_DURATION_MS = 400L; + private static final long LINK_SCALE_DURATION_MS = 192L; private static final long TRANSLATE_DELAY_DURATION_MS = 100L; private static final long SHRINK_DELAY_DURATION_MS = 50L; @@ -95,13 +93,11 @@ target[1] -= Math.round(mLinkIcon.getHeight() / 2f); // TODO(crbug.com/419065710): Clean up versions. - boolean isNewDuration = ChromeFeatureList.sShowNewTabAnimationsNewDuration.getValue(); @NewTabAnim int version = ChromeFeatureList.sShowNewTabAnimationsVersion.getValue(); - long pathDuration = isNewDuration ? NEW_PATH_ARC_DURATION_MS : PATH_ARC_DURATION_MS; - AnimatorSet transitionAnimator = getTransitionAnimator(isNewDuration); + AnimatorSet transitionAnimator = getTransitionAnimator(); ObjectAnimator pathAnimator = - getPathArcAnimator(originX, originY, target[0], target[1], pathDuration, version); + getPathArcAnimator(originX, originY, target[0], target[1], version); AnimatorSet backgroundAnimation = new AnimatorSet(); AnimatorSet fakeTabSwitcherAnimator; @@ -126,7 +122,7 @@ .with(fakeTabSwitcherAnimator) .after(pathAnimator); } else { - transitionAnimator.setStartDelay(pathDuration - CROSS_FADE_DURATION_MS); + transitionAnimator.setStartDelay(PATH_ARC_DURATION_MS - CROSS_FADE_DURATION_MS); fakeTabSwitcherAnimator = mFakeTabSwitcherButton.getTranslateAnimator( NewBackgroundTabFakeTabSwitcherButton.TranslateDirection.UP); @@ -212,33 +208,24 @@ * @param originY y-coordinate for the start point. * @param finalX x-coordinate for the end point. * @param finalY y-coordinate for the end point. - * @param duration Animation duration in ms. * @param version The {@link NewTabAnim} animation version. */ private ObjectAnimator getPathArcAnimator( - float originX, - float originY, - float finalX, - float finalY, - long duration, - @NewTabAnim int version) { + float originX, float originY, float finalX, float finalY, @NewTabAnim int version) { boolean isClockwise = mIsTopToolbar ? (originX >= finalX) : (originX <= finalX); ObjectAnimator animator = ViewCurvedMotionAnimatorFactory.build( mLinkIcon, originX, originY, finalX, finalY, isClockwise); - animator.setDuration(duration); + animator.setDuration(PATH_ARC_DURATION_MS); - Interpolator pathInterpolator; - pathInterpolator = + Interpolator pathInterpolator = switch (version) { + case NewTabAnim.M137 -> Interpolators + .NEW_BACKGROUND_TAB_ANIMATION_PATH_INTERPOLATOR; case NewTabAnim.BOUNCE -> Interpolators .NEW_BACKGROUND_TAB_ANIMATION_SECOND_PATH_INTERPOLATOR; - case NewTabAnim.DECELERATE, - NewTabAnim.BOUNCE_DECELERATE, - NewTabAnim.BOUNCE_DECELERATE_WITH_DELAY -> Interpolators - .EMPHASIZED_DECELERATE; - default -> Interpolators.NEW_BACKGROUND_TAB_ANIMATION_PATH_INTERPOLATOR; + default -> Interpolators.EMPHASIZED_DECELERATE; }; animator.setInterpolator(pathInterpolator); @@ -256,7 +243,7 @@ /** * Returns the {@link AnimatorSet} for the transition between the Link icon and the Tab icon. */ - private AnimatorSet getTransitionAnimator(boolean isNewDuration) { + private AnimatorSet getTransitionAnimator() { AnimatorSet animatorSet = new AnimatorSet(); ObjectAnimator fadeAnimator = ObjectAnimator.ofFloat(mLinkIcon, View.ALPHA, 1f, 0f); @@ -267,8 +254,7 @@ ObjectAnimator scaleXAnimator = ObjectAnimator.ofFloat(mLinkIcon, View.SCALE_X, 1f, 0f); ObjectAnimator scaleYAnimator = ObjectAnimator.ofFloat(mLinkIcon, View.SCALE_Y, 1f, 0f); animatorSet.playTogether(scaleXAnimator, scaleYAnimator, fadeAnimator); - animatorSet.setDuration( - isNewDuration ? NEW_LINK_SCALE_DURATION_MS : LINK_SCALE_DURATION_MS); + animatorSet.setDuration(LINK_SCALE_DURATION_MS); animatorSet.setInterpolator(Interpolators.STANDARD_INTERPOLATOR); } else { AnimatorSet fakeTabSwitcherAnimator = mFakeTabSwitcherButton.getScaleFadeAnimator();
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabFakeTabSwitcherButton.java b/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabFakeTabSwitcherButton.java index 2f1bbb7..02b98f4 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabFakeTabSwitcherButton.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/compositor/layouts/phone/NewBackgroundTabFakeTabSwitcherButton.java
@@ -24,7 +24,6 @@ import org.chromium.build.BuildConfig; import org.chromium.chrome.R; -import org.chromium.chrome.browser.flags.ChromeFeatureList; import org.chromium.chrome.browser.theme.ThemeUtils; import org.chromium.chrome.browser.toolbar.TabSwitcherDrawable; import org.chromium.chrome.browser.toolbar.TabSwitcherDrawable.TabSwitcherDrawableLocation; @@ -46,8 +45,7 @@ */ public class NewBackgroundTabFakeTabSwitcherButton extends FrameLayout implements RunOnNextLayout { @VisibleForTesting /* package */ static final long TRANSLATE_DURATION_MS = 200L; - @VisibleForTesting /* package */ static final long SHRINK_DURATION_MS = 250L; - @VisibleForTesting /* package */ static final long NEW_SHRINK_DURATION_MS = 300L; + @VisibleForTesting /* package */ static final long SHRINK_DURATION_MS = 300L; @VisibleForTesting /* package */ static final long SCALE_DOWN_DURATION_MS = 50L; @IntDef({ @@ -133,10 +131,7 @@ AnimatorSet animatorSet = new AnimatorSet(); animatorSet.playTogether(scaleXAnimator, scaleYAnimator); - animatorSet.setDuration( - ChromeFeatureList.sShowNewTabAnimationsNewDuration.getValue() - ? NEW_SHRINK_DURATION_MS - : SHRINK_DURATION_MS); + animatorSet.setDuration(SHRINK_DURATION_MS); animatorSet.addListener( new AnimatorListenerAdapter() {
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/crash/ChromePureJavaExceptionReporter.java b/chrome/android/java/src/org/chromium/chrome/browser/crash/ChromePureJavaExceptionReporter.java index 516aff6..6e09216d 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/crash/ChromePureJavaExceptionReporter.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/crash/ChromePureJavaExceptionReporter.java
@@ -52,6 +52,19 @@ /** * Asynchronously report and upload the stack trace as if it was a crash. * + * @param msg The message to report. + * @param isWarning Whether the message should be treated as a warning. + */ + public static void reportJavaExceptionFromMsg(String msg, boolean isWarning) { + if (isWarning) { + msg = "This is not a crash. " + msg; + } + reportJavaException(new Throwable(msg)); + } + + /** + * Asynchronously report and upload the stack trace as if it was a crash. + * * @param exception The exception to report. */ public static void reportJavaException(Throwable exception) {
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/hub/NewTabAnimationUtils.java b/chrome/android/java/src/org/chromium/chrome/browser/hub/NewTabAnimationUtils.java index d6ca88a..eae5cd3 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/hub/NewTabAnimationUtils.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/hub/NewTabAnimationUtils.java
@@ -48,6 +48,7 @@ * <p>These numbers match with the "version" feature param for ShowNewTabAnimations. */ @IntDef({ + NewTabAnim.M137, NewTabAnim.BOUNCE, NewTabAnim.DECELERATE, NewTabAnim.BOUNCE_DECELERATE, @@ -56,6 +57,7 @@ @Target(ElementType.TYPE_USE) @Retention(RetentionPolicy.SOURCE) public @interface NewTabAnim { + int M137 = 0; int BOUNCE = 1; int DECELERATE = 2; int BOUNCE_DECELERATE = 3;
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java b/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java index a108169..3be8fe6d 100644 --- a/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java +++ b/chrome/android/java/src/org/chromium/chrome/browser/ui/RootUiCoordinator.java
@@ -1900,7 +1900,9 @@ hasEdgeToEdgeController, isSupportedConfiguration, callSite, - (info) -> ChromePureJavaExceptionReporter.reportJavaException(new Throwable(info))); + (info) -> + ChromePureJavaExceptionReporter.reportJavaExceptionFromMsg( + info, /* isWarning= */ true)); } /** Create a bottom chin for Edge-to-Edge. */
diff --git a/chrome/app/os_settings_strings.grdp b/chrome/app/os_settings_strings.grdp index b92cef7..6b3d5529 100644 --- a/chrome/app/os_settings_strings.grdp +++ b/chrome/app/os_settings_strings.grdp
@@ -4385,6 +4385,9 @@ <message name="IDS_SETTINGS_PRINTING_CUPS_PRINTER_ADVANCED_CONFIG_SELECT_DRIVER" desc="Label for the file selector to manually select a PPD file from the user's file system."> Alternatively, select printer PPD. <ph name="LINK_BEGIN"><a></ph>Learn more<ph name="LINK_END"></a></ph> </message> + <message name="IDS_SETTINGS_PRINTING_CUPS_PRINTER_MANAGED_PRINTER_PPD" desc="Label for the text box displaying a path to the used PPD file for the active printer."> + Printer PPD + </message> <message name="IDS_SETTINGS_PRINTING_CUPS_PRINTER_SELECT_DRIVER" desc="Label for the file selector to manually select a PPD file from the user's file system."> or select PPD. <ph name="LINK_BEGIN"><a></ph>Learn more<ph name="LINK_END"></a></ph> </message>
diff --git a/chrome/app/os_settings_strings_grdp/IDS_SETTINGS_PRINTING_CUPS_PRINTER_MANAGED_PRINTER_PPD.png.sha1 b/chrome/app/os_settings_strings_grdp/IDS_SETTINGS_PRINTING_CUPS_PRINTER_MANAGED_PRINTER_PPD.png.sha1 new file mode 100644 index 0000000..7504c0a --- /dev/null +++ b/chrome/app/os_settings_strings_grdp/IDS_SETTINGS_PRINTING_CUPS_PRINTER_MANAGED_PRINTER_PPD.png.sha1
@@ -0,0 +1 @@ +22a0a883d053078e8d6a43fe9e24923b2097f875 \ No newline at end of file
diff --git a/chrome/browser/about_flags.cc b/chrome/browser/about_flags.cc index 62f3fc4..256d81e 100644 --- a/chrome/browser/about_flags.cc +++ b/chrome/browser/about_flags.cc
@@ -1242,6 +1242,17 @@ std::size(kTextSafetyClassifierNoRetractParams), nullptr}, }; +const FeatureEntry::FeatureParam kPageActionsMigrationParams[] = { + {"lens_overlay", "true"}, {"translate", "true"}, + {"memory_saver", "true"}, {"price_insights", "true"}, + {"offer_notification", "true"}, {"intent_picker", "true"}, + {"file_system_access", "true"}, +}; +const FeatureEntry::FeatureVariation kPageActionsMigrationVariations[] = { + {"with all migrated page actions enabled", kPageActionsMigrationParams, + std::size(kPageActionsMigrationParams), nullptr}, +}; + const FeatureEntry::FeatureParam kPageContentAnnotationsContentParams[] = { {"annotate_title_instead_of_page_content", "false"}, {"extract_related_searches", "true"}, @@ -3757,35 +3768,24 @@ {" - all windowing modes", kAuxiliaryNavigationStaysInBrowserOn, std::size(kAuxiliaryNavigationStaysInBrowserOn), nullptr}}; -const FeatureEntry::FeatureParam kShowNewTabAnimationsNewDurationOnly[] = { - {"version", "0"}, - {"new-duration", "true"}}; const FeatureEntry::FeatureParam kShowNewTabAnimationsBounce[] = { - {"version", "1"}, - {"new-duration", "true"}}; + {"version", "1"}}; const FeatureEntry::FeatureParam kShowNewTabAnimationsDecelerate[] = { - {"version", "2"}, - {"new-duration", "true"}}; + {"version", "2"}}; const FeatureEntry::FeatureParam kShowNewTabAnimationsBounceDecelerate[] = { - {"version", "3"}, - {"new-duration", "true"}}; -const FeatureEntry::FeatureParam - kShowNewTabAnimationsBounceDecelerateWithDelay[] = { - {"version", "4"}, - {"new-duration", "true"}}; + {"version", "3"}}; +const FeatureEntry::FeatureParam kShowNewTabAnimationsM137[] = { + {"version", "0"}}; const FeatureEntry::FeatureVariation kShowNewTabAnimationsVariations[] = { - {"- Use new duration only", kShowNewTabAnimationsNewDurationOnly, - std::size(kShowNewTabAnimationsNewDurationOnly), nullptr}, {"- Bouncy GTS icon with delay", kShowNewTabAnimationsBounce, std::size(kShowNewTabAnimationsBounce), nullptr}, {"- Bouncy GTS icon with decelerate arc", kShowNewTabAnimationsBounceDecelerate, std::size(kShowNewTabAnimationsBounceDecelerate), nullptr}, - {"- Bouncy GTS icon with decelerate arc and delay", - kShowNewTabAnimationsBounceDecelerateWithDelay, - std::size(kShowNewTabAnimationsBounceDecelerateWithDelay), nullptr}, {"- Decelerate arc", kShowNewTabAnimationsDecelerate, std::size(kShowNewTabAnimationsDecelerate), nullptr}, + {"- M137 with new duration", kShowNewTabAnimationsM137, + std::size(kShowNewTabAnimationsM137), nullptr}, }; #endif // BUILDFLAG(IS_ANDROID) @@ -11229,6 +11229,11 @@ {"infinite-tabs-freezing", flag_descriptions::kInfiniteTabsFreezingName, flag_descriptions::kInfiniteTabsFreezingDescription, kOsDesktop, FEATURE_VALUE_TYPE(performance_manager::features::kInfiniteTabsFreezing)}, + + {"memory-purge-on-freeze-limit", + flag_descriptions::kMemoryPurgeOnFreezeLimitName, + flag_descriptions::kMemoryPurgeOnFreezeLimitDescription, kOsDesktop, + FEATURE_VALUE_TYPE(blink::features::kMemoryPurgeOnFreezeLimit)}, #endif // !BUILDFLAG(IS_ANDROID) #if BUILDFLAG(IS_WIN) @@ -12592,6 +12597,18 @@ FEATURE_VALUE_TYPE(::features::kAccessibilityManifestV3EspeakNGTts)}, #endif +#if BUILDFLAG(IS_ANDROID) + {"mvc-update-view-when-model-changed", + flag_descriptions::kMvcUpdateViewWhenModelChangedName, + flag_descriptions::kMvcUpdateViewWhenModelChangedDescription, kOsAndroid, + FEATURE_VALUE_TYPE(chrome::android::kMvcUpdateViewWhenModelChanged)}, +#endif // BUILDFLAG(IS_ANDROID) + + {"page-actions-migration", flag_descriptions::kPageActionsMigrationName, + flag_descriptions::kPageActionsMigrationDescription, kOsDesktop, + FEATURE_WITH_PARAMS_VALUE_TYPE(features::kPageActionsMigration, + kPageActionsMigrationVariations, + "PageActionsMigration")}, // Add new entries above this line. // NOTE: Adding a new flag requires adding a corresponding entry to enum
diff --git a/chrome/browser/actor/BUILD.gn b/chrome/browser/actor/BUILD.gn index 037378a..ac5ec46b 100644 --- a/chrome/browser/actor/BUILD.gn +++ b/chrome/browser/actor/BUILD.gn
@@ -45,6 +45,7 @@ "tools/wait_tool.h", ] public_deps = [ + ":types", "//base", "//chrome/browser:browser_public_dependencies", "//components/optimization_guide/content/browser", @@ -66,6 +67,14 @@ ] } +# This target contains only type definitions that may be depended on by other +# headers without depending on all of :actor. +# This avoids dependency cycles. +source_set("types") { + sources = [ "task_id.h" ] + public_deps = [ "//base" ] +} + source_set("test_support") { testonly = true sources = [
diff --git a/chrome/browser/actor/actor_coordinator.cc b/chrome/browser/actor/actor_coordinator.cc index 125c05d..6d24eeca 100644 --- a/chrome/browser/actor/actor_coordinator.cc +++ b/chrome/browser/actor/actor_coordinator.cc
@@ -116,7 +116,7 @@ }; // static -ActorCoordinator::TaskId::Generator ActorCoordinator::Task::id_generator_; +TaskId::Generator ActorCoordinator::Task::id_generator_; ActorCoordinator::Action::Action(const BrowserAction& action, ActionResultCallback callback) @@ -169,6 +169,21 @@ task_state_.reset(); } +void ActorCoordinator::PauseTask() { + if (!task_state_) { + return; + } + + if (task_state_->current_action) { + CompleteAction( + MakeResult(mojom::ActionResultCode::kTaskPaused, "Task was paused")); + } +} + +tabs::TabInterface* ActorCoordinator::GetTabOfCurrentTask() const { + return task_state_ ? task_state_->tab.get() : nullptr; +} + bool ActorCoordinator::HasTask() const { return !!task_state_; }
diff --git a/chrome/browser/actor/actor_coordinator.h b/chrome/browser/actor/actor_coordinator.h index 18e9e1f..b78b4bc0 100644 --- a/chrome/browser/actor/actor_coordinator.h +++ b/chrome/browser/actor/actor_coordinator.h
@@ -13,6 +13,7 @@ #include "base/memory/weak_ptr.h" #include "base/sequence_checker.h" #include "base/types/id_type.h" +#include "chrome/browser/actor/task_id.h" #include "chrome/browser/actor/tools/tool_controller.h" #include "chrome/common/actor.mojom-forward.h" #include "components/tabs/public/tab_interface.h" @@ -75,9 +76,15 @@ StartTaskCallback callback, std::optional<tabs::TabHandle> tab_handle); - // Stops the currently running task, if one is active. Callbacks for + // Stops the current task, if it's active. Callbacks for // in-progress actions are invoked. void StopTask(); + // Pauses the current task, if it's active. Callbacks for in-progress actions + // are invoked. + void PauseTask(); + + // Returns the tab associated with the current task if it exists. + tabs::TabInterface* GetTabOfCurrentTask() const; // Returns true if a task is currently active. bool HasTask() const; @@ -96,8 +103,6 @@ private: class NewTabWebContentsObserver; - struct Task; - using TaskId = base::IdType32<Task>; // Starts a new task, after validating there isn't already a task being // initialized or in progress. @@ -152,6 +157,8 @@ TaskId id; + // TODO(mcnee): Ensure this task can't outlive the tab, then stop using weak + // ptr. base::WeakPtr<tabs::TabInterface> tab; ToolController tool_controller;
diff --git a/chrome/browser/actor/actor_features.cc b/chrome/browser/actor/actor_features.cc index 7ea17d9..fb0d7387 100644 --- a/chrome/browser/actor/actor_features.cc +++ b/chrome/browser/actor/actor_features.cc
@@ -13,7 +13,7 @@ BASE_FEATURE(kGlicActionAllowlist, "GlicActionAllowlist", - base::FEATURE_DISABLED_BY_DEFAULT); + base::FEATURE_ENABLED_BY_DEFAULT); BASE_FEATURE_PARAM(std::string, kAllowlist,
diff --git a/chrome/browser/actor/actor_task.h b/chrome/browser/actor/actor_task.h index a52ed48d..56d2aee 100644 --- a/chrome/browser/actor/actor_task.h +++ b/chrome/browser/actor/actor_task.h
@@ -23,11 +23,19 @@ // Once state leaves kCreated it should never go back. One state enters // kFinished it should never change. We may want to add a kCancelled in the // future, TBD. - enum class State { kCreated, kActing, kReflecting, kFinished }; + enum class State { + kCreated, + kActing, + kReflecting, + kPausedByClient, + kFinished + }; State GetState() const; void SetState(State state); + bool IsPaused() const { return GetState() == State::kPausedByClient; } + ActorCoordinator* GetActorCoordinator() const; private:
diff --git a/chrome/browser/actor/task_id.h b/chrome/browser/actor/task_id.h new file mode 100644 index 0000000..b94f2e4 --- /dev/null +++ b/chrome/browser/actor/task_id.h
@@ -0,0 +1,18 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_ACTOR_TASK_ID_H_ +#define CHROME_BROWSER_ACTOR_TASK_ID_H_ + +#include "base/types/id_type.h" + +namespace actor { + +using TaskId = base::IdType32<class TaskIdTag>; + +static_assert(TaskId(0).is_null(), "0 must be a null TaskId"); + +} // namespace actor + +#endif // CHROME_BROWSER_ACTOR_TASK_ID_H_
diff --git a/chrome/browser/browsing_data/chrome_browsing_data_remover_delegate.cc b/chrome/browser/browsing_data/chrome_browsing_data_remover_delegate.cc index 2b9e8c2..e64d972 100644 --- a/chrome/browser/browsing_data/chrome_browsing_data_remover_delegate.cc +++ b/chrome/browser/browsing_data/chrome_browsing_data_remover_delegate.cc
@@ -24,7 +24,6 @@ #include "base/metrics/histogram_functions.h" #include "base/metrics/histogram_macros.h" #include "base/metrics/user_metrics.h" -#include "base/not_fatal_until.h" #include "base/strings/strcat.h" #include "base/task/bind_post_task.h" #include "base/task/thread_pool.h" @@ -1053,8 +1052,7 @@ kClearBrowsingData); } - CHECK(deferred_disable_passwords_auto_signin_cb_.is_null(), - base::NotFatalUntil::M125); + CHECK(deferred_disable_passwords_auto_signin_cb_.is_null()); if ((remove_mask & content::BrowsingDataRemover::DATA_TYPE_COOKIES) && !filter_builder->PartitionedCookiesOnly()) { // Unretained() is safe, this is only executed in OnTasksComplete() if the
diff --git a/chrome/browser/chrome_resource_bundle_helper.cc b/chrome/browser/chrome_resource_bundle_helper.cc index ce767eb..2c437e5 100644 --- a/chrome/browser/chrome_resource_bundle_helper.cc +++ b/chrome/browser/chrome_resource_bundle_helper.cc
@@ -65,15 +65,10 @@ std::string InitResourceBundleAndDetermineLocale(PrefService* local_state, bool is_running_tests) { #if BUILDFLAG(IS_ANDROID) - // In order for SetLoadSecondaryLocalePaks() to work ResourceBundle must - // not have been created yet. + // In order for DetectAndSetLoadSecondaryLocalePaks() to work ResourceBundle + // must not have been created yet. DCHECK(!ui::ResourceBundle::HasSharedInstance()); - // Auto-detect based on en-US whether secondary locale .pak files exist. - bool in_split = false; - bool log_error = false; - ui::SetLoadSecondaryLocalePaks( - !ui::GetPathForAndroidLocalePakWithinApk("en-US", in_split, log_error) - .empty()); + ui::DetectAndSetLoadSecondaryLocalePaks(); #endif std::string preferred_locale;
diff --git a/chrome/browser/devtools/devtools_embedder_message_dispatcher.cc b/chrome/browser/devtools/devtools_embedder_message_dispatcher.cc index e38a1bc..f85f061f 100644 --- a/chrome/browser/devtools/devtools_embedder_message_dispatcher.cc +++ b/chrome/browser/devtools/devtools_embedder_message_dispatcher.cc
@@ -266,6 +266,23 @@ return true; } +bool GetValue(const base::Value& value, FunctionCallEvent* event) { + if (!value.is_dict()) { + return false; + } + + std::optional<int> name = value.GetDict().FindInt("name"); + if (name) { + event->name = *name; + } + + std::optional<int> context = value.GetDict().FindInt("context"); + if (context) { + event->context = *context; + } + return true; +} + template <typename T> struct StorageTraits { using StorageType = T; @@ -459,6 +476,8 @@ d->RegisterHandler("recordKeyDown", &Delegate::RecordKeyDown, delegate); d->RegisterHandler("recordSettingAccess", &Delegate::RecordSettingAccess, delegate); + d->RegisterHandler("recordFunctionCall", &Delegate::RecordFunctionCall, + delegate); d->RegisterHandler("registerPreference", &Delegate::RegisterPreference, delegate); d->RegisterHandlerWithCallback("getPreferences",
diff --git a/chrome/browser/devtools/devtools_embedder_message_dispatcher.h b/chrome/browser/devtools/devtools_embedder_message_dispatcher.h index d3caa806..a5d49c8 100644 --- a/chrome/browser/devtools/devtools_embedder_message_dispatcher.h +++ b/chrome/browser/devtools/devtools_embedder_message_dispatcher.h
@@ -24,6 +24,7 @@ struct ChangeEvent; struct KeyDownEvent; struct SettingAccessEvent; +struct FunctionCallEvent; /** * Dispatcher for messages sent from the DevTools frontend running in an @@ -127,6 +128,7 @@ virtual void RecordChange(const ChangeEvent& event) = 0; virtual void RecordKeyDown(const KeyDownEvent& event) = 0; virtual void RecordSettingAccess(const SettingAccessEvent& event) = 0; + virtual void RecordFunctionCall(const FunctionCallEvent& event) = 0; virtual void Reattach(DispatchCallback callback) = 0; virtual void ReadyForTest() = 0; virtual void ConnectionReady() = 0;
diff --git a/chrome/browser/devtools/devtools_ui_bindings.cc b/chrome/browser/devtools/devtools_ui_bindings.cc index a3f1e1c..533c3a7 100644 --- a/chrome/browser/devtools/devtools_ui_bindings.cc +++ b/chrome/browser/devtools/devtools_ui_bindings.cc
@@ -2155,6 +2155,18 @@ .SetSessionId(session_id_for_logging_.GetLowForSerialization())); } +void DevToolsUIBindings::RecordFunctionCall(const FunctionCallEvent& event) { + if (!MaybeStartLogging()) { + return; + } + metrics::structured::StructuredMetricsClient::Record( + metrics::structured::events::v2::dev_tools::FunctionCall() + .SetName(event.name) + .SetContext(event.context) + .SetTimeSinceSessionStart(GetTimeSinceSessionStart().InMilliseconds()) + .SetSessionId(session_id_for_logging_.GetLowForSerialization())); +} + void DevToolsUIBindings::DeviceCountChanged(int count) { CallClientMethod("DevToolsAPI", "deviceCountUpdated", base::Value(count)); }
diff --git a/chrome/browser/devtools/devtools_ui_bindings.h b/chrome/browser/devtools/devtools_ui_bindings.h index dca492dd..09580c9e 100644 --- a/chrome/browser/devtools/devtools_ui_bindings.h +++ b/chrome/browser/devtools/devtools_ui_bindings.h
@@ -218,6 +218,7 @@ void RecordChange(const ChangeEvent& event) override; void RecordKeyDown(const KeyDownEvent& event) override; void RecordSettingAccess(const SettingAccessEvent& event) override; + void RecordFunctionCall(const FunctionCallEvent& event) override; void RegisterPreference(const std::string& name, const RegisterOptions& options) override; void GetPreferences(DispatchCallback callback) override;
diff --git a/chrome/browser/devtools/visual_logging.h b/chrome/browser/devtools/visual_logging.h index 22233576..b6dd8e8 100644 --- a/chrome/browser/devtools/visual_logging.h +++ b/chrome/browser/devtools/visual_logging.h
@@ -64,6 +64,11 @@ int string_value = -1; }; +struct FunctionCallEvent { + int name = -1; + int context = -1; +}; + enum SessionTags { kUserSignedIn = 1 << 0, kDevToolsGetAiEnterprisePolicyDisabled = 1 << 1,
diff --git a/chrome/browser/enterprise/client_certificates/client_certificates_browsertest.cc b/chrome/browser/enterprise/client_certificates/client_certificates_browsertest.cc deleted file mode 100644 index 734396ef..0000000 --- a/chrome/browser/enterprise/client_certificates/client_certificates_browsertest.cc +++ /dev/null
@@ -1,159 +0,0 @@ -// Copyright 2025 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/strings/stringprintf.h" -#include "base/test/metrics/histogram_tester.h" -#include "base/test/test_future.h" -#include "chrome/browser/browser_process.h" -#include "chrome/browser/enterprise/client_certificates/certificate_provisioning_service_factory.h" -#include "chrome/browser/enterprise/test/management_context_mixin.h" -#include "chrome/browser/policy/chrome_browser_policy_connector.h" -#include "chrome/browser/profiles/profile.h" -#include "chrome/browser/ui/browser.h" -#include "chrome/test/base/chrome_test_utils.h" -#include "chrome/test/base/mixin_based_in_process_browser_test.h" -#include "chrome/test/base/platform_browser_test.h" -#include "components/enterprise/browser/controller/chrome_browser_cloud_management_controller.h" -#include "components/enterprise/client_certificates/core/certificate_provisioning_service.h" -#include "components/enterprise/client_certificates/core/client_identity.h" -#include "components/enterprise/client_certificates/core/features.h" -#include "components/policy/core/common/policy_switches.h" -#include "components/policy/policy_constants.h" -#include "components/policy/test_support/embedded_policy_test_server.h" -#include "content/public/test/browser_test.h" -#include "crypto/scoped_fake_unexportable_key_provider.h" -#include "testing/gmock/include/gmock/gmock.h" -#include "testing/gtest/include/gtest/gtest.h" - -namespace client_certificates { - -using ManagementContextMixin = enterprise::test::ManagementContextMixin; -using ManagementContext = enterprise::test::ManagementContext; - -namespace { - -constexpr char kProfileIssuerCommonName[] = "Profile Root CA"; -constexpr char kBrowserIssuerCommonName[] = "Browser Root CA"; - -} // namespace - -class ClientCertificateBrowserTest : public MixinBasedInProcessBrowserTest, - public testing::WithParamInterface<bool> { - protected: - ClientCertificateBrowserTest() { - management_mixin_ = ManagementContextMixin::Create( - &mixin_host_, this, - { - .is_cloud_user_managed = is_profile_scenario(), - .is_cloud_machine_managed = !is_profile_scenario(), - .affiliated = false, - }); - } - - void SetUpInProcessBrowserTestFixture() override { - test_dm_server_ = std::make_unique<policy::EmbeddedPolicyTestServer>(); - ASSERT_TRUE(test_dm_server_->Start()); - - policy::ChromeBrowserPolicyConnector::EnableCommandLineSupportForTesting(); - base::CommandLine* command_line = base::CommandLine::ForCurrentProcess(); - command_line->AppendSwitchASCII(policy::switches::kDeviceManagementUrl, - test_dm_server_->GetServiceURL().spec()); - - MixinBasedInProcessBrowserTest::SetUpInProcessBrowserTestFixture(); - } - - void SetUserPolicy(bool enable_provisioning) { - base::flat_map<std::string, std::optional<base::Value>> policy_values; - policy_values.insert( - {policy::key::kProvisionManagedClientCertificateForUser, - base::Value(enable_provisioning ? 1 : 0)}); - - management_mixin()->SetCloudUserPolicies(std::move(policy_values)); - } - - void SetBrowserPolicy(bool enable_provisioning) { - base::flat_map<std::string, std::optional<base::Value>> policy_values; - policy_values.insert( - {policy::key::kProvisionManagedClientCertificateForBrowser, - base::Value(enable_provisioning ? 1 : 0)}); - - management_mixin()->SetCloudMachinePolicies(std::move(policy_values)); - } - - void EnablePolicyAndWaitForIdentity() { - CertificateProvisioningService* provisioning_service; - if (is_profile_scenario()) { - SetUserPolicy(true); - provisioning_service = - CertificateProvisioningServiceFactory::GetForProfile( - browser()->profile()); - } else { - SetBrowserPolicy(true); - provisioning_service = g_browser_process->browser_policy_connector() - ->chrome_browser_cloud_management_controller() - ->GetCertificateProvisioningService(); - } - - ASSERT_TRUE(provisioning_service); - - base::test::TestFuture<std::optional<ClientIdentity>> test_future; - provisioning_service->GetManagedIdentity(test_future.GetCallback()); - - VerifyIdentity(test_future.Get()); - } - - void VerifyIdentity(const std::optional<ClientIdentity>& managed_identity) { - ASSERT_TRUE(managed_identity); - ASSERT_TRUE(managed_identity->is_valid()); - - // Verify that the right cert was created based on the root CA's CN. - auto& cert = managed_identity->certificate; - EXPECT_EQ(cert->issuer().common_name, is_profile_scenario() - ? kProfileIssuerCommonName - : kBrowserIssuerCommonName); - } - - ManagementContextMixin* management_mixin() { return management_mixin_.get(); } - - base::HistogramTester& histogram_tester() { return histogram_tester_; } - - bool is_profile_scenario() const { return GetParam(); } - - private: - base::HistogramTester histogram_tester_; - std::unique_ptr<policy::EmbeddedPolicyTestServer> test_dm_server_; - crypto::ScopedFakeUnexportableKeyProvider scoped_key_provider_; - std::unique_ptr<ManagementContextMixin> management_mixin_; -}; - -IN_PROC_BROWSER_TEST_P(ClientCertificateBrowserTest, CreateNewIdentity) { - EnablePolicyAndWaitForIdentity(); - histogram_tester().ExpectUniqueSample( - base::StringPrintf( - "Enterprise.ClientCertificate.%s.Provisioning.CertificateCreation." - "Outcome", - is_profile_scenario() ? "Profile" : "Browser"), - true, 1); -} - -IN_PROC_BROWSER_TEST_P(ClientCertificateBrowserTest, PRE_LoadExistingIdentity) { - EnablePolicyAndWaitForIdentity(); -} - -IN_PROC_BROWSER_TEST_P(ClientCertificateBrowserTest, LoadExistingIdentity) { - EnablePolicyAndWaitForIdentity(); - histogram_tester().ExpectUniqueSample( - base::StringPrintf( - "Enterprise.ClientCertificate.%s.Provisioning.ExistingIdentity." - "Outcome", - is_profile_scenario() ? "Profile" : "Browser"), - true, 1); -} - -INSTANTIATE_TEST_SUITE_P( - /* no prefix */, - ClientCertificateBrowserTest, - testing::Bool()); - -} // namespace client_certificates
diff --git a/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog.cc b/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog.cc index 97a159c..968d702 100644 --- a/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog.cc +++ b/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog.cc
@@ -254,15 +254,8 @@ scoped_ignore_input_events_ = top_web_contents->IgnoreInputEvents(std::nullopt); - if (auto* tab_interface = - tabs::TabInterface::MaybeGetFromContents(top_web_contents); - tab_interface && tab_interface->CanShowModalUI()) { - tab_interface->GetTabFeatures() - ->tab_dialog_manager() - ->ShowDialogAndBlockTabInteraction(widget_.get()); - } else { - widget_->Show(); - } + constrained_window::ShowModalDialog(widget_->GetNativeWindow(), + top_web_contents); } void DesktopDataControlsDialog::CloseDialog(
diff --git a/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_browsertest.cc b/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_browsertest.cc index b3cd98fb..463d639 100644 --- a/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_browsertest.cc +++ b/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_browsertest.cc
@@ -6,6 +6,7 @@ #include "base/functional/callback_helpers.h" #include "chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_factory.h" +#include "chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_test_helper.h" #include "chrome/browser/profiles/profile.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_commands.h" @@ -29,9 +30,18 @@ // DialogBrowserTest: void ShowUi(const std::string& name) override { + helper_ = std::make_unique<DesktopDataControlsDialogTestHelper>(type()); DesktopDataControlsDialogFactory::GetInstance()->ShowDialogIfNeeded( browser()->tab_strip_model()->GetActiveWebContents(), type()); } + + void DismissUi() override { + helper_->CloseDialogWithoutBypass(); + helper_->WaitForDialogToClose(); + } + + private: + std::unique_ptr<DesktopDataControlsDialogTestHelper> helper_; }; class DesktopDataControlsDialogTest : public InProcessBrowserTest,
diff --git a/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_test_helper.h b/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_test_helper.h index 00e80f32..0ac280e 100644 --- a/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_test_helper.h +++ b/chrome/browser/enterprise/data_controls/desktop_data_controls_dialog_test_helper.h
@@ -18,7 +18,7 @@ public: explicit DesktopDataControlsDialogTestHelper( DataControlsDialog::Type expected_dialog_type); - ~DesktopDataControlsDialogTestHelper(); + virtual ~DesktopDataControlsDialogTestHelper(); // DesktopDataControlsDialog::TestObserver: void OnConstructed(DesktopDataControlsDialog* dialog,
diff --git a/chrome/browser/enterprise/test/browser/management_context_mixin_browser.cc b/chrome/browser/enterprise/test/browser/management_context_mixin_browser.cc index a601cdb..a1c1ecd8 100644 --- a/chrome/browser/enterprise/test/browser/management_context_mixin_browser.cc +++ b/chrome/browser/enterprise/test/browser/management_context_mixin_browser.cc
@@ -10,6 +10,7 @@ #include "chrome/browser/policy/chrome_browser_policy_connector.h" #include "chrome/browser/profiles/profile.h" #include "chrome/test/base/in_process_browser_test.h" +#include "components/enterprise/browser/controller/fake_browser_dm_token_storage.h" #include "components/enterprise/browser/enterprise_switches.h" #include "components/policy/core/common/cloud/machine_level_user_cloud_policy_manager.h" #include "components/policy/core/common/cloud/mock_cloud_policy_client.h" @@ -43,10 +44,7 @@ InProcessBrowserTestMixinHost* host, InProcessBrowserTest* test_base, ManagementContext management_context) - : ManagementContextMixin(host, test_base, std::move(management_context)) { - // Fake the OS' device ID. - browser_dm_token_storage_.SetClientId(kBrowserClientId); -} + : ManagementContextMixin(host, test_base, std::move(management_context)) {} ManagementContextMixinBrowser::~ManagementContextMixinBrowser() = default; @@ -81,6 +79,14 @@ } } +void ManagementContextMixinBrowser::SetUpInProcessBrowserTestFixture() { + browser_dm_token_storage_ = + std::make_unique<policy::FakeBrowserDMTokenStorage>(); + + policy::BrowserDMTokenStorage::SetForTesting(browser_dm_token_storage_.get()); + ManagementContextMixin::SetUpInProcessBrowserTestFixture(); +} + #if !BUILDFLAG(GOOGLE_CHROME_BRANDING) void ManagementContextMixinBrowser::SetUpDefaultCommandLine( base::CommandLine* command_line) { @@ -91,8 +97,11 @@ void ManagementContextMixinBrowser::ManageCloudMachine() { ManagementContextMixin::ManageCloudMachine(); - browser_dm_token_storage_.SetEnrollmentToken(kEnrollmentToken); - browser_dm_token_storage_.SetDMToken(kBrowserDmToken); + CHECK(browser_dm_token_storage_); + browser_dm_token_storage_->SetEnrollmentToken(kEnrollmentToken); + browser_dm_token_storage_->SetClientId(kBrowserClientId); + browser_dm_token_storage_->EnableStorage(true); + browser_dm_token_storage_->SetDMToken(kBrowserDmToken); } void ManagementContextMixinBrowser::SetCloudMachinePolicies(
diff --git a/chrome/browser/enterprise/test/browser/management_context_mixin_browser.h b/chrome/browser/enterprise/test/browser/management_context_mixin_browser.h index 8ca8df7c..25415c3 100644 --- a/chrome/browser/enterprise/test/browser/management_context_mixin_browser.h +++ b/chrome/browser/enterprise/test/browser/management_context_mixin_browser.h
@@ -10,7 +10,6 @@ #include "build/branding_buildflags.h" #include "chrome/browser/enterprise/test/management_context_mixin.h" #include "chrome/test/base/mixin_based_in_process_browser_test.h" -#include "components/enterprise/browser/controller/fake_browser_dm_token_storage.h" namespace policy { class FakeBrowserDMTokenStorage; @@ -37,6 +36,9 @@ // InProcessBrowserTestMixin: void SetUpOnMainThread() override; + // ManagementContextMixin: + void SetUpInProcessBrowserTestFixture() override; + #if !BUILDFLAG(GOOGLE_CHROME_BRANDING) void SetUpDefaultCommandLine(base::CommandLine* command_line) override; #endif @@ -48,7 +50,7 @@ override; private: - policy::FakeBrowserDMTokenStorage browser_dm_token_storage_; + std::unique_ptr<policy::FakeBrowserDMTokenStorage> browser_dm_token_storage_; }; } // namespace enterprise::test
diff --git a/chrome/browser/enterprise/test/management_context_mixin.cc b/chrome/browser/enterprise/test/management_context_mixin.cc index 3282170..17d5889 100644 --- a/chrome/browser/enterprise/test/management_context_mixin.cc +++ b/chrome/browser/enterprise/test/management_context_mixin.cc
@@ -94,8 +94,6 @@ user_policy_data->add_user_affiliation_ids(user_customer_id); user_policy_data->set_username(kTestUserEmail); user_policy_data->set_gaia_id(kTestUserId); - user_policy_data->set_device_id(kProfileClientId); - user_policy_data->set_request_token(kProfileDmToken); return user_policy_data; }
diff --git a/chrome/browser/flag-metadata.json b/chrome/browser/flag-metadata.json index 0b9e273..9760d9dd 100644 --- a/chrome/browser/flag-metadata.json +++ b/chrome/browser/flag-metadata.json
@@ -6480,6 +6480,11 @@ "expiry_milestone": -1 }, { + "name": "memory-purge-on-freeze-limit", + "owners": [ "fdoray@chromium.org", "catan-team@chromium.org" ], + "expiry_milestone": 142 + }, + { "name": "merchant-trust", "owners": [ "tommasin@chromium.org", "privacy-on-the-web@google.com" ], "expiry_milestone": 145 @@ -6572,6 +6577,11 @@ "expiry_milestone": 96 }, { + "name": "mvc-update-view-when-model-changed", + "owners": [ "acondor@chromium.org" ], + "expiry_milestone": 139 + }, + { "name": "nav-bar-color-animation", "owners": [ "clhager@google.com", "wenyufu@chromium.org","twellington@chromium.org" ], "expiry_milestone": 150 @@ -7413,6 +7423,11 @@ "expiry_milestone": 150 }, { + "name": "page-actions-migration", + "owners": [ "alsan@google.com", "chrome-desktop-ui-waterloo@google.com" ], + "expiry_milestone": 150 + }, + { "name": "page-content-annotations", "owners": [ "sophiechang@chromium.org", "mcrouse@chromium.org", "chrome-intelligence-core@google.com"], "expiry_milestone": 150
diff --git a/chrome/browser/flag_descriptions.cc b/chrome/browser/flag_descriptions.cc index 8914d1b3..49841ddd 100644 --- a/chrome/browser/flag_descriptions.cc +++ b/chrome/browser/flag_descriptions.cc
@@ -1173,6 +1173,14 @@ "Enables the 'enterpictureinpicture' MediaSessionAction to allow websites " "to register an action handler for entering picture-in-picture."; +#if BUILDFLAG(IS_ANDROID) +const char kMvcUpdateViewWhenModelChangedName[] = + "MVC Update View when Model Changed"; +const char kMvcUpdateViewWhenModelChangedDescription[] = + "Performance optimization to the MVC framework where a View is only " + "updated when the corresponding Model changes."; +#endif // !BUILDFLAG(IS_ANDROID) + const char kCodeBasedRBDName[] = "Code-based RBD"; const char kCodeBasedRBDDescription[] = "Enables the Code-based RBD."; @@ -3135,6 +3143,10 @@ const char kOverscrollHistoryNavigationDescription[] = "History navigation in response to horizontal overscroll."; +const char kPageActionsMigrationName[] = "Page actions migration"; +const char kPageActionsMigrationDescription[] = + "Enables a new internal framework for driving page actions behavior."; + const char kPageContentAnnotationsName[] = "Page content annotations"; const char kPageContentAnnotationsDescription[] = "Enables page content to be annotated on-device."; @@ -5528,6 +5540,12 @@ "functionality (e.g. playing audio, handling a video call) are not " "eligible for freezing."; +const char kMemoryPurgeOnFreezeLimitName[] = "Memory Purge on Freeze Limit"; +const char kMemoryPurgeOnFreezeLimitDescription[] = + "Do not purge memory in renderers with frozen pages more than once per " + "backgrounded interval, to minimize overhead when pages are periodically " + "unfrozen. To be enabled with memory-purge-on-freeze-limit."; + const char kKeyboardLockPromptName[] = "Keyboard Lock prompt"; const char kKeyboardLockPromptDescription[] = "Requesting to use the keyboard lock API causes a permission prompt to be "
diff --git a/chrome/browser/flag_descriptions.h b/chrome/browser/flag_descriptions.h index 7d390644..776cd1f 100644 --- a/chrome/browser/flag_descriptions.h +++ b/chrome/browser/flag_descriptions.h
@@ -321,7 +321,7 @@ extern const char kClearInstanceInfoWhenClosedIntentionallyName[]; extern const char kClearInstanceInfoWhenClosedIntentionallyDescription[]; -#endif +#endif // !BUILDFLAG(IS_ANDROID) extern const char kEnableBenchmarkingName[]; extern const char kEnableBenchmarkingDescription[]; @@ -359,6 +359,11 @@ extern const char kMediaSessionEnterPictureInPictureName[]; extern const char kMediaSessionEnterPictureInPictureDescription[]; +#if BUILDFLAG(IS_ANDROID) +extern const char kMvcUpdateViewWhenModelChangedName[]; +extern const char kMvcUpdateViewWhenModelChangedDescription[]; +#endif // !BUILDFLAG(IS_ANDROID) + extern const char kEnableDrDcName[]; extern const char kEnableDrDcDescription[]; @@ -1812,6 +1817,9 @@ extern const char kOverscrollHistoryNavigationName[]; extern const char kOverscrollHistoryNavigationDescription[]; +extern const char kPageActionsMigrationName[]; +extern const char kPageActionsMigrationDescription[]; + extern const char kPageContentAnnotationsName[]; extern const char kPageContentAnnotationsDescription[]; @@ -3243,6 +3251,9 @@ extern const char kInfiniteTabsFreezingName[]; extern const char kInfiniteTabsFreezingDescription[]; +extern const char kMemoryPurgeOnFreezeLimitName[]; +extern const char kMemoryPurgeOnFreezeLimitDescription[]; + extern const char kKeyboardLockPromptName[]; extern const char kKeyboardLockPromptDescription[];
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 8b5d39a..8adadbe1 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
@@ -1587,10 +1587,8 @@ sDisableBottomControlsStackerYOffsetDispatching = sBottomBrowserControlsRefactor.newBooleanParam( "disable_bottom_controls_stacker_y_offset", false); - public static final MutableBooleanParamWithSafeDefault sShowNewTabAnimationsNewDuration = - sShowNewTabAnimations.newBooleanParam("new-duration", false); public static final MutableIntParamWithSafeDefault sShowNewTabAnimationsVersion = - sShowNewTabAnimations.newIntParam("version", 0); + sShowNewTabAnimations.newIntParam("version", 4); public static final MutableIntParamWithSafeDefault sTabSwitcherColorBlendAnimateDurationMs = sTabSwitcherColorBlendAnimate.newIntParam("animation_duration_ms", 240); public static final MutableIntParamWithSafeDefault sTabSwitcherColorBlendAnimateInterpolator =
diff --git a/chrome/browser/gesturenav/android/tab_on_back_gesture_handler.cc b/chrome/browser/gesturenav/android/tab_on_back_gesture_handler.cc index 868e133..d74101b 100644 --- a/chrome/browser/gesturenav/android/tab_on_back_gesture_handler.cc +++ b/chrome/browser/gesturenav/android/tab_on_back_gesture_handler.cc
@@ -61,7 +61,7 @@ is_in_progress_ = true; content::WebContents* web_contents = tab_android_->web_contents(); - CHECK(web_contents, base::NotFatalUntil::M123); + CHECK(web_contents); AssertHasWindowAndCompositor(web_contents); ui::BackGestureEvent back_gesture(progress);
diff --git a/chrome/browser/glic/BUILD.gn b/chrome/browser/glic/BUILD.gn index 51a70054..d2eac20 100644 --- a/chrome/browser/glic/BUILD.gn +++ b/chrome/browser/glic/BUILD.gn
@@ -75,6 +75,7 @@ "//ui/webui", ] deps = [ + "//chrome/browser/actor:types", "//chrome/common", "//components/user_education/common", ]
diff --git a/chrome/browser/glic/glic_keyed_service.cc b/chrome/browser/glic/glic_keyed_service.cc index e995442..6e90279 100644 --- a/chrome/browser/glic/glic_keyed_service.cc +++ b/chrome/browser/glic/glic_keyed_service.cc
@@ -378,10 +378,25 @@ std::move(callback)); } -void GlicKeyedService::StopActorTask() { +void GlicKeyedService::StopActorTask(actor::TaskId task_id) { CHECK(base::FeatureList::IsEnabled(features::kGlicActor)); CHECK(actor_controller_); - actor_controller_->StopTask(); + actor_controller_->StopTask(task_id); +} + +void GlicKeyedService::PauseActorTask(actor::TaskId task_id) { + CHECK(base::FeatureList::IsEnabled(features::kGlicActor)); + CHECK(actor_controller_); + actor_controller_->PauseTask(task_id); +} + +void GlicKeyedService::ResumeActorTask( + actor::TaskId task_id, + const mojom::GetTabContextOptions& context_options, + glic::mojom::WebClientHandler::ResumeActorTaskCallback callback) { + CHECK(base::FeatureList::IsEnabled(features::kGlicActor)); + CHECK(actor_controller_); + actor_controller_->ResumeTask(task_id, context_options, std::move(callback)); } bool GlicKeyedService::IsActorCoordinatorActingOnTab(
diff --git a/chrome/browser/glic/glic_keyed_service.h b/chrome/browser/glic/glic_keyed_service.h index 77a72dca..337e3dca3 100644 --- a/chrome/browser/glic/glic_keyed_service.h +++ b/chrome/browser/glic/glic_keyed_service.h
@@ -12,6 +12,7 @@ #include "base/containers/flat_set.h" #include "base/memory/memory_pressure_listener.h" #include "base/memory/raw_ptr.h" +#include "chrome/browser/actor/task_id.h" #include "chrome/browser/glic/host/context/glic_focused_tab_manager.h" #include "chrome/browser/glic/host/glic.mojom.h" #include "components/keyed_service/core/keyed_service.h" @@ -200,7 +201,12 @@ const mojom::GetTabContextOptions& options, mojom::WebClientHandler::ActInFocusedTabCallback callback); - void StopActorTask(); + void StopActorTask(actor::TaskId task_id); + void PauseActorTask(actor::TaskId task_id); + void ResumeActorTask( + actor::TaskId task_id, + const mojom::GetTabContextOptions& context_options, + glic::mojom::WebClientHandler::ResumeActorTaskCallback callback); // Returns true if the associated ActorCoordinator is active on the given // `tab`. This can be used by callers to customize certain behaviour that
diff --git a/chrome/browser/glic/glic_user_status_browsertest.cc b/chrome/browser/glic/glic_user_status_browsertest.cc index b3c8607..32829c6 100644 --- a/chrome/browser/glic/glic_user_status_browsertest.cc +++ b/chrome/browser/glic/glic_user_status_browsertest.cc
@@ -72,7 +72,8 @@ {features::kTabstripComboButton, {}}, {features::kGlicRollout, {}}, {features::kGlicUserStatusCheck, - {{features::kGlicUserStatusRequestDelay.name, "200ms"}}}}, + {{features::kGlicUserStatusRequestDelay.name, "200ms"}, + {features::kGlicUserStatusRequestDelayJitter.name, "0"}}}}, {/* disabled_features */}); RegisterGeminiSettingsPrefs(pref_service_.registry());
diff --git a/chrome/browser/glic/glic_user_status_fetcher.cc b/chrome/browser/glic/glic_user_status_fetcher.cc index bca219e..4bd0508 100644 --- a/chrome/browser/glic/glic_user_status_fetcher.cc +++ b/chrome/browser/glic/glic_user_status_fetcher.cc
@@ -105,7 +105,7 @@ if (next_update_time <= base::Time::Now()) { UpdateUserStatus(); } else { - ScheduleUserStatusUpdate(next_update_time); + ScheduleUserStatusUpdate(next_update_time - base::Time::Now()); } } @@ -219,9 +219,19 @@ } void GlicUserStatusFetcher::ScheduleUserStatusUpdate( - base::Time next_update_time) { + base::TimeDelta time_to_next_update) { + // Calculate a random offset for the delay. The range of the offset will be + // from [1- jitter*random_multiplier, 1 + jitter*random_multiplier). + // random_multiplier is in the range [-1,1) by (base::RandDouble() - 0.5)* 2. + const double jitter_factor = + 1 + features::kGlicUserStatusRequestDelayJitter.Get() * + (base::RandDouble() - 0.5) * 2; + + base::Time scheduled_time = + base::Time::Now() + jitter_factor * time_to_next_update; + refresh_status_timer_.Start( - FROM_HERE, next_update_time, + FROM_HERE, scheduled_time, base::BindOnce(&GlicUserStatusFetcher::UpdateUserStatus, base::Unretained(this))); } @@ -250,8 +260,7 @@ CancelUserStatusUpdateIfNeeded(); // schedule next run regardless. - ScheduleUserStatusUpdate(base::Time::Now() + - features::kGlicUserStatusRequestDelay.Get()); + ScheduleUserStatusUpdate(features::kGlicUserStatusRequestDelay.Get()); auto account_info = GetGaiaIdHashForPrimaryAccount(profile_);
diff --git a/chrome/browser/glic/glic_user_status_fetcher.h b/chrome/browser/glic/glic_user_status_fetcher.h index 0d7216f..ead3b2e 100644 --- a/chrome/browser/glic/glic_user_status_fetcher.h +++ b/chrome/browser/glic/glic_user_status_fetcher.h
@@ -69,7 +69,7 @@ void InvalidateCachedStatus(); void UpdateUserStatus(); void UpdateUserStatusIfNeeded(); - void ScheduleUserStatusUpdate(base::Time next_update_time); + void ScheduleUserStatusUpdate(base::TimeDelta time_to_next_update); void CancelUserStatusUpdateIfNeeded(); void SetGlicUserStatusUrlForTest(GURL test_url) { endpoint_ = test_url; }
diff --git a/chrome/browser/glic/host/glic.mojom b/chrome/browser/glic/host/glic.mojom index c945994..f6a3048 100644 --- a/chrome/browser/glic/host/glic.mojom +++ b/chrome/browser/glic/host/glic.mojom
@@ -395,15 +395,33 @@ // // Actions can only be executed in a tab after act task has been started. An // act task is started by calling this function with a Navigate BrowserAction - // on a tab without an active task. + // on a tab without an active task. It is an error to act with a paused task. // TODO(crbug.com/407860715): Add an explicit method for starting a task. ActInFocusedTab(array<uint8> action_proto, GetTabContextOptions options) => (ActInFocusedTabResult result); - // Immediately stops the actor from taking any further actions and exits - // acting mode. Any in flight actions are canceled and their callbacks will be - // (asynchronously) invoked. No-op if the actor doesn't have an active task. - StopActorTask(); + // Immediately stops the actor from taking any further actions associated with + // the given id and exits acting mode. Any in flight actions are canceled and + // their callbacks will be (asynchronously) invoked. No-op if a task with the + // given id does not exist. An id of 0 refers to the most recent task. + StopActorTask(int32 task_id); + + // Pauses the task associated with the given id. Any restrictions on the tab + // which would prevent user interaction with it are lifted. ResumeActorTask + // restores these restrictions, and allows for further actions. Any in flight + // actions are canceled and their callbacks will be (asynchronously) invoked. + // No-op if a task with the given id does not exist. An id of 0 refers to the + // most recent task. + PauseActorTask(int32 task_id); + + // Resumes a paused task associated with the given id, allowing for further + // actions. Any restrictions on the tab lifted by PauseActorTask are + // reimposed. After resumption, computes the context of the tab associated + // with the task according to the given `context_options` and returns the + // result. Returns an error if the task doesn't exist or is not paused. An id + // of 0 refers to the most recent task. + ResumeActorTask(int32 task_id, GetTabContextOptions context_options) + => (GetContextResult result); // Resize the widget hosting the WebUI to the given size. // If `duration` is 0 or less, instantly resize, otherwise run an animation.
diff --git a/chrome/browser/glic/host/glic_actor_controller.cc b/chrome/browser/glic/host/glic_actor_controller.cc index f4f06be..0111fb9 100644 --- a/chrome/browser/glic/host/glic_actor_controller.cc +++ b/chrome/browser/glic/host/glic_actor_controller.cc
@@ -43,7 +43,13 @@ base::SequencedTaskRunner::GetCurrentDefault()->PostTask( FROM_HERE, base::BindOnce(std::move(callback), std::move(result))); - return; +} + +void PostTaskForActionResultCallback( + actor::ActorCoordinator::ActionResultCallback callback, + actor::mojom::ActionResultPtr result) { + base::SequencedTaskRunner::GetCurrentDefault()->PostTask( + FROM_HERE, base::BindOnce(std::move(callback), std::move(result))); } void OnGetContextFromFocusedTab( @@ -64,6 +70,12 @@ std::move(callback).Run(std::move(result)); } +void MaybeWarnMultiTaskNotImplemented(actor::TaskId task_id) { + if (task_id) { + NOTIMPLEMENTED() << "Multi-task not implemented."; + } +} + } // namespace GlicActorController::GlicActorController(Profile* profile) : profile_(profile) { @@ -103,17 +115,66 @@ ActImpl(focused_tab_data, action, options, std::move(callback)); } -void GlicActorController::StopTask() { - if (!GetActorCoordinator()) { +// TODO(mcnee): Determine if we need additional mechanisms, within the browser, +// to stop a task. +void GlicActorController::StopTask(actor::TaskId task_id) { + MaybeWarnMultiTaskNotImplemented(task_id); + if (!GetActorCoordinator() || + actor_task_->GetState() == actor::ActorTask::State::kFinished) { return; } GetActorCoordinator()->StopTask(); actor_task_->SetState(actor::ActorTask::State::kFinished); } +void GlicActorController::PauseTask(actor::TaskId task_id) { + MaybeWarnMultiTaskNotImplemented(task_id); + if (!GetActorCoordinator() || + actor_task_->GetState() == actor::ActorTask::State::kFinished) { + return; + } + GetActorCoordinator()->PauseTask(); + actor_task_->SetState(actor::ActorTask::State::kPausedByClient); +} + +void GlicActorController::ResumeTask( + actor::TaskId task_id, + const mojom::GetTabContextOptions& context_options, + glic::mojom::WebClientHandler::ResumeActorTaskCallback callback) { + MaybeWarnMultiTaskNotImplemented(task_id); + if (!GetActorCoordinator() || + actor_task_->GetState() == actor::ActorTask::State::kFinished) { + std::move(callback).Run(mojom::GetContextResult::NewErrorReason( + std::string("task does not exist"))); + return; + } + + if (!actor_task_->IsPaused()) { + std::move(callback).Run(mojom::GetContextResult::NewErrorReason( + std::string("task is not paused"))); + return; + } + + tabs::TabInterface* tab_of_resumed_task = + GetActorCoordinator()->GetTabOfCurrentTask(); + if (!tab_of_resumed_task) { + std::move(callback).Run(mojom::GetContextResult::NewErrorReason( + std::string("tab does not exist"))); + return; + } + + actor_task_->SetState(actor::ActorTask::State::kReflecting); + // TODO(mcnee): Refactor to make it clear we're specifying the tab to get the + // context for, not glic's concept of a focused tab. + GetContextFromFocusedTab( + FocusedTabData{tab_of_resumed_task->GetContents()->GetWeakPtr()}, + context_options, std::move(callback)); +} + bool GlicActorController::IsActorCoordinatorActingOnTab( const content::WebContents* tab) const { - return GetActorCoordinator() && GetActorCoordinator()->HasTaskForTab(tab); + return GetActorCoordinator() && GetActorCoordinator()->HasTaskForTab(tab) && + actor_task_->GetState() != actor::ActorTask::State::kFinished; } actor::ActorCoordinator& GlicActorController::GetActorCoordinatorForTesting() { @@ -148,10 +209,20 @@ const optimization_guide::proto::BrowserAction& action, const mojom::GetTabContextOptions& options, mojom::WebClientHandler::ActInFocusedTabCallback callback) const { - GetActorCoordinator()->Act( - action, + actor::ActorCoordinator::ActionResultCallback action_callback = base::BindOnce(&GlicActorController::OnActionFinished, GetWeakPtr(), - focused_tab_data, options, std::move(callback))); + focused_tab_data, options, std::move(callback)); + + if (actor_task_->IsPaused()) { + VLOG(1) << "Unable to perform action: task is paused"; + PostTaskForActionResultCallback( + std::move(action_callback), + actor::MakeResult(actor::mojom::ActionResultCode::kError, + "Task is paused")); + return; + } + + GetActorCoordinator()->Act(action, std::move(action_callback)); } void GlicActorController::OnActionFinished(
diff --git a/chrome/browser/glic/host/glic_actor_controller.h b/chrome/browser/glic/host/glic_actor_controller.h index 6d9e2506..dd8c200 100644 --- a/chrome/browser/glic/host/glic_actor_controller.h +++ b/chrome/browser/glic/host/glic_actor_controller.h
@@ -7,6 +7,7 @@ #include "base/functional/callback_forward.h" #include "base/memory/weak_ptr.h" +#include "chrome/browser/actor/task_id.h" #include "chrome/browser/glic/host/context/glic_tab_data.h" #include "chrome/browser/glic/host/glic.mojom.h" #include "chrome/browser/profiles/profile.h" @@ -42,7 +43,12 @@ const mojom::GetTabContextOptions& options, mojom::WebClientHandler::ActInFocusedTabCallback callback); - void StopTask(); + void StopTask(actor::TaskId task_id); + void PauseTask(actor::TaskId task_id); + void ResumeTask( + actor::TaskId task_id, + const mojom::GetTabContextOptions& context_options, + glic::mojom::WebClientHandler::ResumeActorTaskCallback callback); bool IsActorCoordinatorActingOnTab(const content::WebContents* tab) const;
diff --git a/chrome/browser/glic/host/glic_actor_controller_interactive_uitest.cc b/chrome/browser/glic/host/glic_actor_controller_interactive_uitest.cc index 258eb02..a2dfdec 100644 --- a/chrome/browser/glic/host/glic_actor_controller_interactive_uitest.cc +++ b/chrome/browser/glic/host/glic_actor_controller_interactive_uitest.cc
@@ -160,15 +160,75 @@ WaitForWebContentsReady(new_tab_id, task_url)); } - // Stops a running task by calling the glic StopActingTask API. + // After invoking APIs that don't return promises, we round trip to both the + // client and host to make sure the call has made it to the browser. + auto RoundTrip() { + return Steps(InAnyContext(WithElement( + kGlicContentsElementId, + [](ui::TrackedElement* el) { + content::WebContents* glic_contents = + AsInstrumentedWebContents(el)->web_contents(); + ASSERT_TRUE(content::ExecJs(glic_contents, "true;")); + })), + InAnyContext(WithElement( + kGlicHostElementId, [](ui::TrackedElement* el) { + content::WebContents* webui_contents = + AsInstrumentedWebContents(el)->web_contents(); + ASSERT_TRUE(content::ExecJs(webui_contents, "true;")); + }))); + } + + // Stops a running task by calling the glic StopActorTask API. auto StopActorTask() { - return Steps(InAnyContext( - WithElement(kGlicContentsElementId, [](ui::TrackedElement* el) { + return Steps(InAnyContext(WithElement( + kGlicContentsElementId, + [](ui::TrackedElement* el) { + content::WebContents* glic_contents = + AsInstrumentedWebContents(el)->web_contents(); + constexpr std::string_view script = + "client.browser.stopActorTask(0);"; + ASSERT_TRUE(content::ExecJs(glic_contents, script)); + })), + RoundTrip()); + } + + // Pauses a running task by calling the glic PauseActorTask API. + auto PauseActorTask() { + return Steps(InAnyContext(WithElement( + kGlicContentsElementId, + [](ui::TrackedElement* el) { + content::WebContents* glic_contents = + AsInstrumentedWebContents(el)->web_contents(); + constexpr std::string_view script = + "client.browser.pauseActorTask(0);"; + ASSERT_TRUE(content::ExecJs(glic_contents, script)); + })), + RoundTrip()); + } + + // Resumes a paused task by calling the glic ResumeActorTask API. + auto ResumeActorTask(base::Value::Dict context_options, bool expected) { + return Steps(InAnyContext(CheckElement( + kGlicContentsElementId, + [context_options = + std::move(context_options)](ui::TrackedElement* el) mutable { content::WebContents* glic_contents = AsInstrumentedWebContents(el)->web_contents(); - std::string script = "client.browser.stopActorTask();"; - ASSERT_TRUE(content::ExecJs(glic_contents, std::move(script))); - }))); + std::string script = content::JsReplace( + R"js( + (async () => { + try { + await client.browser.resumeActorTask(0, $1); + return true; + } catch (err) { + return false; + } + })(); + )js", + std::move(context_options)); + return content::EvalJs(glic_contents, script).ExtractBool(); + }, + expected))); } // Returns a callback that builds an encoded proto for a click action on a @@ -276,6 +336,20 @@ })); } + auto CheckHasTaskForTab(ui::ElementIdentifier tab, bool expected) { + return Steps(InAnyContext(CheckElement( + tab, + [](ui::TrackedElement* el) { + content::WebContents* tab_contents = + AsInstrumentedWebContents(el)->web_contents(); + const auto* glic_service = + GlicKeyedService::Get(tab_contents->GetBrowserContext()); + return glic_service && + glic_service->IsActorCoordinatorActingOnTab(tab_contents); + }, + expected))); + } + private: int32_t SearchAnnotatedPageContent(std::string_view label) { CHECK(annotated_page_content_) @@ -409,13 +483,15 @@ GetPageContextFromFocusedTab(), ExecuteAction(ClickActionProvider(kClickableButtonLabel), UpdatedContextOptions()), - WaitForJsResult(kNewActorTabId, "() => button_clicked"), StopActorTask(), + WaitForJsResult(kNewActorTabId, "() => button_clicked"), + CheckHasTaskForTab(kNewActorTabId, true), StopActorTask(), // TODO(crbug.com/409558980): Expect kTargetNotFound since that's // currently the error returned anytime a tool fails but in the future we // should add an error code for "NoActiveTask". ExecuteAction(ClickActionProvider(kClickableButtonLabel), UpdatedContextOptions(), - glic::mojom::ActInFocusedTabErrorReason::kTargetNotFound)); + glic::mojom::ActInFocusedTabErrorReason::kTargetNotFound), + CheckHasTaskForTab(kNewActorTabId, false)); } // Ensure that a task can be started after a previous task was stopped. @@ -448,6 +524,115 @@ WaitForJsResult(kThirdTabId, "() => button_clicked"), StopActorTask()); } +// Ensure that a task can be paused and that further actions fail. +IN_PROC_BROWSER_TEST_F(GlicActorControllerUiTest, PauseActorTask) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kNewActorTabId); + constexpr std::string_view kClickableButtonLabel = "clickable"; + + const GURL task_url = + embedded_test_server()->GetURL("/actor/page_with_clickable_element.html"); + + RunTestSequence( + InitializeWithOpenGlicWindow(), + StartActorTaskInNewTab(task_url, kNewActorTabId), + GetPageContextFromFocusedTab(), + ExecuteAction(ClickActionProvider(kClickableButtonLabel), + UpdatedContextOptions()), + WaitForJsResult(kNewActorTabId, "() => button_clicked"), + CheckHasTaskForTab(kNewActorTabId, true), PauseActorTask(), + // TODO(crbug.com/409558980): Expect kTargetNotFound since that's + // currently the error returned anytime a tool fails but in the future we + // should add an error code for "NoActiveTask". + ExecuteAction(ClickActionProvider(kClickableButtonLabel), + UpdatedContextOptions(), + glic::mojom::ActInFocusedTabErrorReason::kTargetNotFound), + // Unlike stopping, pausing keeps the task. + CheckHasTaskForTab(kNewActorTabId, true)); +} + +IN_PROC_BROWSER_TEST_F(GlicActorControllerUiTest, PauseThenStopActorTask) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kNewActorTabId); + constexpr std::string_view kClickableButtonLabel = "clickable"; + + const GURL task_url = + embedded_test_server()->GetURL("/actor/page_with_clickable_element.html"); + + RunTestSequence(InitializeWithOpenGlicWindow(), + StartActorTaskInNewTab(task_url, kNewActorTabId), + GetPageContextFromFocusedTab(), + ExecuteAction(ClickActionProvider(kClickableButtonLabel), + UpdatedContextOptions()), + WaitForJsResult(kNewActorTabId, "() => button_clicked"), + PauseActorTask(), CheckHasTaskForTab(kNewActorTabId, true), + StopActorTask(), CheckHasTaskForTab(kNewActorTabId, false)); +} + +IN_PROC_BROWSER_TEST_F(GlicActorControllerUiTest, PauseAlreadyPausedActorTask) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kNewActorTabId); + constexpr std::string_view kClickableButtonLabel = "clickable"; + + const GURL task_url = + embedded_test_server()->GetURL("/actor/page_with_clickable_element.html"); + + RunTestSequence(InitializeWithOpenGlicWindow(), + StartActorTaskInNewTab(task_url, kNewActorTabId), + GetPageContextFromFocusedTab(), + ExecuteAction(ClickActionProvider(kClickableButtonLabel), + UpdatedContextOptions()), + WaitForJsResult(kNewActorTabId, "() => button_clicked"), + PauseActorTask(), PauseActorTask(), + CheckHasTaskForTab(kNewActorTabId, true)); +} + +IN_PROC_BROWSER_TEST_F(GlicActorControllerUiTest, PauseThenResumeActorTask) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kNewActorTabId); + constexpr std::string_view kClickableButtonLabel = "clickable"; + + const GURL task_url = + embedded_test_server()->GetURL("/actor/page_with_clickable_element.html"); + + RunTestSequence( + InitializeWithOpenGlicWindow(), + StartActorTaskInNewTab(task_url, kNewActorTabId), + GetPageContextFromFocusedTab(), + ExecuteAction(ClickActionProvider(kClickableButtonLabel), + UpdatedContextOptions()), + WaitForJsResult(kNewActorTabId, "() => button_clicked"), + ExecuteJs(kNewActorTabId, "() => { button_clicked = false; }"), + PauseActorTask(), ResumeActorTask(UpdatedContextOptions(), true), + CheckHasTaskForTab(kNewActorTabId, true), + ExecuteAction(ClickActionProvider(kClickableButtonLabel), + UpdatedContextOptions()), + WaitForJsResult(kNewActorTabId, "() => button_clicked")); +} + +IN_PROC_BROWSER_TEST_F(GlicActorControllerUiTest, ResumeActorTaskWithoutATask) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kNewActorTabId); + + const GURL task_url = + embedded_test_server()->GetURL("/actor/page_with_clickable_element.html"); + + RunTestSequence(InitializeWithOpenGlicWindow(), + StartActorTaskInNewTab(task_url, kNewActorTabId), + StopActorTask(), CheckHasTaskForTab(kNewActorTabId, false), + // Once a task is stopped, it can't be resumed. + ResumeActorTask(UpdatedContextOptions(), false)); +} + +IN_PROC_BROWSER_TEST_F(GlicActorControllerUiTest, + ResumeActorTaskWhenAlreadyResumed) { + DEFINE_LOCAL_ELEMENT_IDENTIFIER_VALUE(kNewActorTabId); + + const GURL task_url = + embedded_test_server()->GetURL("/actor/page_with_clickable_element.html"); + + RunTestSequence(InitializeWithOpenGlicWindow(), + StartActorTaskInNewTab(task_url, kNewActorTabId), + PauseActorTask(), + ResumeActorTask(UpdatedContextOptions(), true), + ResumeActorTask(UpdatedContextOptions(), false)); +} + class GlicActorControllerWithActorDisabledUiTest : public test::InteractiveGlicTest { public:
diff --git a/chrome/browser/glic/host/glic_page_handler.cc b/chrome/browser/glic/host/glic_page_handler.cc index 8e2c31e..812e524 100644 --- a/chrome/browser/glic/host/glic_page_handler.cc +++ b/chrome/browser/glic/host/glic_page_handler.cc
@@ -17,6 +17,7 @@ #include "base/time/time.h" #include "base/timer/timer.h" #include "base/version_info/version_info.h" +#include "chrome/browser/actor/task_id.h" #include "chrome/browser/browser_process.h" #include "chrome/browser/contextual_cueing/contextual_cueing_features.h" #include "chrome/browser/enterprise/browser_management/management_service_factory.h" @@ -469,13 +470,34 @@ glic_service_->ActInFocusedTab(action_proto, *options, std::move(callback)); } - void StopActorTask() override { + void StopActorTask(int32_t task_id) override { if (!base::FeatureList::IsEnabled(features::kGlicActor)) { receiver_.ReportBadMessage( "StopActorTask cannot be called without GlicActor enabled."); return; } - glic_service_->StopActorTask(); + glic_service_->StopActorTask(actor::TaskId(task_id)); + } + + void PauseActorTask(int32_t task_id) override { + if (!base::FeatureList::IsEnabled(features::kGlicActor)) { + receiver_.ReportBadMessage( + "PauseActorTask cannot be called without GlicActor enabled."); + return; + } + glic_service_->PauseActorTask(actor::TaskId(task_id)); + } + + void ResumeActorTask(int32_t task_id, + glic::mojom::GetTabContextOptionsPtr context_options, + ResumeActorTaskCallback callback) override { + if (!base::FeatureList::IsEnabled(features::kGlicActor)) { + receiver_.ReportBadMessage( + "ResumeActorTask cannot be called without GlicActor enabled."); + return; + } + glic_service_->ResumeActorTask(actor::TaskId(task_id), *context_options, + std::move(callback)); } void CaptureScreenshot(CaptureScreenshotCallback callback) override {
diff --git a/chrome/browser/profiles/BUILD.gn b/chrome/browser/profiles/BUILD.gn index 7b8ab5eb..2c049b7 100644 --- a/chrome/browser/profiles/BUILD.gn +++ b/chrome/browser/profiles/BUILD.gn
@@ -299,6 +299,7 @@ deps += [ "//chrome/browser/commerce/merchant_viewer:merchant_viewer_data_manager", "//chrome/browser/fast_checkout", + "//chrome/browser/password_manager/android/one_time_passwords:backend", "//components/commerce/core:merchant_signal_db_proto", "//components/payments/content/browser_binding:browser_bound_keys_deleter_factory", ]
diff --git a/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc b/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc index 613f200..85af536 100644 --- a/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc +++ b/chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.cc
@@ -292,6 +292,7 @@ #include "chrome/browser/fast_checkout/fast_checkout_capabilities_fetcher_factory.h" #include "chrome/browser/flags/android/chrome_feature_list.h" #include "chrome/browser/media/android/cdm/media_drm_origin_id_manager_factory.h" +#include "chrome/browser/password_manager/android/one_time_passwords/android_sms_otp_backend_factory.h" #include "chrome/browser/privacy_sandbox/privacy_sandbox_activity_types_factory.h" #include "chrome/browser/search_resumption/start_suggest_service_factory.h" #include "chrome/browser/signin/signin_manager_android_factory.h" @@ -666,6 +667,9 @@ #endif AffiliationServiceFactory::GetInstance(); AiDataKeyedServiceFactory::GetInstance(); +#if BUILDFLAG(IS_ANDROID) + AndroidSmsOtpBackendFactory::GetInstance(); +#endif AnnouncementNotificationServiceFactory::GetInstance(); #if BUILDFLAG(IS_CHROMEOS) app_list::AppListSyncableServiceFactory::GetInstance();
diff --git a/chrome/browser/resources/glic/glic_api/glic_api.ts b/chrome/browser/resources/glic/glic_api/glic_api.ts index 903c06e..2a0eac8e 100644 --- a/chrome/browser/resources/glic/glic_api/glic_api.ts +++ b/chrome/browser/resources/glic/glic_api/glic_api.ts
@@ -183,15 +183,56 @@ * Inform Chrome about an action. Chrome Takes an action based on the * action proto and returns new context based on the tab context options. * + * Attempts to act while the associated task is stopped/paused will be + * rejected. + * * @throws {ActInFocusedTabError} on failure. */ actInFocusedTab? (params: ActInFocusedTabParams): Promise<ActInFocusedTabResult>; /** - * Stops an actor task in the browser if one exists. No-op otherwise. + * Stops the actor task with the given ID in the browser if it exists. No-op + * otherwise. + * + * Stopping a task removes all actor related restrictions from the associated + * tab. Any in progress actions are canceled and the associated Promises are + * rejected. + * + * If the task ID is not provided or 0, the most recent task is stopped. + * + * @todo Require callers to provide a valid ID. */ - stopActorTask?(): void; + stopActorTask?(taskId?: number): void; + + /** + * Pauses the actor task with the given ID in the browser if it exists. No-op + * otherwise. + * + * Pausing a task removes actor related restrictions that prevent the user + * from interacting with the associated tab. Any in progress actions are + * canceled and the associated Promises are rejected. + * + * If the task ID is 0, the most recent task is paused. + * + * @todo Require callers to provide a valid ID. + */ + pauseActorTask?(taskId: number): void; + + /** + * Resumes a previously paused actor task with the given ID. + * + * Returns the tab context at the time of resumption, based on the provided + * context options. + * + * If the task ID is 0, the most recent task is resumed. + * + * @throws {Error} on failure. + * + * @todo Require callers to provide a valid ID. + */ + resumeActorTask?(taskId: number, tabContextOptions: TabContextOptions): + Promise<TabContextResult>; /** * Requests the host to capture a screenshot. The choice of the screenshot
diff --git a/chrome/browser/resources/glic/glic_api_impl/glic_api_client.ts b/chrome/browser/resources/glic/glic_api_impl/glic_api_client.ts index 69b4c0f..38b1c29 100644 --- a/chrome/browser/resources/glic/glic_api_impl/glic_api_client.ts +++ b/chrome/browser/resources/glic/glic_api_impl/glic_api_client.ts
@@ -240,6 +240,8 @@ if (!state.enableActInFocusedTab) { this.actInFocusedTab = undefined; this.stopActorTask = undefined; + this.pauseActorTask = undefined; + this.resumeActorTask = undefined; } if (state.alwaysDetachedMode) { @@ -345,8 +347,20 @@ context.actInFocusedTabResult); } - stopActorTask?(): void { - this.sender.requestNoResponse('glicBrowserStopActorTask', undefined); + stopActorTask?(taskId?: number): void { + this.sender.requestNoResponse( + 'glicBrowserStopActorTask', {taskId: taskId ?? 0}); + } + + pauseActorTask?(taskId: number): void { + this.sender.requestNoResponse('glicBrowserPauseActorTask', {taskId}); + } + + async resumeActorTask?(taskId: number, tabContextOptions: TabContextOptions): + Promise<TabContextResult> { + const response = await this.sender.requestWithResponse( + 'glicBrowserResumeActorTask', {taskId, tabContextOptions}); + return convertTabContextResultFromPrivate(response.tabContextResult); } async resizeWindow(
diff --git a/chrome/browser/resources/glic/glic_api_impl/glic_api_host.ts b/chrome/browser/resources/glic/glic_api_impl/glic_api_host.ts index 9fdaa36..2a3f211c 100644 --- a/chrome/browser/resources/glic/glic_api_impl/glic_api_host.ts +++ b/chrome/browser/resources/glic/glic_api_impl/glic_api_host.ts
@@ -363,8 +363,28 @@ }; } - glicBrowserStopActorTask(): void { - this.handler.stopActorTask(); + glicBrowserStopActorTask(request: {taskId: number}): void { + this.handler.stopActorTask(request.taskId); + } + + glicBrowserPauseActorTask(request: {taskId: number}): void { + this.handler.pauseActorTask(request.taskId); + } + + async glicBrowserResumeActorTask( + request: {taskId: number, tabContextOptions: TabContextOptions}, + extras: ResponseExtras): + Promise<{tabContextResult: TabContextResultPrivate}> { + const {result: {errorReason, tabContext}} = + await this.handler.resumeActorTask( + request.taskId, + tabContextOptionsFromClient(request.tabContextOptions)); + if (!tabContext) { + throw new Error(`resumeActorTask failed: ${errorReason}`); + } + return { + tabContextResult: tabContextToClient(tabContext, extras), + }; } async glicBrowserResizeWindow(request: {
diff --git a/chrome/browser/resources/glic/glic_api_impl/request_types.ts b/chrome/browser/resources/glic/glic_api_impl/request_types.ts index ad9e336..b476bfa 100644 --- a/chrome/browser/resources/glic/glic_api_impl/request_types.ts +++ b/chrome/browser/resources/glic/glic_api_impl/request_types.ts
@@ -79,7 +79,25 @@ actInFocusedTabResult: ActInFocusedTabResultPrivate, }, }; - glicBrowserStopActorTask: {}; + glicBrowserStopActorTask: { + request: { + taskId: number, + }, + }; + glicBrowserPauseActorTask: { + request: { + taskId: number, + }, + }; + glicBrowserResumeActorTask: { + request: { + taskId: number, + tabContextOptions: TabContextOptions, + }, + response: { + tabContextResult: TabContextResultPrivate, + }, + }; glicBrowserCaptureScreenshot: { response: { screenshot: Screenshot, @@ -292,6 +310,8 @@ GetContextFromFocusedTab: 0, ActInFocusedTab: 0, StopActorTask: 0, + PauseActorTask: 0, + ResumeActorTask: 0, CaptureScreenshot: 0, ResizeWindow: 0, EnableDragResize: 0,
diff --git a/chrome/browser/subresource_filter/subresource_filter_history_observer.cc b/chrome/browser/subresource_filter/subresource_filter_history_observer.cc index 2ab87e1..9b9625a 100644 --- a/chrome/browser/subresource_filter/subresource_filter_history_observer.cc +++ b/chrome/browser/subresource_filter/subresource_filter_history_observer.cc
@@ -5,7 +5,6 @@ #include "chrome/browser/subresource_filter/subresource_filter_history_observer.h" #include "base/check.h" -#include "base/not_fatal_until.h" #include "components/subresource_filter/content/browser/subresource_filter_content_settings_manager.h" #include "url/gurl.h" @@ -14,8 +13,8 @@ settings_manager, history::HistoryService* history_service) : settings_manager_(settings_manager) { - CHECK(settings_manager_, base::NotFatalUntil::M129); - CHECK(history_service, base::NotFatalUntil::M129); + CHECK(settings_manager_); + CHECK(history_service); history_observation_.Observe(history_service); }
diff --git a/chrome/browser/ui/browser_window/browser_window_features.cc b/chrome/browser/ui/browser_window/browser_window_features.cc index 4dce6d3..57e4a41 100644 --- a/chrome/browser/ui/browser_window/browser_window_features.cc +++ b/chrome/browser/ui/browser_window/browser_window_features.cc
@@ -248,6 +248,19 @@ std::make_unique<extensions::Mv2DisabledDialogController>(browser); } } + + if (features::HasTabSearchToolbarButton()) { + // TODO(crbug.com/360163254): We should really be using + // Browser::GetBrowserView, which always returns a non-null BrowserView + // in production, but this crashes during unittests using + // BrowserWithTestWindowTest; these should eventually be refactored. + if (BrowserView* browser_view = + BrowserView::GetBrowserViewForBrowser(browser)) { + tab_search_toolbar_button_controller_ = + std::make_unique<TabSearchToolbarButtonController>( + browser_view, browser_view->GetTabSearchBubbleHost()); + } + } } if (browser->is_type_normal() || browser->is_type_app()) { @@ -306,11 +319,6 @@ std::make_unique<media_router::CastBrowserController>( browser_view->browser()); } - - if (features::HasTabSearchToolbarButton()) { - tab_search_toolbar_button_controller_ = - std::make_unique<TabSearchToolbarButtonController>(browser_view); - } } if (download::IsDownloadBubbleEnabled()) {
diff --git a/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc b/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc index 7e60460..29bd876 100644 --- a/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc +++ b/chrome/browser/ui/commerce/commerce_ui_tab_helper.cc
@@ -259,7 +259,10 @@ tab_interface->GetTabFeatures() ->commerce_price_insights_page_action_view_controller() - ->UpdatePageActionIcon(); + ->UpdatePageActionIcon( + ShouldShowPriceInsightsIconView(), + ShouldExpandPageActionIcon(PageActionIconType::kPriceInsights), + GetPriceInsightsIconLabelTypeForPage()); return; }
diff --git a/chrome/browser/ui/plus_addresses/BUILD.gn b/chrome/browser/ui/plus_addresses/BUILD.gn index a53f242..06292ad 100644 --- a/chrome/browser/ui/plus_addresses/BUILD.gn +++ b/chrome/browser/ui/plus_addresses/BUILD.gn
@@ -2,6 +2,7 @@ # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. +import("//build/config/chrome_build.gni") import("//build/config/ui.gni") assert(toolkit_views || is_android)
diff --git a/chrome/browser/ui/tabs/tab_group_model.cc b/chrome/browser/ui/tabs/tab_group_model.cc index 238e4076..7206aa7 100644 --- a/chrome/browser/ui/tabs/tab_group_model.cc +++ b/chrome/browser/ui/tabs/tab_group_model.cc
@@ -35,7 +35,7 @@ } TabGroup* TabGroupModel::GetTabGroup(const tab_groups::TabGroupId& id) const { - CHECK(ContainsTabGroup(id), base::NotFatalUntil::M127); + CHECK(ContainsTabGroup(id)); return groups_.find(id)->second.get(); }
diff --git a/chrome/browser/ui/tabs/tab_strip_model.cc b/chrome/browser/ui/tabs/tab_strip_model.cc index db4d689..bed2c0f 100644 --- a/chrome/browser/ui/tabs/tab_strip_model.cc +++ b/chrome/browser/ui/tabs/tab_strip_model.cc
@@ -3099,8 +3099,7 @@ int add_types, std::optional<tab_groups::TabGroupId> group) { if (group_model_ && group.has_value()) { - CHECK(group_model_->ContainsTabGroup(group.value()), - base::NotFatalUntil::M129); + CHECK(group_model_->ContainsTabGroup(group.value())); } delegate()->WillAddWebContents(tab->GetContents()); @@ -4460,8 +4459,8 @@ std::optional<tab_groups::TabGroupId> TabStripModel::GetGroupToAssign( int index, int to_position) { - CHECK(ContainsIndex(index), base::NotFatalUntil::M129); - CHECK(ContainsIndex(to_position), base::NotFatalUntil::M129); + CHECK(ContainsIndex(index)); + CHECK(ContainsIndex(to_position)); tabs::TabInterface* tab_to_move = GetTabAtIndex(index);
diff --git a/chrome/browser/ui/toasts/BUILD.gn b/chrome/browser/ui/toasts/BUILD.gn index ede7d8f..f10d2c1 100644 --- a/chrome/browser/ui/toasts/BUILD.gn +++ b/chrome/browser/ui/toasts/BUILD.gn
@@ -4,6 +4,7 @@ assert(is_win || is_mac || is_linux || is_chromeos) +import("//build/config/chrome_build.gni") import("//build/config/ui.gni") source_set("toasts") {
diff --git a/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.cc b/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.cc index b6fa197..648d49d 100644 --- a/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.cc +++ b/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.cc
@@ -13,16 +13,16 @@ #include "chrome/common/chrome_features.h" TabSearchToolbarButtonController::TabSearchToolbarButtonController( - BrowserView* browser_view) - : browser_view_(browser_view) {} + BrowserView* browser_view, + TabSearchBubbleHost* tab_search_bubble_host) + : browser_view_(browser_view) { + tab_search_bubble_host_observation_.Observe(tab_search_bubble_host); +} TabSearchToolbarButtonController::~TabSearchToolbarButtonController() = default; void TabSearchToolbarButtonController::OnBubbleInitializing() { - bubble_showing_ = true; - auto* tab_search_action_item = actions::ActionManager::Get().FindAction( - kActionTabSearch, - browser_view_->browser()->browser_actions()->root_action_item()); + actions::ActionItem* tab_search_action_item = GetTabSearchActionItem(); tab_search_action_item->SetIsShowingBubble(true); PinnedToolbarActionsContainer* pinned_toolbar_actions_container = browser_view_->toolbar()->pinned_toolbar_actions_container(); @@ -36,10 +36,7 @@ } void TabSearchToolbarButtonController::OnBubbleDestroying() { - bubble_showing_ = false; - auto* tab_search_action_item = actions::ActionManager::Get().FindAction( - kActionTabSearch, - browser_view_->browser()->browser_actions()->root_action_item()); + actions::ActionItem* tab_search_action_item = GetTabSearchActionItem(); tab_search_action_item->SetIsShowingBubble(false); PinnedToolbarActionsContainer* pinned_toolbar_actions_container = browser_view_->toolbar()->pinned_toolbar_actions_container(); @@ -74,7 +71,7 @@ PinnedToolbarActionsContainer* pinned_toolbar_actions_container = browser_view_->toolbar()->pinned_toolbar_actions_container(); - if (bubble_showing_ || + if (GetTabSearchActionItem()->GetIsShowingBubble() || pinned_toolbar_actions_container->IsActionPinned(kActionTabSearch)) { return; } @@ -82,3 +79,10 @@ pinned_toolbar_actions_container->ShowActionEphemerallyInToolbar( kActionTabSearch, false); } + +actions::ActionItem* +TabSearchToolbarButtonController::GetTabSearchActionItem() { + return actions::ActionManager::Get().FindAction( + kActionTabSearch, + browser_view_->browser()->browser_actions()->root_action_item()); +}
diff --git a/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.h b/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.h index 9f364030..0f4d1d4 100644 --- a/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.h +++ b/chrome/browser/ui/toolbar/pinned_toolbar/tab_search_toolbar_button_controller.h
@@ -7,13 +7,19 @@ #include "base/memory/raw_ptr.h" #include "base/memory/weak_ptr.h" +#include "base/scoped_observation.h" #include "chrome/browser/ui/views/tab_search_bubble_host.h" +namespace actions { +class ActionItem; +} // namespace actions + class BrowserView; class TabSearchToolbarButtonController : public TabSearchBubbleHost::Observer { public: - explicit TabSearchToolbarButtonController(BrowserView* browser_view); + TabSearchToolbarButtonController(BrowserView* browser_view, + TabSearchBubbleHost* tab_search_bubble_host); ~TabSearchToolbarButtonController() override; TabSearchToolbarButtonController(const TabSearchToolbarButtonController&) = @@ -30,8 +36,17 @@ private: void MaybeHideActionEphemerallyInToolbar(); - raw_ptr<BrowserView> browser_view_; - bool bubble_showing_ = false; + // Gets the TabSearch ActionItem from the hosting browser. + actions::ActionItem* GetTabSearchActionItem(); + + // BrowserView hosting the Tab Search toolbar button, outlives this. + // TODO(crbug.com/417823694): Pass only the specific BrowserView dependencies + // into the controller. + const raw_ptr<BrowserView> browser_view_; + + base::ScopedObservation<TabSearchBubbleHost, TabSearchBubbleHost::Observer> + tab_search_bubble_host_observation_{this}; + base::WeakPtrFactory<TabSearchToolbarButtonController> weak_ptr_factory_{ this}; };
diff --git a/chrome/browser/ui/user_education/recent_session_observer_impl.h b/chrome/browser/ui/user_education/recent_session_observer_impl.h index 6bb23634..688c200 100644 --- a/chrome/browser/ui/user_education/recent_session_observer_impl.h +++ b/chrome/browser/ui/user_education/recent_session_observer_impl.h
@@ -31,7 +31,7 @@ void Init(RecentSessionTracker& tracker) override; private: - friend class RecentSessionObserverImplTest; + friend class RecentSessionObserverImplBrowserTest; void OnRecentSessionsUpdated(const RecentSessionData& recent_sessions);
diff --git a/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.cc b/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.cc index f7c3276..bd6555f 100644 --- a/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.cc +++ b/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.cc
@@ -8,7 +8,6 @@ #include "chrome/browser/ui/browser_window/public/browser_window_interface.h" #include "chrome/browser/ui/commerce/commerce_ui_tab_helper.h" #include "chrome/browser/ui/tabs/public/tab_features.h" -#include "chrome/browser/ui/views/commerce/price_insights_icon_view.h" #include "chrome/browser/ui/views/page_action/page_action_controller.h" #include "components/strings/grit/components_strings.h" #include "ui/base/l10n/l10n_util.h" @@ -24,15 +23,15 @@ PriceInsightsPageActionViewController:: ~PriceInsightsPageActionViewController() = default; -void PriceInsightsPageActionViewController::UpdatePageActionIcon() { - auto* tab_helper = tab_interface_->GetTabFeatures()->commerce_ui_tab_helper(); - CHECK(tab_helper); - +void PriceInsightsPageActionViewController::UpdatePageActionIcon( + bool should_shown_icon, + bool should_expand_icon, + PriceInsightsIconLabelType label_type) { page_actions::PageActionController* page_action_controller = tab_interface_->GetTabFeatures()->page_action_controller(); CHECK(page_action_controller); - if (!tab_helper->ShouldShowPriceInsightsIconView()) { + if (!should_shown_icon) { // Suggestion chip may be previously shown, ensure that the state is // cleared. page_action_controller->HideSuggestionChip(kActionCommercePriceInsights); @@ -43,8 +42,7 @@ page_action_controller->Show(kActionCommercePriceInsights); - if (!tab_helper->ShouldExpandPageActionIcon( - PageActionIconType::kPriceInsights)) { + if (!should_expand_icon) { return; } @@ -55,9 +53,6 @@ scoped_window_call_to_action_ptr_ = tab_interface_->GetBrowserWindowInterface()->ShowCallToAction(); - PriceInsightsIconLabelType label_type = - tab_helper->GetPriceInsightsIconLabelTypeForPage(); - switch (label_type) { case PriceInsightsIconLabelType::kPriceIsLow: page_action_controller->OverrideText(
diff --git a/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.h b/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.h index 0314bc1..fa440d1 100644 --- a/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.h +++ b/chrome/browser/ui/views/commerce/price_insights_page_action_view_controller.h
@@ -5,7 +5,10 @@ #ifndef CHROME_BROWSER_UI_VIEWS_COMMERCE_PRICE_INSIGHTS_PAGE_ACTION_VIEW_CONTROLLER_H_ #define CHROME_BROWSER_UI_VIEWS_COMMERCE_PRICE_INSIGHTS_PAGE_ACTION_VIEW_CONTROLLER_H_ +#include <memory> + #include "base/memory/raw_ref.h" +#include "chrome/browser/ui/views/commerce/price_insights_icon_view.h" class ScopedWindowCallToAction; @@ -34,7 +37,9 @@ // If the icon should be shown, it may also display an expanded label or a // suggestion chip depending on the context provided by the commerce UI tab // helper. - void UpdatePageActionIcon(); + void UpdatePageActionIcon(bool should_shown_icon, + bool should_expand_icon, + PriceInsightsIconLabelType label_type); private: // Reference to the tab interface, which provides access to tab-specific
diff --git a/chrome/browser/ui/views/frame/browser_view.cc b/chrome/browser/ui/views/frame/browser_view.cc index 89c1620..16ec3a1 100644 --- a/chrome/browser/ui/views/frame/browser_view.cc +++ b/chrome/browser/ui/views/frame/browser_view.cc
@@ -1202,13 +1202,6 @@ // other cleanups that destroy views referenced in the layout manager. SetLayoutManager(nullptr); - auto* tab_search_toolbar_button_controller = - browser_->GetFeatures().tab_search_toolbar_button_controller(); - if (tab_search_toolbar_button_controller) { - tab_search_bubble_host_->RemoveObserver( - tab_search_toolbar_button_controller); - } - tab_search_bubble_host_.reset(); // Destroy the top controls slide controller first as it depends on the @@ -5292,8 +5285,6 @@ tab_search_bubble_host_ = std::make_unique<TabSearchBubbleHost>( toolbar_->tab_search_button(), browser_.get(), tabstrip_->AsWeakPtr()); - tab_search_bubble_host_->AddObserver( - browser_->GetFeatures().tab_search_toolbar_button_controller()); } else { tab_search_bubble_host_ = std::make_unique<TabSearchBubbleHost>( tab_strip_region_view_->GetTabSearchButton(), browser_.get(),
diff --git a/chrome/browser/ui/views/profiles/profile_picker_flow_controller.cc b/chrome/browser/ui/views/profiles/profile_picker_flow_controller.cc index db261804a..a7542d44 100644 --- a/chrome/browser/ui/views/profiles/profile_picker_flow_controller.cc +++ b/chrome/browser/ui/views/profiles/profile_picker_flow_controller.cc
@@ -12,7 +12,6 @@ #include "base/functional/callback_helpers.h" #include "base/functional/overloaded.h" #include "base/metrics/histogram_functions.h" -#include "base/not_fatal_until.h" #include "base/strings/utf_string_conversions.h" #include "base/trace_event/trace_event.h" #include "chrome/browser/browser_process.h" @@ -754,11 +753,11 @@ // TODO(crbug.com/40942098): Find a way to get the web contents without // relying on the weak ptr. web_contents = weak_signed_in_flow_controller_->contents(); - CHECK(web_contents, base::NotFatalUntil::M127); + CHECK(web_contents); } else { // TODO(crbug.com/40942098): Find another way to fetch the web contents. web_contents = GetSignedOutFlowWebContents(); - CHECK(web_contents, base::NotFatalUntil::M127); + CHECK(web_contents); } auto search_engine_choice_step_completed = base::BindOnce(
diff --git a/chrome/browser/ui/views/profiles/profile_picker_view.cc b/chrome/browser/ui/views/profiles/profile_picker_view.cc index f35dda9..c894f2d1 100644 --- a/chrome/browser/ui/views/profiles/profile_picker_view.cc +++ b/chrome/browser/ui/views/profiles/profile_picker_view.cc
@@ -463,7 +463,7 @@ if (!profile) { NOTREACHED() << "Local fail in creating new profile"; } - CHECK(!signin_util::IsForceSigninEnabled(), base::NotFatalUntil::M127); + CHECK(!signin_util::IsForceSigninEnabled()); // Apply a new color to the profile or use the default theme. // TODO(b/328587059): Share the theme color logic with the same code in
diff --git a/chrome/browser/ui/views/tabs/tab_strip.cc b/chrome/browser/ui/views/tabs/tab_strip.cc index d4a7ae4..dd9fcb0 100644 --- a/chrome/browser/ui/views/tabs/tab_strip.cc +++ b/chrome/browser/ui/views/tabs/tab_strip.cc
@@ -32,7 +32,6 @@ #include "base/metrics/histogram_functions.h" #include "base/metrics/histogram_macros.h" #include "base/metrics/user_metrics.h" -#include "base/not_fatal_until.h" #include "base/numerics/safe_conversions.h" #include "base/observer_list.h" #include "base/scoped_observation.h" @@ -313,9 +312,9 @@ } } - CHECK(!dragging_views.empty(), base::NotFatalUntil::M128) + CHECK(!dragging_views.empty()) << "Dragging views cannot be empty during drag initialization."; - CHECK(base::Contains(dragging_views, source), base::NotFatalUntil::M128) + CHECK(base::Contains(dragging_views, source)) << "Source must be part of dragging views."; // Delete the existing DragController before creating a new one. We do this @@ -325,8 +324,7 @@ CHECK((event.type() == ui::EventType::kMousePressed || event.type() == ui::EventType::kGestureTapDown || - event.type() == ui::EventType::kGestureScrollBegin), - base::NotFatalUntil::M128) + event.type() == ui::EventType::kGestureScrollBegin)) << "Event type must be suitable for starting a drag."; drag_controller_ = std::make_unique<TabDragController>(); @@ -421,10 +419,10 @@ void OwnDragController( std::unique_ptr<TabDragController> controller) override { - CHECK(controller, base::NotFatalUntil::M128) + CHECK(controller) << "The provided TabDragController is null, which is not expected."; - CHECK(!drag_controller_, base::NotFatalUntil::M128) + CHECK(!drag_controller_) << "Attempting to own a new drag controller while one already exists."; drag_controller_ = std::move(controller); @@ -540,8 +538,7 @@ std::vector<gfx::Rect> CalculateBoundsForDraggedViews( const std::vector<TabSlotView*>& views) override { - CHECK(!views.empty(), base::NotFatalUntil::M128) - << "The views vector must not be empty."; + CHECK(!views.empty()) << "The views vector must not be empty."; std::vector<gfx::Rect> bounds; const int overlap = TabStyle::Get()->GetTabOverlap(); @@ -557,10 +554,10 @@ void SetBoundsForDrag(const std::vector<TabSlotView*>& views, const std::vector<gfx::Rect>& bounds) override { - CHECK(!views.empty() || !bounds.empty(), base::NotFatalUntil::M128) + CHECK(!views.empty() || !bounds.empty()) << "Views and bounds cannot both be empty."; tab_strip_->tab_container_->CancelAnimation(); - CHECK_EQ(views.size(), bounds.size(), base::NotFatalUntil::M128) + CHECK_EQ(views.size(), bounds.size()) << "The sizes of views and bounds must match."; for (size_t i = 0; i < views.size(); ++i) { views[i]->SetBoundsRect(bounds[i]); @@ -594,12 +591,12 @@ // No tabs should be dragging at this point. for (int i = 0; i < GetTabCount(); ++i) { - CHECK(!GetTabAt(i)->dragging(), base::NotFatalUntil::M128) + CHECK(!GetTabAt(i)->dragging()) << "A tab is still marked as dragging when starting a new drag."; } for (TabSlotView* dragged_view : views) { - CHECK_NE(dragged_view->parent(), this, base::NotFatalUntil::M128); + CHECK_NE(dragged_view->parent(), this); AddChildViewRaw(dragged_view); dragged_view->set_dragging(true); if (TabGroupHeader* header = @@ -667,7 +664,7 @@ const gfx::Point& location, bool initial_drag) override { std::vector<gfx::Rect> bounds = CalculateBoundsForDraggedViews(views); - CHECK_EQ(views.size(), bounds.size(), base::NotFatalUntil::M128) + CHECK_EQ(views.size(), bounds.size()) << "The sizes of views and bounds must match in LayoutDraggedViewsAt."; // The index of `source_view` in the TabStrip's viewmodel. @@ -1166,7 +1163,7 @@ void TabStrip::MoveTab(int from_model_index, int to_model_index, TabRendererData data) { - CHECK_GT(GetTabCount(), 0, base::NotFatalUntil::M128) + CHECK_GT(GetTabCount(), 0) << "The tab strip must contain at least one tab to perform a move " "operation."; @@ -1188,8 +1185,7 @@ // OnTabWillBeRemoved should have ended any ongoing drags containing // `contents` already - unless the call is coming from inside the house! (i.e. // the TabDragController is doing the removing as part of reverting a drag) - CHECK(drag_context_->CanRemoveTabIfDragging(contents), - base::NotFatalUntil::M128) + CHECK(drag_context_->CanRemoveTabIfDragging(contents)) << "Attempted to remove a tab that could not be removed during drag."; tab_container_->RemoveTab(model_index, was_active); @@ -1371,7 +1367,7 @@ void TabStrip::SetSelection(const ui::ListSelectionModel& new_selection) { // This CHECK ensures there is always an active tab to maintain UI // consistency. - CHECK(new_selection.active().has_value(), base::NotFatalUntil::M128) + CHECK(new_selection.active().has_value()) << "We should never transition to a state where no tab is active."; Tab* const new_active_tab = tab_at(new_selection.active().value()); @@ -1842,9 +1838,7 @@ // Check that the source is either a valid tab or a tab group header, which // are the only valid drag targets. CHECK(GetModelIndexOf(source).has_value() || - source->GetTabSlotViewType() == - TabSlotView::ViewType::kTabGroupHeader, - base::NotFatalUntil::M128) + source->GetTabSlotViewType() == TabSlotView::ViewType::kTabGroupHeader) << "Drag source must be a valid tab or a tab group header."; drag_context_->MaybeStartDrag(source, event, original_selection); @@ -2079,7 +2073,7 @@ // TabStrip, views::View overrides: views::SizeBounds TabStrip::GetAvailableSize(const views::View* child) const { - CHECK(child == base::to_address(tab_container_), base::NotFatalUntil::M128) + CHECK(child == base::to_address(tab_container_)) << "The child view does not match the expected tab_container_ address."; return parent()->GetAvailableSize(this); } @@ -2326,7 +2320,7 @@ } void TabStrip::ShiftTabRelative(Tab* tab, int offset) { - CHECK_EQ(1, std::abs(offset), base::NotFatalUntil::M128) + CHECK_EQ(1, std::abs(offset)) << "Offset must be 1 or -1 to shift tab left or right."; const std::optional<int> maybe_start_index = GetModelIndexOf(tab); if (!maybe_start_index.has_value()) { @@ -2397,7 +2391,7 @@ void TabStrip::ShiftGroupRelative(const tab_groups::TabGroupId& group, int offset) { - CHECK_EQ(1, std::abs(offset), base::NotFatalUntil::M128) + CHECK_EQ(1, std::abs(offset)) << "Offset must be 1 or -1 to shift the group left or right."; gfx::Range tabs_in_group = controller_->ListTabsInGroup(group); @@ -2443,8 +2437,7 @@ ui::mojom::MenuSourceType source_type) { // We are only intended to be installed as a context-menu handler for tabs, so // this cast should be safe. - CHECK(views::IsViewClass<Tab>(source), base::NotFatalUntil::M128) - << "The source must be a Tab class."; + CHECK(views::IsViewClass<Tab>(source)) << "The source must be a Tab class."; Tab* const tab = static_cast<Tab*>(source); if (tab->closing()) { return;
diff --git a/chrome/browser/ui/views/toolbar/webui_tab_counter_button_browsertest.cc b/chrome/browser/ui/views/toolbar/webui_tab_counter_button_browsertest.cc new file mode 100644 index 0000000..4eab4443 --- /dev/null +++ b/chrome/browser/ui/views/toolbar/webui_tab_counter_button_browsertest.cc
@@ -0,0 +1,24 @@ +// Copyright 2020 The Chromium Authors +// 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/toolbar/webui_tab_counter_button.h" + +#include "chrome/browser/ui/browser_tabstrip.h" +#include "chrome/browser/ui/browser_window.h" +#include "chrome/browser/ui/views/frame/browser_view.h" +#include "chrome/test/base/in_process_browser_test.h" +#include "content/public/test/browser_test.h" +#include "testing/gtest/include/gtest/gtest.h" +#include "ui/views/controls/button/button.h" +#include "ui/views/view.h" + +using WebUITabCounterButtonTest = InProcessBrowserTest; + +IN_PROC_BROWSER_TEST_F(WebUITabCounterButtonTest, CheckFocusBehavior) { + auto button = CreateWebUITabCounterButton( + views::Button::PressedCallback(), + BrowserView::GetBrowserViewForBrowser(browser())); + EXPECT_EQ(button->GetFocusBehavior(), + views::View::FocusBehavior::ACCESSIBLE_ONLY); +}
diff --git a/chrome/browser/ui/views/toolbar/webui_tab_counter_button_unittest.cc b/chrome/browser/ui/views/toolbar/webui_tab_counter_button_unittest.cc deleted file mode 100644 index 1096d4a4..0000000 --- a/chrome/browser/ui/views/toolbar/webui_tab_counter_button_unittest.cc +++ /dev/null
@@ -1,20 +0,0 @@ -// Copyright 2020 The Chromium Authors -// 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/toolbar/webui_tab_counter_button.h" - -#include "chrome/browser/ui/views/frame/browser_view.h" -#include "chrome/browser/ui/views/frame/test_with_browser_view.h" -#include "testing/gtest/include/gtest/gtest.h" -#include "ui/views/controls/button/button.h" -#include "ui/views/view.h" - -using WebUITabCounterButtonTest = TestWithBrowserView; - -TEST_F(WebUITabCounterButtonTest, CheckFocusBehavior) { - auto button = CreateWebUITabCounterButton(views::Button::PressedCallback(), - browser_view()); - EXPECT_EQ(views::View::FocusBehavior::ACCESSIBLE_ONLY, - button->GetFocusBehavior()); -}
diff --git a/chrome/browser/ui/views/user_education/recent_session_observer_impl_unittest.cc b/chrome/browser/ui/views/user_education/recent_session_observer_impl_browsertest.cc similarity index 82% rename from chrome/browser/ui/views/user_education/recent_session_observer_impl_unittest.cc rename to chrome/browser/ui/views/user_education/recent_session_observer_impl_browsertest.cc index bf0c37a..4d57bc65 100644 --- a/chrome/browser/ui/views/user_education/recent_session_observer_impl_unittest.cc +++ b/chrome/browser/ui/views/user_education/recent_session_observer_impl_browsertest.cc
@@ -10,10 +10,11 @@ #include "base/callback_list.h" #include "base/functional/callback_forward.h" #include "base/memory/raw_ptr.h" +#include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/user_education/recent_session_policy.h" -#include "chrome/browser/ui/views/frame/browser_view.h" -#include "chrome/browser/ui/views/frame/test_with_browser_view.h" #include "chrome/browser/user_education/browser_user_education_storage_service.h" +#include "chrome/test/base/in_process_browser_test.h" +#include "content/public/test/browser_test.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" #include "ui/base/interaction/expect_call_in_scope.h" @@ -37,10 +38,10 @@ } // namespace -class RecentSessionObserverImplTest : public TestWithBrowserView { +class RecentSessionObserverImplBrowserTest : public InProcessBrowserTest { public: - RecentSessionObserverImplTest() = default; - ~RecentSessionObserverImplTest() override = default; + RecentSessionObserverImplBrowserTest() = default; + ~RecentSessionObserverImplBrowserTest() override = default; static void SendUpdate(RecentSessionObserverImpl& observer, const RecentSessionData& data) { @@ -48,12 +49,13 @@ } }; -TEST_F(RecentSessionObserverImplTest, OnRecentSessionsUpdated) { +IN_PROC_BROWSER_TEST_F(RecentSessionObserverImplBrowserTest, + OnRecentSessionsUpdated) { auto policy_ptr = std::make_unique<testing::StrictMock<MockRecentSessionPolicy>>(); auto& policy = *policy_ptr; const auto observer = std::make_unique<RecentSessionObserverImpl>( - *browser_view()->GetProfile(), std::move(policy_ptr)); + *browser()->profile(), std::move(policy_ptr)); RecentSessionData data; @@ -63,13 +65,13 @@ SendUpdate(*observer, data); } -TEST_F(RecentSessionObserverImplTest, SessionCallback) { +IN_PROC_BROWSER_TEST_F(RecentSessionObserverImplBrowserTest, SessionCallback) { UNCALLED_MOCK_CALLBACK(base::RepeatingClosure, callback); auto policy_ptr = std::make_unique<testing::StrictMock<MockRecentSessionPolicy>>(); auto& policy = *policy_ptr; const auto observer = std::make_unique<RecentSessionObserverImpl>( - *browser_view()->GetProfile(), std::move(policy_ptr)); + *browser()->profile(), std::move(policy_ptr)); const auto subscription = observer->AddLowUsageSessionCallback(callback.Get()); @@ -88,13 +90,14 @@ EXPECT_CALL_IN_SCOPE(callback, Run, SendUpdate(*observer, data)); } -TEST_F(RecentSessionObserverImplTest, SessionCallbackOnObserve) { +IN_PROC_BROWSER_TEST_F(RecentSessionObserverImplBrowserTest, + SessionCallbackOnObserve) { UNCALLED_MOCK_CALLBACK(base::RepeatingClosure, callback); auto policy_ptr = std::make_unique<testing::StrictMock<MockRecentSessionPolicy>>(); auto& policy = *policy_ptr; const auto observer = std::make_unique<RecentSessionObserverImpl>( - *browser_view()->GetProfile(), std::move(policy_ptr)); + *browser()->profile(), std::move(policy_ptr)); RecentSessionData data;
diff --git a/chrome/browser/ui/views/webauthn/authenticator_qr_centered_view.cc b/chrome/browser/ui/views/webauthn/authenticator_qr_centered_view.cc index 5a8bcba5..5378cb8 100644 --- a/chrome/browser/ui/views/webauthn/authenticator_qr_centered_view.cc +++ b/chrome/browser/ui/views/webauthn/authenticator_qr_centered_view.cc
@@ -10,7 +10,6 @@ #include "base/check.h" #include "base/containers/span.h" #include "base/memory/raw_ptr.h" -#include "base/not_fatal_until.h" #include "chrome/browser/ui/color/chrome_color_id.h" #include "chrome/grit/generated_resources.h" #include "components/qr_code_generator/bitmap_generator.h" @@ -63,7 +62,7 @@ // Success is guaranteed, because `qr_string`'s size is bounded and smaller // than QR code limits. - CHECK(qr_code.has_value(), base::NotFatalUntil::M124); + CHECK(qr_code.has_value()); qr_code_image_->SetImage(ui::ImageModel::FromImageSkia(qr_code.value())); qr_code_image_->SetVisible(true);
diff --git a/chrome/browser/web_applications/commands/set_user_display_mode_command.cc b/chrome/browser/web_applications/commands/set_user_display_mode_command.cc index 93ddf2ef..ff157b4c 100644 --- a/chrome/browser/web_applications/commands/set_user_display_mode_command.cc +++ b/chrome/browser/web_applications/commands/set_user_display_mode_command.cc
@@ -9,7 +9,6 @@ #include "base/functional/callback.h" #include "base/metrics/user_metrics.h" -#include "base/not_fatal_until.h" #include "base/values.h" #include "chrome/browser/web_applications/commands/web_app_command.h" #include "chrome/browser/web_applications/locks/app_lock.h" @@ -112,7 +111,7 @@ { ScopedRegistryUpdate update = resources.sync_bridge().BeginUpdate(); WebApp* web_app = update->UpdateApp(app_id); - CHECK(web_app, base::NotFatalUntil::M127); + CHECK(web_app); if (web_app) { web_app->SetUserDisplayMode(user_display_mode); if (needs_os_integration_sync) {
diff --git a/chrome/browser/web_applications/web_app.cc b/chrome/browser/web_applications/web_app.cc index fe23383..55a4fe7 100644 --- a/chrome/browser/web_applications/web_app.cc +++ b/chrome/browser/web_applications/web_app.cc
@@ -692,7 +692,7 @@ void WebApp::SetSyncProto(sync_pb::WebAppSpecifics sync_proto) { // Populate sync_proto's start_url from this WebApp if missing. if (!start_url().is_empty()) { - CHECK(start_url().is_valid(), base::NotFatalUntil::M126); + CHECK(start_url().is_valid()); // Note: sync data may have a start_url that does not match the `WebApp` // start_url, but it does not update the app (matching pre-M125 behaviour). if (!sync_proto.has_start_url()) { @@ -701,11 +701,10 @@ } // Sync data must never be set on an app with mismatching manifest_id. - CHECK(manifest_id().is_valid(), base::NotFatalUntil::M126); + CHECK(manifest_id().is_valid()); std::string relative_manifest_id_path = RelativeManifestIdPath(manifest_id()); if (sync_proto.has_relative_manifest_id()) { - CHECK_EQ(sync_proto.relative_manifest_id(), relative_manifest_id_path, - base::NotFatalUntil::M127); + CHECK_EQ(sync_proto.relative_manifest_id(), relative_manifest_id_path); } else { sync_proto.set_relative_manifest_id(relative_manifest_id_path); } @@ -750,7 +749,7 @@ CHECK(manifest_id.is_valid()); CHECK(start_url_.is_empty() || url::IsSameOriginWith(start_url_, manifest_id)) << start_url_.spec() << " vs " << manifest_id.spec(); - CHECK(!manifest_id.has_ref(), base::NotFatalUntil::M127); + CHECK(!manifest_id.has_ref()); manifest_id_ = manifest_id; // Ensure sync proto is initialized and remains consistent. Logic in
diff --git a/chrome/browser/web_applications/web_app.h b/chrome/browser/web_applications/web_app.h index 2e76fa4..32757035 100644 --- a/chrome/browser/web_applications/web_app.h +++ b/chrome/browser/web_applications/web_app.h
@@ -15,7 +15,6 @@ #include "base/containers/flat_map.h" #include "base/containers/flat_set.h" -#include "base/not_fatal_until.h" #include "base/time/time.h" #include "base/values.h" #include "base/version.h" @@ -258,9 +257,9 @@ // wins. const sync_pb::WebAppSpecifics& sync_proto() const { // Ensure the sync proto has been initialized. - CHECK(sync_proto_.has_start_url(), base::NotFatalUntil::M126); - CHECK(GURL(sync_proto_.start_url()).is_valid(), base::NotFatalUntil::M126); - CHECK(sync_proto_.has_relative_manifest_id(), base::NotFatalUntil::M126); + CHECK(sync_proto_.has_start_url()); + CHECK(GURL(sync_proto_.start_url()).is_valid()); + CHECK(sync_proto_.has_relative_manifest_id()); return sync_proto_; }
diff --git a/chrome/browser/web_applications/web_app_install_finalizer.cc b/chrome/browser/web_applications/web_app_install_finalizer.cc index 5252282..caaa134 100644 --- a/chrome/browser/web_applications/web_app_install_finalizer.cc +++ b/chrome/browser/web_applications/web_app_install_finalizer.cc
@@ -19,7 +19,6 @@ #include "base/logging.h" #include "base/metrics/histogram_functions.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/notreached.h" #include "base/strings/utf_string_conversions.h" #include "base/task/sequenced_task_runner.h" @@ -144,8 +143,7 @@ } // Guaranteed by EnsureAppsHaveUserDisplayModeForCurrentPlatform(). - CHECK(web_app.sync_proto().has_user_display_mode_cros(), - base::NotFatalUntil::M125); + CHECK(web_app.sync_proto().has_user_display_mode_cros()); // Don't mitigate installations from sync, this is only for installs that will // be newly uploaded to sync.
diff --git a/chrome/browser/web_applications/web_app_install_info.cc b/chrome/browser/web_applications/web_app_install_info.cc index 99f9b90..378694d1 100644 --- a/chrome/browser/web_applications/web_app_install_info.cc +++ b/chrome/browser/web_applications/web_app_install_info.cc
@@ -12,7 +12,6 @@ #include "base/check.h" #include "base/check_is_test.h" #include "base/containers/flat_tree.h" -#include "base/not_fatal_until.h" #include "base/strings/to_string.h" #include "base/strings/utf_string_conversions.h" #include "base/trace_event/trace_event.h" @@ -379,12 +378,11 @@ namespace { void CheckValidManifestIdAndStartUrl(const webapps::ManifestId& manifest_id, const GURL& start_url) { - CHECK(manifest_id.is_valid(), base::NotFatalUntil::M129); - CHECK(!manifest_id.has_ref(), base::NotFatalUntil::M129); - CHECK(start_url.is_valid(), base::NotFatalUntil::M129); + CHECK(manifest_id.is_valid()); + CHECK(!manifest_id.has_ref()); + CHECK(start_url.is_valid()); CHECK(url::Origin::Create(start_url).IsSameOriginWith( - url::Origin::Create(manifest_id)), - base::NotFatalUntil::M129); + url::Origin::Create(manifest_id))); } } // namespace
diff --git a/chrome/browser/web_applications/web_app_install_utils.cc b/chrome/browser/web_applications/web_app_install_utils.cc index d2c66a70..1f7194f 100644 --- a/chrome/browser/web_applications/web_app_install_utils.cc +++ b/chrome/browser/web_applications/web_app_install_utils.cc
@@ -31,7 +31,6 @@ #include "base/metrics/histogram.h" #include "base/metrics/histogram_base.h" #include "base/metrics/histogram_functions.h" -#include "base/not_fatal_until.h" #include "base/notreached.h" #include "base/strings/utf_string_conversions.h" #include "base/time/time.h" @@ -1136,8 +1135,8 @@ sync_pb::WebAppSpecifics sync_proto = web_app.sync_proto(); // Sync proto has already been initialized by setting the start_url and/or // manifest_id above. - CHECK(sync_proto.has_start_url(), base::NotFatalUntil::M126); - CHECK(sync_proto.has_relative_manifest_id(), base::NotFatalUntil::M126); + CHECK(sync_proto.has_start_url()); + CHECK(sync_proto.has_relative_manifest_id()); sync_proto.set_name(base::UTF16ToUTF8(web_app_info.title)); sync_proto.clear_theme_color(); if (web_app_info.theme_color.has_value()) {
diff --git a/chrome/browser/web_applications/web_app_proto_utils.cc b/chrome/browser/web_applications/web_app_proto_utils.cc index f8e29cb7..0e9c4c9f 100644 --- a/chrome/browser/web_applications/web_app_proto_utils.cc +++ b/chrome/browser/web_applications/web_app_proto_utils.cc
@@ -3,7 +3,6 @@ // found in the LICENSE file. #include "chrome/browser/web_applications/web_app_proto_utils.h" -#include "base/not_fatal_until.h" #include "base/strings/utf_string_conversions.h" #include "chrome/browser/web_applications/mojom/user_display_mode.mojom.h" #include "chrome/browser/web_applications/proto/web_app_url_pattern.pb.h" @@ -399,7 +398,7 @@ } std::string RelativeManifestIdPath(webapps::ManifestId manifest_id) { - CHECK(manifest_id.is_valid(), base::NotFatalUntil::M127); + CHECK(manifest_id.is_valid()); // The relative id does not include the initial '/' character. std::string relative_manifest_id_path = manifest_id.PathForRequest(); if (relative_manifest_id_path.starts_with("/")) {
diff --git a/chrome/browser/web_applications/web_app_sync_bridge.cc b/chrome/browser/web_applications/web_app_sync_bridge.cc index 4bd79be..86f22cd6 100644 --- a/chrome/browser/web_applications/web_app_sync_bridge.cc +++ b/chrome/browser/web_applications/web_app_sync_bridge.cc
@@ -25,7 +25,6 @@ #include "base/functional/callback_helpers.h" #include "base/logging.h" #include "base/metrics/histogram_functions.h" -#include "base/not_fatal_until.h" #include "base/strings/to_string.h" #include "base/types/expected.h" #include "base/types/pass_key.h" @@ -370,7 +369,7 @@ void WebAppSyncBridge::SetUserPageOrdinal(const webapps::AppId& app_id, syncer::StringOrdinal page_ordinal) { - CHECK(page_ordinal.IsValid(), base::NotFatalUntil::M126); + CHECK(page_ordinal.IsValid()); ScopedRegistryUpdate update = BeginUpdate(); WebApp* web_app = update->UpdateApp(app_id); // Due to the extensions sync system setting ordinals on sync, this can get @@ -390,7 +389,7 @@ void WebAppSyncBridge::SetUserLaunchOrdinal( const webapps::AppId& app_id, syncer::StringOrdinal launch_ordinal) { - CHECK(launch_ordinal.IsValid(), base::NotFatalUntil::M126); + CHECK(launch_ordinal.IsValid()); ScopedRegistryUpdate update = BeginUpdate(); // Due to the extensions sync system setting ordinals on sync, this can get // called before the app is installed in the web apps system. Until apps are @@ -523,7 +522,7 @@ } for (const webapps::AppId& app_id : update_data->apps_to_delete) { auto it = registrar_->registry().find(app_id); - CHECK(it != registrar_->registry().end(), base::NotFatalUntil::M130); + CHECK(it != registrar_->registry().end()); registrar_->registry().erase(it); } } @@ -542,7 +541,7 @@ for (const std::unique_ptr<WebApp>& new_app : update_data.apps_to_create) { if (new_app->IsSynced()) { - CHECK(new_app->manifest_id().is_valid(), base::NotFatalUntil::M125); + CHECK(new_app->manifest_id().is_valid()); change_processor()->Put(new_app->app_id(), CreateSyncEntityData(*new_app), metadata_change_list); } @@ -558,7 +557,7 @@ // the app if IsSynced flag stays true. Exclude the app from the sync "view" // if IsSynced flag becomes false. if (new_state->IsSynced()) { - CHECK(new_state->manifest_id().is_valid(), base::NotFatalUntil::M125); + CHECK(new_state->manifest_id().is_valid()); // Only call 'Put' if it wasn't synced, or if the sync data has changed. // TODO(https://crbug.com/409867622): We can remove this optimization // after tests are updated to use a Fake version instead of the Mock @@ -917,12 +916,12 @@ std::string WebAppSyncBridge::GetClientTag( const syncer::EntityData& entity_data) const { - CHECK(entity_data.specifics.has_web_app(), base::NotFatalUntil::M125); + CHECK(entity_data.specifics.has_web_app()); base::expected<webapps::ManifestId, StorageKeyParseResult> manifest_id = ParseManifestIdFromSyncEntity(entity_data.specifics.web_app()); // This is guaranteed to be true, as the contract for this function is that // IsEntityDataValid must be true. - CHECK(manifest_id.has_value(), base::NotFatalUntil::M125); + CHECK(manifest_id.has_value()); return GenerateAppIdFromManifestId(manifest_id.value()); }
diff --git a/chrome/build/android-arm32.pgo.txt b/chrome/build/android-arm32.pgo.txt index e27ee5e..bcb266f 100644 --- a/chrome/build/android-arm32.pgo.txt +++ b/chrome/build/android-arm32.pgo.txt
@@ -1 +1 @@ -chrome-android32-main-1748260543-a570212d6c379a3f0bef0b7704e763912f3d2600-436cf5a446bcda10aa2bc655f57ce243f534330d.profdata +chrome-android32-main-1748281879-f6307920645d7c967935982bdcc31bd8d8219885-45948ebd114566ec45402d34c635daf1833726d9.profdata
diff --git a/chrome/build/android-arm64.pgo.txt b/chrome/build/android-arm64.pgo.txt index 433ae64..766cf05 100644 --- a/chrome/build/android-arm64.pgo.txt +++ b/chrome/build/android-arm64.pgo.txt
@@ -1 +1 @@ -chrome-android64-main-1748263541-59195261a4aeb4cce5b3c4648602558b3b74a52b-59dd52af4a9d415e1daf1c0fb3e6c29c57203361.profdata +chrome-android64-main-1748285041-8d50d17d839af992aa35ba597047910cf9e0c3fd-def4aa84cb21b505f52ce398a3a29962094a23a7.profdata
diff --git a/chrome/build/linux.pgo.txt b/chrome/build/linux.pgo.txt index 81f68c1..34a6d03 100644 --- a/chrome/build/linux.pgo.txt +++ b/chrome/build/linux.pgo.txt
@@ -1 +1 @@ -chrome-linux-main-1748260543-125c386337e2dbc00eb2263d09a9eb017bef0a64-436cf5a446bcda10aa2bc655f57ce243f534330d.profdata +chrome-linux-main-1748281879-7667e8e2fd64748ae4601eb3058cede98a5f150a-45948ebd114566ec45402d34c635daf1833726d9.profdata
diff --git a/chrome/build/mac-arm.pgo.txt b/chrome/build/mac-arm.pgo.txt index 13bacf87..75121aa 100644 --- a/chrome/build/mac-arm.pgo.txt +++ b/chrome/build/mac-arm.pgo.txt
@@ -1 +1 @@ -chrome-mac-arm-main-1748267682-dae69aa8d12b9a0e606d9e80c6448940324f75ea-222fa6a40d583aab260429585088a0469723108d.profdata +chrome-mac-arm-main-1748289504-5a78a4991f4bf92a93cc7a2ae35d8d605fad4c17-532a20f725c527d371febeefac67f20014f514b2.profdata
diff --git a/chrome/build/mac.pgo.txt b/chrome/build/mac.pgo.txt index b2a0ab5..612627e 100644 --- a/chrome/build/mac.pgo.txt +++ b/chrome/build/mac.pgo.txt
@@ -1 +1 @@ -chrome-mac-main-1748260543-8fcd83f27ccf8087ec2ee3b48213aced51434d62-436cf5a446bcda10aa2bc655f57ce243f534330d.profdata +chrome-mac-main-1748281879-ccab29a8196a7d38897915fe44e0ad7ab0166168-45948ebd114566ec45402d34c635daf1833726d9.profdata
diff --git a/chrome/build/win-arm64.pgo.txt b/chrome/build/win-arm64.pgo.txt index 5f0a53d..400fca3 100644 --- a/chrome/build/win-arm64.pgo.txt +++ b/chrome/build/win-arm64.pgo.txt
@@ -1 +1 @@ -chrome-win-arm64-main-1748260543-e2b99b128af326ae056c0fda7dd938c61152b77f-436cf5a446bcda10aa2bc655f57ce243f534330d.profdata +chrome-win-arm64-main-1748281879-71ed81f464062b9e978f33a4c510be0f8ed3fb60-45948ebd114566ec45402d34c635daf1833726d9.profdata
diff --git a/chrome/build/win32.pgo.txt b/chrome/build/win32.pgo.txt index 25da11b3..88c342d 100644 --- a/chrome/build/win32.pgo.txt +++ b/chrome/build/win32.pgo.txt
@@ -1 +1 @@ -chrome-win32-main-1748249926-c5c67c4fb659007438429c3f05a9a626a09b1eee-50eafedd2577ddad80c88efdcc91b0f46b3325f7.profdata +chrome-win32-main-1748260543-369d748d0e83b5094a87f8601251a6774bf4ba8b-436cf5a446bcda10aa2bc655f57ce243f534330d.profdata
diff --git a/chrome/build/win64.pgo.txt b/chrome/build/win64.pgo.txt index 3adf13c..54a9015 100644 --- a/chrome/build/win64.pgo.txt +++ b/chrome/build/win64.pgo.txt
@@ -1 +1 @@ -chrome-win64-main-1748238035-71c35c1b355083c736b11be97d6a2914c42ec1e8-418ce0257f6ebe8f9a141d27ee77e7f0e38cc2cb.profdata +chrome-win64-main-1748260543-1b8a25b0391224b1b4bf93020837290e05fc6b4c-436cf5a446bcda10aa2bc655f57ce243f534330d.profdata
diff --git a/chrome/common/actor.mojom b/chrome/common/actor.mojom index d97588a..ede0704 100644 --- a/chrome/common/actor.mojom +++ b/chrome/common/actor.mojom
@@ -173,6 +173,9 @@ // Arguments supplied to the tool are invalid. kArgumentsInvalid = 22, + // The task for the action was paused. + kTaskPaused = 23, + /////////////////////////////////////////////////////////////////////// // Codes 100-199: Errors for navigation. (Not part of the ToolAction union // as it's a browser-side tool.)
diff --git a/chrome/common/chrome_features.cc b/chrome/common/chrome_features.cc index 4c21e30..7a97160 100644 --- a/chrome/common/chrome_features.cc +++ b/chrome/common/chrome_features.cc
@@ -328,7 +328,7 @@ BASE_FEATURE(kGeoLanguage, "GeoLanguage", base::FEATURE_DISABLED_BY_DEFAULT); // Controls whether the actor component of Glic is enabled. -BASE_FEATURE(kGlicActor, "GlicActor", base::FEATURE_ENABLED_BY_DEFAULT); +BASE_FEATURE(kGlicActor, "GlicActor", base::FEATURE_DISABLED_BY_DEFAULT); const base::FeatureParam<base::TimeDelta> kGlicActorActorObservationDelay{ &kGlicActor, "glic-actor-observation-delay", base::Seconds(3)}; @@ -423,6 +423,11 @@ "glic-user-status-oauth2-scope", "https://www.googleapis.com/auth/gemini"); +BASE_FEATURE_PARAM(double, + kGlicUserStatusRequestDelayJitter, + &kGlicUserStatusCheck, + "glic-user-status-request-delay-jitter", + 0.005); BASE_FEATURE(kGlicFreURLConfig, "GlicFreURLConfig", base::FEATURE_DISABLED_BY_DEFAULT);
diff --git a/chrome/common/chrome_features.h b/chrome/common/chrome_features.h index 2adec6ec..7437532 100644 --- a/chrome/common/chrome_features.h +++ b/chrome/common/chrome_features.h
@@ -236,6 +236,10 @@ extern const base::FeatureParam<base::TimeDelta> kGlicUserStatusRequestDelay; COMPONENT_EXPORT(CHROME_FEATURES) extern const base::FeatureParam<std::string> kGeminiOAuth2Scope; +COMPONENT_EXPORT(CHROME_FEATURES) +// This is the maximum deviation. The jitter to the delay is a uniformly random +// sample from the chosen deviation. The value should be less than 1. +extern const base::FeatureParam<double> kGlicUserStatusRequestDelayJitter; COMPONENT_EXPORT(CHROME_FEATURES) BASE_DECLARE_FEATURE(kGlicFreURLConfig); COMPONENT_EXPORT(CHROME_FEATURES)
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn index 09cc75b3..936b931 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn
@@ -4503,6 +4503,7 @@ "../browser/supervised_user/desktop/supervised_user_extension_browsertest.cc", "../browser/supervised_user/extensions_interactive_uitest.cc", "../browser/ui/views/autofill/popup/custom_cursor_suppressor_browsertest.cc", + "../browser/ui/views/user_education/recent_session_observer_impl_browsertest.cc", "../browser/ui/views/web_apps/create_shortcut_confirmation_view_browsertest.cc", "../browser/ui/views/web_apps/simple_install_dialog_bubble_view_browsertest.cc", "../browser/ui/views/web_apps/web_app_identity_update_confirmation_view_browsertest.cc", @@ -4589,10 +4590,6 @@ ] } - if (enterprise_client_certificates) { - sources += [ "../browser/enterprise/client_certificates/client_certificates_browsertest.cc" ] - } - if (is_win || is_linux || is_mac) { deps += [ "//chrome/browser/enterprise/connectors/device_trust/key_management/browser/commands:test_support", @@ -5629,6 +5626,7 @@ if (enable_webui_tab_strip) { sources += [ "../browser/ui/views/frame/webui_tab_strip_field_trial_browsertest.cc", + "../browser/ui/views/toolbar/webui_tab_counter_button_browsertest.cc", "../browser/ui/webui/tab_strip/tab_strip_ui_browsertest.cc", ] } @@ -6492,7 +6490,6 @@ if (enable_webui_tab_strip) { sources += [ "../browser/ui/views/frame/webui_tab_strip_container_view_unittest.cc", - "../browser/ui/views/toolbar/webui_tab_counter_button_unittest.cc", "../browser/ui/webui/tab_strip/tab_strip_page_handler_unittest.cc", "../browser/ui/webui/tab_strip/tab_strip_ui_layout_unittest.cc", "../browser/ui/webui/tab_strip/thumbnail_tracker_unittest.cc", @@ -10279,7 +10276,6 @@ "../browser/ui/views/translate/translate_bubble_view_unittest.cc", "../browser/ui/views/user_education/browser_user_education_service_unittest.cc", "../browser/ui/views/user_education/help_bubble_view_timeout_unittest.cc", - "../browser/ui/views/user_education/recent_session_observer_impl_unittest.cc", "../browser/ui/views/user_education/views_tutorial_unittest.cc", "../browser/ui/views/web_apps/isolated_web_apps/callback_delayer_unittest.cc", "../browser/ui/views/web_apps/isolated_web_apps/isolated_web_app_installer_view_controller_unittest.cc",
diff --git a/chromeos/ash/services/network_config/cros_network_config.cc b/chromeos/ash/services/network_config/cros_network_config.cc index df098c2..63fe78c 100644 --- a/chromeos/ash/services/network_config/cros_network_config.cc +++ b/chromeos/ash/services/network_config/cros_network_config.cc
@@ -15,7 +15,6 @@ #include "base/containers/flat_map.h" #include "base/i18n/time_formatting.h" #include "base/metrics/histogram_functions.h" -#include "base/not_fatal_until.h" #include "base/strings/string_number_conversions.h" #include "base/strings/string_split.h" #include "base/strings/string_util.h" @@ -673,8 +672,7 @@ std::string GetRequiredString(const base::Value::Dict* dict, const char* key) { const base::Value* v = dict->Find(key); if (!v) { - NOTREACHED(base::NotFatalUntil::M127) << "Required key missing: " << key; - return std::string(); + NOTREACHED() << "Required key missing: " << key; } if (!v->is_string()) { NET_LOG(ERROR) << "Expected string, found: " << *v;
diff --git a/clank b/clank index c6f37b2..7b3b668 160000 --- a/clank +++ b/clank
@@ -1 +1 @@ -Subproject commit c6f37b2a1ac4f90393eff3c734ca926a8e602153 +Subproject commit 7b3b66843fe0c37489709a09bf6e4c57c6087f53
diff --git a/components/BUILD.gn b/components/BUILD.gn index 51f59a7c..6eb0b602 100644 --- a/components/BUILD.gn +++ b/components/BUILD.gn
@@ -8,6 +8,7 @@ import("//build/config/ui.gni") import("//components/compose/features.gni") import("//components/enterprise/buildflags/buildflags.gni") +import("//components/guest_contents/common/buildflags.gni") import("//components/guest_view/buildflags/buildflags.gni") import("//components/nacl/features.gni") import("//components/optimization_guide/features.gni") @@ -726,6 +727,10 @@ ] } + if (enable_guest_contents) { + deps += [ "//components/guest_contents/browser:unit_tests" ] + } + if (enable_guest_view) { deps += [ "//components/guest_view/browser:unit_tests" ] } @@ -1233,6 +1238,7 @@ "autofill/core/browser/ml_model/field_classification_model_executor_perftest.cc", "discardable_memory/common/discardable_shared_memory_heap_perftest.cc", "omnibox/browser/history_quick_provider_performance_unittest.cc", + "persistent_cache/persistent_cache_perftest.cc", "subresource_filter/core/common/perftests/indexed_ruleset_perftest.cc", "test/run_all_perftests.cc", "visitedlink/test/visitedlink_perftest.cc", @@ -1248,6 +1254,8 @@ "//components/history/core/test", "//components/omnibox/browser", "//components/omnibox/browser:test_support", + "//components/persistent_cache", + "//components/persistent_cache:test_support", "//components/subresource_filter/core/common", "//components/subresource_filter/tools:tools_lib", "//components/test:test_support",
diff --git a/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.cc b/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.cc index 080b7c3f..e0f316f 100644 --- a/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.cc +++ b/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.cc
@@ -18,6 +18,8 @@ #include "components/autofill/core/browser/autofill_field.h" #include "components/autofill/core/browser/crowdsourcing/disambiguate_possible_field_types.h" #include "components/autofill/core/browser/data_model/addresses/address.h" +#include "components/autofill/core/browser/data_model/addresses/autofill_profile_comparator.h" +#include "components/autofill/core/browser/data_model/autofill_ai/entity_instance.h" #include "components/autofill/core/browser/data_model/data_model_utils.h" #include "components/autofill/core/browser/data_model/payments/credit_card.h" #include "components/autofill/core/browser/data_model/valuables/loyalty_card.h" @@ -34,6 +36,31 @@ namespace { +// Matches a date consisting of year, month, and day in a the given string. +std::vector<std::u16string> GetMatchingCompleteDateFormats( + std::u16string_view date) { + std::vector<std::u16string> format_strings; + for (std::u16string_view format : + {// Ordering: year month day. + u"YYYY*MM*DD", u"YY*MM*DD", u"YYYY+M+D", u"YY+M+D", + // Ordering: month day year. + u"MM*DD*YYYY", u"MM*DD*YY", u"M+D+YYYY", u"M+D+YY", + // Ordering: day month year. + u"DD*MM*YYYY", u"DD*MM*YY", u"D+M+YYYY", u"D+M+YY"}) { + data_util::Date result; + const char16_t* separator = nullptr; + if (data_util::ParseDate(date, format, result, separator) && + data_util::IsValidDateForFormat(result, format)) { + std::u16string instantiated_format; + base::ReplaceChars(format, u"*+", separator, &instantiated_format); + if (data_util::ParseDate(date, instantiated_format, result)) { + format_strings.push_back(instantiated_format); + } + } + } + return format_strings; +} + // Finds the first field in |form_structure| with |field.value|=|value|. AutofillField* FindFirstFieldWithValue(const FormStructure& form_structure, std::u16string_view value) { @@ -132,6 +159,88 @@ return HeuristicallyFindCVCFieldForUpload(form_structure); } +// Returns the FieldTypes for some given EntityInstance defines a non-empty +// value. +// +// This may not just include Autofill AI types like PASSPORT_NUMBER but +// also tag types like PASSPORT_NAME_TAG together with the refined type like +// NAME_FIRST. +FieldTypeSet GetAvailableAutofillAiFieldTypes( + base::span<const EntityInstance> entities, + const std::string& app_locale) { + CHECK(base::FeatureList::IsEnabled(features::kAutofillAiWithDataSchema)); + AutofillProfileComparator comparator(app_locale); + FieldTypeSet types; + for (const EntityInstance& entity : entities) { + for (const AttributeInstance& attribute : entity.attributes()) { + for (FieldType field_type : attribute.GetSupportedTypes()) { + bool is_empty = comparator.HasOnlySkippableCharacters(attribute.GetInfo( + field_type, comparator.app_locale(), std::nullopt)); + if (!is_empty) { + types.insert(attribute.type().field_type()); + types.insert(field_type); + } + } + } + } + return types; +} + +// Returns the FieldTypes for some given EntityInstance has an attribute whose +// value matches `value_u16`. +// +// This may not just include Autofill AI types like PASSPORT_NUMBER but +// also tag types like PASSPORT_NAME_TAG together with the refined type like +// NAME_FIRST. +FieldTypeSet GetPossibleAutofillAiFieldTypes( + base::span<const EntityInstance> entities, + std::u16string_view value_u16, + const std::string& app_locale) { + CHECK(base::FeatureList::IsEnabled(features::kAutofillAiWithDataSchema)); + + AutofillProfileComparator comparator(app_locale); + if (comparator.HasOnlySkippableCharacters(value_u16)) { + return {}; + } + + std::u16string value = + AutofillProfileComparator::NormalizeForComparison(value_u16); + + auto date_matches = [&comparator, &value](const AttributeInstance& attribute, + FieldType field_type) { + return std::ranges::any_of(GetMatchingCompleteDateFormats(value), + [&](const std::u16string& format) { + return attribute.GetInfo( + field_type, comparator.app_locale(), + format) == value; + }); + }; + + auto nondate_matches = [&comparator, &value]( + const AttributeInstance& attribute, + FieldType field_type) { + return comparator.Compare( + value, + attribute.GetInfo(field_type, comparator.app_locale(), std::nullopt), + AutofillProfileComparator::DISCARD_WHITESPACE); + }; + + FieldTypeSet types; + for (const EntityInstance& entity : entities) { + for (const AttributeInstance& attribute : entity.attributes()) { + for (FieldType field_type : attribute.GetSupportedTypes()) { + if (IsDateFieldType(field_type) + ? date_matches(attribute, field_type) + : nondate_matches(attribute, field_type)) { + types.insert(attribute.type().field_type()); + types.insert(field_type); + } + } + } + } + return types; +} + // Extracts the value from `field`. Then for each profile or credit card, // identify any stored types that match the value. Runs additional heuristics // for increased accuracy. Defaults to `{UNKNOWN_TYPE}` if no types could be @@ -140,6 +249,7 @@ AutofillField& field, base::span<const AutofillProfile> profiles, base::span<const CreditCard> credit_cards, + base::span<const EntityInstance> entities, base::span<const LoyaltyCard> loyalty_cards, const std::set<FieldGlobalId> fields_that_match_state, const std::string& app_locale) { @@ -158,9 +268,14 @@ for (const AutofillProfile& profile : profiles) { profile.GetMatchingTypes(value_u16, app_locale, &matching_types); } + if (fields_that_match_state.contains(field.global_id())) { + matching_types.insert(ADDRESS_HOME_STATE); + } + for (const CreditCard& card : credit_cards) { card.GetMatchingTypes(value_u16, app_locale, &matching_types); } + if (base::FeatureList::IsEnabled( features::kAutofillEnableLoyaltyCardsFilling)) { const std::string value_u8 = base::UTF16ToUTF8(value_u16); @@ -171,9 +286,11 @@ } } - if (fields_that_match_state.contains(field.global_id())) { - matching_types.insert(ADDRESS_HOME_STATE); + if (base::FeatureList::IsEnabled(features::kAutofillAiWithDataSchema)) { + matching_types.insert_all( + GetPossibleAutofillAiFieldTypes(entities, value_u16, app_locale)); } + if (matching_types.empty()) { matching_types.insert(UNKNOWN_TYPE); } @@ -186,15 +303,16 @@ void FindAndSetPossibleFieldTypes( base::span<const AutofillProfile> profiles, base::span<const CreditCard> credit_cards, + base::span<const EntityInstance> entities, base::span<const LoyaltyCard> loyalty_cards, const std::set<FieldGlobalId> fields_that_match_state, std::u16string_view last_unlocked_credit_card_cvc, const std::string& app_locale, FormStructure& form) { - for (size_t i = 0; i < form.field_count(); ++i) { - FindAndSetPossibleFieldTypesForField(*form.field(i), profiles, credit_cards, - loyalty_cards, fields_that_match_state, - app_locale); + for (const std::unique_ptr<AutofillField>& field : form.fields()) { + FindAndSetPossibleFieldTypesForField(*field, profiles, credit_cards, + entities, loyalty_cards, + fields_that_match_state, app_locale); } // As CVCs are not stored, run special heuristics to detect CVC-like values. @@ -208,31 +326,6 @@ } } -// Matches a date consisting of year, month, and day in a the given string. -std::vector<std::u16string> GetMatchingCompleteDateFormats( - std::u16string_view date) { - std::vector<std::u16string> format_strings; - for (std::u16string_view format : - {// Ordering: year month day. - u"YYYY*MM*DD", u"YY*MM*DD", u"YYYY+M+D", u"YY+M+D", - // Ordering: month day year. - u"MM*DD*YYYY", u"MM*DD*YY", u"M+D+YYYY", u"M+D+YY", - // Ordering: day month year. - u"DD*MM*YYYY", u"DD*MM*YY", u"D+M+YYYY", u"D+M+YY"}) { - data_util::Date result; - const char16_t* separator = nullptr; - if (data_util::ParseDate(date, format, result, separator) && - data_util::IsValidDateForFormat(result, format)) { - std::u16string instantiated_format; - base::ReplaceChars(format, u"*+", separator, &instantiated_format); - if (data_util::ParseDate(date, instantiated_format, result)) { - format_strings.push_back(instantiated_format); - } - } - } - return format_strings; -} - } // namespace std::set<FieldGlobalId> PreProcessStateMatchingTypes( @@ -275,6 +368,7 @@ void DeterminePossibleFieldTypesForUpload( base::span<const AutofillProfile> profiles, base::span<const CreditCard> credit_cards, + base::span<const EntityInstance> entities, base::span<const LoyaltyCard> loyalty_cards, const std::set<FieldGlobalId>& fields_that_match_state, std::u16string_view last_unlocked_credit_card_cvc, @@ -285,7 +379,7 @@ // the values so that the first call does not affect later calls. field->set_possible_types({}); } - FindAndSetPossibleFieldTypes(profiles, credit_cards, loyalty_cards, + FindAndSetPossibleFieldTypes(profiles, credit_cards, entities, loyalty_cards, fields_that_match_state, last_unlocked_credit_card_cvc, app_locale, form); DisambiguatePossibleFieldTypes(form); @@ -294,6 +388,7 @@ FieldTypeSet DetermineAvailableFieldTypes( base::span<const AutofillProfile> profiles, base::span<const CreditCard> credit_cards, + base::span<const EntityInstance> entities, base::span<const LoyaltyCard> loyalty_cards, std::u16string_view last_unlocked_credit_card_cvc, const std::string& app_locale) { @@ -301,6 +396,7 @@ for (const AutofillProfile& profile : profiles) { profile.GetNonEmptyTypes(app_locale, &types); } + for (const CreditCard& card : credit_cards) { card.GetNonEmptyTypes(app_locale, &types); } @@ -309,12 +405,16 @@ types.contains(CREDIT_CARD_NUMBER)) { types.insert(CREDIT_CARD_VERIFICATION_CODE); } + + if (base::FeatureList::IsEnabled(features::kAutofillAiWithDataSchema)) { + types.insert_all(GetAvailableAutofillAiFieldTypes(entities, app_locale)); + } + if (base::FeatureList::IsEnabled( features::kAutofillEnableLoyaltyCardsFilling) && !loyalty_cards.empty()) { types.insert(LOYALTY_MEMBERSHIP_ID); } - return types; }
diff --git a/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.h b/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.h index ec92c64..3d8b2a2 100644 --- a/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.h +++ b/components/autofill/core/browser/crowdsourcing/determine_possible_field_types.h
@@ -20,6 +20,7 @@ class AutofillProfile; class CreditCard; +class EntityInstance; class FormStructure; class LoyaltyCard; @@ -32,14 +33,16 @@ const FormStructure& form_structure, const std::string& app_locale); -// Uses the existing personal data in `profiles`, `credit_cards` and -// `loyalty_cards` to determine possible field types for the `form`. This is -// potentially expensive -- on the order of 50ms even for a small set of +// Determines the `FieldType`s for which profiles etc. define non-empty +// values. The result is stored in FormStructure::possible_types(). +// +// This is potentially expensive -- on the order of 50ms even for a small set of // `stored_data`. Hence, it should not run on the UI thread -- to avoid // locking up the UI -- nor on the IO thread -- to avoid blocking IPC calls. void DeterminePossibleFieldTypesForUpload( base::span<const AutofillProfile> profiles, base::span<const CreditCard> credit_cards, + base::span<const EntityInstance> entities, base::span<const LoyaltyCard> loyalty_cards, const std::set<FieldGlobalId>& fields_that_match_state, std::u16string_view last_unlocked_credit_card_cvc, @@ -51,6 +54,7 @@ FieldTypeSet DetermineAvailableFieldTypes( base::span<const AutofillProfile> profiles, base::span<const CreditCard> credit_cards, + base::span<const EntityInstance> entities, base::span<const LoyaltyCard> loyalty_cards, std::u16string_view last_unlocked_credit_card_cvc, const std::string& app_locale);
diff --git a/components/autofill/core/browser/crowdsourcing/determine_possible_field_types_unittest.cc b/components/autofill/core/browser/crowdsourcing/determine_possible_field_types_unittest.cc index 9194386a..0f7145e8 100644 --- a/components/autofill/core/browser/crowdsourcing/determine_possible_field_types_unittest.cc +++ b/components/autofill/core/browser/crowdsourcing/determine_possible_field_types_unittest.cc
@@ -35,6 +35,7 @@ using ::testing::Matcher; using ::testing::Not; using ::testing::Pair; +using ::testing::UnorderedElementsAre; using ::testing::UnorderedElementsAreArray; // Fakes that a `form` has been seen (without its field value) and parsed and @@ -328,7 +329,8 @@ ConstructFormStructureFromFormData(form); DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, std::vector<LoyaltyCard>(), + profiles, credit_cards, std::vector<EntityInstance>(), + std::vector<LoyaltyCard>(), /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/u"", "en-us", *form_structure); @@ -343,8 +345,17 @@ testing::ValuesIn(kProfileMatchingTypesTestCases)); class DeterminePossibleFieldTypesForUploadTest : public ::testing::Test { - protected: + public: + DeterminePossibleFieldTypesForUploadTest() { + scoped_feature_list_.InitWithFeatures( + {features::kAutofillAiWithDataSchema, + features::kAutofillEnableLoyaltyCardsFilling}, + {}); + } + + private: test::AutofillUnitTestEnvironment autofill_test_environment_; + base::test::ScopedFeatureList scoped_feature_list_; }; // If a server-side credit card is unmasked by entering the CVC, the @@ -377,7 +388,8 @@ form_structure->field(0)->set_possible_types({CREDIT_CARD_NUMBER}); DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, std::vector<LoyaltyCard>(), + profiles, credit_cards, std::vector<EntityInstance>(), + std::vector<LoyaltyCard>(), /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/kCvc16, "en-us", *form_structure); @@ -427,7 +439,8 @@ std::vector<AutofillProfile> profiles; DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, std::vector<LoyaltyCard>(), + profiles, credit_cards, std::vector<EntityInstance>(), + std::vector<LoyaltyCard>(), /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/std::u16string(), "en-us", *form_structure); @@ -478,7 +491,8 @@ std::vector<AutofillProfile> profiles; DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, std::vector<LoyaltyCard>(), + profiles, credit_cards, std::vector<EntityInstance>(), + std::vector<LoyaltyCard>(), /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/std::u16string(), "en-us", *form_structure); @@ -528,7 +542,8 @@ std::vector<AutofillProfile> profiles; DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, std::vector<LoyaltyCard>(), + profiles, credit_cards, std::vector<EntityInstance>(), + std::vector<LoyaltyCard>(), /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/std::u16string(), "en-us", *form_structure); @@ -578,7 +593,8 @@ std::vector<AutofillProfile> profiles; DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, std::vector<LoyaltyCard>(), + profiles, credit_cards, std::vector<EntityInstance>(), + std::vector<LoyaltyCard>(), /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/std::u16string(), "en-us", *form_structure); @@ -625,7 +641,8 @@ std::vector<AutofillProfile> profiles; DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, std::vector<LoyaltyCard>(), + profiles, credit_cards, std::vector<EntityInstance>(), + std::vector<LoyaltyCard>(), /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/u"", "en-us", *form_structure); @@ -635,8 +652,6 @@ // Tests if the loyalty card field detected. TEST_F(DeterminePossibleFieldTypesForUploadTest, CrowdsourceLoyaltyCardField) { - base::test::ScopedFeatureList scoped_feature_list_{ - features::kAutofillEnableLoyaltyCardsFilling}; constexpr char loyalty_card_program[] = "test_program"; constexpr char loyalty_card_number[] = "4234567890123456"; @@ -661,7 +676,8 @@ loyalty_card.set_loyalty_card_number(loyalty_card_number); loyalty_cards.push_back(loyalty_card); DeterminePossibleFieldTypesForUpload( - std::vector<AutofillProfile>(), std::vector<CreditCard>(), loyalty_cards, + std::vector<AutofillProfile>(), std::vector<CreditCard>(), + std::vector<EntityInstance>(), loyalty_cards, /*fields_that_match_state=*/{}, /*last_unlocked_credit_card_cvc=*/u"", "en-us", *form_structure); @@ -670,6 +686,51 @@ FieldPropertiesFlags::kNoFlags); } +// Tests if the Autofill AI field types are crowdsourced. +TEST_F(DeterminePossibleFieldTypesForUploadTest, CrowdsourceAutofillAiTypes) { + FormData form; + form.set_fields({ + CreateTestFormField("first-name", "first-name", "Pippi", + FormControlType::kInputText), + CreateTestFormField("last-name", "last-name", "Longstocking", + FormControlType::kInputText), + CreateTestFormField("number", "number", "1234567", + FormControlType::kInputText), + CreateTestFormField("expiry-date", "expiry-date", "30/08/2019", + FormControlType::kInputText), + CreateTestFormField("wrong-country", "wrong-country", "Finland", + FormControlType::kInputText), + }); + std::unique_ptr<FormStructure> form_structure = + ConstructFormStructureFromFormData(form); + + EntityInstance entity = test::GetPassportEntityInstance({ + .name = u"Pippi Longstocking", + .number = u"1234567", + .country = u"Sweden", + .expiry_date = u"2019-08-30", + .issue_date = u"2010-09-01", + }); + + DeterminePossibleFieldTypesForUpload( + std::vector<AutofillProfile>(), std::vector<CreditCard>(), + base::span_from_ref(entity), std::vector<LoyaltyCard>(), + /*fields_that_match_state=*/{}, + /*last_unlocked_credit_card_cvc=*/u"", "en-US", *form_structure); + + EXPECT_THAT(form_structure->fields()[0]->possible_types(), + UnorderedElementsAre(PASSPORT_NAME_TAG, NAME_FIRST)); + EXPECT_THAT( + form_structure->fields()[1]->possible_types(), + UnorderedElementsAre(PASSPORT_NAME_TAG, NAME_LAST, NAME_LAST_SECOND)); + EXPECT_THAT(form_structure->fields()[2]->possible_types(), + UnorderedElementsAre(PASSPORT_NUMBER)); + EXPECT_THAT(form_structure->fields()[3]->possible_types(), + UnorderedElementsAre(PASSPORT_EXPIRATION_DATE)); + EXPECT_THAT(form_structure->fields()[4]->possible_types(), + UnorderedElementsAre(UNKNOWN_TYPE)); +} + // Test fixture for PreProcessStateMatchingTypes(). class PreProcessStateMatchingTypesTest : public testing::Test { public: @@ -990,11 +1051,13 @@ UnorderedElementsAreArray(expectations)); } +// Test fixture for DetermineAvailableFieldTypes(). class DetermineAvailableFieldTypesTest : public ::testing::Test { public: DetermineAvailableFieldTypesTest() { features_.InitWithFeatures( - {features::kAutofillEnableLoyaltyCardsFilling, + {features::kAutofillAiWithDataSchema, + features::kAutofillEnableLoyaltyCardsFilling, features::kAutofillEnableEmailOrLoyaltyCardsFilling}, {}); } @@ -1004,13 +1067,28 @@ base::test::ScopedFeatureList features_; }; +// Tests that entities are included in the set of available field types. +TEST_F(DetermineAvailableFieldTypesTest, Entities) { + EntityInstance entity = test::GetPassportEntityInstance(); + FieldTypeSet available_types = DetermineAvailableFieldTypes( + /*profiles=*/{}, /*credit_cards=*/{}, /*entities=*/{entity}, + /*loyalty_cards=*/{}, + /*last_unlocked_credit_card_cvc=*/u"", + /*app_locale=*/"en-US"); + EXPECT_THAT(available_types, + UnorderedElementsAre( + NAME_FULL, NAME_FIRST, NAME_LAST, NAME_LAST_SECOND, + PASSPORT_NAME_TAG, PASSPORT_NUMBER, PASSPORT_EXPIRATION_DATE, + PASSPORT_ISSUE_DATE, PASSPORT_ISSUING_COUNTRY)); +} + // Tests that loyalty cards are included in the set of available field types. TEST_F(DetermineAvailableFieldTypesTest, LoyaltyCards) { LoyaltyCard card = test::CreateLoyaltyCard(); - FieldTypeSet available_types = - DetermineAvailableFieldTypes(/*profiles=*/{}, /*credit_cards=*/{}, {card}, - /*last_unlocked_credit_card_cvc=*/u"", - /*app_locale=*/""); + FieldTypeSet available_types = DetermineAvailableFieldTypes( + /*profiles=*/{}, /*credit_cards=*/{}, /*entities=*/{}, {card}, + /*last_unlocked_credit_card_cvc=*/u"", + /*app_locale=*/""); EXPECT_TRUE(available_types.contains(LOYALTY_MEMBERSHIP_ID)); }
diff --git a/components/autofill/core/browser/crowdsourcing/votes_uploader.cc b/components/autofill/core/browser/crowdsourcing/votes_uploader.cc index 612a1362..cced470 100644 --- a/components/autofill/core/browser/crowdsourcing/votes_uploader.cc +++ b/components/autofill/core/browser/crowdsourcing/votes_uploader.cc
@@ -206,6 +206,11 @@ .payments_data_manager() .GetCreditCards(); + base::span<const EntityInstance> entities; + if (EntityDataManager* edm = client_->GetEntityDataManager()) { + entities = edm->GetEntityInstances(); + } + std::vector<LoyaltyCard> loyalty_cards; if (ValuablesDataManager* valuables_data_manager = client_->GetValuablesDataManager()) { @@ -213,12 +218,13 @@ [](LoyaltyCard card) { return card; }); } - if (profiles.empty() && credit_cards.empty() && loyalty_cards.empty()) { + if (profiles.empty() && credit_cards.empty() && entities.empty() && + loyalty_cards.empty()) { return false; } - if (form->field_count() * - (profiles.size() + credit_cards.size() + loyalty_cards.size()) >= + if (form->field_count() * (profiles.size() + credit_cards.size() + + entities.size() + loyalty_cards.size()) >= kMaxTypeMatchingCalls) { return false; } @@ -243,6 +249,7 @@ base::BindOnce( [](const std::vector<AutofillProfile>& profiles, const std::vector<CreditCard>& credit_cards, + const std::vector<EntityInstance>& entities, const std::vector<LoyaltyCard>& loyalty_cards, const std::u16string& last_unlocked_credit_card_cvc, const std::string& app_locale, bool observed_submission, @@ -251,15 +258,16 @@ FormStructure::FormAssociations form_associations, std::set<FieldGlobalId> fields_that_match_state) { DeterminePossibleFieldTypesForUpload( - profiles, credit_cards, loyalty_cards, fields_that_match_state, - last_unlocked_credit_card_cvc, app_locale, *form); + profiles, credit_cards, entities, loyalty_cards, + fields_that_match_state, last_unlocked_credit_card_cvc, + app_locale, *form); EncodeUploadRequestOptions options; options.encoder = std::move(randomized_encoder); options.form_associations = std::move(form_associations); options.observed_submission = observed_submission; options.available_field_types = DetermineAvailableFieldTypes( - profiles, credit_cards, loyalty_cards, + profiles, credit_cards, entities, loyalty_cards, last_unlocked_credit_card_cvc, app_locale); for (auto& [field_id, format_strings] : DeterminePossibleFormatStringsForUpload(form->fields())) { @@ -275,8 +283,9 @@ // function is called asynchronously. base::ToVector(profiles, [](const auto* ptr) { return *ptr; }), base::ToVector(credit_cards, [](const auto* ptr) { return *ptr; }), - std::move(loyalty_cards), last_unlocked_credit_card_cvc, - client_->GetAppLocale(), observed_submission, std::move(form), + base::ToVector(entities), std::move(loyalty_cards), + last_unlocked_credit_card_cvc, client_->GetAppLocale(), + observed_submission, std::move(form), RandomizedEncoder::Create(client_->GetPrefs()), std::move(form_associations), std::move(fields_that_match_state)), base::BindOnce(&VotesUploader::OnFieldTypesDetermined,
diff --git a/components/autofill/core/browser/webdata/valuables/valuable_sync_bridge_unittest.cc b/components/autofill/core/browser/webdata/valuables/valuable_sync_bridge_unittest.cc index 64a4035..a4c58b5b 100644 --- a/components/autofill/core/browser/webdata/valuables/valuable_sync_bridge_unittest.cc +++ b/components/autofill/core/browser/webdata/valuables/valuable_sync_bridge_unittest.cc
@@ -187,6 +187,23 @@ EXPECT_THAT(GetAllDataFromTable(), UnorderedElementsAre(remote1, remote2)); } +// Tests that loyalty cards with empty logo url are synced and stored. +TEST_F(ValuableSyncBridgeTest, LoyaltyCardsWithNoProgramLogo) { + const LoyaltyCard remote1 = LoyaltyCard( + ValuableId(std::string("no_logo")), "merchant_name", "program_name", + GURL(), "card_number", {GURL("https://domain.example")}); + + EXPECT_CALL(mock_processor(), Put).Times(0); + EXPECT_CALL(mock_processor(), Delete).Times(0); + EXPECT_CALL(backend(), CommitChanges); + EXPECT_CALL(backend(), + NotifyOnAutofillChangedBySync(syncer::AUTOFILL_VALUABLE)); + + EXPECT_TRUE(StartSyncing({remote1})); + + EXPECT_THAT(GetAllDataFromTable(), UnorderedElementsAre(remote1)); +} + // Tests that `MergeFullSyncData()` replaces currently stored loyalty cards. TEST_F(ValuableSyncBridgeTest, MergeFullSyncData_ReplacePreviousData) { const LoyaltyCard remote1 = TestLoyaltyCard(kId1);
diff --git a/components/autofill/core/browser/webdata/valuables/valuables_sync_util.cc b/components/autofill/core/browser/webdata/valuables/valuables_sync_util.cc index 30cd6d4..5b1a60cf 100644 --- a/components/autofill/core/browser/webdata/valuables/valuables_sync_util.cc +++ b/components/autofill/core/browser/webdata/valuables/valuables_sync_util.cc
@@ -59,9 +59,16 @@ bool AreAutofillLoyaltyCardSpecificsValid( const AutofillValuableSpecifics& specifics) { + const auto HasEmptyOrValidProgramLogo = + [](const AutofillValuableSpecifics& specifics) { + return !specifics.loyalty_card().has_program_logo() || + specifics.loyalty_card().program_logo().empty() || + GURL(specifics.loyalty_card().program_logo()).is_valid(); + }; + return !specifics.id().empty() && specifics.has_loyalty_card() && !specifics.loyalty_card().loyalty_card_number().empty() && - GURL(specifics.loyalty_card().program_logo()).is_valid(); + HasEmptyOrValidProgramLogo(specifics); } AutofillValuableSpecifics TrimAutofillValuableSpecificsDataForCaching(
diff --git a/components/autofill/core/browser/webdata/valuables/valuables_sync_util_unittest.cc b/components/autofill/core/browser/webdata/valuables/valuables_sync_util_unittest.cc index c5d2c26e..dec0c4e0 100644 --- a/components/autofill/core/browser/webdata/valuables/valuables_sync_util_unittest.cc +++ b/components/autofill/core/browser/webdata/valuables/valuables_sync_util_unittest.cc
@@ -107,6 +107,12 @@ TestLoyaltyCardSpecifics(kId1, kValidProgramLogo, /*number=*/""))); EXPECT_TRUE( AreAutofillLoyaltyCardSpecificsValid(TestLoyaltyCardSpecifics(kId1))); + + sync_pb::AutofillValuableSpecifics specifics = TestLoyaltyCardSpecifics(kId1); + specifics.mutable_loyalty_card()->clear_program_logo(); + EXPECT_TRUE(AreAutofillLoyaltyCardSpecificsValid(specifics)); + EXPECT_TRUE(AreAutofillLoyaltyCardSpecificsValid( + TestLoyaltyCardSpecifics(kId1, /*program_logo=*/""))); } TEST_F(LoyaltyCardSyncUtilTest, TrimAutofillValuableSpecificsDataForCaching) {
diff --git a/components/content_settings/core/common/cookie_settings_base.cc b/components/content_settings/core/common/cookie_settings_base.cc index 2b32299..39766d36c 100644 --- a/components/content_settings/core/common/cookie_settings_base.cc +++ b/components/content_settings/core/common/cookie_settings_base.cc
@@ -762,13 +762,11 @@ std::get_if<AllowAllCookies>(&choice)) { CHECK(IsAllowed(cookie_setting)); CHECK(!is_third_party_request || !block_third_party_cookies || - allow_cookies->mechanism != ThirdPartyCookieAllowMechanism::kNone, - base::NotFatalUntil::M128); + allow_cookies->mechanism != ThirdPartyCookieAllowMechanism::kNone); // `!is_third_party_request` implies that the exemption reason must be // kNone. (It doesn't make sense to exempt a first-party cookie from 3PCD.) CHECK(is_third_party_request || - allow_cookies->mechanism == ThirdPartyCookieAllowMechanism::kNone, - base::NotFatalUntil::M128); + allow_cookies->mechanism == ThirdPartyCookieAllowMechanism::kNone); FireStorageAccessHistogram( GetStorageAccessResult(allow_cookies->mechanism)); @@ -800,9 +798,9 @@ } if (std::holds_alternative<AllowPartitionedCookies>(choice)) { - CHECK(is_third_party_request, base::NotFatalUntil::M128); - CHECK(block_third_party_cookies, base::NotFatalUntil::M128); - CHECK(!is_explicit_setting, base::NotFatalUntil::M128); + CHECK(is_third_party_request); + CHECK(block_third_party_cookies); + CHECK(!is_explicit_setting); FireStorageAccessHistogram(StorageAccessResult::ACCESS_BLOCKED); @@ -822,7 +820,7 @@ } CHECK(std::holds_alternative<BlockAllCookies>(choice)); - CHECK_EQ(cookie_setting, CONTENT_SETTING_BLOCK, base::NotFatalUntil::M128); + CHECK_EQ(cookie_setting, CONTENT_SETTING_BLOCK); FireStorageAccessHistogram(StorageAccessResult::ACCESS_BLOCKED); if (info) {
diff --git a/components/dom_distiller/core/distiller_page.cc b/components/dom_distiller/core/distiller_page.cc index 0df1b5e..2ee387b8 100644 --- a/components/dom_distiller/core/distiller_page.cc +++ b/components/dom_distiller/core/distiller_page.cc
@@ -37,9 +37,9 @@ const GURL& gurl, const dom_distiller::proto::DomDistillerOptions options, DistillerPageCallback callback) { - CHECK(ready_, base::NotFatalUntil::M126); - CHECK(callback, base::NotFatalUntil::M127); - CHECK(!distiller_page_callback_, base::NotFatalUntil::M127); + CHECK(ready_); + CHECK(callback); + CHECK(!distiller_page_callback_); // It is only possible to distill one page at a time. |ready_| is reset when // the callback to OnDistillationDone happens. ready_ = false;
diff --git a/components/enterprise/watermarking/features.cc b/components/enterprise/watermarking/features.cc index d486d51597..a89e6e5 100644 --- a/components/enterprise/watermarking/features.cc +++ b/components/enterprise/watermarking/features.cc
@@ -10,6 +10,6 @@ BASE_FEATURE(kEnablePrintWatermark, "EnablePrintWatermark", - base::FEATURE_DISABLED_BY_DEFAULT); + base::FEATURE_ENABLED_BY_DEFAULT); } // namespace enterprise_watermark::features
diff --git a/components/fingerprinting_protection_filter/browser/fingerprinting_protection_ruleset_publisher.cc b/components/fingerprinting_protection_filter/browser/fingerprinting_protection_ruleset_publisher.cc index 96d7ad6..104d513 100644 --- a/components/fingerprinting_protection_filter/browser/fingerprinting_protection_ruleset_publisher.cc +++ b/components/fingerprinting_protection_filter/browser/fingerprinting_protection_ruleset_publisher.cc
@@ -30,9 +30,9 @@ void FingerprintingProtectionRulesetPublisher::SendRulesetToRenderProcess( base::File* file, content::RenderProcessHost* rph) { - CHECK(rph, base::NotFatalUntil::M129); - CHECK(file, base::NotFatalUntil::M129); - CHECK(file->IsValid(), base::NotFatalUntil::M129); + CHECK(rph); + CHECK(file); + CHECK(file->IsValid()); if (!rph->GetChannel()) { return; }
diff --git a/components/guest_contents/DIR_METADATA b/components/guest_contents/DIR_METADATA new file mode 100644 index 0000000..4caf504 --- /dev/null +++ b/components/guest_contents/DIR_METADATA
@@ -0,0 +1,3 @@ +buganizer_public: { + component_id: 1681552 +}
diff --git a/components/guest_contents/OWNERS b/components/guest_contents/OWNERS new file mode 100644 index 0000000..32c5d76 --- /dev/null +++ b/components/guest_contents/OWNERS
@@ -0,0 +1,7 @@ +kerenzhu@chromium.org +tluk@chromium.org +dayeung@chromium.org +robliao@chromium.org + +per-file *.mojom=set noparent +per-file *.mojom=file://ipc/SECURITY_OWNERS
diff --git a/components/guest_contents/browser/BUILD.gn b/components/guest_contents/browser/BUILD.gn new file mode 100644 index 0000000..fb91e33 --- /dev/null +++ b/components/guest_contents/browser/BUILD.gn
@@ -0,0 +1,38 @@ +# Copyright 2025 The Chromium Authors +# Use of this source code is governed by a BSD-style license that can be +# found in the LICENSE file. +import("//components/guest_contents/common/buildflags.gni") +import("//mojo/public/tools/bindings/mojom.gni") + +assert(enable_guest_contents) + +static_library("browser") { + sources = [ + "guest_contents_handle.cc", + "guest_contents_handle.h", + ] + + deps = [ + "//base", + "//content/public/browser", + "//content/public/common", + ] +} + +source_set("unit_tests") { + testonly = true + + sources = [ + "guest_contents_handle_unittest.cc", + ] + + public_deps = [ + "//content/test:test_support", + ] + + deps = [ + ":browser", + "//base", + "//testing/gtest", + ] +}
diff --git a/components/guest_contents/browser/DEPS b/components/guest_contents/browser/DEPS new file mode 100644 index 0000000..1254dcc --- /dev/null +++ b/components/guest_contents/browser/DEPS
@@ -0,0 +1,10 @@ +include_rules = [ + "+content/public/browser", + "+content/public/common", +] + +specific_include_rules = { + "^(test_|.*_(unit|pixel|perf)?test).*\.(cc|h)": [ + "+content/public/test", + ], +}
diff --git a/components/guest_contents/browser/guest_contents_handle.cc b/components/guest_contents/browser/guest_contents_handle.cc new file mode 100644 index 0000000..2696d82 --- /dev/null +++ b/components/guest_contents/browser/guest_contents_handle.cc
@@ -0,0 +1,86 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/guest_contents/browser/guest_contents_handle.h" + +#include <map> + +#include "base/no_destructor.h" +#include "content/public/browser/unowned_inner_web_contents_client.h" +#include "content/public/browser/web_contents.h" +#include "content/public/browser/web_contents_observer.h" +#include "content/public/browser/web_contents_user_data.h" + +namespace guest_contents { + +namespace { + +std::map<GuestId, GuestContentsHandle*>& GetGuestContentsMap() { + static base::NoDestructor<std::map<GuestId, GuestContentsHandle*>> + guest_contents_map; + return *guest_contents_map; +} + +} // namespace + +// static +GuestContentsHandle* GuestContentsHandle::CreateForWebContents( + content::WebContents* web_contents) { + content::WebContentsUserData<GuestContentsHandle>::CreateForWebContents( + web_contents); + return FromWebContents(web_contents); +} + +// static +GuestContentsHandle* GuestContentsHandle::FromID(GuestId id) { + return GetGuestContentsMap().contains(id) ? GetGuestContentsMap()[id] + : nullptr; +} + +GuestContentsHandle::GuestContentsHandle(content::WebContents* web_contents) + : content::WebContentsUserData<GuestContentsHandle>(*web_contents), + content::WebContentsObserver(web_contents), + id_(GetNextId()) { + CHECK(!GetGuestContentsMap().contains(id_)); + GetGuestContentsMap()[id_] = this; +} + +GuestContentsHandle::~GuestContentsHandle() { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + GetGuestContentsMap().erase(id_); +} + +void GuestContentsHandle::AttachToOuterWebContents( + content::RenderFrameHost* outer_delegate_frame) { + content::WebContents* outer_web_contents = + content::WebContents::FromRenderFrameHost(outer_delegate_frame); + CHECK(outer_web_contents); + outer_web_contents->AttachUnownedInnerWebContents( + content::UnownedInnerWebContentsClient::GetPassKey(), web_contents(), + outer_delegate_frame); +} + +void GuestContentsHandle::DetachFromOuterWebContents() { + content::WebContents* outer_web_contents = + web_contents()->GetOuterWebContents(); + if (!outer_web_contents) { + return; + } + + outer_web_contents->DetachUnownedInnerWebContents( + content::UnownedInnerWebContentsClient::GetPassKey(), web_contents()); +} + +void GuestContentsHandle::WebContentsDestroyed() { + DetachFromOuterWebContents(); +} + +GuestId GuestContentsHandle::GetNextId() { + static GuestId next_id = 0; + return next_id++; +} + +WEB_CONTENTS_USER_DATA_KEY_IMPL(GuestContentsHandle); + +} // namespace guest_contents
diff --git a/components/guest_contents/browser/guest_contents_handle.h b/components/guest_contents/browser/guest_contents_handle.h new file mode 100644 index 0000000..0a871156 --- /dev/null +++ b/components/guest_contents/browser/guest_contents_handle.h
@@ -0,0 +1,59 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef COMPONENTS_GUEST_CONTENTS_BROWSER_GUEST_CONTENTS_HANDLE_H_ +#define COMPONENTS_GUEST_CONTENTS_BROWSER_GUEST_CONTENTS_HANDLE_H_ + +#include "base/sequence_checker.h" +#include "content/public/browser/web_contents.h" +#include "content/public/browser/web_contents_observer.h" +#include "content/public/browser/web_contents_user_data.h" + +namespace guest_contents { + +using GuestId = int; + +// A handle for a guest WebContents, uniquely identified by a GuestId. It +// provides APIs for attaching and detaching the guest WebContents from the +// outer WebContents. It has the same lifetime as the guest WebContents. +class GuestContentsHandle + : public content::WebContentsUserData<GuestContentsHandle>, + public content::WebContentsObserver { + public: + ~GuestContentsHandle() override; + + // Creates a handle for the given `web_contents`. + static GuestContentsHandle* CreateForWebContents( + content::WebContents* web_contents); + + static GuestContentsHandle* FromID(GuestId id); + + // Returns the unique ID of this guest. This ID is automatically assigned + // when the GuestContentsHandle is created. + GuestId id() { return id_; } + + void AttachToOuterWebContents( + content::RenderFrameHost* outer_delegate_frame); + + void DetachFromOuterWebContents(); + + private: + friend content::WebContentsUserData<GuestContentsHandle>; + WEB_CONTENTS_USER_DATA_KEY_DECL(); + + explicit GuestContentsHandle(content::WebContents* web_contents); + + // content::WebContentsObserver: + void WebContentsDestroyed() override; + + GuestId GetNextId(); + + GuestId id_; + + SEQUENCE_CHECKER(sequence_checker_); +}; + +} // namespace guest_contents + +#endif // COMPONENTS_GUEST_CONTENTS_BROWSER_GUEST_CONTENTS_HANDLE_H_
diff --git a/components/guest_contents/browser/guest_contents_handle_unittest.cc b/components/guest_contents/browser/guest_contents_handle_unittest.cc new file mode 100644 index 0000000..af13a2d --- /dev/null +++ b/components/guest_contents/browser/guest_contents_handle_unittest.cc
@@ -0,0 +1,147 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/guest_contents/browser/guest_contents_handle.h" + +#include "base/location.h" +#include "base/test/scoped_feature_list.h" +#include "content/public/common/content_features.h" +#include "content/public/test/test_renderer_host.h" + +namespace guest_contents { + +class GuestContentsHandleTest : public content::RenderViewHostTestHarness { + public: + void SetUp() override { + content::RenderViewHostTestHarness::SetUp(); + guest_web_contents_ = CreateTestWebContents(); + content::RenderFrameHostTester::For( + guest_web_contents_->GetPrimaryMainFrame()) + ->InitializeRenderFrameIfNeeded(); + outer_web_contents_ = CreateTestWebContents(); + content::RenderFrameHostTester* outer_rfh_tester = + content::RenderFrameHostTester::For( + outer_web_contents_->GetPrimaryMainFrame()); + outer_rfh_tester->InitializeRenderFrameIfNeeded(); + outer_delegate_rfh_ = outer_rfh_tester->AppendChild("outer_delegate"); + ASSERT_TRUE(outer_delegate_rfh_); + } + + void TearDown() override { + outer_delegate_rfh_ = nullptr; + guest_web_contents_.reset(); + outer_web_contents_.reset(); + content::RenderViewHostTestHarness::TearDown(); + } + + std::unique_ptr<content::WebContents>& guest_web_contents() { + return guest_web_contents_; + } + std::unique_ptr<content::WebContents>& outer_web_contents() { + return outer_web_contents_; + } + content::RenderFrameHost& outer_delegate_rfh() { + return *outer_delegate_rfh_; + } + + protected: + std::unique_ptr<content::WebContents> guest_web_contents_; + std::unique_ptr<content::WebContents> outer_web_contents_; + raw_ptr<content::RenderFrameHost> outer_delegate_rfh_; + + private: + base::test::ScopedFeatureList scoped_feature_list_{ + features::kAttachUnownedInnerWebContents}; +}; + +TEST_F(GuestContentsHandleTest, CreateAndGetById) { + GuestContentsHandle* handle = + GuestContentsHandle::CreateForWebContents(guest_web_contents().get()); + ASSERT_TRUE(handle); + EXPECT_EQ(handle, + GuestContentsHandle::FromWebContents(guest_web_contents().get())); + + GuestId id = handle->id(); + EXPECT_EQ(handle, GuestContentsHandle::FromID(id)); + + // Test invalid ID + EXPECT_EQ(nullptr, GuestContentsHandle::FromID(id + 1)); + EXPECT_EQ(nullptr, GuestContentsHandle::FromID(-1)); + + // Destroy the WebContents, which should destroy the handle + guest_web_contents().reset(); + + // Handle should no longer be findable by ID + EXPECT_EQ(nullptr, GuestContentsHandle::FromID(id)); +} + +TEST_F(GuestContentsHandleTest, UniqueIds) { + GuestContentsHandle* handle1 = + GuestContentsHandle::CreateForWebContents(guest_web_contents().get()); + ASSERT_TRUE(handle1); + + // Create a second guest WebContents and handle + std::unique_ptr<content::WebContents> guest_web_contents2 = + CreateTestWebContents(); + GuestContentsHandle* handle2 = + GuestContentsHandle::CreateForWebContents(guest_web_contents2.get()); + ASSERT_TRUE(handle2); + + EXPECT_NE(handle1->id(), handle2->id()); + + // Clean up second guest + guest_web_contents2.reset(); + // First handle should still exist + EXPECT_EQ(handle1, GuestContentsHandle::FromID(handle1->id())); +} + +TEST_F(GuestContentsHandleTest, AttachAndDetach) { + GuestContentsHandle* handle = + GuestContentsHandle::CreateForWebContents(guest_web_contents().get()); + ASSERT_TRUE(handle); + + handle->AttachToOuterWebContents(&outer_delegate_rfh()); + EXPECT_EQ(guest_web_contents()->GetOuterWebContents(), + outer_web_contents().get()); + EXPECT_TRUE(base::Contains(outer_web_contents()->GetInnerWebContents(), + guest_web_contents().get())); + + handle->DetachFromOuterWebContents(); + EXPECT_EQ(nullptr, guest_web_contents()->GetOuterWebContents()); + EXPECT_TRUE(outer_web_contents()->GetInnerWebContents().empty()); +} + +TEST_F(GuestContentsHandleTest, DestroyGuestContents) { + GuestContentsHandle* handle = + GuestContentsHandle::CreateForWebContents(guest_web_contents().get()); + ASSERT_TRUE(handle); + + handle->AttachToOuterWebContents(&outer_delegate_rfh()); + EXPECT_EQ(guest_web_contents()->GetOuterWebContents(), + outer_web_contents().get()); + EXPECT_TRUE(base::Contains(outer_web_contents()->GetInnerWebContents(), + guest_web_contents().get())); + + // Destroy the guest WebContents while it is still attached to the outer + // WebContents. + guest_web_contents().reset(); + EXPECT_TRUE(outer_web_contents()->GetInnerWebContents().empty()); +} + +TEST_F(GuestContentsHandleTest, DestroyOuterWebContents) { + GuestContentsHandle* handle = + GuestContentsHandle::CreateForWebContents(guest_web_contents().get()); + ASSERT_TRUE(handle); + + handle->AttachToOuterWebContents(&outer_delegate_rfh()); + EXPECT_EQ(guest_web_contents()->GetOuterWebContents(), + outer_web_contents().get()); + + // Destroy the outer WebContents while it still has a guest WebContents. + outer_delegate_rfh_ = nullptr; + outer_web_contents().reset(); + EXPECT_EQ(nullptr, guest_web_contents()->GetOuterWebContents()); +} + +} // namespace guest_contents
diff --git a/components/guest_contents/common/BUILD.gn b/components/guest_contents/common/BUILD.gn new file mode 100644 index 0000000..aa1a8a3 --- /dev/null +++ b/components/guest_contents/common/BUILD.gn
@@ -0,0 +1,10 @@ +# Copyright 2025 The Chromium Authors +# Use of this source code is governed by a BSD-style license that can be +# found in the LICENSE file. + +import("//build/buildflag_header.gni") + +buildflag_header("buildflags") { + header = "buildflags.h" + flags = [ "ENABLE_GUEST_CONTENTS=$enable_guest_contents" ] +}
diff --git a/components/guest_contents/common/buildflags.gni b/components/guest_contents/common/buildflags.gni new file mode 100644 index 0000000..3b3a29e --- /dev/null +++ b/components/guest_contents/common/buildflags.gni
@@ -0,0 +1,11 @@ +# Copyright 2025 The Chromium Authors +# Use of this source code is governed by a BSD-style license that can be +# found in the LICENSE file. + +import("//build/config/cast.gni") +import("//build/config/chrome_build.gni") + +declare_args() { + # `enable_guest_contents` controls whether the guest_contents is compiled. + enable_guest_contents = !is_android && !is_ios && !is_castos +}
diff --git a/components/history/core/browser/history_backend_unittest.cc b/components/history/core/browser/history_backend_unittest.cc index 26442f9..928442d 100644 --- a/components/history/core/browser/history_backend_unittest.cc +++ b/components/history/core/browser/history_backend_unittest.cc
@@ -61,6 +61,7 @@ #include "components/sync/base/features.h" #include "sql/sqlite_result_code_values.h" #include "sql/test/test_helpers.h" +#include "sql/transaction.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" #include "third_party/skia/include/core/SkBitmap.h" @@ -233,6 +234,7 @@ using HistoryBackend::expirer_; using HistoryBackend::favicon_backend_; using HistoryBackend::recent_redirects_; + using HistoryBackend::singleton_transaction_; VisitTracker& visit_tracker() { return tracker_; } @@ -3277,6 +3279,22 @@ /*user_initiated*/ true); } +// Tests for https://crbug.com/420369590. +TEST_F(HistoryBackendTest, DatabaseErrorOnClosedDatabase) { + // Clear the pending transaction to avoid DCHECKs to trigger. This is required + // since we are closing the raw sqlite database. + backend_->singleton_transaction_.reset(); + + // Close the database. This is simulating a case where the open failed but + // the database is not poisoned. + backend_->db()->GetDBForTesting().Close(); + + // Retrieve the error diagnostic information. + std::string result = backend_->db()->GetDiagnosticInfo( + static_cast<int>(sql::SqliteResultCode::kCorrupt), nullptr, nullptr); + EXPECT_EQ(result, "Database is not opened."); +} + // Tests that a typed navigation which results in a redirect from HTTP to HTTPS // will cause the HTTPS URL to accrue the typed count, and the HTTP URL to not. TEST_F(HistoryBackendTest, RedirectScoring) {
diff --git a/components/history/core/browser/history_database.cc b/components/history/core/browser/history_database.cc index 89a1da12..0d0ef1a 100644 --- a/components/history/core/browser/history_database.cc +++ b/components/history/core/browser/history_database.cc
@@ -427,6 +427,9 @@ int extended_error, sql::Statement* statement, sql::DatabaseDiagnostics* diagnostics) { + if (!db_.is_open()) { + return "Database is not opened."; + } return db_.GetDiagnosticInfo(extended_error, statement, diagnostics); }
diff --git a/components/optimization_guide/core/model_execution/model_execution_features_controller.cc b/components/optimization_guide/core/model_execution/model_execution_features_controller.cc index 0af64f0..ab2197b2 100644 --- a/components/optimization_guide/core/model_execution/model_execution_features_controller.cc +++ b/components/optimization_guide/core/model_execution/model_execution_features_controller.cc
@@ -415,10 +415,9 @@ // When the feature is enabled, check the user is valid to enable the // feature. CHECK(!is_enabled || - GetCurrentUserValidityResult(feature, - /*skip_enterprise_check=*/false) == - ModelExecutionFeaturesController::UserValidityResult::kValid, - base::NotFatalUntil::M125); + GetCurrentUserValidityResult(feature, + /*skip_enterprise_check=*/false) == + ModelExecutionFeaturesController::UserValidityResult::kValid); if (pref_value != prefs::FeatureOptInState::kNotInitialized) { base::UmaHistogramBoolean(
diff --git a/components/payments/core/payment_manifest_downloader.cc b/components/payments/core/payment_manifest_downloader.cc index 340d4f7f..af2de5f 100644 --- a/components/payments/core/payment_manifest_downloader.cc +++ b/components/payments/core/payment_manifest_downloader.cc
@@ -227,20 +227,18 @@ void PaymentManifestDownloader::OnURLLoaderComplete( network::SimpleURLLoader* url_loader, - std::unique_ptr<std::string> response_body) { + std::optional<std::string> response_body) { scoped_refptr<net::HttpResponseHeaders> headers; if (url_loader->ResponseInfo()) { headers = url_loader->ResponseInfo()->headers; } - std::string response_body_str; - if (response_body.get()) { - response_body_str = std::move(*response_body); + if (!response_body.has_value()) { + response_body.emplace(); } OnURLLoaderCompleteInternal(url_loader, url_loader->GetFinalURL(), - response_body_str, headers, - url_loader->NetError()); + *response_body, headers, url_loader->NetError()); } void PaymentManifestDownloader::OnURLLoaderCompleteInternal(
diff --git a/components/payments/core/payment_manifest_downloader.h b/components/payments/core/payment_manifest_downloader.h index 9e12937..f0b6dac9 100644 --- a/components/payments/core/payment_manifest_downloader.h +++ b/components/payments/core/payment_manifest_downloader.h
@@ -174,7 +174,7 @@ // Called by SimpleURLLoader on completion. void OnURLLoaderComplete(network::SimpleURLLoader* url_loader, - std::unique_ptr<std::string> response_body); + std::optional<std::string> response_body); // Internally called by OnURLLoaderComplete, exposed to ease unit tests. void OnURLLoaderCompleteInternal(
diff --git a/components/persistent_cache/BUILD.gn b/components/persistent_cache/BUILD.gn index 2e0a2e8b..d9205d22 100644 --- a/components/persistent_cache/BUILD.gn +++ b/components/persistent_cache/BUILD.gn
@@ -47,16 +47,35 @@ ] } +static_library("test_support") { + testonly = true + + sources = [ + "mock/mock_backend_impl.cc", + "mock/mock_backend_impl.h", + "mock/mock_entry_impl.cc", + "mock/mock_entry_impl.h", + "sqlite/test_utils.cc", + "sqlite/test_utils.h", + ] + + deps = [ + ":persistent_cache", + "//base", + "//base/test:test_support", + "//sql", + "//testing/gmock", + "//testing/gtest", + "//third_party/sqlite", + ] +} + source_set("unit_tests") { testonly = true sources = [ "backend_params_manager_unittest.cc", "entry_unittest.cc", - "mock/mock_backend_impl.cc", - "mock/mock_backend_impl.h", - "mock/mock_entry_impl.cc", - "mock/mock_entry_impl.h", "sqlite/sqlite_entry_unittest.cc", ] @@ -64,14 +83,13 @@ if (!is_fuchsia) { sources += [ "persistent_cache_unittest.cc", - "sqlite/test_utils.cc", - "sqlite/test_utils.h", "sqlite/vfs/sqlite_sandboxed_vfs_unittest.cc", ] } deps = [ ":persistent_cache", + ":test_support", "//base", "//base/test:test_support", "//sql",
diff --git a/components/persistent_cache/persistent_cache_perftest.cc b/components/persistent_cache/persistent_cache_perftest.cc new file mode 100644 index 0000000..e131b3c --- /dev/null +++ b/components/persistent_cache/persistent_cache_perftest.cc
@@ -0,0 +1,50 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "components/persistent_cache/persistent_cache.h" + +#include "base/time/time.h" +#include "base/timer/elapsed_timer.h" +#include "build/buildflag.h" +#include "components/persistent_cache/entry.h" +#include "components/persistent_cache/sqlite/test_utils.h" +#include "testing/gtest/include/gtest/gtest.h" +#include "testing/perf/perf_result_reporter.h" + +namespace persistent_cache { + +using PersistentCachePerftest = testing::Test; + +#if !BUILDFLAG(IS_FUCHSIA) + +TEST_F(PersistentCachePerftest, OpenClose) { + test_utils::TestHelper provider; + BackendParams backend_params = + provider.CreateBackendFilesAndBuildParams(BackendType::kSqlite); + auto persistent_cache = PersistentCache::Open(backend_params.Copy()); + ASSERT_TRUE(persistent_cache); + + // Ensures there are entries in the cache. + const char* kKey = "foo"; + persistent_cache->Insert(kKey, base::byte_span_from_cstring("1")); + auto entry = persistent_cache->Find(kKey); + ASSERT_TRUE(entry); + + base::ElapsedTimer timer; + const int kAmountOfIteration = 16 * 1024; + for (size_t i = 0; i < kAmountOfIteration; ++i) { + auto persistent_cache_under_test = + PersistentCache::Open(backend_params.Copy()); + } + + perf_test::PerfResultReporter reporter("PersistentCache", "OpenClose"); + reporter.RegisterImportantMetric(".wall_time", "us"); + reporter.AddResult(".wall_time", + static_cast<size_t>(timer.Elapsed().InMicroseconds() / + kAmountOfIteration)); +} + +#endif // !BUILDFLAG(IS_FUCHSIA) + +} // namespace persistent_cache
diff --git a/components/policy/test_support/BUILD.gn b/components/policy/test_support/BUILD.gn index 50009316..e9a5cf4 100644 --- a/components/policy/test_support/BUILD.gn +++ b/components/policy/test_support/BUILD.gn
@@ -22,8 +22,6 @@ "request_handler_for_api_authorization.h", "request_handler_for_auto_enrollment.cc", "request_handler_for_auto_enrollment.h", - "request_handler_for_browser_public_key_upload.cc", - "request_handler_for_browser_public_key_upload.h", "request_handler_for_cert_upload.cc", "request_handler_for_cert_upload.h", "request_handler_for_check_android_management.cc", @@ -143,7 +141,6 @@ "remote_commands_state_unittest.cc", "request_handler_for_api_authorization_unittest.cc", "request_handler_for_auto_enrollment_unittest.cc", - "request_handler_for_browser_public_key_upload_unittest.cc", "request_handler_for_cert_upload_unittest.cc", "request_handler_for_check_android_management_unittest.cc", "request_handler_for_check_user_account_unittest.cc",
diff --git a/components/policy/test_support/embedded_policy_test_server.cc b/components/policy/test_support/embedded_policy_test_server.cc index 9ee7b46..b15cd41 100644 --- a/components/policy/test_support/embedded_policy_test_server.cc +++ b/components/policy/test_support/embedded_policy_test_server.cc
@@ -19,7 +19,6 @@ #include "components/policy/test_support/policy_storage.h" #include "components/policy/test_support/request_handler_for_api_authorization.h" #include "components/policy/test_support/request_handler_for_auto_enrollment.h" -#include "components/policy/test_support/request_handler_for_browser_public_key_upload.h" #include "components/policy/test_support/request_handler_for_cert_upload.h" #include "components/policy/test_support/request_handler_for_check_android_management.h" #include "components/policy/test_support/request_handler_for_chrome_desktop_report.h" @@ -112,8 +111,6 @@ ResetServerState(); RegisterHandler(std::make_unique<RequestHandlerForApiAuthorization>(this)); RegisterHandler(std::make_unique<RequestHandlerForAutoEnrollment>(this)); - RegisterHandler( - std::make_unique<RequestHandlerForBrowserPublicKeyUpload>(this)); RegisterHandler(std::make_unique<RequestHandlerForCertUpload>(this)); RegisterHandler( std::make_unique<RequestHandlerForCheckAndroidManagement>(this));
diff --git a/components/policy/test_support/embedded_policy_test_server_test_base.cc b/components/policy/test_support/embedded_policy_test_server_test_base.cc index 4b0085a..88d76e15 100644 --- a/components/policy/test_support/embedded_policy_test_server_test_base.cc +++ b/components/policy/test_support/embedded_policy_test_server_test_base.cc
@@ -66,11 +66,6 @@ AddQueryParam(dm_protocol::kParamDeviceID, device_id); } -void EmbeddedPolicyTestServerTestBase::SetProfileIdParam( - const std::string& profile_id) { - AddQueryParam(dm_protocol::kParamProfileID, profile_id); -} - void EmbeddedPolicyTestServerTestBase::SetDeviceType( const std::string& device_type) { AddQueryParam(dm_protocol::kParamDeviceType, device_type);
diff --git a/components/policy/test_support/embedded_policy_test_server_test_base.h b/components/policy/test_support/embedded_policy_test_server_test_base.h index c659e0a..604bb67 100644 --- a/components/policy/test_support/embedded_policy_test_server_test_base.h +++ b/components/policy/test_support/embedded_policy_test_server_test_base.h
@@ -44,7 +44,6 @@ void SetMethod(const std::string& method); void SetAppType(const std::string& app_type); void SetDeviceIdParam(const std::string& device_id); - void SetProfileIdParam(const std::string& profile_id); void SetDeviceType(const std::string& device_type); void SetOAuthToken(const std::string& oauth_token); void SetRequestTypeParam(const std::string& request_type);
diff --git a/components/policy/test_support/request_handler_for_browser_public_key_upload.cc b/components/policy/test_support/request_handler_for_browser_public_key_upload.cc deleted file mode 100644 index c2a0609..0000000 --- a/components/policy/test_support/request_handler_for_browser_public_key_upload.cc +++ /dev/null
@@ -1,112 +0,0 @@ -// Copyright 2025 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "components/policy/test_support/request_handler_for_browser_public_key_upload.h" - -#include "components/policy/core/common/cloud/cloud_policy_constants.h" -#include "components/policy/proto/device_management_backend.pb.h" -#include "components/policy/test_support/test_server_helpers.h" -#include "net/http/http_status_code.h" -#include "net/test/embedded_test_server/http_request.h" -#include "net/test/embedded_test_server/http_response.h" - -using net::test_server::HttpRequest; -using net::test_server::HttpResponse; - -namespace em = enterprise_management; -using BPKUR = enterprise_management::BrowserPublicKeyUploadRequest; - -namespace policy { - -namespace { - -// Generates a self-signed issuer_cert_builder certificate with -// `issuer_common_name`. Then issues a certificate for the public key `spki_der` -// (DER-encoded X.509 SubjectPublicKeyInfo) with SubjectCommonName -// `subject_common_name`. Returns a PEM-encoded representation of that -// certificate. -std::string GeneratePEMEncodedCertificate( - const std::string& public_key, - const std::string& issuer_common_name, - const std::string& subject_common_name) { - std::vector<uint8_t> pk(public_key.begin(), public_key.end()); - base::span<const uint8_t> spki_der(pk); - net::CertBuilder issuer_cert_builder(/*orig_cert=*/nullptr, - /*issuer=*/nullptr); - issuer_cert_builder.SetSubjectCommonName(issuer_common_name); - issuer_cert_builder.GenerateRSAKey(); - std::unique_ptr<net::CertBuilder> cert_builder = - net::CertBuilder::FromSubjectPublicKeyInfo(spki_der, - &issuer_cert_builder); - cert_builder->SetSignatureAlgorithm( - bssl::SignatureAlgorithm::kRsaPkcs1Sha256); - cert_builder->SetValidity(base::Time::Now(), - base::Time::Now() + base::Days(30)); - cert_builder->SetSubjectCommonName(subject_common_name); - - return cert_builder->GetPEM(); -} - -} // namespace - -RequestHandlerForBrowserPublicKeyUpload:: - RequestHandlerForBrowserPublicKeyUpload(EmbeddedPolicyTestServer* parent) - : EmbeddedPolicyTestServer::RequestHandler(parent) {} - -RequestHandlerForBrowserPublicKeyUpload:: - ~RequestHandlerForBrowserPublicKeyUpload() = default; - -std::string RequestHandlerForBrowserPublicKeyUpload::RequestType() { - return dm_protocol::kValueBrowserUploadPublicKey; -} - -std::unique_ptr<HttpResponse> -RequestHandlerForBrowserPublicKeyUpload::HandleRequest( - const HttpRequest& request) { - // Make sure dm token is present. - std::string dm_token; - if (!GetDeviceTokenFromRequest(request, &dm_token)) { - return CreateHttpResponse(net::HTTP_UNAUTHORIZED, "Missing dm token"); - } - - // Verify if Profile or Browser. - std::string profile_id; - bool is_profile = GetProfileIdFromRequest(request, &profile_id); - - em::DeviceManagementRequest device_management_request; - device_management_request.ParseFromString(request.content); - const em::BrowserPublicKeyUploadRequest& key_upload_request = - device_management_request.browser_public_key_upload_request(); - - if (key_upload_request.public_key().empty()) { - return CreateHttpResponse(net::HTTP_BAD_REQUEST, "Missing public key"); - } - - if (key_upload_request.key_trust_level() == - BPKUR::KEY_TRUST_LEVEL_UNSPECIFIED) { - return CreateHttpResponse(net::HTTP_BAD_REQUEST, - "Missing public key trust level"); - } - - if (key_upload_request.key_type() == BPKUR::KEY_TYPE_UNSPECIFIED) { - return CreateHttpResponse(net::HTTP_BAD_REQUEST, "Missing public key type"); - } - - em::DeviceManagementResponse device_management_response; - if (key_upload_request.provision_certificate()) { - device_management_response.mutable_browser_public_key_upload_response() - ->set_pem_encoded_certificate(GeneratePEMEncodedCertificate( - key_upload_request.public_key(), - /*issuer_common_name=*/ - is_profile ? "Profile Root CA" : "Browser Root CA", - /*subject_common_name=*/"Test Client Cert")); - } - - device_management_response.mutable_browser_public_key_upload_response() - ->set_response_code(em::BrowserPublicKeyUploadResponse::SUCCESS); - - return CreateHttpResponse(net::HTTP_OK, device_management_response); -} - -} // namespace policy
diff --git a/components/policy/test_support/request_handler_for_browser_public_key_upload.h b/components/policy/test_support/request_handler_for_browser_public_key_upload.h deleted file mode 100644 index c97d9b0..0000000 --- a/components/policy/test_support/request_handler_for_browser_public_key_upload.h +++ /dev/null
@@ -1,33 +0,0 @@ -// Copyright 2025 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef COMPONENTS_POLICY_TEST_SUPPORT_REQUEST_HANDLER_FOR_BROWSER_PUBLIC_KEY_UPLOAD_H_ -#define COMPONENTS_POLICY_TEST_SUPPORT_REQUEST_HANDLER_FOR_BROWSER_PUBLIC_KEY_UPLOAD_H_ - -#include "components/policy/test_support/embedded_policy_test_server.h" - -namespace policy { - -class RequestHandlerForBrowserPublicKeyUpload - : public EmbeddedPolicyTestServer::RequestHandler { - public: - explicit RequestHandlerForBrowserPublicKeyUpload( - EmbeddedPolicyTestServer* parent); - - RequestHandlerForBrowserPublicKeyUpload( - RequestHandlerForBrowserPublicKeyUpload&& handler) = delete; - RequestHandlerForBrowserPublicKeyUpload& operator=( - RequestHandlerForBrowserPublicKeyUpload&& handler) = delete; - - ~RequestHandlerForBrowserPublicKeyUpload() override; - - // EmbeddedPolicyTestServer::RequestHandler: - std::string RequestType() override; - std::unique_ptr<net::test_server::HttpResponse> HandleRequest( - const net::test_server::HttpRequest& request) override; -}; - -} // namespace policy - -#endif // COMPONENTS_POLICY_TEST_SUPPORT_REQUEST_HANDLER_FOR_BROWSER_PUBLIC_KEY_UPLOAD_H_
diff --git a/components/policy/test_support/request_handler_for_browser_public_key_upload_unittest.cc b/components/policy/test_support/request_handler_for_browser_public_key_upload_unittest.cc deleted file mode 100644 index 3c2266c..0000000 --- a/components/policy/test_support/request_handler_for_browser_public_key_upload_unittest.cc +++ /dev/null
@@ -1,217 +0,0 @@ -// Copyright 2025 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "components/policy/test_support/request_handler_for_browser_public_key_upload.h" - -#include <optional> -#include <utility> - -#include "base/base64.h" -#include "base/containers/span.h" -#include "components/policy/core/common/cloud/cloud_policy_constants.h" -#include "components/policy/proto/device_management_backend.pb.h" -#include "components/policy/test_support/embedded_policy_test_server_test_base.h" -#include "components/policy/test_support/policy_storage.h" -#include "crypto/keypair.h" -#include "net/cert/x509_certificate.h" -#include "net/http/http_status_code.h" -#include "testing/gtest/include/gtest/gtest.h" - -using BPKUR = enterprise_management::BrowserPublicKeyUploadRequest; - -namespace policy { - -namespace { - -constexpr char kDeviceId[] = "fake_device_id"; -constexpr char kProfileId[] = "fake_profile_id"; -constexpr char kDmToken[] = "dm_token"; - -// Base64-encoded EC private key PKCS #8 PrivateKeyInfo block. -constexpr char kEncodedPrivateKey[] = - "MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgzsLi0tbAG43E2lR6vwq4t+" - "mDmBRGXhkbco2G2v5+0gKhRANCAAQ8YD0im5qm9EF6c1R/Yn9b/" - "vnWWcVnQwc+rk5VziUjnoRGGyBwC52+5w2R7u68SkkN2BTRGZ/RQ/bop4Mpwa/O"; - -std::optional<crypto::keypair::PrivateKey> LoadPrivateKey() { - auto decoded_key = base::Base64Decode(kEncodedPrivateKey); - if (!decoded_key) { - return std::nullopt; - } - - return crypto::keypair::PrivateKey::FromPrivateKeyInfo(decoded_key.value()); -} - -void VerifyIssuerCommonName(const std::string& pem_encoded_certificate, - std::string_view expected_issuer_name) { - net::CertificateList certs = - net::X509Certificate::CreateCertificateListFromBytes( - base::as_byte_span(pem_encoded_certificate), - net::X509Certificate::FORMAT_AUTO); - ASSERT_FALSE(certs.empty()); - ASSERT_TRUE(certs[0]); - EXPECT_EQ(certs[0]->issuer().common_name, expected_issuer_name); -} - -} // namespace - -class RequestHandlerForBrowserPublicKeyUploadTest - : public EmbeddedPolicyTestServerTestBase { - public: - RequestHandlerForBrowserPublicKeyUploadTest() = default; - ~RequestHandlerForBrowserPublicKeyUploadTest() override = default; - - void SetUp() override { - EmbeddedPolicyTestServerTestBase::SetUp(); - - SetRequestTypeParam(dm_protocol::kValueBrowserUploadPublicKey); - SetAppType(dm_protocol::kValueAppType); - SetDeviceType(dm_protocol::kValueDeviceType); - SetDeviceIdParam(kDeviceId); - SetDeviceTokenHeader(kDmToken); - } -}; - -TEST_F(RequestHandlerForBrowserPublicKeyUploadTest, HandleBrowserKeyUpload) { - // Can set a fake public key when not requiring a cert. - enterprise_management::DeviceManagementRequest device_management_request; - auto* request = - device_management_request.mutable_browser_public_key_upload_request(); - request->set_public_key("test_key"); - request->set_key_trust_level(BPKUR::CHROME_BROWSER_HW_KEY); - request->set_key_type(BPKUR::RSA_KEY); - - SetPayload(device_management_request); - - StartRequestAndWait(); - - EXPECT_EQ(GetResponseCode(), net::HTTP_OK); - ASSERT_TRUE(HasResponseBody()); - auto response = GetDeviceManagementResponse(); - EXPECT_TRUE(response.has_browser_public_key_upload_response()); -} - -TEST_F(RequestHandlerForBrowserPublicKeyUploadTest, HandleProfileKeyUpload) { - SetProfileIdParam(kProfileId); - - // Can set a fake public key when not requiring a cert. - enterprise_management::DeviceManagementRequest device_management_request; - auto* request = - device_management_request.mutable_browser_public_key_upload_request(); - request->set_public_key("test_key"); - request->set_key_trust_level(BPKUR::CHROME_BROWSER_HW_KEY); - request->set_key_type(BPKUR::RSA_KEY); - - SetPayload(device_management_request); - - StartRequestAndWait(); - - EXPECT_EQ(GetResponseCode(), net::HTTP_OK); - ASSERT_TRUE(HasResponseBody()); - auto response = GetDeviceManagementResponse(); - EXPECT_TRUE(response.has_browser_public_key_upload_response()); -} - -TEST_F(RequestHandlerForBrowserPublicKeyUploadTest, HandleBrowserCertRequest) { - auto ec_private_key = LoadPrivateKey(); - ASSERT_TRUE(ec_private_key); - auto public_key = ec_private_key->ToSubjectPublicKeyInfo(); - - enterprise_management::DeviceManagementRequest device_management_request; - auto* request = - device_management_request.mutable_browser_public_key_upload_request(); - request->set_public_key(public_key.data(), public_key.size()); - request->set_key_trust_level(BPKUR::CHROME_BROWSER_OS_KEY); - request->set_key_type(BPKUR::EC_KEY); - request->set_provision_certificate(true); - - SetPayload(device_management_request); - - StartRequestAndWait(); - - EXPECT_EQ(GetResponseCode(), net::HTTP_OK); - ASSERT_TRUE(HasResponseBody()); - auto response = GetDeviceManagementResponse(); - ASSERT_TRUE(response.has_browser_public_key_upload_response()); - - auto& upload_response = response.browser_public_key_upload_response(); - ASSERT_TRUE(upload_response.has_pem_encoded_certificate()); - VerifyIssuerCommonName(upload_response.pem_encoded_certificate(), - "Browser Root CA"); -} - -TEST_F(RequestHandlerForBrowserPublicKeyUploadTest, HandleProfileCertRequest) { - auto ec_private_key = LoadPrivateKey(); - ASSERT_TRUE(ec_private_key); - auto public_key = ec_private_key->ToSubjectPublicKeyInfo(); - - SetProfileIdParam(kProfileId); - - enterprise_management::DeviceManagementRequest device_management_request; - auto* request = - device_management_request.mutable_browser_public_key_upload_request(); - request->set_public_key(public_key.data(), public_key.size()); - request->set_key_trust_level(BPKUR::CHROME_BROWSER_OS_KEY); - request->set_key_type(BPKUR::EC_KEY); - request->set_provision_certificate(true); - - SetPayload(device_management_request); - - StartRequestAndWait(); - - EXPECT_EQ(GetResponseCode(), net::HTTP_OK); - ASSERT_TRUE(HasResponseBody()); - auto response = GetDeviceManagementResponse(); - ASSERT_TRUE(response.has_browser_public_key_upload_response()); - - auto& upload_response = response.browser_public_key_upload_response(); - ASSERT_TRUE(upload_response.has_pem_encoded_certificate()); - VerifyIssuerCommonName(upload_response.pem_encoded_certificate(), - "Profile Root CA"); -} - -TEST_F(RequestHandlerForBrowserPublicKeyUploadTest, - FailWithMissingPublicKeyData) { - enterprise_management::DeviceManagementRequest device_management_request; - auto* request = - device_management_request.mutable_browser_public_key_upload_request(); - request->set_key_trust_level(BPKUR::CHROME_BROWSER_HW_KEY); - request->set_key_type(BPKUR::RSA_KEY); - - SetPayload(device_management_request); - - StartRequestAndWait(); - - EXPECT_EQ(GetResponseCode(), net::HTTP_BAD_REQUEST); -} - -TEST_F(RequestHandlerForBrowserPublicKeyUploadTest, FailWithMissingTrustLevel) { - enterprise_management::DeviceManagementRequest device_management_request; - auto* request = - device_management_request.mutable_browser_public_key_upload_request(); - request->set_public_key("test_key"); - request->set_key_type(BPKUR::RSA_KEY); - - SetPayload(device_management_request); - - StartRequestAndWait(); - - EXPECT_EQ(GetResponseCode(), net::HTTP_BAD_REQUEST); -} - -TEST_F(RequestHandlerForBrowserPublicKeyUploadTest, FailWithMissingKeyType) { - enterprise_management::DeviceManagementRequest device_management_request; - auto* request = - device_management_request.mutable_browser_public_key_upload_request(); - request->set_public_key("test_key"); - request->set_key_trust_level(BPKUR::CHROME_BROWSER_HW_KEY); - - SetPayload(device_management_request); - - StartRequestAndWait(); - - EXPECT_EQ(GetResponseCode(), net::HTTP_BAD_REQUEST); -} - -} // namespace policy
diff --git a/components/policy/test_support/test_server_helpers.cc b/components/policy/test_support/test_server_helpers.cc index 09dd290..c65ad8c 100644 --- a/components/policy/test_support/test_server_helpers.cc +++ b/components/policy/test_support/test_server_helpers.cc
@@ -109,17 +109,6 @@ dm_protocol::kOAuthTokenHeaderPrefix, out); } -bool GetProfileIdFromRequest(const net::test_server::HttpRequest& request, - std::string* out) { - std::string profile_id = - KeyValueFromUrl(request.GetURL(), dm_protocol::kParamProfileID); - if (profile_id.empty()) { - return false; - } - *out = profile_id; - return true; -} - std::unique_ptr<HttpResponse> CreateHttpResponse( net::HttpStatusCode code, const em::DeviceManagementResponse& proto_content) {
diff --git a/components/policy/test_support/test_server_helpers.h b/components/policy/test_support/test_server_helpers.h index fe420c6..de1e7cfa0 100644 --- a/components/policy/test_support/test_server_helpers.h +++ b/components/policy/test_support/test_server_helpers.h
@@ -60,11 +60,6 @@ bool GetGoogleLoginFromRequest(const net::test_server::HttpRequest& request, std::string* out); -// Returns true if a Profile ID is specified in the `request` URL, and copies -// its value to `out`. -bool GetProfileIdFromRequest(const net::test_server::HttpRequest& request, - std::string* out); - // Returns a text/plain HttpResponse with a given `code` and `content`. std::unique_ptr<net::test_server::HttpResponse> CreateHttpResponse( net::HttpStatusCode code,
diff --git a/components/safe_browsing/content/renderer/phishing_classifier/scorer.cc b/components/safe_browsing/content/renderer/phishing_classifier/scorer.cc index 43b3fa9..fedfacba1 100644 --- a/components/safe_browsing/content/renderer/phishing_classifier/scorer.cc +++ b/components/safe_browsing/content/renderer/phishing_classifier/scorer.cc
@@ -16,7 +16,6 @@ #include "base/memory/shared_memory_mapping.h" #include "base/metrics/histogram_functions.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/strings/string_number_conversions.h" #include "base/task/sequenced_task_runner.h" #include "base/task/task_traits.h" @@ -174,8 +173,8 @@ return std::string(); } - CHECK_EQ(downsampled.width(), width, base::NotFatalUntil::M125); - CHECK_EQ(downsampled.height(), height, base::NotFatalUntil::M125); + CHECK_EQ(downsampled.width(), width); + CHECK_EQ(downsampled.height(), height); // Format as an RGB buffer for input into the model std::string data;
diff --git a/components/search_engines/android/template_url_service_android.cc b/components/search_engines/android/template_url_service_android.cc index 3f50161..dc1bcf0 100644 --- a/components/search_engines/android/template_url_service_android.cc +++ b/components/search_engines/android/template_url_service_android.cc
@@ -18,7 +18,6 @@ #include "base/functional/bind.h" #include "base/memory/raw_ptr.h" #include "base/metrics/field_trial_params.h" -#include "base/not_fatal_until.h" #include "base/notreached.h" #include "base/strings/string_util.h" #include "base/strings/utf_string_conversions.h" @@ -406,7 +405,7 @@ jimage_translate_target_language_param_key) { // The function is scheduled to run only when the service is loaded, see // `TemplateUrlService#runWhenLoaded()`. - CHECK(template_url_service_->loaded(), base::NotFatalUntil::M128); + CHECK(template_url_service_->loaded()); // Check if there is already a search engine created by a regulatory program. TemplateURLService::TemplateURLVector template_urls =
diff --git a/components/search_engines/template_url_service.cc b/components/search_engines/template_url_service.cc index fdb4a31..0165abc0 100644 --- a/components/search_engines/template_url_service.cc +++ b/components/search_engines/template_url_service.cc
@@ -29,7 +29,6 @@ #include "base/metrics/field_trial_params.h" #include "base/metrics/histogram_functions.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/notreached.h" #include "base/observer_list.h" #include "base/rand_util.h" @@ -1139,7 +1138,7 @@ // it as DSE means that we don't have a policy-enforced engine, and we // know that the incoming engine otherwise meets the criteria to be to be // set as DSE. - CHECK(CanMakeDefault(new_play_api_turl.get()), base::NotFatalUntil::M129); + CHECK(CanMakeDefault(new_play_api_turl.get())); // Clearing the member is OK here, we just have to make sure it is // re-populated by the time `scoper` is cleared. @@ -1156,7 +1155,7 @@ // Adding the engine should be successful, we already checked for blockers // above. - CHECK(new_play_api_turl_ptr, base::NotFatalUntil::M129); + CHECK(new_play_api_turl_ptr); // Part 2: Set as DSE. // It is still possible that policies control the DSE, so ensure we don't @@ -1241,8 +1240,8 @@ // kicked in after a choice screen was shown, that could be a way to // enter this state // TODO(crbug.com/328041262): Investigate mitigation options. - CHECK_NE(choice_made_location, search_engines::ChoiceMadeLocation::kOther, - base::NotFatalUntil::M127); + CHECK_NE(choice_made_location, + search_engines::ChoiceMadeLocation::kOther); } } else { // We rely on the DefaultSearchManager to call ApplyDefaultSearchChange if,
diff --git a/components/subresource_filter/android/ads_blocked_dialog.cc b/components/subresource_filter/android/ads_blocked_dialog.cc index 8e84eb87..3c74bd43 100644 --- a/components/subresource_filter/android/ads_blocked_dialog.cc +++ b/components/subresource_filter/android/ads_blocked_dialog.cc
@@ -12,7 +12,6 @@ #include "base/android/jni_string.h" #include "base/check.h" #include "base/memory/ptr_util.h" -#include "base/not_fatal_until.h" #include "content/public/browser/web_contents.h" #include "ui/android/window_android.h" @@ -27,7 +26,7 @@ base::OnceClosure allow_ads_clicked_callback, base::OnceClosure learn_more_clicked_callback, base::OnceClosure dialog_dismissed_callback) { - CHECK(web_contents, base::NotFatalUntil::M129); + CHECK(web_contents); ui::WindowAndroid* window_android = web_contents->GetTopLevelNativeWindow(); if (!window_android) {
diff --git a/components/subresource_filter/content/browser/ads_blocked_message_delegate.cc b/components/subresource_filter/content/browser/ads_blocked_message_delegate.cc index a5a6315..b5ace67 100644 --- a/components/subresource_filter/content/browser/ads_blocked_message_delegate.cc +++ b/components/subresource_filter/content/browser/ads_blocked_message_delegate.cc
@@ -9,7 +9,6 @@ #include "base/check.h" #include "base/functional/bind.h" #include "base/memory/ptr_util.h" -#include "base/not_fatal_until.h" #include "base/strings/utf_string_conversions.h" #include "components/messages/android/message_dispatcher_bridge.h" #include "components/resources/android/theme_resources.h" @@ -116,7 +115,7 @@ void AdsBlockedMessageDelegate::HandleMessageDismissed( messages::DismissReason dismiss_reason) { - CHECK(message_, base::NotFatalUntil::M129); + CHECK(message_); message_.reset(); } @@ -145,12 +144,12 @@ // will be restored when the user navigates back to the original tab. return; } - CHECK(ads_blocked_dialog_, base::NotFatalUntil::M129); + CHECK(ads_blocked_dialog_); ads_blocked_dialog_.reset(); } void AdsBlockedMessageDelegate::ShowDialog(bool should_post_dialog) { - CHECK(!reprompt_required_, base::NotFatalUntil::M129); + CHECK(!reprompt_required_); // Binding with base::Unretained(this) is safe here because // AdsBlockedMessageDelegate owns ads_blocked_dialog_. Callbacks won't be // called after the AdsBlockedMessageDelegate object is destroyed.
diff --git a/components/subresource_filter/content/browser/content_activation_list_utils.cc b/components/subresource_filter/content/browser/content_activation_list_utils.cc index 7b7eb43c..491fecdc 100644 --- a/components/subresource_filter/content/browser/content_activation_list_utils.cc +++ b/components/subresource_filter/content/browser/content_activation_list_utils.cc
@@ -5,7 +5,6 @@ #include "components/subresource_filter/content/browser/content_activation_list_utils.h" #include "base/check.h" -#include "base/not_fatal_until.h" #include "components/subresource_filter/core/browser/subresource_filter_features.h" namespace subresource_filter { @@ -65,7 +64,7 @@ safe_browsing::SBThreatType threat_type, const safe_browsing::ThreatMetadata& threat_type_metadata, bool* warning) { - CHECK(warning, base::NotFatalUntil::M129); + CHECK(warning); bool is_phishing_interstitial = (threat_type == safe_browsing::SBThreatType::SB_THREAT_TYPE_URL_PHISHING); bool is_soc_engineering_ads_interstitial =
diff --git a/components/subresource_filter/content/browser/content_subresource_filter_throttle_manager.cc b/components/subresource_filter/content/browser/content_subresource_filter_throttle_manager.cc index 8ed5ff52..85700a67 100644 --- a/components/subresource_filter/content/browser/content_subresource_filter_throttle_manager.cc +++ b/components/subresource_filter/content/browser/content_subresource_filter_throttle_manager.cc
@@ -14,7 +14,6 @@ #include "base/functional/bind.h" #include "base/metrics/histogram_functions.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/strings/stringprintf.h" #include "base/trace_event/trace_event.h" #include "base/trace_event/traced_value.h" @@ -76,8 +75,7 @@ VerifiedRulesetDealer::Handle* dealer_handle, ContentSubresourceFilterWebContentsHelper& web_contents_helper, content::NavigationHandle& initiating_navigation_handle) { - CHECK(IsInSubresourceFilterRoot(&initiating_navigation_handle), - base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(&initiating_navigation_handle)); if (!base::FeatureList::IsEnabled(kSafeBrowsingSubresourceFilter)) { return nullptr; @@ -331,8 +329,7 @@ filter->activation_state(), kSafeBrowsingRulesetConfig.uma_tag); if (filter->activation_state().enable_logging) { CHECK(filter->activation_state().activation_level != - mojom::ActivationLevel::kDisabled, - base::NotFatalUntil::M129); + mojom::ActivationLevel::kDisabled); frame_host->AddMessageToConsole( blink::mojom::ConsoleMessageLevel::kWarning, kActivationConsoleMessage); @@ -354,8 +351,8 @@ ActivationStateComputingNavigationThrottle* throttle, content::RenderFrameHost* frame_host, bool& did_inherit_opener_activation) { - CHECK(navigation_handle, base::NotFatalUntil::M129); - CHECK(frame_host, base::NotFatalUntil::M129); + CHECK(navigation_handle); + CHECK(frame_host); std::unique_ptr<AsyncDocumentSubresourceFilter> filter; std::optional<mojom::ActivationState> activation_to_inherit; @@ -384,8 +381,7 @@ // navigation redirects from a URL handled by the network stack to // about:blank, a filter can already exist here. We replace it to match // behavior for other about:blank frames. - CHECK(!filter || navigation_handle->GetRedirectChain().size() != 1, - base::NotFatalUntil::M129); + CHECK(!filter || navigation_handle->GetRedirectChain().size() != 1); activation_to_inherit = GetFrameActivationState(navigation_handle->GetParentFrame()); } @@ -393,7 +389,7 @@ if (activation_to_inherit.has_value() && activation_to_inherit->activation_level != mojom::ActivationLevel::kDisabled) { - CHECK(dealer_handle_, base::NotFatalUntil::M129); + CHECK(dealer_handle_); // This constructs the filter in a way that allows it to be immediately // used. See the AsyncDocumentSubresourceFilter constructor for details. @@ -428,8 +424,7 @@ content::NavigationHandle* navigation_handle, const mojom::ActivationLevel& activation_level, bool did_inherit_opener_activation) { - CHECK(IsInSubresourceFilterRoot(navigation_handle), - base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(navigation_handle)); UMA_HISTOGRAM_ENUMERATION("SubresourceFilter.PageLoad.ActivationState", activation_level); @@ -450,8 +445,8 @@ } void ContentSubresourceFilterThrottleManager::DidBecomePrimaryPage() { - CHECK(page_, base::NotFatalUntil::M129); - CHECK(page_->IsPrimary(), base::NotFatalUntil::M129); + CHECK(page_); + CHECK(page_->IsPrimary()); // If we tried to notify while non-primary, we didn't show UI so do that now // that the page became primary. This also leads to reattempting notification // if a page transitioned from primary to non-primary and back (BFCache). @@ -462,8 +457,8 @@ void ContentSubresourceFilterThrottleManager::OnPageCreated( content::Page& page) { - CHECK(!page.GetMainDocument().IsFencedFrameRoot(), base::NotFatalUntil::M129); - CHECK(!page_, base::NotFatalUntil::M129); + CHECK(!page.GetMainDocument().IsFencedFrameRoot()); + CHECK(!page_); page_ = &page; profile_interaction_manager_->DidCreatePage(*page_); } @@ -475,9 +470,8 @@ void ContentSubresourceFilterThrottleManager::OnPageActivationComputed( content::NavigationHandle* navigation_handle, const mojom::ActivationState& activation_state) { - CHECK(IsInSubresourceFilterRoot(navigation_handle), - base::NotFatalUntil::M129); - CHECK(!navigation_handle->HasCommitted(), base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(navigation_handle)); + CHECK(!navigation_handle->HasCommitted()); auto it = ongoing_activation_throttles_.find(navigation_handle->GetNavigationId()); @@ -505,8 +499,7 @@ void ContentSubresourceFilterThrottleManager::OnChildFrameNavigationEvaluated( content::NavigationHandle* navigation_handle, LoadPolicy load_policy) { - CHECK(!IsInSubresourceFilterRoot(navigation_handle), - base::NotFatalUntil::M129); + CHECK(!IsInSubresourceFilterRoot(navigation_handle)); if (!navigation_handle->GetParentFrameOrOuterDocument()) { return; } @@ -533,9 +526,8 @@ MaybeCreateAndAddNavigationThrottles( content::NavigationThrottleRegistry& registry) { content::NavigationHandle& navigation_handle = registry.GetNavigationHandle(); - CHECK(!navigation_handle.IsSameDocument(), base::NotFatalUntil::M129); - CHECK(!ShouldInheritActivation(navigation_handle.GetURL()), - base::NotFatalUntil::M129); + CHECK(!navigation_handle.IsSameDocument()); + CHECK(!ShouldInheritActivation(navigation_handle.GetURL())); if (IsInSubresourceFilterRoot(&navigation_handle) && database_manager_) { registry.AddThrottle(std::make_unique<SafeBrowsingPageActivationThrottle>( @@ -548,8 +540,7 @@ MaybeCreateAndAddChildNavigationThrottle(registry); CHECK(!base::Contains(ongoing_activation_throttles_, - navigation_handle.GetNavigationId()), - base::NotFatalUntil::M129); + navigation_handle.GetNavigationId())); if (auto activation_throttle = MaybeCreateActivationStateComputingThrottle(registry)) { ongoing_activation_throttles_[navigation_handle.GetNavigationId()] = @@ -583,8 +574,8 @@ } void ContentSubresourceFilterThrottleManager::OnReloadRequested() { - CHECK(page_, base::NotFatalUntil::M129); - CHECK(page_->IsPrimary(), base::NotFatalUntil::M129); + CHECK(page_); + CHECK(page_->IsPrimary()); profile_interaction_manager_->OnReloadRequested(); } @@ -647,7 +638,7 @@ if (!parent_filter) { return nullptr; } - CHECK(ruleset_handle_, base::NotFatalUntil::M129); + CHECK(ruleset_handle_); return ActivationStateComputingNavigationThrottle::CreateForChild( registry, ruleset_handle_.get(), parent_filter->activation_state(), kSafeBrowsingRulesetConfig.uma_tag); @@ -656,8 +647,7 @@ AsyncDocumentSubresourceFilter* ContentSubresourceFilterThrottleManager::GetParentFrameFilter( content::NavigationHandle* child_frame_navigation) { - CHECK(!IsInSubresourceFilterRoot(child_frame_navigation), - base::NotFatalUntil::M129); + CHECK(!IsInSubresourceFilterRoot(child_frame_navigation)); return GetFrameFilter( child_frame_navigation->GetParentFrameOrOuterDocument()); } @@ -674,22 +664,21 @@ AsyncDocumentSubresourceFilter* ContentSubresourceFilterThrottleManager::GetFrameFilter( content::RenderFrameHost* frame_host) { - CHECK(frame_host, base::NotFatalUntil::M129); + CHECK(frame_host); auto it = frame_host_filter_map_.find(frame_host); if (it == frame_host_filter_map_.end()) { return nullptr; } - CHECK(it->second, base::NotFatalUntil::M129); + CHECK(it->second); return it->second.get(); } void ContentSubresourceFilterThrottleManager::MaybeShowNotification( content::RenderFrameHost* frame_host) { - CHECK(page_, base::NotFatalUntil::M129); - CHECK_EQ(&GetSubresourceFilterRootPage(frame_host), page_, - base::NotFatalUntil::M129); + CHECK(page_); + CHECK_EQ(&GetSubresourceFilterRootPage(frame_host), page_); if (current_committed_load_has_notified_disallowed_load_) { return; @@ -741,15 +730,13 @@ bool is_ad_frame) { content::FrameTreeNodeId frame_tree_node_id = render_frame_host->GetFrameTreeNodeId(); - CHECK(base::Contains(tracked_ad_evidence_, frame_tree_node_id), - base::NotFatalUntil::M129); + CHECK(base::Contains(tracked_ad_evidence_, frame_tree_node_id)); // TODO(crbug.com/373985560): This is rarely hit. After fixing, upgrade to a // CHECK. DCHECK_EQ(tracked_ad_evidence_.at(frame_tree_node_id).IndicatesAdFrame(), is_ad_frame); - CHECK(render_frame_host->GetParentOrOuterDocument(), - base::NotFatalUntil::M129); + CHECK(render_frame_host->GetParentOrOuterDocument()); // `ad_frames_` does not need updating. if (is_ad_frame == base::Contains(ad_frames_, frame_tree_node_id)) { @@ -774,8 +761,7 @@ void ContentSubresourceFilterThrottleManager::SetIsAdFrameForTesting( content::RenderFrameHost* render_frame_host, bool is_ad_frame) { - CHECK(render_frame_host->GetParentOrOuterDocument(), - base::NotFatalUntil::M129); + CHECK(render_frame_host->GetParentOrOuterDocument()); if (is_ad_frame == base::Contains(ad_frames_, render_frame_host->GetFrameTreeNodeId())) { return; @@ -824,7 +810,7 @@ // iframes, see `AdScriptDidCreateFencedFrame`. content::RenderFrameHost* render_frame_host = receiver_.GetCurrentTargetFrame(); - CHECK(!render_frame_host->IsFencedFrameRoot(), base::NotFatalUntil::M129); + CHECK(!render_frame_host->IsFencedFrameRoot()); OnFrameIsAd(receiver_.GetCurrentTargetFrame()); } @@ -837,9 +823,9 @@ void ContentSubresourceFilterThrottleManager::OnAdsViolationTriggered( mojom::AdsViolation violation) { - CHECK(page_, base::NotFatalUntil::M129); + CHECK(page_); CHECK_EQ(&GetSubresourceFilterRootPage(receiver_.GetCurrentTargetFrame()), - page_, base::NotFatalUntil::M129); + page_); // TODO(bokan) How should we deal with violations coming from a fenced frame? // Should we pass in the fenced frame root instead? crbug.com/1263541. OnAdsViolationTriggered(&page_->GetMainDocument(), violation); @@ -870,7 +856,7 @@ // fenced frames. content::RenderFrameHost* owner_frame = receiver_.GetCurrentTargetFrame(); - CHECK(owner_frame, base::NotFatalUntil::M129); + CHECK(owner_frame); auto* fenced_frame_root = content::RenderFrameHost::FromPlaceholderToken( owner_frame->GetProcess()->GetDeprecatedID(), placeholder_token); @@ -894,15 +880,14 @@ } CHECK(!base::Contains(tracked_ad_evidence_, - fenced_frame_root->GetFrameTreeNodeId()), - base::NotFatalUntil::M129); + fenced_frame_root->GetFrameTreeNodeId())); OnChildFrameWasCreatedByAdScript(fenced_frame_root); } void ContentSubresourceFilterThrottleManager::OnChildFrameWasCreatedByAdScript( content::RenderFrameHost* frame_host) { - CHECK(frame_host, base::NotFatalUntil::M129); - CHECK(!IsSubresourceFilterRoot(frame_host), base::NotFatalUntil::M129); + CHECK(frame_host); + CHECK(!IsSubresourceFilterRoot(frame_host)); EnsureFrameAdEvidence(frame_host) .set_created_by_ad_script( @@ -912,8 +897,7 @@ blink::FrameAdEvidence& ContentSubresourceFilterThrottleManager::EnsureFrameAdEvidence( content::NavigationHandle* navigation_handle) { - CHECK(!IsInSubresourceFilterRoot(navigation_handle), - base::NotFatalUntil::M129); + CHECK(!IsInSubresourceFilterRoot(navigation_handle)); auto frame_tree_node_id = navigation_handle->GetFrameTreeNodeId(); auto parent_frame_tree_node_id = navigation_handle->GetParentFrameOrOuterDocument()->GetFrameTreeNodeId(); @@ -923,7 +907,7 @@ blink::FrameAdEvidence& ContentSubresourceFilterThrottleManager::EnsureFrameAdEvidence( content::RenderFrameHost* render_frame_host) { - CHECK(!IsSubresourceFilterRoot(render_frame_host), base::NotFatalUntil::M129); + CHECK(!IsSubresourceFilterRoot(render_frame_host)); auto frame_tree_node_id = render_frame_host->GetFrameTreeNodeId(); auto parent_frame_tree_node_id = render_frame_host->GetParentOrOuterDocument()->GetFrameTreeNodeId(); @@ -934,8 +918,8 @@ ContentSubresourceFilterThrottleManager::EnsureFrameAdEvidence( content::FrameTreeNodeId frame_tree_node_id, content::FrameTreeNodeId parent_frame_tree_node_id) { - CHECK(frame_tree_node_id, base::NotFatalUntil::M129); - CHECK(parent_frame_tree_node_id, base::NotFatalUntil::M129); + CHECK(frame_tree_node_id); + CHECK(parent_frame_tree_node_id); return tracked_ad_evidence_ .emplace(frame_tree_node_id, /*parent_is_ad=*/base::Contains(ad_frames_,
diff --git a/components/subresource_filter/content/browser/content_subresource_filter_web_contents_helper.cc b/components/subresource_filter/content/browser/content_subresource_filter_web_contents_helper.cc index 4b012d7..bddc151 100644 --- a/components/subresource_filter/content/browser/content_subresource_filter_web_contents_helper.cc +++ b/components/subresource_filter/content/browser/content_subresource_filter_web_contents_helper.cc
@@ -9,7 +9,6 @@ #include "base/check.h" #include "base/feature_list.h" -#include "base/not_fatal_until.h" #include "base/supports_user_data.h" #include "components/subresource_filter/content/browser/content_subresource_filter_throttle_manager.h" #include "components/subresource_filter/content/shared/browser/utils.h" @@ -126,7 +125,7 @@ // We should never be requesting the throttle manager for a navigation that // moves a page into the primary frame tree (e.g. prerender activation, // BFCache restoration). - CHECK(!handle.IsPageActivation(), base::NotFatalUntil::M129); + CHECK(!handle.IsPageActivation()); if (WillCreateNewThrottleManager(handle)) { auto* container = @@ -137,7 +136,7 @@ ContentSubresourceFilterThrottleManager* throttle_manager = container->Get(); - CHECK(throttle_manager, base::NotFatalUntil::M129); + CHECK(throttle_manager); return throttle_manager; } @@ -151,8 +150,7 @@ // due to a parent's navigation (where the navigation's handle's RFH may be // null); this does not affect the result as both frames have the same // throttle manager. - CHECK(handle.IsSameDocument() || !IsInSubresourceFilterRoot(&handle), - base::NotFatalUntil::M129); + CHECK(handle.IsSameDocument() || !IsInSubresourceFilterRoot(&handle)); content::RenderFrameHost* rfh = IsInSubresourceFilterRoot(&handle) ? handle.GetRenderFrameHost() : handle.GetParentFrameOrOuterDocument(); @@ -182,7 +180,7 @@ void ContentSubresourceFilterWebContentsHelper::WillDestroyThrottleManager( ContentSubresourceFilterThrottleManager* throttle_manager) { bool was_erased = throttle_managers_.erase(throttle_manager); - CHECK(was_erased, base::NotFatalUntil::M129); + CHECK(was_erased); } void ContentSubresourceFilterWebContentsHelper::RenderFrameDeleted( @@ -248,13 +246,12 @@ // TODO(bokan): Once the BFCache restoration navigation is made synchronous // like prerender activation we can remove this special case. if (!navigation_handle->HasCommitted()) { - CHECK(navigation_handle->IsServedFromBackForwardCache(), - base::NotFatalUntil::M129); + CHECK(navigation_handle->IsServedFromBackForwardCache()); return; } - CHECK(navigation_handle->HasCommitted(), base::NotFatalUntil::M129); - CHECK(navigation_handle->GetRenderFrameHost(), base::NotFatalUntil::M129); + CHECK(navigation_handle->HasCommitted()); + CHECK(navigation_handle->GetRenderFrameHost()); ContentSubresourceFilterThrottleManager* throttle_manager = GetThrottleManager(navigation_handle->GetRenderFrameHost()->GetPage()); @@ -296,7 +293,7 @@ return; } - CHECK(throttle_manager, base::NotFatalUntil::M129); + CHECK(throttle_manager); // If the navigation was successful it will have created a new page, // transfer the throttle manager to Page user data. If it failed, but it's @@ -351,7 +348,7 @@ void ContentSubresourceFilterWebContentsHelper::OnSubresourceFilterGoingAway() { // Stop observing here because the observer manager could be destroyed by the // time this class is destroyed. - CHECK(scoped_observation_.IsObserving(), base::NotFatalUntil::M129); + CHECK(scoped_observation_.IsObserving()); scoped_observation_.Reset(); } @@ -368,8 +365,7 @@ void ContentSubresourceFilterWebContentsHelper::OnChildFrameNavigationEvaluated( content::NavigationHandle* navigation_handle, LoadPolicy load_policy) { - CHECK(!IsInSubresourceFilterRoot(navigation_handle), - base::NotFatalUntil::M129); + CHECK(!IsInSubresourceFilterRoot(navigation_handle)); if (ContentSubresourceFilterThrottleManager* throttle_manager = GetThrottleManager(*navigation_handle)) { throttle_manager->OnChildFrameNavigationEvaluated(navigation_handle,
diff --git a/components/subresource_filter/content/browser/navigation_console_logger.cc b/components/subresource_filter/content/browser/navigation_console_logger.cc index 4586ed1..d88b5df9 100644 --- a/components/subresource_filter/content/browser/navigation_console_logger.cc +++ b/components/subresource_filter/content/browser/navigation_console_logger.cc
@@ -7,7 +7,6 @@ #include "base/check.h" #include "base/check_op.h" #include "base/memory/ptr_util.h" -#include "base/not_fatal_until.h" #include "components/subresource_filter/content/shared/browser/utils.h" #include "content/public/browser/frame_type.h" #include "content/public/browser/navigation_handle.h" @@ -19,9 +18,9 @@ content::NavigationHandle* handle, blink::mojom::ConsoleMessageLevel level, const std::string& message) { - CHECK(IsInSubresourceFilterRoot(handle), base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(handle)); CHECK_NE(handle->GetNavigatingFrameType(), - content::FrameType::kFencedFrameRoot, base::NotFatalUntil::M129); + content::FrameType::kFencedFrameRoot); if (handle->HasCommitted() && !handle->IsErrorPage()) { handle->GetRenderFrameHost()->AddMessageToConsole(level, message); @@ -34,9 +33,9 @@ // static NavigationConsoleLogger* NavigationConsoleLogger::CreateIfNeededForNavigation( content::NavigationHandle* handle) { - CHECK(IsInSubresourceFilterRoot(handle), base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(handle)); CHECK_NE(handle->GetNavigatingFrameType(), - content::FrameType::kFencedFrameRoot, base::NotFatalUntil::M129); + content::FrameType::kFencedFrameRoot); return GetOrCreateForNavigationHandle(*handle); }
diff --git a/components/subresource_filter/content/browser/profile_interaction_manager.cc b/components/subresource_filter/content/browser/profile_interaction_manager.cc index d0e353f8..a707918 100644 --- a/components/subresource_filter/content/browser/profile_interaction_manager.cc +++ b/components/subresource_filter/content/browser/profile_interaction_manager.cc
@@ -6,7 +6,6 @@ #include "base/check.h" #include "base/logging.h" -#include "base/not_fatal_until.h" #include "build/build_config.h" #include "components/content_settings/browser/page_specific_content_settings.h" #include "components/content_settings/core/common/content_settings_types.h" @@ -36,15 +35,15 @@ void ProfileInteractionManager::DidCreatePage(content::Page& page) { // A new ProfileInteractionManager is created for each page so we should only // call this, at most, once. - CHECK(!page_, base::NotFatalUntil::M129); + CHECK(!page_); page_ = &page; } void ProfileInteractionManager::OnReloadRequested() { // A reload request comes from browser so it will always be associated with // the primary page. - CHECK(page_, base::NotFatalUntil::M129); - CHECK(page_->IsPrimary(), base::NotFatalUntil::M129); + CHECK(page_); + CHECK(page_->IsPrimary()); ContentSubresourceFilterThrottleManager::LogAction( SubresourceFilterAction::kAllowlistedSite); @@ -99,8 +98,7 @@ content::NavigationHandle* navigation_handle, mojom::ActivationLevel initial_activation_level, ActivationDecision* decision) { - CHECK(IsInSubresourceFilterRoot(navigation_handle), - base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(navigation_handle)); mojom::ActivationLevel effective_activation_level = initial_activation_level; @@ -132,8 +130,8 @@ void ProfileInteractionManager::MaybeShowNotification() { // The caller should make sure this is only called from pages that are // currently primary. - CHECK(page_, base::NotFatalUntil::M129); - CHECK(page_->IsPrimary(), base::NotFatalUntil::M129); + CHECK(page_); + CHECK(page_->IsPrimary()); const GURL& top_level_url = page_->GetMainDocument().GetLastCommittedURL(); if (profile_context_->settings_manager()->ShouldShowUIForSite( @@ -174,8 +172,8 @@ } content::WebContents* ProfileInteractionManager::GetWebContents() { - CHECK(page_, base::NotFatalUntil::M129); - CHECK(page_->IsPrimary(), base::NotFatalUntil::M129); + CHECK(page_); + CHECK(page_->IsPrimary()); return content::WebContents::FromRenderFrameHost(&page_->GetMainDocument()); }
diff --git a/components/subresource_filter/content/browser/safe_browsing_page_activation_throttle.cc b/components/subresource_filter/content/browser/safe_browsing_page_activation_throttle.cc index d0d80d7..c22cb53 100644 --- a/components/subresource_filter/content/browser/safe_browsing_page_activation_throttle.cc +++ b/components/subresource_filter/content/browser/safe_browsing_page_activation_throttle.cc
@@ -14,7 +14,6 @@ #include "base/check_op.h" #include "base/functional/bind.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/task/single_thread_task_runner.h" #include "base/timer/timer.h" #include "base/trace_event/trace_event.h" @@ -81,10 +80,9 @@ std::move(database_manager), this, base::SingleThreadTaskRunner::GetCurrentDefault())); - CHECK(IsInSubresourceFilterRoot(®istry.GetNavigationHandle()), - base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(®istry.GetNavigationHandle())); CheckCurrentUrl(); - CHECK(!check_results_.empty(), base::NotFatalUntil::M129); + CHECK(!check_results_.empty()); } SafeBrowsingPageActivationThrottle::~SafeBrowsingPageActivationThrottle() = @@ -115,9 +113,9 @@ void SafeBrowsingPageActivationThrottle::OnCheckUrlResultOnUI( const SubresourceFilterSafeBrowsingClient::CheckResult& result) { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); size_t request_id = result.request_id; - CHECK_LT(request_id, check_results_.size(), base::NotFatalUntil::M129); + CHECK_LT(request_id, check_results_.size()); auto& stored_result = check_results_.at(request_id); CHECK(!stored_result.finished); @@ -151,7 +149,7 @@ SafeBrowsingPageActivationThrottle::ConfigResult::~ConfigResult() = default; void SafeBrowsingPageActivationThrottle::CheckCurrentUrl() { - CHECK(database_client_, base::NotFatalUntil::M129); + CHECK(database_client_); check_results_.emplace_back(); size_t id = check_results_.size() - 1; database_client_->CheckUrl(navigation_handle()->GetURL(), id, @@ -161,7 +159,7 @@ void SafeBrowsingPageActivationThrottle::NotifyResult() { TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("loading"), "SafeBrowsingPageActivationThrottle::NotifyResult"); - CHECK(!check_results_.empty(), base::NotFatalUntil::M129); + CHECK(!check_results_.empty()); // Determine which results to consider for safebrowsing/abusive enforcement. // We only consider the final check result in a redirect chain. @@ -173,8 +171,7 @@ // Get the activation decision with the associated ConfigResult. ActivationDecision activation_decision = GetActivationDecision(selection); - CHECK_NE(activation_decision, ActivationDecision::UNKNOWN, - base::NotFatalUntil::M129); + CHECK_NE(activation_decision, ActivationDecision::UNKNOWN); // Notify the observers of the check results. SubresourceFilterObserverManager::FromWebContents( @@ -223,7 +220,7 @@ ActivationList matched_list, ActivationDecision decision, mojom::ActivationLevel level) const { - CHECK(HasFinishedAllSafeBrowsingChecks(), base::NotFatalUntil::M129); + CHECK(HasFinishedAllSafeBrowsingChecks()); base::TimeDelta delay = defer_time_.is_null() ? base::Milliseconds(0) @@ -235,8 +232,7 @@ ukm::builders::SubresourceFilter builder(source_id); builder.SetActivationDecision(static_cast<int64_t>(decision)); if (level == mojom::ActivationLevel::kDryRun) { - CHECK_EQ(ActivationDecision::ACTIVATED, decision, - base::NotFatalUntil::M129); + CHECK_EQ(ActivationDecision::ACTIVATED, decision); builder.SetDryRun(true); } @@ -267,7 +263,7 @@ SafeBrowsingPageActivationThrottle::ConfigResult SafeBrowsingPageActivationThrottle::GetHighestPriorityConfiguration( const SubresourceFilterSafeBrowsingClient::CheckResult& result) { - CHECK(result.finished, base::NotFatalUntil::M129); + CHECK(result.finished); Configuration selected_config; bool warning = false; bool matched = false;
diff --git a/components/subresource_filter/content/browser/safe_browsing_ruleset_publisher.cc b/components/subresource_filter/content/browser/safe_browsing_ruleset_publisher.cc index 6026672..441aa8c 100644 --- a/components/subresource_filter/content/browser/safe_browsing_ruleset_publisher.cc +++ b/components/subresource_filter/content/browser/safe_browsing_ruleset_publisher.cc
@@ -30,9 +30,9 @@ void SafeBrowsingRulesetPublisher::SendRulesetToRenderProcess( base::File* file, content::RenderProcessHost* rph) { - CHECK(rph, base::NotFatalUntil::M129); - CHECK(file, base::NotFatalUntil::M129); - CHECK(file->IsValid(), base::NotFatalUntil::M129); + CHECK(rph); + CHECK(file); + CHECK(file->IsValid()); if (!rph->GetChannel()) { return; }
diff --git a/components/subresource_filter/content/browser/subresource_filter_content_settings_manager.cc b/components/subresource_filter/content/browser/subresource_filter_content_settings_manager.cc index cf3716d7..a767f7c 100644 --- a/components/subresource_filter/content/browser/subresource_filter_content_settings_manager.cc +++ b/components/subresource_filter/content/browser/subresource_filter_content_settings_manager.cc
@@ -11,7 +11,6 @@ #include "base/check.h" #include "base/functional/bind.h" #include "base/json/values_util.h" -#include "base/not_fatal_until.h" #include "base/time/default_clock.h" #include "base/values.h" #include "build/build_config.h" @@ -55,7 +54,7 @@ : settings_map_(settings_map), clock_(std::make_unique<base::DefaultClock>(base::DefaultClock())), should_use_smart_ui_(ShouldUseSmartUI()) { - CHECK(settings_map_, base::NotFatalUntil::M129); + CHECK(settings_map_); } SubresourceFilterContentSettingsManager:: @@ -115,7 +114,7 @@ if (!is_activated && ShouldDeleteDataWithNoActivation(dict, activation_source)) { // If we are clearing metadata, there should be no additional_data dict. - CHECK(!additional_data, base::NotFatalUntil::M129); + CHECK(!additional_data); SetSiteMetadata(url, std::nullopt); return; } @@ -188,7 +187,7 @@ if (dict && dict->Find(kNonRenewingExpiryTime)) { std::optional<double> metadata_expiry_time = dict->FindDouble(kNonRenewingExpiryTime); - CHECK(metadata_expiry_time, base::NotFatalUntil::M129); + CHECK(metadata_expiry_time); expiry_time = base::Time::FromSecondsSinceUnixEpoch(*metadata_expiry_time); // If the lifetime was stored explicitly, we should use that instead of
diff --git a/components/subresource_filter/content/browser/subresource_filter_profile_context.cc b/components/subresource_filter/content/browser/subresource_filter_profile_context.cc index 438ca660..4c247b8 100644 --- a/components/subresource_filter/content/browser/subresource_filter_profile_context.cc +++ b/components/subresource_filter/content/browser/subresource_filter_profile_context.cc
@@ -5,7 +5,6 @@ #include "components/subresource_filter/content/browser/subresource_filter_profile_context.h" #include "base/check.h" -#include "base/not_fatal_until.h" #include "components/content_settings/core/browser/cookie_settings.h" #include "components/subresource_filter/content/browser/ads_intervention_manager.h" #include "components/subresource_filter/content/browser/subresource_filter_content_settings_manager.h" @@ -27,7 +26,7 @@ void SubresourceFilterProfileContext::SetEmbedderData( std::unique_ptr<SubresourceFilterProfileContext::EmbedderData> embedder_data) { - CHECK(!embedder_data_, base::NotFatalUntil::M129); + CHECK(!embedder_data_); embedder_data_ = std::move(embedder_data); }
diff --git a/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client.cc b/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client.cc index 0724497..6f19daf 100644 --- a/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client.cc +++ b/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client.cc
@@ -10,7 +10,6 @@ #include "base/check_op.h" #include "base/functional/bind.h" #include "base/location.h" -#include "base/not_fatal_until.h" #include "base/task/single_thread_task_runner.h" #include "base/trace_event/trace_event.h" #include "base/trace_event/traced_value.h" @@ -40,7 +39,7 @@ : database_manager_(std::move(database_manager)), throttle_(throttle), throttle_task_runner_(std::move(throttle_task_runner)) { - CHECK(database_manager_, base::NotFatalUntil::M129); + CHECK(database_manager_); } SubresourceFilterSafeBrowsingClient::~SubresourceFilterSafeBrowsingClient() = @@ -49,14 +48,13 @@ void SubresourceFilterSafeBrowsingClient::CheckUrl(const GURL& url, size_t request_id, base::TimeTicks start_time) { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); - CHECK(!url.is_empty(), base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); + CHECK(!url.is_empty()); auto request = std::make_unique<SubresourceFilterSafeBrowsingClientRequest>( request_id, start_time, database_manager_, this); auto* raw_request = request.get(); - CHECK(requests_.find(raw_request) == requests_.end(), - base::NotFatalUntil::M129); + CHECK(requests_.find(raw_request) == requests_.end()); requests_[raw_request] = std::move(request); TRACE_EVENT_NESTABLE_ASYNC_BEGIN1( TRACE_DISABLED_BY_DEFAULT("loading"), "SubresourceFilterSBCheck", @@ -69,11 +67,11 @@ void SubresourceFilterSafeBrowsingClient::OnCheckBrowseUrlResult( SubresourceFilterSafeBrowsingClientRequest* request, const CheckResult& check_result) { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); TRACE_EVENT_NESTABLE_ASYNC_END1( TRACE_DISABLED_BY_DEFAULT("loading"), "SubresourceFilterSBCheck", TRACE_ID_LOCAL(request), "check_result", check_result.ToTracedValue()); - CHECK(requests_.find(request) != requests_.end(), base::NotFatalUntil::M129); + CHECK(requests_.find(request) != requests_.end()); requests_.erase(request); if (throttle_) { throttle_->OnCheckUrlResultOnUI(check_result);
diff --git a/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client_request.cc b/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client_request.cc index cc51021..2d6a44f 100644 --- a/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client_request.cc +++ b/components/subresource_filter/content/browser/subresource_filter_safe_browsing_client_request.cc
@@ -33,12 +33,12 @@ start_time_(start_time), database_manager_(std::move(database_manager)), client_(client) { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); } SubresourceFilterSafeBrowsingClientRequest:: ~SubresourceFilterSafeBrowsingClientRequest() { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); if (!request_completed_) { database_manager_->CancelCheck(this); } @@ -46,7 +46,7 @@ } void SubresourceFilterSafeBrowsingClientRequest::Start(const GURL& url) { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); // Just return SAFE if the database is not supported. bool synchronous_finish = database_manager_->CheckUrlForSubresourceFilter(url, this); @@ -68,14 +68,14 @@ const GURL& url, safe_browsing::SBThreatType threat_type, const safe_browsing::ThreatMetadata& metadata) { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); request_completed_ = true; SendCheckResultToClient(true /* served_from_network */, threat_type, metadata); } void SubresourceFilterSafeBrowsingClientRequest::OnCheckUrlTimeout() { - CHECK_CURRENTLY_ON(content::BrowserThread::UI, base::NotFatalUntil::M129); + CHECK_CURRENTLY_ON(content::BrowserThread::UI); SendCheckResultToClient(true /* served_from_network */, safe_browsing::SBThreatType::SB_THREAT_TYPE_SAFE, safe_browsing::ThreatMetadata());
diff --git a/components/subresource_filter/content/renderer/subresource_filter_agent.cc b/components/subresource_filter/content/renderer/subresource_filter_agent.cc index cc9d7ba..c84c7c5 100644 --- a/components/subresource_filter/content/renderer/subresource_filter_agent.cc +++ b/components/subresource_filter/content/renderer/subresource_filter_agent.cc
@@ -11,7 +11,6 @@ #include "base/functional/bind.h" #include "base/memory/ref_counted.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/time/time.h" #include "components/subresource_filter/content/renderer/unverified_ruleset_dealer.h" #include "components/subresource_filter/content/renderer/web_document_subresource_filter_impl.h" @@ -54,13 +53,13 @@ : content::RenderFrameObserver(render_frame), content::RenderFrameObserverTracker<SubresourceFilterAgent>(render_frame), ruleset_dealer_(ruleset_dealer) { - CHECK(ruleset_dealer, base::NotFatalUntil::M129); + CHECK(ruleset_dealer); } void SubresourceFilterAgent::Initialize() { const GURL& url = GetDocumentURL(); // The initial empty document will always inherit activation. - CHECK(ShouldInheritActivation(url), base::NotFatalUntil::M129); + CHECK(ShouldInheritActivation(url)); // We must check for provisional here because in that case 2 RenderFrames will // be created for the same FrameTreeNode in the browser. The browser service @@ -137,7 +136,7 @@ bool SubresourceFilterAgent::IsParentAdFrame() { // A fenced frame root should never ask this since it can't see the outer // frame tree. Its AdEvidence is always computed by the browser. - CHECK(!IsFencedFrameRoot(render_frame()), base::NotFatalUntil::M129); + CHECK(!IsFencedFrameRoot(render_frame())); return render_frame()->GetWebFrame()->Parent()->IsAdFrame(); } @@ -146,14 +145,14 @@ } bool SubresourceFilterAgent::IsFrameCreatedByAdScript() { - CHECK(!IsFencedFrameRoot(render_frame()), base::NotFatalUntil::M129); + CHECK(!IsFencedFrameRoot(render_frame())); return render_frame()->GetWebFrame()->IsFrameCreatedByAdScript(); } void SubresourceFilterAgent::SetSubresourceFilterForCurrentDocument( std::unique_ptr<blink::WebDocumentSubresourceFilter> filter) { blink::WebLocalFrame* web_frame = render_frame()->GetWebFrame(); - CHECK(web_frame->GetDocumentLoader(), base::NotFatalUntil::M129); + CHECK(web_frame->GetDocumentLoader()); web_frame->GetDocumentLoader()->SetSubresourceFilter(filter.release()); } @@ -172,7 +171,7 @@ } void SubresourceFilterAgent::SendFrameWasCreatedByAdScript() { - CHECK(!IsFencedFrameRoot(render_frame()), base::NotFatalUntil::M129); + CHECK(!IsFencedFrameRoot(render_frame())); GetSubresourceFilterHost()->FrameWasCreatedByAdScript(); } @@ -272,10 +271,10 @@ const std::optional<blink::FrameAdEvidence>& ad_evidence) { activation_state_for_next_document_ = *activation_state; if (IsSubresourceFilterChild()) { - CHECK(ad_evidence.has_value(), base::NotFatalUntil::M129); + CHECK(ad_evidence.has_value()); SetAdEvidence(ad_evidence.value()); } else { - CHECK(!ad_evidence.has_value(), base::NotFatalUntil::M129); + CHECK(!ad_evidence.has_value()); } } @@ -284,9 +283,9 @@ } void SubresourceFilterAgent::SetAdEvidenceForInitialEmptySubframe() { - CHECK(!IsAdFrame(), base::NotFatalUntil::M129); - CHECK(!AdEvidence().has_value(), base::NotFatalUntil::M129); - CHECK(!IsFencedFrameRoot(render_frame()), base::NotFatalUntil::M129); + CHECK(!IsAdFrame()); + CHECK(!AdEvidence().has_value()); + CHECK(!IsFencedFrameRoot(render_frame())); blink::FrameAdEvidence ad_evidence(IsParentAdFrame()); ad_evidence.set_created_by_ad_script( @@ -332,7 +331,7 @@ const mojom::ActivationState SubresourceFilterAgent::GetInheritedActivationStateForNewDocument() { - CHECK(ShouldInheritActivation(GetDocumentURL()), base::NotFatalUntil::M129); + CHECK(ShouldInheritActivation(GetDocumentURL())); return GetInheritedActivationState(render_frame()); }
diff --git a/components/subresource_filter/content/renderer/web_document_subresource_filter_impl.cc b/components/subresource_filter/content/renderer/web_document_subresource_filter_impl.cc index 193958e..8fe52bf 100644 --- a/components/subresource_filter/content/renderer/web_document_subresource_filter_impl.cc +++ b/components/subresource_filter/content/renderer/web_document_subresource_filter_impl.cc
@@ -11,7 +11,6 @@ #include "base/functional/bind.h" #include "base/functional/callback.h" #include "base/memory/scoped_refptr.h" -#include "base/not_fatal_until.h" #include "base/task/single_thread_task_runner.h" #include "components/subresource_filter/content/shared/renderer/filter_utils.h" #include "components/subresource_filter/core/common/constants.h" @@ -78,8 +77,7 @@ WebLoadPolicy WebDocumentSubresourceFilterImpl::GetLoadPolicyForWebSocketConnect( const blink::WebURL& url) { - CHECK(url.ProtocolIs("ws") || url.ProtocolIs("wss"), - base::NotFatalUntil::M129); + CHECK(url.ProtocolIs("ws") || url.ProtocolIs("wss")); return getLoadPolicyImpl(url, proto::ELEMENT_TYPE_WEBSOCKET); } @@ -128,7 +126,7 @@ std::unique_ptr<blink::WebDocumentSubresourceFilter> WebDocumentSubresourceFilterImpl::BuilderImpl::Build() { - CHECK(ruleset_file_.IsValid(), base::NotFatalUntil::M129); + CHECK(ruleset_file_.IsValid()); scoped_refptr<MemoryMappedRuleset> ruleset = MemoryMappedRuleset::CreateAndInitialize(std::move(ruleset_file_)); if (!ruleset) {
diff --git a/components/subresource_filter/content/shared/browser/activation_state_computing_navigation_throttle.cc b/components/subresource_filter/content/shared/browser/activation_state_computing_navigation_throttle.cc index 0c43b201..42977d2e 100644 --- a/components/subresource_filter/content/shared/browser/activation_state_computing_navigation_throttle.cc +++ b/components/subresource_filter/content/shared/browser/activation_state_computing_navigation_throttle.cc
@@ -12,7 +12,6 @@ #include "base/functional/bind.h" #include "base/functional/callback.h" #include "base/memory/ptr_util.h" -#include "base/not_fatal_until.h" #include "components/subresource_filter/content/shared/browser/utils.h" #include "components/subresource_filter/core/browser/async_document_subresource_filter.h" #include "content/public/browser/navigation_handle.h" @@ -26,8 +25,7 @@ ActivationStateComputingNavigationThrottle::CreateForRoot( content::NavigationThrottleRegistry& registry, std::string_view uma_tag) { - CHECK(IsInSubresourceFilterRoot(®istry.GetNavigationHandle()), - base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(®istry.GetNavigationHandle())); return base::WrapUnique(new ActivationStateComputingNavigationThrottle( registry, /*parent_activation_state=*/std::nullopt, /*ruleset_handle*/ nullptr, uma_tag)); @@ -40,11 +38,10 @@ VerifiedRuleset::Handle* ruleset_handle, const mojom::ActivationState& parent_activation_state, std::string_view uma_tag) { - CHECK(!IsInSubresourceFilterRoot(®istry.GetNavigationHandle()), - base::NotFatalUntil::M129); + CHECK(!IsInSubresourceFilterRoot(®istry.GetNavigationHandle())); CHECK_NE(mojom::ActivationLevel::kDisabled, - parent_activation_state.activation_level, base::NotFatalUntil::M129); - CHECK(ruleset_handle, base::NotFatalUntil::M129); + parent_activation_state.activation_level); + CHECK(ruleset_handle); return base::WrapUnique(new ActivationStateComputingNavigationThrottle( registry, parent_activation_state, ruleset_handle, uma_tag)); } @@ -67,12 +64,11 @@ NotifyPageActivationWithRuleset( VerifiedRuleset::Handle* ruleset_handle, const mojom::ActivationState& page_activation_state) { - CHECK(IsInSubresourceFilterRoot(navigation_handle()), - base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(navigation_handle())); CHECK_NE(mojom::ActivationLevel::kDisabled, - page_activation_state.activation_level, base::NotFatalUntil::M129); + page_activation_state.activation_level); parent_activation_state_ = page_activation_state; - CHECK(ruleset_handle, base::NotFatalUntil::M129); + CHECK(ruleset_handle); ruleset_handle_ = ruleset_handle->AsWeakPtr(); } @@ -97,10 +93,9 @@ // If no parent activation, this is root frame that was never notified of // activation. if (!parent_activation_state_) { - CHECK(IsInSubresourceFilterRoot(navigation_handle()), - base::NotFatalUntil::M129); - CHECK(!async_filter_, base::NotFatalUntil::M129); - CHECK(!ruleset_handle_, base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(navigation_handle())); + CHECK(!async_filter_); + CHECK(!ruleset_handle_); return content::NavigationThrottle::PROCEED; } @@ -114,11 +109,10 @@ } return content::NavigationThrottle::PROCEED; } - CHECK(!deferred_, base::NotFatalUntil::M129); + CHECK(!deferred_); deferred_ = true; if (!async_filter_) { - CHECK(IsInSubresourceFilterRoot(navigation_handle()), - base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(navigation_handle())); CheckActivationState(); } return content::NavigationThrottle::DEFER; @@ -129,15 +123,15 @@ } void ActivationStateComputingNavigationThrottle::CheckActivationState() { - CHECK(parent_activation_state_, base::NotFatalUntil::M129); - CHECK(ruleset_handle_, base::NotFatalUntil::M129); + CHECK(parent_activation_state_); + CHECK(ruleset_handle_); AsyncDocumentSubresourceFilter::InitializationParams params; params.document_url = navigation_handle()->GetURL(); params.parent_activation_state = parent_activation_state_.value(); if (!IsInSubresourceFilterRoot(navigation_handle())) { content::RenderFrameHost* parent = navigation_handle()->GetParentFrameOrOuterDocument(); - CHECK(parent, base::NotFatalUntil::M129); + CHECK(parent); params.parent_document_origin = parent->GetLastCommittedOrigin(); } @@ -167,10 +161,9 @@ // This method is only needed for root frame navigations that are notified of // page activation more than once. Even for those that are updated once, it // should be a no-op. - CHECK(IsInSubresourceFilterRoot(navigation_handle()), - base::NotFatalUntil::M129); - CHECK(parent_activation_state_, base::NotFatalUntil::M129); - CHECK(async_filter_, base::NotFatalUntil::M129); + CHECK(IsInSubresourceFilterRoot(navigation_handle())); + CHECK(parent_activation_state_); + CHECK(async_filter_); async_filter_->UpdateWithMoreAccurateState(*parent_activation_state_); } @@ -195,7 +188,7 @@ void ActivationStateComputingNavigationThrottle:: WillSendActivationToRenderer() { - CHECK(async_filter_, base::NotFatalUntil::M129); + CHECK(async_filter_); will_send_activation_to_renderer_ = true; }
diff --git a/components/subresource_filter/content/shared/browser/child_frame_navigation_filtering_throttle.cc b/components/subresource_filter/content/shared/browser/child_frame_navigation_filtering_throttle.cc index d8066c59..090dffe 100644 --- a/components/subresource_filter/content/shared/browser/child_frame_navigation_filtering_throttle.cc +++ b/components/subresource_filter/content/shared/browser/child_frame_navigation_filtering_throttle.cc
@@ -15,7 +15,6 @@ #include "base/functional/bind.h" #include "base/functional/callback.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/strings/stringprintf.h" #include "components/subresource_filter/content/shared/browser/utils.h" #include "components/subresource_filter/core/browser/subresource_filter_constants.h" @@ -39,9 +38,8 @@ parent_frame_filter_(parent_frame_filter), alias_check_enabled_(alias_check_enabled), disallow_message_callback_(std::move(disallow_message_callback)) { - CHECK(!IsInSubresourceFilterRoot(®istry.GetNavigationHandle()), - base::NotFatalUntil::M129); - CHECK(parent_frame_filter_, base::NotFatalUntil::M129); + CHECK(!IsInSubresourceFilterRoot(®istry.GetNavigationHandle())); + CHECK(parent_frame_filter_); } ChildFrameNavigationFilteringThrottle:: @@ -59,7 +57,7 @@ content::NavigationThrottle::ThrottleCheckResult ChildFrameNavigationFilteringThrottle::WillProcessResponse() { - CHECK_NE(load_policy_, LoadPolicy::DISALLOW, base::NotFatalUntil::M129); + CHECK_NE(load_policy_, LoadPolicy::DISALLOW); if (alias_check_enabled_) { std::vector<GURL> alias_urls; @@ -95,9 +93,8 @@ // run mode or checking aliases. if (pending_load_policy_calculations_ > 0) { CHECK(parent_frame_filter_->activation_state().activation_level == - mojom::ActivationLevel::kDryRun || - navigation_handle()->GetDnsAliases().size() > 0, - base::NotFatalUntil::M129); + mojom::ActivationLevel::kDryRun || + navigation_handle()->GetDnsAliases().size() > 0); DeferStart(DeferStage::kWillProcessResponse); return DEFER; } @@ -127,7 +124,7 @@ content::NavigationThrottle::ThrottleCheckResult ChildFrameNavigationFilteringThrottle::MaybeDeferToCalculateLoadPolicy() { - CHECK_NE(load_policy_, LoadPolicy::DISALLOW, base::NotFatalUntil::M129); + CHECK_NE(load_policy_, LoadPolicy::DISALLOW); if (load_policy_ == LoadPolicy::WOULD_DISALLOW) { return PROCEED; } @@ -162,8 +159,7 @@ } CHECK(defer_stage_ == DeferStage::kWillProcessResponse || - defer_stage_ == DeferStage::kWillStartOrRedirectRequest, - base::NotFatalUntil::M129); + defer_stage_ == DeferStage::kWillStartOrRedirectRequest); // If we have an activation enabled and `load_policy_` is DISALLOW, we need // to cancel the navigation. @@ -196,10 +192,9 @@ void ChildFrameNavigationFilteringThrottle:: OnCalculatedLoadPoliciesFromAliasUrls(std::vector<LoadPolicy> policies) { // We deferred to check aliases in WillProcessResponse. - CHECK(defer_stage_ == DeferStage::kWillProcessResponse, - base::NotFatalUntil::M129); + CHECK(defer_stage_ == DeferStage::kWillProcessResponse); CHECK(alias_check_enabled_); - CHECK(!policies.empty(), base::NotFatalUntil::M129); + CHECK(!policies.empty()); did_alias_check_ = true; @@ -221,15 +216,15 @@ } void ChildFrameNavigationFilteringThrottle::DeferStart(DeferStage stage) { - CHECK(defer_stage_ == DeferStage::kNotDeferring, base::NotFatalUntil::M129); - CHECK(stage != DeferStage::kNotDeferring, base::NotFatalUntil::M129); + CHECK(defer_stage_ == DeferStage::kNotDeferring); + CHECK(stage != DeferStage::kNotDeferring); defer_stage_ = stage; last_defer_timestamp_ = base::TimeTicks::Now(); } void ChildFrameNavigationFilteringThrottle::UpdateDeferInfo() { - CHECK(defer_stage_ != DeferStage::kNotDeferring, base::NotFatalUntil::M129); - CHECK(!last_defer_timestamp_.is_null(), base::NotFatalUntil::M129); + CHECK(defer_stage_ != DeferStage::kNotDeferring); + CHECK(!last_defer_timestamp_.is_null()); total_defer_time_ += base::TimeTicks::Now() - last_defer_timestamp_; defer_stage_ = DeferStage::kNotDeferring; }
diff --git a/components/subresource_filter/content/shared/browser/ruleset_publisher.cc b/components/subresource_filter/content/shared/browser/ruleset_publisher.cc index 3780382f..c397df5 100644 --- a/components/subresource_filter/content/shared/browser/ruleset_publisher.cc +++ b/components/subresource_filter/content/shared/browser/ruleset_publisher.cc
@@ -12,7 +12,6 @@ #include "base/functional/bind.h" #include "base/location.h" #include "base/logging.h" -#include "base/not_fatal_until.h" #include "base/task/sequenced_task_runner.h" #include "base/task/single_thread_task_runner.h" #include "base/task/thread_pool.h" @@ -37,8 +36,7 @@ ruleset_config)) { best_effort_task_runner_ = content::GetUIThreadTaskRunner({base::TaskPriority::BEST_EFFORT}); - CHECK(best_effort_task_runner_->BelongsToCurrentThread(), - base::NotFatalUntil::M129); + CHECK(best_effort_task_runner_->BelongsToCurrentThread()); } RulesetPublisher::~RulesetPublisher() = default; @@ -57,8 +55,8 @@ } void RulesetPublisher::PublishNewRulesetVersion(RulesetFilePtr ruleset_data) { - CHECK(ruleset_data, base::NotFatalUntil::M129); - CHECK(ruleset_data->IsValid(), base::NotFatalUntil::M129); + CHECK(ruleset_data); + CHECK(ruleset_data->IsValid()); ruleset_data_.reset(); // If Ad Tagging is running, then every request does a lookup and it's @@ -91,7 +89,7 @@ void RulesetPublisher::IndexAndStoreAndPublishRulesetIfNeeded( const UnindexedRulesetInfo& unindexed_ruleset_info) { - CHECK(ruleset_service_, base::NotFatalUntil::M129); + CHECK(ruleset_service_); ruleset_service_->IndexAndStoreAndPublishRulesetIfNeeded( unindexed_ruleset_info); }
diff --git a/components/subresource_filter/content/shared/browser/ruleset_service.cc b/components/subresource_filter/content/shared/browser/ruleset_service.cc index 3651363..0cc96e4 100644 --- a/components/subresource_filter/content/shared/browser/ruleset_service.cc +++ b/components/subresource_filter/content/shared/browser/ruleset_service.cc
@@ -17,7 +17,6 @@ #include "base/location.h" #include "base/metrics/histogram_functions.h" #include "base/metrics/histogram_macros.h" -#include "base/not_fatal_until.h" #include "base/numerics/safe_conversions.h" #include "base/strings/strcat.h" #include "base/strings/string_number_conversions.h" @@ -215,8 +214,7 @@ is_initialized_(false), indexed_ruleset_base_dir_(indexed_ruleset_base_dir) { CHECK_NE(local_state_->GetInitializationStatus(), - PrefService::INITIALIZATION_STATUS_WAITING, - base::NotFatalUntil::M129); + PrefService::INITIALIZATION_STATUS_WAITING); publisher_ = publisher_factory.Create(this, std::move(blocking_task_runner)); IndexedRulesetVersion most_recently_indexed_version(config.filter_tag); most_recently_indexed_version.ReadFromPrefs(local_state_); @@ -230,8 +228,7 @@ IndexedRulesetVersion(config.filter_tag).SaveToPrefs(local_state_); } - CHECK(publisher_->BestEffortTaskRunner()->BelongsToCurrentThread(), - base::NotFatalUntil::M129); + CHECK(publisher_->BestEffortTaskRunner()->BelongsToCurrentThread()); publisher_->BestEffortTaskRunner()->PostTask( FROM_HERE, base::BindOnce(&RulesetService::FinishInitialization, weak_ptr_factory_.GetWeakPtr())); @@ -352,7 +349,7 @@ return IndexedRulesetVersion(config.filter_tag); } - CHECK(indexed_version.IsValid(), base::NotFatalUntil::M129); + CHECK(indexed_version.IsValid()); return indexed_version; } @@ -419,8 +416,7 @@ // Creating a temporary directory also makes sure the path (except for the // final segment) gets created. ReplaceFile would not create the path. - CHECK(base::PathExists(indexed_ruleset_version_dir.DirName()), - base::NotFatalUntil::M129); + CHECK(base::PathExists(indexed_ruleset_version_dir.DirName())); // Need to manually delete the previously stored ruleset with the same // version, if any, as ReplaceFile would not overwrite a non-empty directory. @@ -463,8 +459,7 @@ void RulesetService::IndexAndStoreRuleset( const UnindexedRulesetInfo& unindexed_ruleset_info, WriteRulesetCallback success_callback) { - CHECK(!unindexed_ruleset_info.content_version.empty(), - base::NotFatalUntil::M129); + CHECK(!unindexed_ruleset_info.content_version.empty()); background_task_runner_->PostTaskAndReplyWithResult( FROM_HERE, base::BindOnce(&RulesetService::IndexAndWriteRuleset, config_, @@ -476,7 +471,7 @@ void RulesetService::OnWrittenRuleset(WriteRulesetCallback result_callback, const IndexedRulesetVersion& version) { - CHECK(!result_callback.is_null(), base::NotFatalUntil::M129); + CHECK(!result_callback.is_null()); if (!version.IsValid()) { return; }
diff --git a/components/subresource_filter/content/shared/browser/unindexed_ruleset_stream_generator.cc b/components/subresource_filter/content/shared/browser/unindexed_ruleset_stream_generator.cc index bbdaeff..5dbdc44a 100644 --- a/components/subresource_filter/content/shared/browser/unindexed_ruleset_stream_generator.cc +++ b/components/subresource_filter/content/shared/browser/unindexed_ruleset_stream_generator.cc
@@ -7,7 +7,6 @@ #include "base/check.h" #include "base/check_op.h" #include "base/files/file_path.h" -#include "base/not_fatal_until.h" #include "components/subresource_filter/core/browser/ruleset_version.h" #include "components/subresource_filter/core/common/copying_file_stream.h" #include "third_party/protobuf/src/google/protobuf/io/zero_copy_stream_impl.h" @@ -20,10 +19,8 @@ const UnindexedRulesetInfo& ruleset_info) { bool has_ruleset_file = !ruleset_info.ruleset_path.empty(); - CHECK(has_ruleset_file || ruleset_info.resource_id, - base::NotFatalUntil::M129); - CHECK(!(has_ruleset_file && ruleset_info.resource_id), - base::NotFatalUntil::M129); + CHECK(has_ruleset_file || ruleset_info.resource_id); + CHECK(!(has_ruleset_file && ruleset_info.resource_id)); if (has_ruleset_file) { GenerateStreamFromFile(ruleset_info.ruleset_path); @@ -36,9 +33,9 @@ void UnindexedRulesetStreamGenerator::GenerateStreamFromFile( base::FilePath ruleset_path) { - CHECK(!ruleset_stream_, base::NotFatalUntil::M129); - CHECK(!copying_stream_, base::NotFatalUntil::M129); - CHECK_EQ(ruleset_size_, -1, base::NotFatalUntil::M129); + CHECK(!ruleset_stream_); + CHECK(!copying_stream_); + CHECK_EQ(ruleset_size_, -1); base::File unindexed_ruleset_file( ruleset_path, base::File::FLAG_OPEN | base::File::FLAG_READ);
diff --git a/components/subresource_filter/core/browser/async_document_subresource_filter.cc b/components/subresource_filter/core/browser/async_document_subresource_filter.cc index 529372d5..c82c18cc 100644 --- a/components/subresource_filter/core/browser/async_document_subresource_filter.cc +++ b/components/subresource_filter/core/browser/async_document_subresource_filter.cc
@@ -12,7 +12,6 @@ #include "base/functional/bind.h" #include "base/functional/callback.h" #include "base/location.h" -#include "base/not_fatal_until.h" #include "components/subresource_filter/core/browser/verified_ruleset_dealer.h" #include "components/subresource_filter/core/common/constants.h" #include "components/subresource_filter/core/common/document_subresource_filter.h" @@ -30,7 +29,7 @@ const url::Origin& parent_document_origin, const mojom::ActivationState& parent_activation_state, const MemoryMappedRuleset* ruleset) { - CHECK(ruleset, base::NotFatalUntil::M129); + CHECK(ruleset); IndexedRulesetMatcher matcher(ruleset->data()); mojom::ActivationState activation_state = parent_activation_state; @@ -67,8 +66,7 @@ mojom::ActivationLevel activation_level, bool measure_performance) : document_url(std::move(document_url)) { - CHECK_NE(mojom::ActivationLevel::kDisabled, activation_level, - base::NotFatalUntil::M129); + CHECK_NE(mojom::ActivationLevel::kDisabled, activation_level); parent_activation_state.activation_level = activation_level; parent_activation_state.measure_performance = measure_performance; } @@ -81,7 +79,7 @@ parent_document_origin(std::move(parent_document_origin)), parent_activation_state(parent_activation_state) { CHECK_NE(mojom::ActivationLevel::kDisabled, - parent_activation_state.activation_level, base::NotFatalUntil::M129); + parent_activation_state.activation_level); } InitializationParams::~InitializationParams() = default; @@ -99,8 +97,7 @@ : task_runner_(ruleset_handle->task_runner()), core_(new Core(), base::OnTaskRunnerDeleter(task_runner_.get())) { CHECK_NE(mojom::ActivationLevel::kDisabled, - params.parent_activation_state.activation_level, - base::NotFatalUntil::M129); + params.parent_activation_state.activation_level); // Note: It is safe to post |ruleset_handle|'s VerifiedRuleset pointer, // because a task to delete it can only be posted to (and, therefore, @@ -123,11 +120,11 @@ std::string_view uma_tag) : task_runner_(ruleset_handle->task_runner()), core_(new Core(), base::OnTaskRunnerDeleter(task_runner_.get())) { - CHECK_NE(mojom::ActivationLevel::kDisabled, activation_state.activation_level, - base::NotFatalUntil::M129); + CHECK_NE(mojom::ActivationLevel::kDisabled, + activation_state.activation_level); VerifiedRuleset* verified_ruleset = ruleset_handle->ruleset_.get(); - CHECK(verified_ruleset, base::NotFatalUntil::M129); + CHECK(verified_ruleset); // See previous constructor for the safety of posting |ruleset_handle|'s // VerifiedRuleset pointer. @@ -162,7 +159,7 @@ base::BindOnce( [](AsyncDocumentSubresourceFilter::Core* core, const GURL& subdocument_url) { - CHECK(core, base::NotFatalUntil::M129); + CHECK(core); DocumentSubresourceFilter* filter = core->filter(); return filter ? filter->GetLoadPolicy( @@ -198,7 +195,7 @@ const mojom::ActivationState& updated_page_state) { // DISABLED activation level implies that the ruleset is somehow invalid. Make // sure that we don't update the state in that case. - CHECK(has_activation_state(), base::NotFatalUntil::M129); + CHECK(has_activation_state()); if (activation_state_->activation_level == mojom::ActivationLevel::kDisabled) { return; @@ -250,7 +247,7 @@ void AsyncDocumentSubresourceFilter::Core::SetActivationState( const mojom::ActivationState& state) { - CHECK(filter_, base::NotFatalUntil::M129); + CHECK(filter_); filter_->set_activation_state(state); } @@ -259,7 +256,7 @@ VerifiedRuleset* verified_ruleset, std::string_view uma_tag) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - CHECK(verified_ruleset, base::NotFatalUntil::M129); + CHECK(verified_ruleset); if (!verified_ruleset->Get()) { return mojom::ActivationState(); @@ -269,8 +266,8 @@ params.document_url, params.parent_document_origin, params.parent_activation_state, verified_ruleset->Get()); - CHECK_NE(mojom::ActivationLevel::kDisabled, activation_state.activation_level, - base::NotFatalUntil::M129); + CHECK_NE(mojom::ActivationLevel::kDisabled, + activation_state.activation_level); filter_.emplace(url::Origin::Create(params.document_url), activation_state, verified_ruleset->Get(), uma_tag); @@ -283,7 +280,7 @@ VerifiedRuleset* verified_ruleset, std::string_view uma_tag) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - CHECK(verified_ruleset, base::NotFatalUntil::M129); + CHECK(verified_ruleset); // Avoids a crash in the rare case that the ruleset's status has changed to // unavailable/corrupt since the caller checked. @@ -292,8 +289,8 @@ return; } - CHECK_NE(mojom::ActivationLevel::kDisabled, activation_state.activation_level, - base::NotFatalUntil::M129); + CHECK_NE(mojom::ActivationLevel::kDisabled, + activation_state.activation_level); filter_.emplace(inherited_document_origin, activation_state, verified_ruleset->Get(), uma_tag); }
diff --git a/components/subresource_filter/core/browser/verified_ruleset_dealer.cc b/components/subresource_filter/core/browser/verified_ruleset_dealer.cc index 27cb04fe..f576f92 100644 --- a/components/subresource_filter/core/browser/verified_ruleset_dealer.cc +++ b/components/subresource_filter/core/browser/verified_ruleset_dealer.cc
@@ -11,7 +11,6 @@ #include "base/functional/bind.h" #include "base/functional/callback_helpers.h" #include "base/location.h" -#include "base/not_fatal_until.h" #include "base/notreached.h" #include "base/task/sequenced_task_runner.h" #include "base/trace_event/trace_event.h" @@ -141,7 +140,7 @@ void VerifiedRuleset::Initialize(VerifiedRulesetDealer* dealer) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - CHECK(dealer, base::NotFatalUntil::M129); + CHECK(dealer); ruleset_ = dealer->GetRuleset(); }
diff --git a/components/subresource_filter/core/common/document_subresource_filter.cc b/components/subresource_filter/core/common/document_subresource_filter.cc index 44f4d1d6..a9321d5 100644 --- a/components/subresource_filter/core/common/document_subresource_filter.cc +++ b/components/subresource_filter/core/common/document_subresource_filter.cc
@@ -11,7 +11,6 @@ #include "base/check.h" #include "base/check_op.h" #include "base/metrics/histogram_functions.h" -#include "base/not_fatal_until.h" #include "base/strings/strcat.h" #include "base/time/time.h" #include "base/trace_event/trace_event.h" @@ -34,7 +33,7 @@ ruleset_matcher_(ruleset_->data()), uma_tag_(uma_tag) { CHECK_NE(activation_state_.activation_level, - mojom::ActivationLevel::kDisabled, base::NotFatalUntil::M129); + mojom::ActivationLevel::kDisabled); if (!activation_state_.filtering_disabled_for_document) { document_origin_ = std::make_unique<FirstPartyOrigin>(std::move(document_origin)); @@ -83,11 +82,11 @@ }); ++statistics_.num_loads_evaluated; - CHECK(document_origin_, base::NotFatalUntil::M129); + CHECK(document_origin_); LoadPolicy result = ruleset_matcher_.GetLoadPolicyForResourceLoad( subresource_url, *document_origin_, subresource_type, activation_state_.generic_blocking_rules_disabled); - CHECK_NE(LoadPolicy::WOULD_DISALLOW, result, base::NotFatalUntil::M129); + CHECK_NE(LoadPolicy::WOULD_DISALLOW, result); if (result == LoadPolicy::DISALLOW) { ++statistics_.num_loads_matching_rules; if (activation_state_.activation_level ==
diff --git a/components/subresource_filter/core/common/indexed_ruleset.cc b/components/subresource_filter/core/common/indexed_ruleset.cc index 0ecc10e..6e3c34d 100644 --- a/components/subresource_filter/core/common/indexed_ruleset.cc +++ b/components/subresource_filter/core/common/indexed_ruleset.cc
@@ -7,7 +7,6 @@ #include "base/check.h" #include "base/hash/hash.h" #include "base/metrics/histogram_functions.h" -#include "base/not_fatal_until.h" #include "base/strings/strcat.h" #include "base/trace_event/trace_event.h" #include "components/subresource_filter/core/common/first_party_origin.h" @@ -82,7 +81,7 @@ blocklist_.IndexUrlRule(offset); } else { const auto* flat_rule = flatbuffers::GetTemporaryPointer(builder_, offset); - CHECK(flat_rule, base::NotFatalUntil::M129); + CHECK(flat_rule); if (flat_rule->element_types()) { allowlist_.IndexUrlRule(offset); }
diff --git a/components/subresource_filter/core/common/memory_mapped_ruleset.cc b/components/subresource_filter/core/common/memory_mapped_ruleset.cc index 877caf1..53afa5e 100644 --- a/components/subresource_filter/core/common/memory_mapped_ruleset.cc +++ b/components/subresource_filter/core/common/memory_mapped_ruleset.cc
@@ -7,7 +7,6 @@ #include <utility> #include "base/check.h" -#include "base/not_fatal_until.h" namespace subresource_filter { @@ -26,7 +25,7 @@ !ruleset->ruleset_.Initialize(std::move(ruleset_file))) { return nullptr; } - CHECK(ruleset->ruleset_.IsValid(), base::NotFatalUntil::M129); + CHECK(ruleset->ruleset_.IsValid()); return ruleset; }
diff --git a/components/subresource_filter/core/common/ruleset_dealer.cc b/components/subresource_filter/core/common/ruleset_dealer.cc index 63ad55c7..1ff02a0 100644 --- a/components/subresource_filter/core/common/ruleset_dealer.cc +++ b/components/subresource_filter/core/common/ruleset_dealer.cc
@@ -5,7 +5,6 @@ #include "components/subresource_filter/core/common/ruleset_dealer.h" #include "base/check.h" -#include "base/not_fatal_until.h" #include "components/subresource_filter/core/common/memory_mapped_ruleset.h" namespace subresource_filter { @@ -18,7 +17,7 @@ void RulesetDealer::SetRulesetFile(base::File ruleset_file) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - CHECK(ruleset_file.IsValid(), base::NotFatalUntil::M129); + CHECK(ruleset_file.IsValid()); ruleset_file_ = std::move(ruleset_file); weak_cached_ruleset_.reset(); }
diff --git a/components/subresource_filter/core/common/unindexed_ruleset.cc b/components/subresource_filter/core/common/unindexed_ruleset.cc index c76b9de..1522a097d 100644 --- a/components/subresource_filter/core/common/unindexed_ruleset.cc +++ b/components/subresource_filter/core/common/unindexed_ruleset.cc
@@ -6,7 +6,6 @@ #include "base/check.h" #include "base/check_op.h" -#include "base/not_fatal_until.h" #include "base/numerics/safe_conversions.h" #include "components/url_pattern_index/proto/rules.pb.h" #include "third_party/protobuf/src/google/protobuf/io/coded_stream.h" @@ -45,23 +44,22 @@ : coded_stream_(stream), max_rules_per_chunk_(max_rules_per_chunk) {} UnindexedRulesetWriter::~UnindexedRulesetWriter() { - CHECK_EQ(pending_chunk_.url_rules_size(), 0, base::NotFatalUntil::M129); - CHECK_EQ(pending_chunk_.css_rules_size(), 0, base::NotFatalUntil::M129); + CHECK_EQ(pending_chunk_.url_rules_size(), 0); + CHECK_EQ(pending_chunk_.css_rules_size(), 0); } bool UnindexedRulesetWriter::AddUrlRule(const proto::UrlRule& rule) { - CHECK(!had_error(), base::NotFatalUntil::M129); + CHECK(!had_error()); pending_chunk_.add_url_rules()->CopyFrom(rule); if (pending_chunk_.url_rules_size() >= max_rules_per_chunk_) { - CHECK_EQ(pending_chunk_.url_rules_size(), max_rules_per_chunk_, - base::NotFatalUntil::M129); + CHECK_EQ(pending_chunk_.url_rules_size(), max_rules_per_chunk_); return WritePendingChunk(); } return true; } bool UnindexedRulesetWriter::Finish() { - CHECK(!had_error(), base::NotFatalUntil::M129); + CHECK(!had_error()); const bool success = !pending_chunk_.url_rules_size() || WritePendingChunk(); if (success) { coded_stream_.Trim(); @@ -70,8 +68,8 @@ } bool UnindexedRulesetWriter::WritePendingChunk() { - CHECK(!had_error(), base::NotFatalUntil::M129); - CHECK_GT(pending_chunk_.url_rules_size(), 0, base::NotFatalUntil::M129); + CHECK(!had_error()); + CHECK_GT(pending_chunk_.url_rules_size(), 0); proto::FilteringRules chunk; chunk.Swap(&pending_chunk_);
diff --git a/components/subresource_filter/tools/rule_parser/rule.cc b/components/subresource_filter/tools/rule_parser/rule.cc index a8759b2f..582a025 100644 --- a/components/subresource_filter/tools/rule_parser/rule.cc +++ b/components/subresource_filter/tools/rule_parser/rule.cc
@@ -11,7 +11,6 @@ #include "base/check_op.h" #include "base/logging.h" -#include "base/not_fatal_until.h" #include "base/strings/string_util.h" namespace subresource_filter { @@ -277,8 +276,7 @@ if (rule.element_types() & type_mask_for(url_pattern_index::proto::ELEMENT_TYPE_POPUP)) { const auto& popup_type = kElementTypes[11]; - CHECK_EQ(url_pattern_index::proto::ELEMENT_TYPE_POPUP, popup_type.type, - base::NotFatalUntil::M129); + CHECK_EQ(url_pattern_index::proto::ELEMENT_TYPE_POPUP, popup_type.type); options.push_back(popup_type.name); } } @@ -294,8 +292,7 @@ // element_types == kDefaultElementTypes instead of 0. if (!rule.element_types() && !rule.activation_types()) { const auto& image_type = kElementTypes[2]; - CHECK_EQ(url_pattern_index::proto::ELEMENT_TYPE_IMAGE, image_type.type, - base::NotFatalUntil::M129); + CHECK_EQ(url_pattern_index::proto::ELEMENT_TYPE_IMAGE, image_type.type); options.push_back(image_type.name); options.push_back(std::string("~") + image_type.name); }
diff --git a/components/subresource_filter/tools/rule_parser/rule_parser.cc b/components/subresource_filter/tools/rule_parser/rule_parser.cc index f1ce3cf..6c54f8e 100644 --- a/components/subresource_filter/tools/rule_parser/rule_parser.cc +++ b/components/subresource_filter/tools/rule_parser/rule_parser.cc
@@ -12,7 +12,6 @@ #include "base/check.h" #include "base/check_op.h" #include "base/logging.h" -#include "base/not_fatal_until.h" #include "base/strings/string_split.h" #include "base/strings/string_util.h" #include "components/subresource_filter/tools/rule_parser/rule_options.h" @@ -71,8 +70,8 @@ // Creates a generic option. OptionDetails(OptionType type, int flags) : type(type), flags(flags) { - CHECK_NE(type, OPTION_ELEMENT_TYPE, base::NotFatalUntil::M129); - CHECK_NE(type, OPTION_ACTIVATION_TYPE, base::NotFatalUntil::M129); + CHECK_NE(type, OPTION_ELEMENT_TYPE); + CHECK_NE(type, OPTION_ACTIVATION_TYPE); } bool requires_value() const { return flags & FLAG_REQUIRES_VALUE; } @@ -168,7 +167,7 @@ void KeywordMap::AddOption(std::string_view name, const OptionDetails& details) { auto inserted = options_.insert(std::make_pair(std::string(name), details)); - CHECK(inserted.second, base::NotFatalUntil::M129); + CHECK(inserted.second); } KeywordMap* GetKeywordsMapSingleton() { @@ -326,7 +325,7 @@ bool has_seen_element_or_activation_type = false; for (std::string_view piece : base::SplitStringPiece( options, ",", base::TRIM_WHITESPACE, base::SPLIT_WANT_NONEMPTY)) { - CHECK(!piece.empty(), base::NotFatalUntil::M129); + CHECK(!piece.empty()); TriState tri_state = TriState::YES; if (base::StartsWith(piece, "~", base::CompareCase::SENSITIVE)) { @@ -389,7 +388,7 @@ } url_rule_.type_mask |= type_mask_for(option_details->element_type); } else { - CHECK(tri_state == TriState::NO, base::NotFatalUntil::M129); + CHECK(tri_state == TriState::NO); url_rule_.type_mask &= ~type_mask_for(option_details->element_type); } has_seen_element_or_activation_type = true; @@ -429,13 +428,12 @@ // Check for a list of domains. if (css_section_start) { - CHECK(css_section_start != std::string_view::npos, - base::NotFatalUntil::M129); + CHECK(css_section_start != std::string_view::npos); auto pieces = base::SplitStringPiece(part.substr(0, css_section_start), ",", base::TRIM_WHITESPACE, base::SPLIT_WANT_NONEMPTY); for (std::string_view domain : pieces) { - CHECK(!domain.empty(), base::NotFatalUntil::M129); + CHECK(!domain.empty()); css_rule_.domains.push_back(std::string(domain)); } } @@ -468,8 +466,8 @@ void RuleParser::SetParseError(ParseError::ErrorCode code, std::string_view origin, const char* error_begin) { - CHECK(code != ParseError::NONE, base::NotFatalUntil::M129); - CHECK(error_begin >= origin.data(), base::NotFatalUntil::M129); + CHECK(code != ParseError::NONE); + CHECK(error_begin >= origin.data()); parse_error_.error_code = code; parse_error_.line = std::string(origin);
diff --git a/components/variations/variations_ids_provider.cc b/components/variations/variations_ids_provider.cc index 35a3faf..384ad77e 100644 --- a/components/variations/variations_ids_provider.cc +++ b/components/variations/variations_ids_provider.cc
@@ -229,7 +229,7 @@ void VariationsIdsProvider::AddObserver(Observer* observer) { base::AutoLock scoped_lock(lock_); - CHECK(!base::Contains(observer_list_, observer), base::NotFatalUntil::M126); + CHECK(!base::Contains(observer_list_, observer)); observer_list_.push_back(observer); }
diff --git a/components/viz/common/resources/shared_image_format.cc b/components/viz/common/resources/shared_image_format.cc index 181cbe9..2e8d568 100644 --- a/components/viz/common/resources/shared_image_format.cc +++ b/components/viz/common/resources/shared_image_format.cc
@@ -131,11 +131,6 @@ // that operator==() is just memcmp(). That would probably require something // like manually packing bits into a single uint64_t for storage. -bool SharedImageFormat::IsBitmapFormatSupported() const { - return is_single_plane() && - singleplanar_format() == mojom::SingleplanarFormat::RGBA_8888; -} - int SharedImageFormat::NumberOfPlanes() const { if (is_single_plane()) { return 1;
diff --git a/components/viz/common/resources/shared_image_format.h b/components/viz/common/resources/shared_image_format.h index e50178ff..6ae7a49 100644 --- a/components/viz/common/resources/shared_image_format.h +++ b/components/viz/common/resources/shared_image_format.h
@@ -130,10 +130,6 @@ #endif } - // Returns whether the resource format can be used as a software bitmap for - // export to the display compositor. - bool IsBitmapFormatSupported() const; - // Return the number of planes associated with the format. int NumberOfPlanes() const;
diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn index e92d889..933abcca 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn
@@ -2407,6 +2407,8 @@ "webid/fedcm_accounts_fetcher.h", "webid/fedcm_config_fetcher.cc", "webid/fedcm_config_fetcher.h", + "webid/fedcm_idp_registration_handler.cc", + "webid/fedcm_idp_registration_handler.h", "webid/fedcm_mappers.cc", "webid/fedcm_mappers.h", "webid/fedcm_metrics.cc",
diff --git a/content/browser/child_process_launcher.cc b/content/browser/child_process_launcher.cc index 27841d4..f4283806 100644 --- a/content/browser/child_process_launcher.cc +++ b/content/browser/child_process_launcher.cc
@@ -192,9 +192,11 @@ // process. auto* port_provider = ChildProcessTaskPortProvider::GetInstance(); CHECK(port_provider); - CHECK(port_provider->TaskForHandle(process_.process.Handle()) == - MACH_PORT_NULL); - scoped_port_provider_observation_.Observe(port_provider); + if (port_provider->TaskForHandle(process_.process.Handle()) == + MACH_PORT_NULL) { + // In the most common case, the task port is not available at launch time. + scoped_port_provider_observation_.Observe(port_provider); + } #endif // Note:: May delete |this|. @@ -220,9 +222,15 @@ return; } - if (process_.process.Handle() == process_handle && priority_) { + // Ignore notifications about different processes. + if (process_.process.Handle() != process_handle) { + return; + } + + scoped_port_provider_observation_.Reset(); + + if (priority_) { SetProcessPriorityImpl(*priority_); - scoped_port_provider_observation_.Reset(); } } #endif
diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc index 6041f1e..e5795154 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc
@@ -3231,6 +3231,7 @@ } void WebContentsImpl::AttachUnownedInnerWebContents( + base::PassKey<UnownedInnerWebContentsClient>, WebContents* inner_web_contents, RenderFrameHost* render_frame_host) { AttachInnerWebContentsImpl(inner_web_contents, render_frame_host, @@ -3358,6 +3359,12 @@ } void WebContentsImpl::DetachUnownedInnerWebContents( + base::PassKey<UnownedInnerWebContentsClient>, + WebContents* inner_web_contents) { + DetachUnownedInnerWebContents(inner_web_contents); +} + +void WebContentsImpl::DetachUnownedInnerWebContents( WebContents* inner_web_contents) { CHECK(base::FeatureList::IsEnabled(features::kAttachUnownedInnerWebContents)); CHECK(node_.IsUnownedInnerWebContents(inner_web_contents));
diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h index bb00cc8..478c9df 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h
@@ -483,9 +483,13 @@ std::unique_ptr<WebContents> inner_web_contents, RenderFrameHost* render_frame_host, bool is_full_page) override; - void AttachUnownedInnerWebContents(WebContents* inner_web_contents, - RenderFrameHost* render_frame_host) override; - void DetachUnownedInnerWebContents(WebContents* inner_web_contents) override; + void AttachUnownedInnerWebContents( + base::PassKey<UnownedInnerWebContentsClient>, + WebContents* inner_web_contents, + RenderFrameHost* render_frame_host) override; + void DetachUnownedInnerWebContents( + base::PassKey<UnownedInnerWebContentsClient>, + WebContents* inner_web_contents) override; void AttachGuestPage(std::unique_ptr<GuestPageHolder> guest_page, RenderFrameHost* outer_render_frame_host) override; bool IsInnerWebContentsForGuest() override; @@ -1997,6 +2001,10 @@ bool is_full_page, bool should_take_ownership); + // Internal implementation of DetachUnownedInnerWebContents() that does not + // require a pass key. Called by ~WebContentsImpl. + void DetachUnownedInnerWebContents(WebContents* inner_web_contents); + // Called just after an inner web contents is attached. void InnerWebContentsAttached(WebContents* inner_web_contents);
diff --git a/content/browser/web_contents/web_contents_impl_browsertest.cc b/content/browser/web_contents/web_contents_impl_browsertest.cc index 0f21fe9..03f2182 100644 --- a/content/browser/web_contents/web_contents_impl_browsertest.cc +++ b/content/browser/web_contents/web_contents_impl_browsertest.cc
@@ -69,6 +69,7 @@ #include "content/public/browser/render_view_host.h" #include "content/public/browser/render_widget_host_view.h" #include "content/public/browser/site_isolation_policy.h" +#include "content/public/browser/unowned_inner_web_contents_client.h" #include "content/public/browser/web_contents.h" #include "content/public/browser/web_contents_delegate.h" #include "content/public/browser/web_contents_observer.h" @@ -4492,7 +4493,9 @@ run_loop.Quit(); return false; })); - outer_wc->AttachUnownedInnerWebContents(inner_wc.get(), iframe_rfh); + outer_wc->AttachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get(), iframe_rfh); // The outer RFH was unloaded while attaching the inner WC. The RFH was marked // as offline by the asynchronous UnloadACK(). @@ -4551,11 +4554,15 @@ WebContentsImpl* inner_wc_impl = static_cast<WebContentsImpl*>(inner_wc.get()); ASSERT_TRUE(NavigateToURL(inner_wc.get(), inner_url)); - outer_wc->AttachUnownedInnerWebContents(inner_wc.get(), iframe_rfh); + outer_wc->AttachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get(), iframe_rfh); ASSERT_EQ(outer_wc, inner_wc->GetOuterWebContents()); // Detach the inner WebContents - outer_wc->DetachUnownedInnerWebContents(inner_wc.get()); + outer_wc->DetachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get()); // Verify that the connection is broken. EXPECT_EQ(nullptr, inner_wc->GetOuterWebContents()); @@ -4603,13 +4610,19 @@ // Attach the inner WebContents ASSERT_TRUE(NavigateToURL(inner_wc.get(), inner_url)); - outer_wc->AttachUnownedInnerWebContents(inner_wc.get(), iframe_rfh); + outer_wc->AttachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get(), iframe_rfh); ASSERT_EQ(outer_wc, inner_wc->GetOuterWebContents()); // Detach and then reattach the inner WebContents - outer_wc->DetachUnownedInnerWebContents(inner_wc.get()); + outer_wc->DetachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get()); ASSERT_EQ(nullptr, inner_wc->GetOuterWebContents()); - outer_wc->AttachUnownedInnerWebContents(inner_wc.get(), iframe_rfh); + outer_wc->AttachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get(), iframe_rfh); ASSERT_EQ(outer_wc, inner_wc->GetOuterWebContents()); } @@ -4637,7 +4650,9 @@ ASSERT_TRUE(NavigateToURL(inner_wc.get(), inner_url)); // Attach the inner WebContents - outer_wc->AttachUnownedInnerWebContents(inner_wc.get(), iframe_rfh); + outer_wc->AttachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get(), iframe_rfh); ASSERT_EQ(outer_wc, inner_wc->GetOuterWebContents()); // Verify RenderFrameHost is created for the inner WebContents @@ -4674,7 +4689,9 @@ rfh_b2->GetView()); // Detach the inner WebContents - outer_wc->DetachUnownedInnerWebContents(inner_wc.get()); + outer_wc->DetachUnownedInnerWebContents( + UnownedInnerWebContentsClient::GetPassKeyForTesting(), + inner_wc.get()); ASSERT_EQ(nullptr, inner_wc->GetOuterWebContents()); // Verify that the inner WebContents's RFHs are still alive. @@ -4705,7 +4722,6 @@ EXPECT_TRUE(static_cast<RenderViewHostImpl*>( rfh_b2->GetRenderViewHost())->IsRenderViewLive()); } - #endif // !BUILDFLAG(IS_ANDROID) IN_PROC_BROWSER_TEST_F(WebContentsImplBrowserTest,
diff --git a/content/browser/webid/fedcm_accounts_fetcher.cc b/content/browser/webid/fedcm_accounts_fetcher.cc index 0ba3094..9d69260 100644 --- a/content/browser/webid/fedcm_accounts_fetcher.cc +++ b/content/browser/webid/fedcm_accounts_fetcher.cc
@@ -215,13 +215,9 @@ } } - // The login url should be valid unless IdP login status API is - // disabled. - if (idp_info->metadata.idp_login_url.is_valid()) { - federated_auth_request_impl_->SetIdpLoginInfo( - idp_info->metadata.idp_login_url, idp_info->provider->login_hint, - idp_info->provider->domain_hint); - } + federated_auth_request_impl_->SetIdpLoginInfo( + idp_info->metadata.idp_login_url, idp_info->provider->login_hint, + idp_info->provider->domain_hint); // Make sure that we don't fetch accounts if the IDP sign-in bit is // reset to false during the API call. e.g. by the login/logout HEADER.
diff --git a/content/browser/webid/fedcm_idp_registration_handler.cc b/content/browser/webid/fedcm_idp_registration_handler.cc new file mode 100644 index 0000000..0d4147a --- /dev/null +++ b/content/browser/webid/fedcm_idp_registration_handler.cc
@@ -0,0 +1,36 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "content/browser/webid/fedcm_idp_registration_handler.h" + +#include "content/browser/webid/fedcm_config_fetcher.h" +#include "content/browser/webid/idp_network_request_manager.h" +#include "url/gurl.h" + +namespace content { + +FedCmIdpRegistrationHandler::FedCmIdpRegistrationHandler( + RenderFrameHost& render_frame_host, + IdpNetworkRequestManager* network_manager, + const GURL& idp_url) + : render_frame_host_(render_frame_host), + network_manager_(network_manager), + idp_url_(idp_url) {} + +FedCmIdpRegistrationHandler::~FedCmIdpRegistrationHandler() = default; + +void FedCmIdpRegistrationHandler::FetchConfig( + FedCmConfigFetcher::RequesterCallback callback) { + std::vector<FedCmConfigFetcher::FetchRequest> fetch_requests; + fetch_requests.emplace_back(idp_url_, + /*force_skip_well_known_enforcement=*/true); + + config_fetcher_ = std::make_unique<FedCmConfigFetcher>(*render_frame_host_, + network_manager_); + config_fetcher_->Start(fetch_requests, blink::mojom::RpMode::kPassive, + /*icon_ideal_size=*/0, /*icon_minimum_size=*/0, + std::move(callback)); +} + +} // namespace content
diff --git a/content/browser/webid/fedcm_idp_registration_handler.h b/content/browser/webid/fedcm_idp_registration_handler.h new file mode 100644 index 0000000..6b998c1a --- /dev/null +++ b/content/browser/webid/fedcm_idp_registration_handler.h
@@ -0,0 +1,39 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CONTENT_BROWSER_WEBID_FEDCM_IDP_REGISTRATION_HANDLER_H_ +#define CONTENT_BROWSER_WEBID_FEDCM_IDP_REGISTRATION_HANDLER_H_ + +#include "content/browser/webid/fedcm_config_fetcher.h" +#include "url/gurl.h" + +namespace content { + +class RenderFrameHost; + +class CONTENT_EXPORT FedCmIdpRegistrationHandler { + public: + FedCmIdpRegistrationHandler(RenderFrameHost& render_frame_host, + IdpNetworkRequestManager* network_manager, + const GURL& idp_url); + ~FedCmIdpRegistrationHandler(); + + FedCmIdpRegistrationHandler(const FedCmIdpRegistrationHandler&) = delete; + FedCmIdpRegistrationHandler& operator=(const FedCmIdpRegistrationHandler&) = + delete; + + void FetchConfig(FedCmConfigFetcher::RequesterCallback callback); + + private: + // Owned by FederatedAuthRequestImpl. + raw_ref<RenderFrameHost> render_frame_host_; + raw_ptr<IdpNetworkRequestManager> network_manager_; + + GURL idp_url_; + std::unique_ptr<FedCmConfigFetcher> config_fetcher_; +}; + +} // namespace content + +#endif // CONTENT_BROWSER_WEBID_FEDCM_IDP_REGISTRATION_HANDLER_H_
diff --git a/content/browser/webid/federated_auth_request_impl.cc b/content/browser/webid/federated_auth_request_impl.cc index 0798b89..5458912 100644 --- a/content/browser/webid/federated_auth_request_impl.cc +++ b/content/browser/webid/federated_auth_request_impl.cc
@@ -677,6 +677,29 @@ return; } + if (!network_manager_) { + network_manager_ = CreateNetworkManager(); + } + + fedcm_idp_registration_handler_ = + std::make_unique<FedCmIdpRegistrationHandler>( + render_frame_host(), network_manager_.get(), idp); + fedcm_idp_registration_handler_->FetchConfig( + base::BindOnce(&FederatedAuthRequestImpl::OnIdpRegistrationConfigFetched, + weak_ptr_factory_.GetWeakPtr(), std::move(callback), idp)); +} + +void FederatedAuthRequestImpl::OnIdpRegistrationConfigFetched( + RegisterIdPCallback callback, + const GURL& idp, + std::vector<FedCmConfigFetcher::FetchResult> fetch_results) { + CHECK_EQ(fetch_results.size(), 1u); + fedcm_idp_registration_handler_.reset(); + if (fetch_results[0].error) { + std::move(callback).Run(RegisterIdpStatus::kErrorInvalidConfig); + return; + } + if (!request_dialog_controller_) { request_dialog_controller_ = CreateDialogController(); }
diff --git a/content/browser/webid/federated_auth_request_impl.h b/content/browser/webid/federated_auth_request_impl.h index 709df42..768a918 100644 --- a/content/browser/webid/federated_auth_request_impl.h +++ b/content/browser/webid/federated_auth_request_impl.h
@@ -16,6 +16,7 @@ #include "base/memory/scoped_refptr.h" #include "base/time/time.h" #include "content/browser/webid/fedcm_accounts_fetcher.h" +#include "content/browser/webid/fedcm_idp_registration_handler.h" #include "content/browser/webid/fedcm_metrics.h" #include "content/browser/webid/fedcm_url_computations.h" #include "content/browser/webid/federated_sd_jwt_handler.h" @@ -429,6 +430,10 @@ std::optional<IdpNetworkRequestManager::FedCmErrorUrlType> error_url_type); + void OnIdpRegistrationConfigFetched( + RegisterIdPCallback callback, + const GURL& idp, + std::vector<FedCmConfigFetcher::FetchResult> fetch_results); void OnRegisterIdPPermissionResponse(RegisterIdPCallback callback, const GURL& idp, bool accepted); @@ -519,6 +524,8 @@ std::unique_ptr<FederatedSdJwtHandler> federated_sdjwt_handler_; + std::unique_ptr<FedCmIdpRegistrationHandler> fedcm_idp_registration_handler_; + // Set of pending user info requests. base::flat_set<std::unique_ptr<FederatedAuthUserInfoRequest>> user_info_requests_;
diff --git a/content/browser/webid/federated_auth_request_impl_registry_unittest.cc b/content/browser/webid/federated_auth_request_impl_registry_unittest.cc index f9ee54d2..ded42fa 100644 --- a/content/browser/webid/federated_auth_request_impl_registry_unittest.cc +++ b/content/browser/webid/federated_auth_request_impl_registry_unittest.cc
@@ -54,6 +54,38 @@ } }; +class TestIdpNetworkRequestManager : public MockIdpNetworkRequestManager { + public: + void FetchWellKnown(const GURL& provider, + FetchWellKnownCallback callback) override { + // Assume that the well-known file is not found for a registered IDP. + IdpNetworkRequestManager::WellKnown well_known; + FetchStatus fetch_status = {ParseStatus::kHttpNotFoundError, 404}; + base::SequencedTaskRunner::GetCurrentDefault()->PostTask( + FROM_HERE, + base::BindOnce(std::move(callback), fetch_status, well_known)); + } + + void FetchConfig(const GURL& provider, + blink::mojom::RpMode rp_mode, + int idp_brand_icon_ideal_size, + int idp_brand_icon_minimum_size, + FetchConfigCallback callback) override { + IdpNetworkRequestManager::Endpoints endpoints; + endpoints.token = GURL("https://idp.example/token"); + endpoints.accounts = GURL("https://idp.example/accounts"); + + IdentityProviderMetadata idp_metadata; + idp_metadata.config_url = provider; + idp_metadata.idp_login_url = GURL("https://idp.example/login"); + idp_metadata.types = {"idp-type"}; + FetchStatus fetch_status = {ParseStatus::kSuccess, 200}; + base::SequencedTaskRunner::GetCurrentDefault()->PostTask( + FROM_HERE, base::BindOnce(std::move(callback), fetch_status, endpoints, + idp_metadata)); + } +}; + } // namespace class FederatedAuthRequestImplRegistryTest @@ -86,6 +118,10 @@ std::make_unique<NiceMock<MockIdentityRequestDialogController>>(); federated_auth_request_impl_->SetDialogControllerForTests( std::move(mock_dialog_controller)); + std::unique_ptr<TestIdpNetworkRequestManager> network_request_manager = + std::make_unique<TestIdpNetworkRequestManager>(); + federated_auth_request_impl_->SetNetworkManagerForTests( + std::move(network_request_manager)); } void TearDown() override {
diff --git a/content/browser/webid/idp_network_request_manager.cc b/content/browser/webid/idp_network_request_manager.cc index 78755491..401e170 100644 --- a/content/browser/webid/idp_network_request_manager.cc +++ b/content/browser/webid/idp_network_request_manager.cc
@@ -650,7 +650,7 @@ idp_metadata.idp_login_url = ExtractEndpoint(provider, response, kLoginUrlKey); - if (IsFedCmIdPRegistrationEnabled()) { + if (IsFedCmDelegationEnabled()) { const base::Value::List* formats = response.FindList(kFormatsKey); if (formats) { for (const auto& format : *formats) { @@ -1212,7 +1212,7 @@ if (idp_blindness) { // IdP blindness can only be used when the feature is enabled. - DCHECK(IsFedCmIdPRegistrationEnabled()); + DCHECK(IsFedCmDelegationEnabled()); // We have to set this to a Origin: null because the underlying loader // will not let us send a request without Origin header if the request // method is POST.
diff --git a/content/browser/webid/webid_browsertest.cc b/content/browser/webid/webid_browsertest.cc index 7c2e7b0..5add42b8 100644 --- a/content/browser/webid/webid_browsertest.cc +++ b/content/browser/webid/webid_browsertest.cc
@@ -937,6 +937,38 @@ EXPECT_EQ(std::string(kToken), EvalJs(shell(), get_script)); } +IN_PROC_BROWSER_TEST_F(WebIdIdPRegistryBrowserTest, + RegistrationFailsWithInvalidLoginUrl) { + GURL configURL = GURL(BaseIdpUrl()); + auto details = BuildValidConfigDetails(); + // Set this as empty so that the login URL is invalid. + details.login_url = ""; + idp_server()->SetConfigResponseDetails(details); + + auto mock = std::make_unique< + ::testing::NiceMock<MockIdentityRequestDialogController>>(); + test_browser_client_->SetIdentityRequestDialogController(std::move(mock)); + + // We navigate to the IdP's configURL so that we can run + // the script below with the IdP's origin as the top level + // first party context. + EXPECT_TRUE(NavigateToURL(shell(), configURL)); + + std::string script = R"( + (async () => { + await IdentityProvider.register(')" + + configURL.spec() + R"('); + // The permission was accepted if the promise resolves. + return true; + }) () + )"; + + EXPECT_EQ("NotAllowedError: Invalid identity provider registration config.", + ExtractJsError(EvalJs(shell(), script))); + + EXPECT_TRUE(sharing_context()->GetRegisteredIdPs().empty()); +} + // Verify that IDP sign-in headers work. IN_PROC_BROWSER_TEST_F(WebIdIdpSigninStatusBrowserTest, IdpSigninToplevel) { GURL url = https_server().GetURL(kRpHostName, "/header/signin"); @@ -1913,9 +1945,6 @@ std::vector<base::test::FeatureRef> features; features.push_back(features::kFedCm); features.push_back(features::kFedCmDelegation); - // Needs to reconcile well with the IdP Registration and Multi-IdP API - features.push_back(features::kFedCmIdPRegistration); - features.push_back(features::kFedCmMultipleIdentityProviders); scoped_feature_list_.InitWithFeatures(features, {}); command_line->AppendSwitch(switches::kIgnoreCertificateErrors); }
diff --git a/content/common/features.cc b/content/common/features.cc index 100617a5..e5fec52 100644 --- a/content/common/features.cc +++ b/content/common/features.cc
@@ -29,13 +29,6 @@ "AndroidDragDropOopif", base::FEATURE_ENABLED_BY_DEFAULT); -// Whether to allow attaching an inner WebContents not owned by the outer -// WebContents. This is for prototyping purposes and should not be enabled in -// production. -BASE_FEATURE(kAttachUnownedInnerWebContents, - "AttachUnownedInnerWebContents", - base::FEATURE_DISABLED_BY_DEFAULT); - // Synchronously continuing with navigation can lead to trying to start another // navigation synchronously while the first navigation is still being processed // on the stack. This results in re-entrancy which is unsafe and triggers a
diff --git a/content/common/features.h b/content/common/features.h index 9c62eee..ccc1ab3 100644 --- a/content/common/features.h +++ b/content/common/features.h
@@ -16,7 +16,6 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kAllowContentInitiatedDataUrlNavigations); CONTENT_EXPORT BASE_DECLARE_FEATURE(kAndroidDownloadableFontsMatching); CONTENT_EXPORT BASE_DECLARE_FEATURE(kAndroidDragDropOopif); -CONTENT_EXPORT BASE_DECLARE_FEATURE(kAttachUnownedInnerWebContents); CONTENT_EXPORT BASE_DECLARE_FEATURE(kAvoidUnnecessaryBeforeUnloadCheckSync); // Please check the code comment on // ContentBrowserClient::SupportsAvoidUnnecessaryBeforeUnloadCheckSync() in the
diff --git a/content/public/browser/BUILD.gn b/content/public/browser/BUILD.gn index 081f2a1..2714f3b8 100644 --- a/content/public/browser/BUILD.gn +++ b/content/public/browser/BUILD.gn
@@ -470,6 +470,8 @@ "tts_controller.h", "tts_platform.h", "tts_utterance.h", + "unowned_inner_web_contents_client.cc", + "unowned_inner_web_contents_client.h", "url_data_source.cc", "url_data_source.h", "url_loader_request_interceptor.cc",
diff --git a/content/public/browser/unowned_inner_web_contents_client.cc b/content/public/browser/unowned_inner_web_contents_client.cc new file mode 100644 index 0000000..ac25c5d4 --- /dev/null +++ b/content/public/browser/unowned_inner_web_contents_client.cc
@@ -0,0 +1,21 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "content/public/browser/unowned_inner_web_contents_client.h" + +namespace content { + +// static +UnownedInnerWebContentsClient::PassKey +UnownedInnerWebContentsClient::GetPassKeyForTesting() { + return GetPassKey(); +} + +// static +UnownedInnerWebContentsClient::PassKey +UnownedInnerWebContentsClient::GetPassKey() { + return PassKey(); +} + +} // namespace content
diff --git a/content/public/browser/unowned_inner_web_contents_client.h b/content/public/browser/unowned_inner_web_contents_client.h new file mode 100644 index 0000000..ef2822c9 --- /dev/null +++ b/content/public/browser/unowned_inner_web_contents_client.h
@@ -0,0 +1,39 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CONTENT_PUBLIC_BROWSER_UNOWNED_INNER_WEB_CONTENTS_CLIENT_H_ +#define CONTENT_PUBLIC_BROWSER_UNOWNED_INNER_WEB_CONTENTS_CLIENT_H_ + +#include "base/types/pass_key.h" +#include "content/common/content_export.h" + +namespace guest_contents { +class GuestContentsHandle; +} // namespace guest_contents + +namespace content { + +// A static class that provides PassKeys for clients of unowned inner web +// contents to use WebContents::AttachUnownedInnerWebContents() and +// DetachUnownedInnerWebContents(). These APIs are experimental and are intended +// to be used by //components/guest_contents only. If you intend to add new +// clients, please reach out to //components/guest_contents owners and content +// owners. See an explanation of guest-contents at crbug.com/415626990. +class CONTENT_EXPORT UnownedInnerWebContentsClient { + public: + using PassKey = base::PassKey<UnownedInnerWebContentsClient>; + + UnownedInnerWebContentsClient() = delete; + + static PassKey GetPassKeyForTesting(); + + private: + friend class guest_contents::GuestContentsHandle; + + static PassKey GetPassKey(); +}; + +} // namespace content + +#endif // CONTENT_PUBLIC_BROWSER_UNOWNED_INNER_WEB_CONTENTS_CLIENT_H_
diff --git a/content/public/browser/web_contents.h b/content/public/browser/web_contents.h index 700e292..ab2df2f 100644 --- a/content/public/browser/web_contents.h +++ b/content/public/browser/web_contents.h
@@ -124,6 +124,7 @@ class RenderWidgetHostView; class ScreenOrientationDelegate; class SiteInstance; +class UnownedInnerWebContentsClient; class WebContentsDelegate; class WebUI; struct DropData; @@ -955,6 +956,7 @@ // TODO(crbug.com/416609971): Remove this method once we find a way to attach // inner WebContents without using WebContents trees. virtual void AttachUnownedInnerWebContents( + base::PassKey<UnownedInnerWebContentsClient>, WebContents* inner_web_contents, RenderFrameHost* render_frame_host) = 0; @@ -964,6 +966,7 @@ // TODO(crbug.com/416609971): Remove this method once we find a way to attach // inner WebContents without using WebContents trees. virtual void DetachUnownedInnerWebContents( + base::PassKey<UnownedInnerWebContentsClient>, WebContents* inner_web_contents) = 0; // Attaches `guest_page` to the container frame `outer_render_frame_host`,
diff --git a/content/public/common/content_features.cc b/content/public/common/content_features.cc index 75a5d885..41315d1 100644 --- a/content/public/common/content_features.cc +++ b/content/public/common/content_features.cc
@@ -72,6 +72,13 @@ const base::FeatureParam<bool> kAndroidSpareRendererKillWhenBackgrounded{ &kAndroidWarmUpSpareRendererWithTimeout, "kill_when_backgrounded", false}; +// Whether to allow attaching an inner WebContents not owned by the outer +// WebContents. This is for prototyping purposes and should not be enabled in +// production. +BASE_FEATURE(kAttachUnownedInnerWebContents, + "AttachUnownedInnerWebContents", + base::FEATURE_DISABLED_BY_DEFAULT); + // Launches the audio service on the browser startup. BASE_FEATURE(kAudioServiceLaunchOnStartup, "AudioServiceLaunchOnStartup",
diff --git a/content/public/common/content_features.h b/content/public/common/content_features.h index 5cf8fd3..d3d813f 100644 --- a/content/public/common/content_features.h +++ b/content/public/common/content_features.h
@@ -45,6 +45,7 @@ kAndroidSpareRendererMemoryThreshold; CONTENT_EXPORT extern const base::FeatureParam<bool> kAndroidSpareRendererKillWhenBackgrounded; +CONTENT_EXPORT BASE_DECLARE_FEATURE(kAttachUnownedInnerWebContents); CONTENT_EXPORT BASE_DECLARE_FEATURE(kAudioServiceLaunchOnStartup); CONTENT_EXPORT BASE_DECLARE_FEATURE(kAudioServiceOutOfProcess); CONTENT_EXPORT BASE_DECLARE_FEATURE(kAudioServiceSandbox);
diff --git a/content/test/test_web_contents.h b/content/test/test_web_contents.h index 3aee1810..f678753 100644 --- a/content/test/test_web_contents.h +++ b/content/test/test_web_contents.h
@@ -246,7 +246,6 @@ const std::u16string& suggested_filename, RenderFrameHost* rfh, bool is_subresource) override; - void ReattachToOuterWebContentsFrame() override {} void SetPageFrozen(bool frozen) override; bool IsBackForwardCacheSupported() override; const std::optional<blink::mojom::PictureInPictureWindowOptions>&
diff --git a/gpu/ipc/client/gpu_channel_host.cc b/gpu/ipc/client/gpu_channel_host.cc index 5ee6c2a..fd0aac0 100644 --- a/gpu/ipc/client/gpu_channel_host.cc +++ b/gpu/ipc/client/gpu_channel_host.cc
@@ -381,7 +381,7 @@ GpuChannelHost::ConnectionTracker::ConnectionTracker() = default; GpuChannelHost::ConnectionTracker::~ConnectionTracker() { - CHECK(observer_list_.empty(), base::NotFatalUntil::M126); + CHECK(observer_list_.empty()); } void GpuChannelHost::ConnectionTracker::OnDisconnectedFromGpuProcess() { @@ -392,7 +392,7 @@ void GpuChannelHost::ConnectionTracker::AddObserver( GpuChannelLostObserver* obs) { AutoLock lock(channel_obs_lock_); - CHECK(!base::Contains(observer_list_, obs), base::NotFatalUntil::M126); + CHECK(!base::Contains(observer_list_, obs)); observer_list_.push_back(obs); }
diff --git a/gpu/vulkan/android/vulkan_implementation_android.cc b/gpu/vulkan/android/vulkan_implementation_android.cc index ffb15d28..9388b65b 100644 --- a/gpu/vulkan/android/vulkan_implementation_android.cc +++ b/gpu/vulkan/android/vulkan_implementation_android.cc
@@ -5,7 +5,6 @@ #include "gpu/vulkan/android/vulkan_implementation_android.h" #include "base/android/android_hardware_buffer_compat.h" -#include "base/feature_list.h" #include "base/files/file_path.h" #include "base/functional/callback_helpers.h" #include "base/logging.h" @@ -20,16 +19,6 @@ #include "ui/gfx/gpu_memory_buffer.h" namespace gpu { -namespace { - -// VK_KHR_external_memory_capabilities + VK_KHR_external_semaphore_capabilities -// were promoted in Vulkan 1.1 so we shouldn't need to list them in the required -// extensions. -BASE_FEATURE(kRequirePromotedVulkanExtensions, - "RequirePromotedVulkanExtensions", - base::FEATURE_DISABLED_BY_DEFAULT); - -} // namespace VulkanImplementationAndroid::VulkanImplementationAndroid() = default; @@ -39,13 +28,6 @@ DCHECK(using_surface); std::vector<const char*> required_extensions = { VK_KHR_SURFACE_EXTENSION_NAME, VK_KHR_ANDROID_SURFACE_EXTENSION_NAME}; - if (base::FeatureList::IsEnabled(kRequirePromotedVulkanExtensions)) { - required_extensions.push_back( - VK_KHR_EXTERNAL_MEMORY_CAPABILITIES_EXTENSION_NAME); - required_extensions.push_back( - VK_KHR_EXTERNAL_SEMAPHORE_CAPABILITIES_EXTENSION_NAME); - } - return vulkan_instance_.Initialize(base::FilePath("libvulkan.so"), required_extensions, {}); }
diff --git a/infra/config/generated/builders/ci/android-12l-x64-rel-cq/targets/chromium.android.json b/infra/config/generated/builders/ci/android-12l-x64-rel-cq/targets/chromium.android.json index ccee355..a70cfe0 100644 --- a/infra/config/generated/builders/ci/android-12l-x64-rel-cq/targets/chromium.android.json +++ b/infra/config/generated/builders/ci/android-12l-x64-rel-cq/targets/chromium.android.json
@@ -3,7 +3,7 @@ "gtest_tests": [ { "args": [ - "--annotation=Restriction=Tablet,ImportantFormFactors=Tablet", + "--annotation=Restriction=Tablet,Restriction=TabletOrDesktop,ImportantFormFactors=Tablet,ImportantFormFactors=TabletOrDesktop", "--git-revision=${got_revision}", "--avd-config=../../tools/android/avd/proto/android_32_google_apis_x64_foldable.textpb", "--gs-results-bucket=chromium-result-details",
diff --git a/infra/config/generated/builders/try/android-12l-x64-rel-cq/targets/chromium.android.json b/infra/config/generated/builders/try/android-12l-x64-rel-cq/targets/chromium.android.json index ccee355..a70cfe0 100644 --- a/infra/config/generated/builders/try/android-12l-x64-rel-cq/targets/chromium.android.json +++ b/infra/config/generated/builders/try/android-12l-x64-rel-cq/targets/chromium.android.json
@@ -3,7 +3,7 @@ "gtest_tests": [ { "args": [ - "--annotation=Restriction=Tablet,ImportantFormFactors=Tablet", + "--annotation=Restriction=Tablet,Restriction=TabletOrDesktop,ImportantFormFactors=Tablet,ImportantFormFactors=TabletOrDesktop", "--git-revision=${got_revision}", "--avd-config=../../tools/android/avd/proto/android_32_google_apis_x64_foldable.textpb", "--gs-results-bucket=chromium-result-details",
diff --git a/infra/config/generated/builders/try/android-x64-rel/targets/chromium.android.json b/infra/config/generated/builders/try/android-x64-rel/targets/chromium.android.json index ec84f9d3..a5e11d6 100644 --- a/infra/config/generated/builders/try/android-x64-rel/targets/chromium.android.json +++ b/infra/config/generated/builders/try/android-x64-rel/targets/chromium.android.json
@@ -3,7 +3,7 @@ "gtest_tests": [ { "args": [ - "--annotation=Restriction=Tablet,ImportantFormFactors=Tablet", + "--annotation=Restriction=Tablet,Restriction=TabletOrDesktop,ImportantFormFactors=Tablet,ImportantFormFactors=TabletOrDesktop", "--git-revision=${got_revision}", "--avd-config=../../tools/android/avd/proto/android_32_google_apis_x64_foldable.textpb", "--gs-results-bucket=chromium-result-details",
diff --git a/infra/config/targets/tests.star b/infra/config/targets/tests.star index e0fec9f..306d5f0f 100644 --- a/infra/config/targets/tests.star +++ b/infra/config/targets/tests.star
@@ -558,7 +558,7 @@ "skia_gold_test", ], args = [ - "--annotation=Restriction=Tablet,ImportantFormFactors=Tablet", + "--annotation=Restriction=Tablet,Restriction=TabletOrDesktop,ImportantFormFactors=Tablet,ImportantFormFactors=TabletOrDesktop", ], binary = "chrome_public_test_apk", )
diff --git a/internal b/internal index d001483..f8e36dc 160000 --- a/internal +++ b/internal
@@ -1 +1 @@ -Subproject commit d001483ef1f2440291ad1fa8c15b897b7be0e72f +Subproject commit f8e36dcd08ab67bfc9e717b3ed315fef7e8e6cba
diff --git a/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.h b/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.h index 7373b45..7b70114 100644 --- a/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.h +++ b/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.h
@@ -12,7 +12,6 @@ #import "components/breadcrumbs/core/breadcrumb_manager_browser_agent.h" #import "ios/chrome/browser/overlays/model/public/overlay_presenter.h" #import "ios/chrome/browser/overlays/model/public/overlay_presenter_observer.h" -#import "ios/chrome/browser/shared/model/browser/browser_observer.h" #import "ios/chrome/browser/shared/model/browser/browser_user_data.h" #import "ios/chrome/browser/shared/model/web_state_list/web_state_list_observer.h" @@ -47,7 +46,6 @@ class BreadcrumbManagerBrowserAgent : public breadcrumbs::BreadcrumbManagerBrowserAgent, - public BrowserObserver, public OverlayPresenterObserver, public BrowserUserData<BreadcrumbManagerBrowserAgent>, public WebStateListObserver { @@ -65,9 +63,6 @@ // breadcrumbs::BreadcrumbManagerBrowserAgent: void PlatformLogEvent(const std::string& event) override; - // BrowserObserver: - void BrowserDestroyed(Browser* browser) override; - // WebStateListObserver: void WebStateListDidChange(WebStateList* web_state_list, const WebStateListChange& change, @@ -81,8 +76,6 @@ bool initial_presentation) override; void OverlayPresenterDestroyed(OverlayPresenter* presenter) override; - raw_ptr<Browser> browser_ = nullptr; - // Keeps track of WebState mutation count to avoid logging every event. // Created in WillBeginBatchOperation and destroyed in BatchOperationEnded. // Final mutation count is logged in BatchOperationEnded.
diff --git a/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.mm b/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.mm index 192055c..9e25c60 100644 --- a/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.mm +++ b/ios/chrome/browser/crash_report/model/breadcrumbs/breadcrumb_manager_browser_agent.mm
@@ -39,19 +39,15 @@ const char kBreadcrumbOverlayJsPrompt[] = "#js-prompt"; BreadcrumbManagerBrowserAgent::BreadcrumbManagerBrowserAgent(Browser* browser) - : BrowserUserData(browser), browser_(browser) { - browser_->AddObserver(this); + : BrowserUserData(browser) { browser_->GetWebStateList()->AddObserver(this); overlay_observation_.Observe( OverlayPresenter::FromBrowser(browser, OverlayModality::kWebContentArea)); } -BreadcrumbManagerBrowserAgent::~BreadcrumbManagerBrowserAgent() = default; - -void BreadcrumbManagerBrowserAgent::BrowserDestroyed(Browser* browser) { +BreadcrumbManagerBrowserAgent::~BreadcrumbManagerBrowserAgent() { browser_->GetWebStateList()->RemoveObserver(this); - browser_->RemoveObserver(this); } void BreadcrumbManagerBrowserAgent::PlatformLogEvent(const std::string& event) {
diff --git a/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.h b/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.h index 2f66253f..963f844f 100644 --- a/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.h +++ b/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.h
@@ -10,7 +10,6 @@ #import "base/memory/raw_ptr.h" #import "base/scoped_observation.h" #import "components/webauthn/core/browser/passkey_model.h" -#import "ios/chrome/browser/shared/model/browser/browser_observer.h" #import "ios/chrome/browser/shared/model/browser/browser_user_data.h" namespace webauthn { @@ -21,7 +20,6 @@ // notification when required. class CredentialProviderBrowserAgent : public BrowserUserData<CredentialProviderBrowserAgent>, - public BrowserObserver, public webauthn::PasskeyModel::Observer { public: ~CredentialProviderBrowserAgent() override; @@ -40,23 +38,15 @@ void RemoveObservers(); - // BrowserObserver:: - void BrowserDestroyed(Browser* browser) override; - // webauthn::PasskeyModel::Observer: void OnPasskeysChanged( const std::vector<webauthn::PasskeyModelChange>& changes) override; void OnPasskeyModelShuttingDown() override; void OnPasskeyModelIsReady(bool is_ready) override; - // The owning Browser - raw_ptr<Browser> browser_; - // Owned by the IOSPasskeyModelFactory which should outlive this class raw_ptr<webauthn::PasskeyModel> model_; - base::ScopedObservation<Browser, BrowserObserver> browser_observation_{this}; - base::ScopedObservation<webauthn::PasskeyModel, webauthn::PasskeyModel::Observer> model_observation_{this};
diff --git a/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.mm b/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.mm index 40e6cc1..db67f70 100644 --- a/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.mm +++ b/ios/chrome/browser/credential_provider/model/credential_provider_browser_agent.mm
@@ -18,20 +18,20 @@ #import "ios/chrome/browser/webauthn/model/ios_passkey_model_factory.h" #import "ios/web/public/web_state.h" +namespace { // Maximum amount of time since a passkey was created for it to count as a // recently added passkey. -static constexpr base::TimeDelta kRecentlyAddedDelay = base::Seconds(5); +constexpr base::TimeDelta kRecentlyAddedDelay = base::Seconds(5); +} // namespace CredentialProviderBrowserAgent::CredentialProviderBrowserAgent(Browser* browser) : BrowserUserData(browser), - browser_(browser), model_(IOSPasskeyModelFactory::GetForProfile( // Here, we want to observe the user's passkey model, so we need the // original profile. browser_->GetProfile()->GetOriginalProfile())) { if (model_) { model_observation_.Observe(model_.get()); - browser_observation_.Observe(browser_.get()); } } @@ -43,7 +43,7 @@ void CredentialProviderBrowserAgent::DisplayInfoBar( const sync_pb::WebauthnCredentialSpecifics& passkey) { - if (!browser_ || !infobar_allowed_) { + if (!infobar_allowed_) { return; } @@ -81,12 +81,6 @@ void CredentialProviderBrowserAgent::RemoveObservers() { model_observation_.Reset(); - browser_observation_.Reset(); - browser_ = nullptr; -} - -void CredentialProviderBrowserAgent::BrowserDestroyed(Browser* browser) { - RemoveObservers(); } void CredentialProviderBrowserAgent::OnPasskeysChanged(
diff --git a/ios/chrome/browser/default_promo/ui_bundled/default_browser_promo_non_modal_metrics_util.mm b/ios/chrome/browser/default_promo/ui_bundled/default_browser_promo_non_modal_metrics_util.mm index e6156fd..fff8b07 100644 --- a/ios/chrome/browser/default_promo/ui_bundled/default_browser_promo_non_modal_metrics_util.mm +++ b/ios/chrome/browser/default_promo/ui_bundled/default_browser_promo_non_modal_metrics_util.mm
@@ -85,7 +85,7 @@ default: // TODO(crbug.com/327429982): M124 validation necessary. - NOTREACHED(base::NotFatalUntil::M126); + NOTREACHED(); } UmaHistogramEnumeration(histogramString, action);
diff --git a/ios/chrome/browser/first_run/ui_bundled/best_features/ui/best_features_view_controller.mm b/ios/chrome/browser/first_run/ui_bundled/best_features/ui/best_features_view_controller.mm index 77cf3b5..6c37e9f 100644 --- a/ios/chrome/browser/first_run/ui_bundled/best_features/ui/best_features_view_controller.mm +++ b/ios/chrome/browser/first_run/ui_bundled/best_features/ui/best_features_view_controller.mm
@@ -107,7 +107,7 @@ #pragma mark - BestFeaturesScreenConsumer - (void)setBestFeaturesItems:(NSArray<BestFeaturesItem*>*)items { - CHECK([items count] == 3, base::NotFatalUntil::M128); + CHECK([items count] == 3); _bestFeaturesItems = items; } @@ -173,7 +173,7 @@ // Creates the data source for the table view. - (UITableViewDiffableDataSource<NSNumber*, NSNumber*>*) createAndFillDataSource { - CHECK(_bestFeaturesItems, base::NotFatalUntil::M128); + CHECK(_bestFeaturesItems); __weak __typeof(self) weakSelf = self; UITableViewDiffableDataSource<NSNumber*, NSNumber*>* dataSource = [[UITableViewDiffableDataSource alloc]
diff --git a/ios/chrome/browser/infobars/ui_bundled/modals/permissions/infobar_permissions_table_view_controller.mm b/ios/chrome/browser/infobars/ui_bundled/modals/permissions/infobar_permissions_table_view_controller.mm index bdd4ad6ea..2b85501 100644 --- a/ios/chrome/browser/infobars/ui_bundled/modals/permissions/infobar_permissions_table_view_controller.mm +++ b/ios/chrome/browser/infobars/ui_bundled/modals/permissions/infobar_permissions_table_view_controller.mm
@@ -297,7 +297,7 @@ if (tableViewLoaded) { NSIndexPath* index = [self.tableViewModel indexPathForItemType:itemType]; - CHECK_NE(index, nil, base::NotFatalUntil::M128); + CHECK_NE(index, nil); [self.tableView insertRowsAtIndexPaths:@[ index ] withRowAnimation:UITableViewRowAnimationAutomatic]; [self.presentationHandler resizeInfobarModal];
diff --git a/ios/chrome/browser/saved_tab_groups/model/ios_tab_group_sync_util.mm b/ios/chrome/browser/saved_tab_groups/model/ios_tab_group_sync_util.mm index c5145f7..7b6e3577 100644 --- a/ios/chrome/browser/saved_tab_groups/model/ios_tab_group_sync_util.mm +++ b/ios/chrome/browser/saved_tab_groups/model/ios_tab_group_sync_util.mm
@@ -160,8 +160,7 @@ destination_tab_group)); // Check that the source browser has one less group. CHECK_EQ(source_group_count, - source_browser->GetWebStateList()->GetGroups().size() + 1, - base::NotFatalUntil::M128); + source_browser->GetWebStateList()->GetGroups().size() + 1); } void MoveTabGroupToBrowser(const TabGroup* source_tab_group,
diff --git a/ios/chrome/browser/search_engine_choice/ui_bundled/snippet_search_engine_button.mm b/ios/chrome/browser/search_engine_choice/ui_bundled/snippet_search_engine_button.mm index 8a0c085..39d2b5eb 100644 --- a/ios/chrome/browser/search_engine_choice/ui_bundled/snippet_search_engine_button.mm +++ b/ios/chrome/browser/search_engine_choice/ui_bundled/snippet_search_engine_button.mm
@@ -500,7 +500,7 @@ #pragma mark - Accessibility - (NSString*)accessibilityLabel { - CHECK_NE(self.snippetText.length, 0ul, base::NotFatalUntil::M127) + CHECK_NE(self.snippetText.length, 0ul) << base::SysNSStringToUTF8(self.searchEngineName) << " " << base::SysNSStringToUTF8(self.snippetText); return [NSString @@ -508,7 +508,7 @@ } - (NSArray<NSString*>*)accessibilityUserInputLabels { - CHECK_NE(self.searchEngineName.length, 0ul, base::NotFatalUntil::M127) + CHECK_NE(self.searchEngineName.length, 0ul) << base::SysNSStringToUTF8(self.searchEngineName) << " " << base::SysNSStringToUTF8(self.snippetText); return @[ self.searchEngineName ];
diff --git a/ios/chrome/browser/sessions/model/web_state_list_serialization.mm b/ios/chrome/browser/sessions/model/web_state_list_serialization.mm index 603cfb18..56e5e98 100644 --- a/ios/chrome/browser/sessions/model/web_state_list_serialization.mm +++ b/ios/chrome/browser/sessions/model/web_state_list_serialization.mm
@@ -433,7 +433,7 @@ if (base::FeatureList::IsEnabled( session::features::kSessionRestorationSessionIDCheck)) { web::WebStateID web_state_id = web_state->GetUniqueIdentifier(); - CHECK(web_state_id.valid(), base::NotFatalUntil::M125); + CHECK(web_state_id.valid()); if (!max_identifier.is_valid() || max_identifier.id() < web_state_id.identifier()) { max_identifier = web_state_id.ToSessionID();
diff --git a/ios/chrome/browser/settings/ui_bundled/google_services/manage_sync_settings_coordinator.mm b/ios/chrome/browser/settings/ui_bundled/google_services/manage_sync_settings_coordinator.mm index fecbe69..72751a9 100644 --- a/ios/chrome/browser/settings/ui_bundled/google_services/manage_sync_settings_coordinator.mm +++ b/ios/chrome/browser/settings/ui_bundled/google_services/manage_sync_settings_coordinator.mm
@@ -191,7 +191,7 @@ self.mediator.consumer = viewController; - CHECK(_baseNavigationController, base::NotFatalUntil::M129); + CHECK(_baseNavigationController); [self.baseNavigationController pushViewController:viewController animated:YES]; _syncObserver = std::make_unique<SyncObserverBridge>(self, self.syncService); @@ -321,8 +321,7 @@ // `baseNavigationController`, `baseNavigationController` needs to be // closed. CHECK([self.baseNavigationController - isKindOfClass:[SettingsNavigationController class]], - base::NotFatalUntil::M129); + isKindOfClass:[SettingsNavigationController class]]); [self.baseNavigationController performSelector:@selector(closeSettings)]; } else {
diff --git a/ios/chrome/browser/settings/ui_bundled/settings_table_view_controller.mm b/ios/chrome/browser/settings/ui_bundled/settings_table_view_controller.mm index 3b432f4a..2e5e4fa 100644 --- a/ios/chrome/browser/settings/ui_bundled/settings_table_view_controller.mm +++ b/ios/chrome/browser/settings/ui_bundled/settings_table_view_controller.mm
@@ -409,6 +409,10 @@ [[NotificationsSettingsObserver alloc] initWithPrefService:prefService localState:localState]; _notificationsObserver.delegate = self; + + // TODO(crbug.com/41344225): -loadModel should not be called from + // initializer. A possible fix is to move this call to -viewDidLoad. + [self loadModel]; } return self; } @@ -432,8 +436,6 @@ self.navigationItem.largeTitleDisplayMode = UINavigationItemLargeTitleDisplayModeAlways; - - [self loadModel]; } - (void)viewWillAppear:(BOOL)animated {
diff --git a/ios/chrome/browser/settings/ui_bundled/sync/sync_create_passphrase_table_view_controller.mm b/ios/chrome/browser/settings/ui_bundled/sync/sync_create_passphrase_table_view_controller.mm index bba9ae60..e5571842 100644 --- a/ios/chrome/browser/settings/ui_bundled/sync/sync_create_passphrase_table_view_controller.mm +++ b/ios/chrome/browser/settings/ui_bundled/sync/sync_create_passphrase_table_view_controller.mm
@@ -37,17 +37,16 @@ l10n_util::GetNSString(IDS_IOS_NEW_SYNC_ENCRYPTION_PASSPHRASE_INFO_UNO); self.processingMessage = l10n_util::GetNSString(IDS_IOS_SYNC_PASSPHRASE_ENCRYPTING); + + // TODO(crbug.com/41344225): -loadModel should not be called from + // initializer. A possible fix is to move this call to -viewDidLoad. + [self loadModel]; } return self; } #pragma mark - UIViewController -- (void)viewDidLoad { - [super viewDidLoad]; - [self loadModel]; -} - - (void)didReceiveMemoryWarning { [super didReceiveMemoryWarning]; if (![self isViewLoaded]) {
diff --git a/ios/chrome/browser/shared/model/prefs/pref_backed_boolean.mm b/ios/chrome/browser/shared/model/prefs/pref_backed_boolean.mm index d30494e..f9b3717 100644 --- a/ios/chrome/browser/shared/model/prefs/pref_backed_boolean.mm +++ b/ios/chrome/browser/shared/model/prefs/pref_backed_boolean.mm
@@ -30,8 +30,7 @@ } - (void)dealloc { - CHECK(_stopped, base::NotFatalUntil::M140) - << "-stop should be called on PrefBackedBoolean"; + CHECK(_stopped) << "-stop should be called on PrefBackedBoolean"; } - (BOOL)value {
diff --git a/ios/chrome/browser/shared/model/web_state_list/web_state_list.mm b/ios/chrome/browser/shared/model/web_state_list/web_state_list.mm index 96bb2ef..cc412c3 100644 --- a/ios/chrome/browser/shared/model/web_state_list/web_state_list.mm +++ b/ios/chrome/browser/shared/model/web_state_list/web_state_list.mm
@@ -858,7 +858,7 @@ // Figure out the pivot index. int pivot_index = kInvalidIndex; const int first_index = *indices.begin(); - CHECK(ContainsIndex(first_index), base::NotFatalUntil::M128); + CHECK(ContainsIndex(first_index)); if (IsWebStatePinnedAt(first_index)) { // Move to the last pinned tab. pivot_index = pinned_tabs_count_; @@ -980,7 +980,7 @@ // keep ungrouped WebStates in the order they were in the group. for (auto it = indices.rbegin(); it != indices.rend(); ++it) { const int index = *it; - CHECK(ContainsIndex(index), base::NotFatalUntil::M128); + CHECK(ContainsIndex(index)); const TabGroup* group = GetGroupOfWebStateAt(index); if (group) { const int to_index = group->range().range_end() - 1;
diff --git a/ios/chrome/browser/signin/model/BUILD.gn b/ios/chrome/browser/signin/model/BUILD.gn index 14f4b9f..8ef6c5d8 100644 --- a/ios/chrome/browser/signin/model/BUILD.gn +++ b/ios/chrome/browser/signin/model/BUILD.gn
@@ -77,7 +77,9 @@ "//google_apis", "//ios/chrome/app:change_profile_commands", "//ios/chrome/app:tests_hook", + "//ios/chrome/browser/authentication/ui_bundled:continuation", "//ios/chrome/browser/authentication/ui_bundled/account_menu:constants", + "//ios/chrome/browser/authentication/ui_bundled/signin:signin_headers", "//ios/chrome/browser/bookmarks/model:model_utils", "//ios/chrome/browser/content_settings/model", "//ios/chrome/browser/crash_report/model",
diff --git a/ios/chrome/browser/signin/model/DEPS b/ios/chrome/browser/signin/model/DEPS index 454baaf..8563902 100644 --- a/ios/chrome/browser/signin/model/DEPS +++ b/ios/chrome/browser/signin/model/DEPS
@@ -19,6 +19,10 @@ ] specific_include_rules = { + "^account_consistency_browser_agent.mm": [ + "+ios/chrome/browser/authentication/ui_bundled/continuation.h", + "+ios/chrome/browser/authentication/ui_bundled/signin/signin_coordinator.h", + ], # TODO(crbug.com/331781927): remove when kIdentityDiscAccountMenu launches. "^authentication_service_delegate_impl.cc": [ "+ios/chrome/browser/ntp/ui_bundled/new_tab_page_feature.h",
diff --git a/ios/chrome/browser/signin/model/account_consistency_browser_agent.h b/ios/chrome/browser/signin/model/account_consistency_browser_agent.h index 1ce3692..8afe5dcf28 100644 --- a/ios/chrome/browser/signin/model/account_consistency_browser_agent.h +++ b/ios/chrome/browser/signin/model/account_consistency_browser_agent.h
@@ -15,6 +15,9 @@ @protocol SettingsCommands; class Browser; @class SceneState; +@class SigninCoordinator; +typedef NS_ENUM(NSUInteger, SigninCoordinatorResult); +@protocol SystemIdentity; @class ManageAccountsDelegateBridge; @class UIViewController; @@ -49,6 +52,9 @@ private: friend class BrowserUserData<AccountConsistencyBrowserAgent>; + void StopSigninCoordinator(SigninCoordinatorResult result, + id<SystemIdentity> identity); + // `base_view_controller` is the view controller which UI will be presented // from. AccountConsistencyBrowserAgent(Browser* browser, @@ -68,6 +74,7 @@ UIViewController* base_view_controller_; id<ApplicationCommands> application_handler_; id<SettingsCommands> settings_handler_; + SigninCoordinator* add_account_coordinator_; // Bridge object to act as the delegate. ManageAccountsDelegateBridge* bridge_;
diff --git a/ios/chrome/browser/signin/model/account_consistency_browser_agent.mm b/ios/chrome/browser/signin/model/account_consistency_browser_agent.mm index 13b858c..f1696e77 100644 --- a/ios/chrome/browser/signin/model/account_consistency_browser_agent.mm +++ b/ios/chrome/browser/signin/model/account_consistency_browser_agent.mm
@@ -6,9 +6,12 @@ #import <UIKit/UIKit.h> +#import "base/functional/callback_helpers.h" #import "components/signin/core/browser/account_reconcilor.h" #import "components/signin/ios/browser/account_consistency_service.h" #import "ios/chrome/browser/authentication/ui_bundled/account_menu/account_menu_constants.h" +#import "ios/chrome/browser/authentication/ui_bundled/continuation.h" +#import "ios/chrome/browser/authentication/ui_bundled/signin/signin_coordinator.h" #import "ios/chrome/browser/shared/model/application_context/application_context.h" #import "ios/chrome/browser/shared/model/profile/features.h" #import "ios/chrome/browser/shared/model/profile/profile_attributes_storage_ios.h" @@ -37,7 +40,16 @@ HandlerForProtocol(browser_->GetCommandDispatcher(), SettingsCommands); } -AccountConsistencyBrowserAgent::~AccountConsistencyBrowserAgent() {} +AccountConsistencyBrowserAgent::~AccountConsistencyBrowserAgent() { + StopSigninCoordinator(SigninCoordinatorResultInterrupted, nil); +} + +void AccountConsistencyBrowserAgent::StopSigninCoordinator( + SigninCoordinatorResult result, + id<SystemIdentity> identity) { + [add_account_coordinator_ stop]; + add_account_coordinator_ = nil; +} void AccountConsistencyBrowserAgent::InstallDependency( web::WebState* web_state) { @@ -105,13 +117,20 @@ if (ShouldShowAccountMenu()) { ShowAccountMenu(url); } else { - ShowSigninCommand* command = [[ShowSigninCommand alloc] - initWithOperation:AuthenticationOperation::kAddAccount - accessPoint:signin_metrics::AccessPoint:: - kAccountConsistencyService]; - command.skipIfUINotAvailable = YES; - [application_handler_ showSignin:command - baseViewController:base_view_controller_]; + signin_metrics::AccessPoint access_point = + signin_metrics::AccessPoint::kAccountConsistencyService; + SigninContextStyle context_style = SigninContextStyle::kDefault; + add_account_coordinator_ = [SigninCoordinator + addAccountCoordinatorWithBaseViewController:base_view_controller_ + browser:browser_ + contextStyle:context_style + accessPoint:access_point + continuationProvider: + DoNothingContinuationProvider()]; + add_account_coordinator_.signinCompletion = CallbackToBlock( + base::BindOnce(&AccountConsistencyBrowserAgent::StopSigninCoordinator, + base::Unretained(this))); + [add_account_coordinator_ start]; } }
diff --git a/ios/chrome/browser/signin/model/account_consistency_browser_agent_unittest.mm b/ios/chrome/browser/signin/model/account_consistency_browser_agent_unittest.mm index b127579..4965549 100644 --- a/ios/chrome/browser/signin/model/account_consistency_browser_agent_unittest.mm +++ b/ios/chrome/browser/signin/model/account_consistency_browser_agent_unittest.mm
@@ -146,28 +146,22 @@ // is a strict mock. } -// Tests OnAddAccount() to send ShowSigninCommand if there is no view presented -// on top of the base view controller. -// See http://crbug.com/1399464. +// Tests OnAddAccount() to show present a view controller if there is no view +// presented on top of the base view controller. See http://crbug.com/1399464. TEST_P(AccountConsistencyBrowserAgentTest, OnAddAccountWithoutPresentedView) { OCMStub([base_view_controller_mock_ presentedViewController]) .andReturn((id)nil); - __block ShowSigninCommand* received_command = nil; - OCMExpect([application_commands_mock_ - showSignin:[OCMArg - checkWithBlock:^BOOL(ShowSigninCommand* command) { - received_command = command; - return YES; - }] - baseViewController:base_view_controller_mock_]); + __block void (^completion)() = nil; + OCMExpect([base_view_controller_mock_ + presentViewController:[OCMArg any] + animated:YES + completion:[OCMArg checkWithBlock:^BOOL(id value) { + completion = value; + return YES; + }]]); agent_->OnAddAccount(GURL()); - EXPECT_NE(received_command, nil); - EXPECT_EQ(received_command.operation, AuthenticationOperation::kAddAccount); - EXPECT_EQ(received_command.identity, nil); - EXPECT_EQ(received_command.accessPoint, - signin_metrics::AccessPoint::kAccountConsistencyService); - EXPECT_EQ(received_command.promoAction, - signin_metrics::PromoAction::PROMO_ACTION_NO_SIGNIN_PROMO); + CHECK(completion); + completion(); } TEST_F(AccountConsistencyBrowserAgentWithSeparateProfilesTest,
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/BUILD.gn b/ios/chrome/browser/tab_switcher/ui_bundled/BUILD.gn index 0d8044e..baf157f 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/BUILD.gn +++ b/ios/chrome/browser/tab_switcher/ui_bundled/BUILD.gn
@@ -24,6 +24,7 @@ "tab_snapshot_and_favicon_configurator.mm", "tab_switcher_item.h", "tab_switcher_item.mm", + "tab_switcher_item_snapshot_and_favicon_data_source.h", "web_state_tab_switcher_item.h", "web_state_tab_switcher_item.mm", ]
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.h index 935032c..d63ccb7 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.h
@@ -16,6 +16,7 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_grid_page_mutator.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_grid_paging.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/toolbars/tab_grid_toolbars_grid_delegate.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h" @class ActivityLabelData; @class BaseGridMediator; @@ -50,13 +51,15 @@ @end // Mediates between model layer and tab grid UI layer. -@interface BaseGridMediator : NSObject <BaseGridMediatorItemProvider, - GridCommands, - GridViewControllerMutator, - SuggestedActionsDelegate, - TabCollectionDragDropHandler, - TabGridPageMutator, - TabGridToolbarsGridDelegate> +@interface BaseGridMediator + : NSObject <BaseGridMediatorItemProvider, + GridCommands, + GridViewControllerMutator, + SuggestedActionsDelegate, + TabCollectionDragDropHandler, + TabGridPageMutator, + TabGridToolbarsGridDelegate, + TabSwitcherItemSnapShotAndFaviconDataSource> // The source browser. @property(nonatomic, assign) Browser* browser;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.mm index f9d85b2..2a4d1c3 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator.mm
@@ -9,6 +9,7 @@ #import <memory> +#import "base/apple/foundation_util.h" #import "base/debug/dump_without_crashing.h" #import "base/functional/bind.h" #import "base/metrics/histogram_functions.h" @@ -2033,4 +2034,17 @@ tabGroupItem, webStateList, completion); } +#pragma mark - TabSwitcherItemSnapShotAndFaviconDataSource + +// Fetches the `item` info and executes the given `completion` block. +- (void)fetchTabSnapshotAndFavicon:(TabSwitcherItem*)item + completion: + (TabSnapshotAndFaviconFetchingCompletionBlock) + completion { + WebStateTabSwitcherItem* tabSwitcherItem = + base::apple::ObjCCastStrict<WebStateTabSwitcherItem>(item); + _tabImagesConfigurator->FetchSnapshotAndFaviconForTabSwitcherItem( + tabSwitcherItem, completion); +} + @end
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator_unittest.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator_unittest.mm index e6a30185..53bc128a 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator_unittest.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_mediator_unittest.mm
@@ -14,6 +14,7 @@ #import "base/strings/sys_string_conversions.h" #import "base/test/ios/wait_util.h" #import "base/test/metrics/histogram_tester.h" +#import "base/test/test_timeouts.h" #import "base/time/time.h" #import "components/commerce/core/commerce_feature_list.h" #import "components/saved_tab_groups/public/saved_tab_group.h" @@ -36,6 +37,7 @@ #import "ios/chrome/browser/shared/model/web_state_list/web_state_opener.h" #import "ios/chrome/browser/shared/public/features/features.h" #import "ios/chrome/browser/snapshots/model/snapshot_browser_agent.h" +#import "ios/chrome/browser/snapshots/model/snapshot_tab_helper.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_metrics.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/grid_item_identifier.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/grid_mediator_test.h" @@ -1287,6 +1289,27 @@ ExpectThatDragItemOriginMetricLogged(DragItemOrigin::kOther); } +// Tests that `fetchTabSnapshotAndFavicon:completion:` is calling `completion` +// twice. +TEST_P(BaseGridMediatorTest, FetchTabSnapshotAndFavicon) { + auto fake_web_state = std::make_unique<web::FakeWebState>(); + web::FakeWebState* web_state = fake_web_state.get(); + SnapshotTabHelper::CreateForWebState(web_state); + WebStateTabSwitcherItem* item = + [[WebStateTabSwitcherItem alloc] initWithWebState:web_state]; + __block int completion_block_called = 0; + auto completion_block = ^(TabSwitcherItem* inner_item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon) { + completion_block_called++; + ASSERT_LE(completion_block_called, 2); + }; + [mediator_ fetchTabSnapshotAndFavicon:item completion:completion_block]; + EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( + TestTimeouts::action_timeout(), ^bool() { + return completion_block_called == 2; + })); +} + INSTANTIATE_TEST_SUITE_P( /* No InstantiationName */, BaseGridMediatorTest,
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.h index a23960c7..bda658f 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.h
@@ -25,9 +25,10 @@ @protocol TabContextMenuProvider; @protocol TabCollectionDragDropHandler; @protocol TabGridCommands; -@protocol TabGroupConfirmationCommands; @class TabGridTransitionItem; class TabGroup; +@protocol TabGroupConfirmationCommands; +@protocol TabSwitcherItemSnapShotAndFaviconDataSource; namespace web { class WebStateID; @@ -162,6 +163,9 @@ tabGroupConfirmationHandler; // The layout guide center to use to refer to the selected cell. @property(nonatomic, strong) LayoutGuideCenter* layoutGuideCenter; +// Handles snapshots and favicons fetches. +@property(nonatomic, weak) id<TabSwitcherItemSnapShotAndFaviconDataSource> + snapshotAndfaviconDataSource; // Returns the layout of the grid for use in an animated transition. - (LegacyGridTransitionLayout*)transitionLayout;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.mm index 61e07d5..ca166e7 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/base_grid_view_controller.mm
@@ -44,7 +44,9 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/transitions/legacy_grid_transition_layout.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/transitions/tab_grid_transition_item.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_group_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_utils.h" #import "ios/chrome/common/ui/colors/semantic_color_names.h" #import "ios/chrome/common/ui/util/constraints_ui_util.h" @@ -1723,19 +1725,18 @@ cell.layoutGuideCenter = self.layoutGuideCenter; [cell registerAsSelectedCellGuide]; } - [item fetchFavicon:^(TabSwitcherItem* innerItem, UIImage* icon) { - // Only update the icon if the cell is not already reused for another item. - if ([cell.itemIdentifier.tabSwitcherItem isEqual:innerItem]) { - cell.icon = icon; - } - }]; - [item fetchSnapshot:^(TabSwitcherItem* innerItem, UIImage* snapshot) { - // Only update the icon if the cell is not already reused for another item. + auto completion = ^(TabSwitcherItem* innerItem, + TabSnapshotAndFavicon* tabSnapshotAndFavicon) { + // Only apply changes if the cell is not already reused for another + // item. if ([cell.itemIdentifier.tabSwitcherItem isEqual:innerItem]) { - cell.snapshot = snapshot; + cell.icon = tabSnapshotAndFavicon.favicon; + cell.snapshot = tabSnapshotAndFavicon.snapshot; } - }]; + }; + [self.snapshotAndfaviconDataSource fetchTabSnapshotAndFavicon:item + completion:completion]; web::WebStateID itemID = item.identifier; [self.priceCardDataSource
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/incognito/incognito_grid_coordinator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/incognito/incognito_grid_coordinator.mm index 387c80b3..514d77a 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/incognito/incognito_grid_coordinator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/incognito/incognito_grid_coordinator.mm
@@ -228,6 +228,7 @@ gridViewController.mutator = _mediator; gridViewController.gridProvider = _mediator; gridViewController.gridHandler = _mediator; + gridViewController.snapshotAndfaviconDataSource = _mediator; gridViewController.incognitoGridHandler = self; // TODO(crbug.com/40273478): Move the following lines to the grid itself when // specific grid file will be created.
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/regular/regular_grid_coordinator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/regular/regular_grid_coordinator.mm index 4bffab7..0b68d28d 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/regular/regular_grid_coordinator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid/regular/regular_grid_coordinator.mm
@@ -157,6 +157,7 @@ gridViewController.mutator = _mediator; gridViewController.gridProvider = _mediator; gridViewController.menuProvider = _contextMenuProvider; + gridViewController.snapshotAndfaviconDataSource = _mediator; // If regular is enabled then the grid exists and it is not disabled. // TODO(crbug.com/40273478): Get disabled status from the mediator. @@ -187,6 +188,7 @@ _pinnedTabsMediator.browser = self.browser; pinnedTabsViewController.menuProvider = _contextMenuProvider; pinnedTabsViewController.dragDropHandler = _pinnedTabsMediator; + pinnedTabsViewController.snapshotAndfaviconDataSource = _pinnedTabsMediator; } [super start];
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/BUILD.gn b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/BUILD.gn index b83bc32..7282780f 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/BUILD.gn +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/BUILD.gn
@@ -23,6 +23,7 @@ "//ios/chrome/browser/shared/ui/symbols", "//ios/chrome/browser/snapshots/model", "//ios/chrome/browser/tab_switcher/ui_bundled", + "//ios/chrome/browser/tab_switcher/ui_bundled:items", "//ios/chrome/browser/tab_switcher/ui_bundled:utils", "//ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/grid:grid_ui", "//ios/chrome/browser/url_loading/model",
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.h index 5bca305..fed082ba 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.h
@@ -8,12 +8,15 @@ #import <Foundation/Foundation.h> #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_handler.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h" class Browser; @protocol PinnedTabCollectionConsumer; // Mediates between model layer and pinned tabs collection UI layer. -@interface PinnedTabsMediator : NSObject <TabCollectionDragDropHandler> +@interface PinnedTabsMediator + : NSObject <TabCollectionDragDropHandler, + TabSwitcherItemSnapShotAndFaviconDataSource> // The source browser. @property(nonatomic, assign) Browser* browser;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.mm index 02138de..e5964c9 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_mediator.mm
@@ -7,6 +7,7 @@ #import <UIKit/UIKit.h> #import <UniformTypeIdentifiers/UniformTypeIdentifiers.h> +#import "base/apple/foundation_util.h" #import "base/metrics/histogram_functions.h" #import "base/metrics/user_metrics.h" #import "base/metrics/user_metrics_action.h" @@ -24,6 +25,7 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/pinned_tab_collection_consumer.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_metrics.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_utils.h" #import "ios/chrome/browser/url_loading/model/url_loading_browser_agent.h" #import "ios/chrome/browser/url_loading/model/url_loading_params.h" @@ -85,6 +87,8 @@ // URL loader to open tabs when needed. raw_ptr<UrlLoadingBrowserAgent> _URLLoader; + // Helper class to configure tab item images. + std::unique_ptr<TabSnapshotAndFaviconConfigurator> _tabImagesConfigurator; } - (instancetype)initWithConsumer:(id<PinnedTabCollectionConsumer>)consumer { @@ -102,6 +106,8 @@ std::make_unique<base::ScopedMultiSourceObservation< web::WebState, web::WebStateObserver>>( _webStateObserverBridge.get()); + _tabImagesConfigurator = + std::make_unique<TabSnapshotAndFaviconConfigurator>(nullptr); } return self; } @@ -485,4 +491,17 @@ } } +#pragma mark - TabSwitcherItemSnapShotAndFaviconDataSource + +// Fetches the `item` info and executes the given `completion` block. +- (void)fetchTabSnapshotAndFavicon:(TabSwitcherItem*)item + completion: + (TabSnapshotAndFaviconFetchingCompletionBlock) + completion { + WebStateTabSwitcherItem* tabSwitcherItem = + base::apple::ObjCCastStrict<WebStateTabSwitcherItem>(item); + _tabImagesConfigurator->FetchSnapshotAndFaviconForTabSwitcherItem( + tabSwitcherItem, completion); +} + @end
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.h index 4778df4..6d2b961 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.h
@@ -14,6 +14,7 @@ @protocol TabCollectionDragDropHandler; @protocol TabContextMenuProvider; @class TabGridTransitionItem; +@protocol TabSwitcherItemSnapShotAndFaviconDataSource; namespace web { class WebStateID; @@ -77,6 +78,10 @@ // Handles drag and drop interactions that involved the model layer. @property(nonatomic, weak) id<TabCollectionDragDropHandler> dragDropHandler; +// Handles snapshots and favicons fetches. +@property(nonatomic, weak) id<TabSwitcherItemSnapShotAndFaviconDataSource> + snapshotAndfaviconDataSource; + // Tracks if a drop animation is in progress. @property(nonatomic, assign) BOOL dropAnimationInProgress;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.mm index 14a0621..12612d7b 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_view_controller.mm
@@ -20,7 +20,9 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_context_menu/tab_context_menu_provider.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/transitions/legacy_grid_transition_layout.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/transitions/tab_grid_transition_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_utils.h" #import "ios/chrome/common/ui/colors/semantic_color_names.h" #import "ios/chrome/common/ui/util/constraints_ui_util.h" @@ -841,20 +843,18 @@ if (item) { cell.pinnedItemIdentifier = item.identifier; cell.title = item.title; - [item fetchFavicon:^(TabSwitcherItem* innerItem, UIImage* icon) { - // Only update the icon if the cell is not already reused for another + + auto completion = ^(TabSwitcherItem* innerItem, + TabSnapshotAndFavicon* tabSnapshotAndFavicon) { + // Only apply changes if the cell is not already reused for another // item. if (cell.pinnedItemIdentifier == innerItem.identifier) { - cell.icon = icon; + cell.icon = tabSnapshotAndFavicon.favicon; + cell.snapshot = tabSnapshotAndFavicon.snapshot; } - }]; - [item fetchSnapshot:^(TabSwitcherItem* innerItem, UIImage* snapshot) { - // Only update the icon if the cell is not already reused for another - // item. - if (cell.pinnedItemIdentifier == innerItem.identifier) { - cell.snapshot = snapshot; - } - }]; + }; + [self.snapshotAndfaviconDataSource fetchTabSnapshotAndFavicon:item + completion:completion]; } cell.accessibilityIdentifier = [NSString
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/BUILD.gn b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/BUILD.gn index d525c3d..8644592 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/BUILD.gn +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/BUILD.gn
@@ -40,6 +40,7 @@ "//ios/chrome/browser/shared/model/web_state_list", "//ios/chrome/browser/shared/model/web_state_list/test:test_support", "//ios/chrome/browser/shared/public/features", + "//ios/chrome/browser/snapshots/model", "//ios/chrome/browser/tab_insertion/model", "//ios/chrome/browser/tab_switcher/ui_bundled", "//ios/chrome/browser/tab_switcher/ui_bundled:items",
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/pinned_tabs_mediator_unittest.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/pinned_tabs_mediator_unittest.mm index 4f62e1d1..85ecb07 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/pinned_tabs_mediator_unittest.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/tests/pinned_tabs_mediator_unittest.mm
@@ -10,6 +10,7 @@ #import "base/test/ios/wait_util.h" #import "base/test/metrics/histogram_tester.h" #import "base/test/scoped_feature_list.h" +#import "base/test/test_timeouts.h" #import "ios/chrome/browser/drag_and_drop/model/drag_item_util.h" #import "ios/chrome/browser/shared/model/browser/browser_list.h" #import "ios/chrome/browser/shared/model/browser/browser_list_factory.h" @@ -19,11 +20,13 @@ #import "ios/chrome/browser/shared/model/web_state_list/web_state_list.h" #import "ios/chrome/browser/shared/model/web_state_list/web_state_opener.h" #import "ios/chrome/browser/shared/public/features/features.h" +#import "ios/chrome/browser/snapshots/model/snapshot_tab_helper.h" #import "ios/chrome/browser/tab_insertion/model/tab_insertion_browser_agent.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_metrics.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/test/fake_drag_session.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/test/fake_drop_session.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/test/fake_pinned_tab_collection_consumer.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h" #import "ios/chrome/browser/url_loading/model/fake_url_loading_delegate.h" #import "ios/chrome/browser/url_loading/model/scene_url_loading_service.h" #import "ios/chrome/browser/url_loading/model/test_scene_url_loading_service.h" @@ -399,3 +402,29 @@ web_state->GetNavigationManager()->GetPendingItem()->GetURL()); ExpectThatDragItemOriginMetricLogged(DragItemOrigin::kOther); } + +// Tests that `fetchTabSnapshotAndFavicon:completion:` is calling `completion` +// twice. +TEST_F(PinnedTabsMediatorTest, FetchTabSnapshotAndFavicon) { + // The Pinned Tabs feature is not available on iPad. + if (!IsPinnedTabsEnabled()) { + return; + } + + auto fake_web_state = std::make_unique<web::FakeWebState>(); + web::FakeWebState* web_state = fake_web_state.get(); + SnapshotTabHelper::CreateForWebState(web_state); + WebStateTabSwitcherItem* item = + [[WebStateTabSwitcherItem alloc] initWithWebState:web_state]; + __block int completion_block_called = 0; + auto completion_block = ^(TabSwitcherItem* inner_item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon) { + completion_block_called++; + ASSERT_LE(completion_block_called, 2); + }; + [mediator_ fetchTabSnapshotAndFavicon:item completion:completion_block]; + EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( + TestTimeouts::action_timeout(), ^bool() { + return completion_block_called == 2; + })); +}
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/shared_tab_groups_egtest.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/shared_tab_groups_egtest.mm index 21cef0a..5e5a1626e 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/shared_tab_groups_egtest.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/shared_tab_groups_egtest.mm
@@ -884,7 +884,14 @@ } // Ensures new tab is added when closing the last tab of a shared group. -- (void)testCloseLastTabInSharedGroup { +// TODO(crbug.com/420464084): Test is failing on iphone-device. +#if TARGET_OS_SIMULATOR +#define MAYBE_testCloseLastTabInSharedGroup testCloseLastTabInSharedGroup +#else +#define MAYBE_testCloseLastTabInSharedGroup \ + DISABLED_testCloseLastTabInSharedGroup +#endif +- (void)MAYBE_testCloseLastTabInSharedGroup { if (@available(iOS 17, *)) { } else if ([ChromeEarlGrey isIPadIdiom]) { EARL_GREY_TEST_SKIPPED(@"Only available on iOS 17+ on iPad.");
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/tab_group_coordinator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/tab_group_coordinator.mm index b3bde9cd..2a60d1bd8 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/tab_group_coordinator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/tab_groups/tab_group_coordinator.mm
@@ -153,6 +153,7 @@ _viewController.gridViewController.gridProvider = _mediator; _viewController.gridViewController.menuProvider = _tabContextMenuHelper; _viewController.gridViewController.dragDropHandler = _mediator; + _viewController.gridViewController.snapshotAndfaviconDataSource = _mediator; [self displayViewControllerAnimated:self.animatedPresentation]; }
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.h index 4fe1fc6..a1307d0 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.h
@@ -13,6 +13,7 @@ @class TabGroupItem; @class TabSnapshotAndFavicon; class WebStateList; +@class WebStateTabSwitcherItem; namespace web { class WebState; @@ -48,8 +49,21 @@ web::WebState* web_state, void (^completion)(TabSnapshotAndFavicon* tab_snapshot_and_favicon)); - // TODO(crbug.com/400966281): Add function to fetch snapshot and favicon for - // TabSwitcherItem. + // Fetches the snapshot and favicon for `tab_item`. + // The `completion` block is invoked twice: once when the snapshot has been + // fetched, and again when the favicon has been fetched. + void FetchSnapshotAndFaviconForTabSwitcherItem( + WebStateTabSwitcherItem* tab_item, + void (^completion)(WebStateTabSwitcherItem* item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon)); + + // Fetches the favicon for `tab_item`. + // The `completion` block is invoked when the favicon has been fetched. + // The snapshot is not fetched and always nil. + void FetchFaviconForTabSwitcherItem( + WebStateTabSwitcherItem* tab_item, + void (^completion)(WebStateTabSwitcherItem* item, + TabSnapshotAndFavicon* tab_snapshot)); private: // Initiates the asynchronous fetching of a snapshot and favicon for a @@ -66,9 +80,9 @@ TabGroupItem* item, NSArray<TabSnapshotAndFavicon*>* tab_snapshots_and_favicons)); - // Called when the snapshot and/or favicon for a web state has been fetched. + // Called when the snapshot and/or favicon for a web state has been fetched. // Checks if all information has been collected and calls the `completion` - // block. + // block once, with all the information. void OnSnapshotAndFaviconFromWebStateFetched( TabGroupItem* group_item, TabSnapshotAndFavicon* tab_snapshot_and_favicon, @@ -81,6 +95,17 @@ TabGroupItem* item, NSArray<TabSnapshotAndFavicon*>* tab_snapshots_and_favicons)); + // Fetches the snapshot and favicon for `tab_item`. + // If `fetch_snapshot` is false, only the favicon will be fetched. + // The `completion` block is invoked twice: once when the snapshot + // has been fetched (if requested), and again when the favicon has been + // fetched. + void FetchSnapshotAndFaviconForTabSwitcherItem( + WebStateTabSwitcherItem* tab_item, + bool fetch_snapshot, + void (^completion)(WebStateTabSwitcherItem* item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon)); + raw_ptr<FaviconLoader> favicon_loader_ = nullptr; // Stores the UUIDs of in-progress TabGroupItem fetch requests, keyed by the
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.mm index 1510d0f7..fcbbd1a 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.mm
@@ -16,6 +16,7 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/item_utils.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_group_item.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h" #import "ios/chrome/common/ui/colors/semantic_color_names.h" #import "ios/chrome/common/ui/favicon/favicon_attributes.h" #import "ios/chrome/common/ui/util/image_util.h" @@ -96,6 +97,23 @@ inner_completion); } +void TabSnapshotAndFaviconConfigurator:: + FetchSnapshotAndFaviconForTabSwitcherItem( + WebStateTabSwitcherItem* tab_item, + void (^completion)(WebStateTabSwitcherItem* item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon)) { + FetchSnapshotAndFaviconForTabSwitcherItem(tab_item, /*fetch_snapshot=*/true, + completion); +} + +void TabSnapshotAndFaviconConfigurator::FetchFaviconForTabSwitcherItem( + WebStateTabSwitcherItem* tab_item, + void (^completion)(WebStateTabSwitcherItem* item, + TabSnapshotAndFavicon* tab_snapshot)) { + FetchSnapshotAndFaviconForTabSwitcherItem(tab_item, /*fetch_snapshot=*/false, + completion); +} + #pragma mark - Private void TabSnapshotAndFaviconConfigurator::FetchSnapshotAndFaviconFromWebState( @@ -233,3 +251,82 @@ } completion(group_item, infos); } + +void TabSnapshotAndFaviconConfigurator:: + FetchSnapshotAndFaviconForTabSwitcherItem( + WebStateTabSwitcherItem* tab_item, + bool fetch_snapshot, + void (^completion)(WebStateTabSwitcherItem* item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon)) { + if (!tab_item.webState) { + completion(tab_item, nil); + return; + } + + TabSnapshotAndFavicon* tab_snapshot_and_favicon = + [[TabSnapshotAndFavicon alloc] init]; + + // Fetch the snapshot. + if (fetch_snapshot) { + SnapshotTabHelper::FromWebState(tab_item.webState) + ->RetrieveColorSnapshot(^(UIImage* snapshot) { + // If there is no available snapshot, configure the snapshot to be an + // empty image in order to pass + // `OnSnapshotAndFaviconForTabSwitcherItemFetched` checks. + tab_snapshot_and_favicon.snapshot = snapshot; + completion(tab_item, tab_snapshot_and_favicon); + }); + } + + UIImageConfiguration* configuration = [UIImageSymbolConfiguration + configurationWithPointSize:kFaviconSize + weight:UIImageSymbolWeightBold + scale:UIImageSymbolScaleMedium]; + const GURL& url = tab_item.webState->GetVisibleURL(); + + // Set the NTP favicon. + if (IsUrlNtp(url)) { + // Each WebStateTabSwitcherItem subclass provides its own NTPFavicon. + tab_snapshot_and_favicon.favicon = tab_item.NTPFavicon; + completion(tab_item, tab_snapshot_and_favicon); + return; + } + + // Use the favicon driver. + favicon::FaviconDriver* favicon_driver = + favicon::WebFaviconDriver::FromWebState(tab_item.webState); + if (favicon_driver) { + gfx::Image favicon = favicon_driver->GetFavicon(); + if (!favicon.IsEmpty()) { + tab_snapshot_and_favicon.favicon = favicon.ToUIImage(); + completion(tab_item, tab_snapshot_and_favicon); + return; + } + } + + // Set the default favicon. + UIImage* default_favicon = + DefaultSymbolWithConfiguration(kGlobeAmericasSymbol, configuration); + if (!favicon_loader_) { + tab_snapshot_and_favicon.favicon = default_favicon; + completion(tab_item, tab_snapshot_and_favicon); + return; + } + + // Fetch the favicon. + favicon_loader_->FaviconForPageUrl( + url, kFaviconSize, kFaviconMinimumSize, + /*fallback_to_google_server=*/true, ^(FaviconAttributes* attributes) { + // Synchronously returned default favicon. + if (attributes.usesDefaultImage) { + return; + } + // Asynchronously returned favicon. + if (attributes.faviconImage) { + tab_snapshot_and_favicon.favicon = attributes.faviconImage; + } else { + tab_snapshot_and_favicon.favicon = default_favicon; + } + completion(tab_item, tab_snapshot_and_favicon); + }); +}
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator_unittest.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator_unittest.mm index 746e17e..600e04cc 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator_unittest.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator_unittest.mm
@@ -15,6 +15,7 @@ #import "ios/chrome/browser/snapshots/model/snapshot_tab_helper.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_group_item.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h" #import "ios/chrome/common/ui/favicon/favicon_attributes.h" #import "ios/web/public/test/fakes/fake_web_state.h" #import "ios/web/public/test/web_task_environment.h" @@ -133,3 +134,38 @@ return completion_block_called; })); } + +// Tests the default use case of `FetchSnapshotAndFaviconForTabSwitcherItem:`. +TEST_F(TabSnapshotAndFaviconConfiguratorTest, + FetchSnapshotAndFaviconForTabSwitcherItem) { + WebStateTabSwitcherItem* item = [[WebStateTabSwitcherItem alloc] + initWithWebState:web_state_list_->GetWebStateAt(0)]; + __block int completion_block_called = 0; + auto completion_block = ^(WebStateTabSwitcherItem* inner_item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon) { + completion_block_called++; + }; + _configurator->FetchSnapshotAndFaviconForTabSwitcherItem(item, + completion_block); + ASSERT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( + TestTimeouts::action_timeout(), ^bool() { + return completion_block_called == 2; + })); +} + +// Tests the default use case of `FetchFaviconForTabSwitcherItem:`. +TEST_F(TabSnapshotAndFaviconConfiguratorTest, FetchFaviconForTabSwitcherItem) { + WebStateTabSwitcherItem* item = [[WebStateTabSwitcherItem alloc] + initWithWebState:web_state_list_->GetWebStateAt(0)]; + __block int completion_block_called = 0; + auto completion_block = + ^(TabSwitcherItem* inner_item, TabSnapshotAndFavicon* tab_snapshot) { + completion_block_called++; + ASSERT_LE(completion_block_called, 2); + }; + _configurator->FetchFaviconForTabSwitcherItem(item, completion_block); + EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( + TestTimeouts::action_timeout(), ^bool() { + return completion_block_called == 1; + })); +}
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/BUILD.gn b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/BUILD.gn index f00a786..899c6ede 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/BUILD.gn +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/BUILD.gn
@@ -20,8 +20,10 @@ "//ios/chrome/app/strings", "//ios/chrome/browser/collaboration/model", "//ios/chrome/browser/collaboration/model:collaboration_delegate", + "//ios/chrome/browser/collaboration/model:features", "//ios/chrome/browser/collaboration/model/messaging", "//ios/chrome/browser/drag_and_drop/model", + "//ios/chrome/browser/favicon/model", "//ios/chrome/browser/main/model", "//ios/chrome/browser/ntp/model:util", "//ios/chrome/browser/policy/model:policy_util", @@ -78,6 +80,7 @@ "//ios/chrome/browser/shared/model/web_state_list", "//ios/chrome/browser/shared/model/web_state_list:utils", "//ios/chrome/browser/tab_switcher/ui_bundled:items", + "//ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui", "//ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui:swift", ] } @@ -136,6 +139,7 @@ "//ios/chrome/browser/tab_switcher/ui_bundled", "//ios/chrome/browser/tab_switcher/ui_bundled:items", "//ios/chrome/browser/tab_switcher/ui_bundled:utils", + "//ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui", "//ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui:swift", "//ios/chrome/browser/url_loading/model", "//ios/chrome/browser/url_loading/model:test_support",
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_coordinator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_coordinator.mm index 55b73f0..f9a900a 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_coordinator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_coordinator.mm
@@ -15,8 +15,10 @@ #import "components/strings/grit/components_strings.h" #import "components/tab_groups/tab_group_visual_data.h" #import "ios/chrome/browser/collaboration/model/collaboration_service_factory.h" +#import "ios/chrome/browser/collaboration/model/features.h" #import "ios/chrome/browser/collaboration/model/ios_collaboration_controller_delegate.h" #import "ios/chrome/browser/collaboration/model/messaging/messaging_backend_service_factory.h" +#import "ios/chrome/browser/favicon/model/ios_chrome_favicon_loader_factory.h" #import "ios/chrome/browser/saved_tab_groups/model/ios_tab_group_sync_util.h" #import "ios/chrome/browser/saved_tab_groups/model/tab_group_sync_service_factory.h" #import "ios/chrome/browser/shared/coordinator/alert/alert_coordinator.h" @@ -123,12 +125,21 @@ collaboration::CollaborationService* collaborationService = collaboration::CollaborationServiceFactory::GetForProfile(profile); + FaviconLoader* faviconLoader = nil; + // Fetch favicons if in regular mode and sync or shared tab groups is enabled. + if (!profile->IsOffTheRecord() && + (IsTabGroupSyncEnabled() || + IsSharedTabGroupsJoinEnabled(collaborationService))) { + faviconLoader = IOSChromeFaviconLoaderFactory::GetForProfile(profile); + } + self.mediator = [[TabStripMediator alloc] initWithConsumer:self.tabStripViewController tabGroupSyncService:tabGroupSyncService browserList:browserList messagingService:messagingService - collaborationService:collaborationService]; + collaborationService:collaborationService + faviconLoader:faviconLoader]; self.mediator.webStateList = self.browser->GetWebStateList(); self.mediator.profile = profile; self.mediator.browser = self.browser; @@ -147,6 +158,7 @@ self.tabStripViewController.mutator = self.mediator; self.tabStripViewController.dragDropHandler = self.mediator; + self.tabStripViewController.snapshotAndfaviconDataSource = self.mediator; self.tabStripViewController.contextMenuProvider = self.contextMenuHelper; }
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.h index f61bba4c3..8e50f18 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.h
@@ -9,9 +9,11 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_handler.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_mutator.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h" class Browser; class BrowserList; +class FaviconLoader; class ProfileIOS; enum class TabGroupActionType; @protocol TabStripCommands; @@ -42,7 +44,9 @@ // This mediator used to manage model interaction for its consumer. @interface TabStripMediator - : NSObject <TabCollectionDragDropHandler, TabStripMutator> + : NSObject <TabCollectionDragDropHandler, + TabSwitcherItemSnapShotAndFaviconDataSource, + TabStripMutator> // The WebStateList that this mediator listens for any changes on the total // number of Webstates. @@ -70,6 +74,7 @@ (collaboration::messaging::MessagingBackendService*)messagingService collaborationService: (collaboration::CollaborationService*)collaborationService + faviconLoader:(FaviconLoader*)faviconLoader NS_DESIGNATED_INITIALIZER; - (instancetype)init NS_UNAVAILABLE;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.mm index 24b98583..2eb7eb1 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator.mm
@@ -22,6 +22,7 @@ #import "ios/chrome/browser/collaboration/model/collaboration_service_factory.h" #import "ios/chrome/browser/collaboration/model/messaging/messaging_backend_service_bridge.h" #import "ios/chrome/browser/drag_and_drop/model/drag_item_util.h" +#import "ios/chrome/browser/favicon/model/favicon_loader.h" #import "ios/chrome/browser/ntp/model/new_tab_page_util.h" #import "ios/chrome/browser/policy/model/policy_util.h" #import "ios/chrome/browser/saved_tab_groups/model/ios_tab_group_sync_util.h" @@ -48,11 +49,12 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_metrics.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_group_action_type.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_group_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon_configurator.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_utils.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/swift.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_features_utils.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_utils.h" -#import "ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h" #import "ios/chrome/browser/url_loading/model/url_loading_browser_agent.h" #import "ios/chrome/browser/url_loading/model/url_loading_params.h" #import "ios/chrome/browser/web_state_list/model/web_state_list_favicon_driver_observer.h" @@ -286,6 +288,8 @@ std::unique_ptr<MessagingBackendServiceBridge> _messagingBackendServiceBridge; // The collaboration service for shared tab group. raw_ptr<collaboration::CollaborationService> _collaborationService; + // Helper class to configure tab item images. + std::unique_ptr<TabSnapshotAndFaviconConfigurator> _tabImagesConfigurator; // A set of a tab ID that has changed and a user has not seen it yet. std::set<tab_groups::LocalTabID> _dirtyTabs; // A set of a shared group ID that has changed and a user has not seen it yet. @@ -303,7 +307,8 @@ messagingService: (collaboration::messaging::MessagingBackendService*)messagingService collaborationService: - (collaboration::CollaborationService*)collaborationService { + (collaboration::CollaborationService*)collaborationService + faviconLoader:(FaviconLoader*)faviconLoader { if ((self = [super init])) { CHECK(browserList); _browserList = browserList; @@ -311,6 +316,8 @@ _tabGroupSyncService = tabGroupSyncService; _consumer = consumer; _messagingService = messagingService; + _tabImagesConfigurator = + std::make_unique<TabSnapshotAndFaviconConfigurator>(faviconLoader); if (_messagingService) { _messagingBackendServiceBridge = std::make_unique<MessagingBackendServiceBridge>(self); @@ -538,7 +545,7 @@ change.As<WebStateListChangeDetach>(); web::WebState* detachedWebState = detachChange.detached_web_state(); TabStripItemIdentifier* item = [TabStripItemIdentifier - tabIdentifier:[[WebStateTabSwitcherItem alloc] + tabIdentifier:[[TabStripTabItem alloc] initWithWebState:detachedWebState]]; [self.consumer removeItems:@[ item ]]; // Reconfigure the group items if needed. @@ -627,11 +634,11 @@ const WebStateListChangeReplace& replaceChange = change.As<WebStateListChangeReplace>(); const int index = replaceChange.index(); - TabSwitcherItem* oldItem = [[WebStateTabSwitcherItem alloc] + TabSwitcherItem* oldItem = [[TabStripTabItem alloc] initWithWebState:replaceChange.replaced_web_state()]; web::WebState* newWebState = replaceChange.inserted_web_state(); TabSwitcherItem* newItem = - [[WebStateTabSwitcherItem alloc] initWithWebState:newWebState]; + [[TabStripTabItem alloc] initWithWebState:newWebState]; TabStripItemIdentifier* newItemIdentifier = [TabStripItemIdentifier tabIdentifier:newItem]; TabStripItemData* newItemData = @@ -757,8 +764,8 @@ [self.consumer selectItem:nil]; return; } - TabSwitcherItem* item = [[WebStateTabSwitcherItem alloc] - initWithWebState:status.new_active_web_state]; + TabSwitcherItem* item = + [[TabStripTabItem alloc] initWithWebState:status.new_active_web_state]; [self.consumer selectItem:item]; // If the active WebState is in a group, ensure that group is not collapsed. const TabGroup* groupOfActiveWebState = @@ -1380,6 +1387,21 @@ } } +#pragma mark - TabSwitcherItemSnapShotAndFaviconDataSource + +// Fetches the `item` info and executes the given `completion` block. +- (void)fetchTabSnapshotAndFavicon:(TabSwitcherItem*)item + completion: + (TabSnapshotAndFaviconFetchingCompletionBlock) + completion { + TabStripTabItem* tabSwitcherItem = + base::apple::ObjCCastStrict<TabStripTabItem>(item); + // This method uses `FetchFaviconForTabSwitcherItem` that only fetches the + // favicon, as the snapshot is not used in the tab strip. + _tabImagesConfigurator->FetchFaviconForTabSwitcherItem(tabSwitcherItem, + completion); +} + #pragma mark - Private // Adds an observation to every WebState of the current WebSateList. @@ -1398,7 +1420,7 @@ - (void)populateConsumerItems { TabSwitcherItem* selectedItem = nil; if (_webStateList->GetActiveWebState()) { - selectedItem = [[WebStateTabSwitcherItem alloc] + selectedItem = [[TabStripTabItem alloc] initWithWebState:_webStateList->GetActiveWebState()]; } NSArray<TabStripItemIdentifier*>* itemIdentifiers =
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_unittest.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_unittest.mm index 973f45c..0f769b6 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_unittest.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_unittest.mm
@@ -9,6 +9,7 @@ #import "base/test/ios/wait_util.h" #import "base/test/metrics/histogram_tester.h" #import "base/test/scoped_feature_list.h" +#import "base/test/test_timeouts.h" #import "components/collaboration/test_support/mock_messaging_backend_service.h" #import "components/data_sharing/public/features.h" #import "components/favicon/core/favicon_service.h" @@ -44,8 +45,8 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/fake_tab_strip_consumer.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/fake_tab_strip_handler.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/swift.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h" -#import "ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h" #import "ios/chrome/browser/url_loading/model/fake_url_loading_delegate.h" #import "ios/chrome/browser/url_loading/model/scene_url_loading_service.h" #import "ios/chrome/browser/url_loading/model/test_scene_url_loading_service.h" @@ -161,7 +162,8 @@ tabGroupSyncService:tab_group_sync_service_.get() browserList:browser_list messagingService:&messaging_backend_ - collaborationService:nil]; + collaborationService:nil + faviconLoader:nil]; mediator_.profile = profile_.get(); mediator_.webStateList = web_state_list_; @@ -714,7 +716,7 @@ ASSERT_EQ(1, web_state_list_->active_index()); ASSERT_EQ(2, web_state_list_->count()); - TabSwitcherItem* item = [[WebStateTabSwitcherItem alloc] + TabSwitcherItem* item = [[TabStripTabItem alloc] initWithWebState:web_state_list_->GetWebStateAt(0)]; [mediator_ activateItem:item]; @@ -735,7 +737,7 @@ ASSERT_EQ(1, web_state_list_->active_index()); ASSERT_EQ(2, web_state_list_->count()); - TabSwitcherItem* item = [[WebStateTabSwitcherItem alloc] + TabSwitcherItem* item = [[TabStripTabItem alloc] initWithWebState:web_state_list_->GetWebStateAt(1)]; [mediator_ closeItem:item]; @@ -764,7 +766,7 @@ ASSERT_EQ(4, web_state_list_->count()); EXPECT_EQ(2, group->range().count()); - TabSwitcherItem* item = [[WebStateTabSwitcherItem alloc] + TabSwitcherItem* item = [[TabStripTabItem alloc] initWithWebState:web_state_list_->GetWebStateAt(1)]; [mediator_ removeItemFromGroup:item]; @@ -795,7 +797,7 @@ EXPECT_CALL(*tab_group_sync_service_, RemoveGroup(tab_group_id)).Times(0); TabSwitcherItem* item = - [[WebStateTabSwitcherItem alloc] initWithWebState:web_state_to_keep]; + [[TabStripTabItem alloc] initWithWebState:web_state_to_keep]; [mediator_ closeAllItemsExcept:item]; ASSERT_EQ("a b* |", builder.GetWebStateListDescription()); @@ -824,7 +826,7 @@ EXPECT_CALL(*tab_group_sync_service_, RemoveGroup(tab_group_id)).Times(0); TabSwitcherItem* item = - [[WebStateTabSwitcherItem alloc] initWithWebState:web_state_to_keep]; + [[TabStripTabItem alloc] initWithWebState:web_state_to_keep]; [mediator_ closeAllItemsExcept:item]; ASSERT_EQ("a b | d*", builder.GetWebStateListDescription()); @@ -853,7 +855,7 @@ EXPECT_CALL(*tab_group_sync_service_, RemoveGroup(tab_group_id)).Times(0); TabSwitcherItem* item = - [[WebStateTabSwitcherItem alloc] initWithWebState:web_state_to_keep]; + [[TabStripTabItem alloc] initWithWebState:web_state_to_keep]; [mediator_ closeAllItemsExcept:item]; ASSERT_EQ("a b | f*", builder.GetWebStateListDescription()); @@ -878,7 +880,7 @@ EXPECT_CALL(*tab_group_sync_service_, RemoveGroup(tab_group_id)).Times(0); TabSwitcherItem* item = - [[WebStateTabSwitcherItem alloc] initWithWebState:web_state_to_keep]; + [[TabStripTabItem alloc] initWithWebState:web_state_to_keep]; [mediator_ closeAllItemsExcept:item]; ASSERT_EQ("a b | [ 1 g* ]", builder.GetWebStateListDescription()); @@ -956,7 +958,7 @@ const int web_state_index = 1; web::WebState* web_state = web_state_list_->GetWebStateAt(web_state_index); TabSwitcherItem* tab_switcher_item = - [[WebStateTabSwitcherItem alloc] initWithWebState:web_state]; + [[TabStripTabItem alloc] initWithWebState:web_state]; [mediator_ createNewGroupWithItem:tab_switcher_item]; EXPECT_EQ(std::set<web::WebStateID>{tab_switcher_item.identifier}, tab_strip_handler_.identifiersForTabGroupCreation); @@ -1159,7 +1161,7 @@ web::WebState* web_state_1 = web_state_list_->GetWebStateAt(1); TabSwitcherItem* item_for_web_state_1 = - [[WebStateTabSwitcherItem alloc] initWithWebState:web_state_1]; + [[TabStripTabItem alloc] initWithWebState:web_state_1]; [mediator_ addItem:item_for_web_state_1 toGroup:group]; // Check model is updated. @@ -1721,3 +1723,24 @@ EXPECT_EQ(consumer_.itemData[consumer_.items[2]].hasNotificationDot, NO); EXPECT_EQ(consumer_.itemData[consumer_.items[3]].hasNotificationDot, NO); } + +// Tests that `fetchTabSnapshotAndFavicon:completion:` is calling `completion` +// once. +TEST_F(TabStripMediatorTest, FetchTabSnapshotAndFavicon) { + auto fake_web_state = std::make_unique<web::FakeWebState>(); + web::FakeWebState* web_state = fake_web_state.get(); + SnapshotTabHelper::CreateForWebState(web_state); + TabStripTabItem* item = [[TabStripTabItem alloc] initWithWebState:web_state]; + __block int completion_block_called = 0; + auto completion_block = ^(TabSwitcherItem* inner_item, + TabSnapshotAndFavicon* tab_snapshot_and_favicon) { + completion_block_called++; + ASSERT_LE(completion_block_called, 1); + }; + InitializeMediator(); + [mediator_ fetchTabSnapshotAndFavicon:item completion:completion_block]; + EXPECT_TRUE(base::test::ios::WaitUntilConditionOrTimeout( + TestTimeouts::action_timeout(), ^bool() { + return completion_block_called == 1; + })); +}
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_utils.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_utils.mm index 8d38ada..a9eea379 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_utils.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/coordinator/tab_strip_mediator_utils.mm
@@ -11,11 +11,11 @@ #import "ios/chrome/browser/shared/model/web_state_list/tab_group.h" #import "ios/chrome/browser/shared/model/web_state_list/tab_utils.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/swift.h" -#import "ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.h" TabStripItemIdentifier* CreateTabItemIdentifier(web::WebState* web_state) { TabSwitcherItem* tab_item = - [[WebStateTabSwitcherItem alloc] initWithWebState:web_state]; + [[TabStripTabItem alloc] initWithWebState:web_state]; TabStripItemIdentifier* tab_item_identifier = [TabStripItemIdentifier tabIdentifier:tab_item]; return tab_item_identifier;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/BUILD.gn b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/BUILD.gn index 18bbb4a6..cc1f6c2 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/BUILD.gn +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/BUILD.gn
@@ -48,6 +48,8 @@ "tab_strip_mutator.h", "tab_strip_tab_cell.h", "tab_strip_tab_cell.mm", + "tab_strip_tab_item.h", + "tab_strip_tab_item.mm", ] deps = [ ":swift_constants_for_objective_c", @@ -59,6 +61,8 @@ "//ios/chrome/browser/shared/ui/util", "//ios/chrome/browser/shared/ui/util", "//ios/chrome/browser/shared/ui/util/image", + "//ios/chrome/browser/tab_switcher/ui_bundled:items", + "//ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs:constants", "//ios/chrome/common/ui/colors", "//ios/chrome/common/ui/elements", "//ios/chrome/common/ui/util",
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_cell.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_cell.mm index d084203..eb270d0 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_cell.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_cell.mm
@@ -68,11 +68,6 @@ constexpr CGFloat kBlueDotSize = 6 + kBlueDotStrokeWidth * 2; constexpr CGFloat kBlueDotInset = 1; -// Returns the default favicon image. -UIImage* DefaultFavicon() { - return DefaultSymbolWithPointSize(kGlobeAmericasSymbol, 14); -} - } // namespace @implementation TabStripTabCell { @@ -256,11 +251,7 @@ } - (void)setFaviconImage:(UIImage*)image { - if (!image) { - _faviconView.image = DefaultFavicon(); - } else { - _faviconView.image = image; - } + _faviconView.image = image; } #pragma mark - TabStripCell @@ -311,7 +302,7 @@ _activityIndicator.hidden = NO; [_activityIndicator startAnimating]; _faviconView.hidden = YES; - _faviconView.image = DefaultFavicon(); + _faviconView.image = nil; } else { _activityIndicator.hidden = YES; [_activityIndicator stopAnimating]; @@ -1038,8 +1029,7 @@ // Returns a new favicon view. - (UIImageView*)createFaviconView { - UIImageView* faviconView = - [[UIImageView alloc] initWithImage:DefaultFavicon()]; + UIImageView* faviconView = [[UIImageView alloc] init]; faviconView.translatesAutoresizingMaskIntoConstraints = NO; faviconView.contentMode = UIViewContentModeScaleAspectFit; return faviconView;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.h new file mode 100644 index 0000000..8c560b9 --- /dev/null +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.h
@@ -0,0 +1,16 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef IOS_CHROME_BROWSER_TAB_SWITCHER_UI_BUNDLED_TAB_STRIP_UI_TAB_STRIP_TAB_ITEM_H_ +#define IOS_CHROME_BROWSER_TAB_SWITCHER_UI_BUNDLED_TAB_STRIP_UI_TAB_STRIP_TAB_ITEM_H_ + +#import "ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h" + +// Item for tabs in tab strip overriding the methods from +// WebStateTabSwitcherItem. +@interface TabStripTabItem : WebStateTabSwitcherItem + +@end + +#endif // IOS_CHROME_BROWSER_TAB_SWITCHER_UI_BUNDLED_TAB_STRIP_UI_TAB_STRIP_TAB_ITEM_H_
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.mm new file mode 100644 index 0000000..f566478 --- /dev/null +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.mm
@@ -0,0 +1,25 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_item.h" + +#import "ios/chrome/browser/shared/ui/symbols/symbols.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_grid/pinned_tabs/pinned_tabs_constants.h" + +namespace { + +// Size of the NTP symbol in points. +const CGFloat kSymbolSize = 14.0; + +} // namespace + +@implementation TabStripTabItem + +#pragma mark - Favicons + +- (UIImage*)NTPFavicon { + return DefaultSymbolWithPointSize(kGlobeAmericasSymbol, kSymbolSize); +} + +@end
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_ui_swift_bridge.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_ui_swift_bridge.h index 31cd3ff..8fc8461 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_ui_swift_bridge.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_ui_swift_bridge.h
@@ -15,6 +15,7 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_handler.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_collection_drag_drop_metrics.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_group_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_snapshot_and_favicon.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/context_menu/tab_strip_context_menu_provider.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_features_utils.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_group_cell.h" @@ -22,6 +23,7 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_tab_cell.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_utils.h" #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h" +#import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h" #import "ios/chrome/common/ui/colors/semantic_color_names.h" #import "ios/chrome/common/ui/elements/gradient_view.h" #import "ios/chrome/grit/ios_strings.h"
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_view_controller.swift b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_view_controller.swift index 53fe7df..5a532f3 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_view_controller.swift +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_strip/ui/tab_strip_view_controller.swift
@@ -80,7 +80,8 @@ public weak var dragDropHandler: TabCollectionDragDropHandler? /// Provides context menu for tab strip items. public weak var contextMenuProvider: TabStripContextMenuProvider? - + /// Handles snapshots and favicons fetches. + public weak var snapshotAndfaviconDataSource: TabSwitcherItemSnapShotAndFaviconDataSource? /// Handler for tab group confirmation commands. public weak var tabGroupConfirmationHandler: TabGroupConfirmationCommands? @@ -584,11 +585,13 @@ } } - item.fetchFavicon { (item: TabSwitcherItem?, image: UIImage?) -> Void in + let completion = { + (item: TabSwitcherItem?, tabSnapshotAndFavicon: TabSnapshotAndFavicon?) -> Void in if let item = item, item == cell.item { - cell.setFaviconImage(image) + cell.setFaviconImage(tabSnapshotAndFavicon?.favicon) } } + self.snapshotAndfaviconDataSource?.fetchTabSnapshotAndFavicon(item, completion: completion) } // UICollectionViewDropPlaceholder uses a TabStripTabCell and needs the class to be
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h index 483e3f4..ae2a252 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h
@@ -44,16 +44,6 @@ @property(nonatomic, readonly) BOOL hidesTitle; @property(nonatomic, readonly) BOOL showsActivity; -#pragma mark - Image Fetching - -// Fetches the favicon, calling `completion` on the calling sequence when the -// operation completes. -- (void)fetchFavicon:(TabSwitcherImageFetchingCompletionBlock)completion; - -// Fetches the snapshot, calling `completion` on the calling sequence when the -// operation completes. -- (void)fetchSnapshot:(TabSwitcherImageFetchingCompletionBlock)completion; - @end #endif // IOS_CHROME_BROWSER_TAB_SWITCHER_UI_BUNDLED_TAB_SWITCHER_ITEM_H_
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.mm b/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.mm index c033c80d..a5384e2 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.mm
@@ -5,7 +5,6 @@ #import "ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item.h" #import "base/check.h" -#import "base/debug/dump_without_crashing.h" #import "ios/web/public/web_state_id.h" #import "url/gurl.h" @@ -27,26 +26,4 @@ [NSString stringWithFormat:@"Tab ID: %d", self.identifier.identifier()]; } -#pragma mark - Image Fetching - -- (void)fetchFavicon:(TabSwitcherImageFetchingCompletionBlock)completion { - // Subclasses should override this method. It is OK not to call super. - completion(self, nil); - // This should not be called in production, as only real - // WebStateTabSwitcherItem should be asked to fetch a favicon. - // TODO(crbug.com/331159004): Remove in a later milestone if we don't receive - // any. - base::debug::DumpWithoutCrashing(); -} - -- (void)fetchSnapshot:(TabSwitcherImageFetchingCompletionBlock)completion { - // Subclasses should override this method. It is OK not to call super. - completion(self, nil); - // This should not be called in production, as only real - // WebStateTabSwitcherItem should be asked to fetch a snapshot. - // TODO(crbug.com/331159004): Remove in a later milestone if we don't receive - // any. - base::debug::DumpWithoutCrashing(); -} - @end
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h b/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h new file mode 100644 index 0000000..2ea5469 --- /dev/null +++ b/ios/chrome/browser/tab_switcher/ui_bundled/tab_switcher_item_snapshot_and_favicon_data_source.h
@@ -0,0 +1,31 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef IOS_CHROME_BROWSER_TAB_SWITCHER_UI_BUNDLED_TAB_SWITCHER_ITEM_SNAPSHOT_AND_FAVICON_DATA_SOURCE_H_ +#define IOS_CHROME_BROWSER_TAB_SWITCHER_UI_BUNDLED_TAB_SWITCHER_ITEM_SNAPSHOT_AND_FAVICON_DATA_SOURCE_H_ + +@class TabSnapshotAndFavicon; +@class TabSwitcherItem; + +// Block invoked when a TabSnapshotAndFavicon fetching operation completes. The +// `tabSnapshotAndFavicon` is nil if the operation failed. +typedef void (^TabSnapshotAndFaviconFetchingCompletionBlock)( + TabSwitcherItem* item, + TabSnapshotAndFavicon* tabSnapshotAndFavicon); + +// Protocol that the UI uses to retrieve snapshots and favicons for tab +// switcher items. +@protocol TabSwitcherItemSnapShotAndFaviconDataSource + +// Fetches the `item` snapshot and favicon. +// The `completion` block is invoked twice: once when the snapshot has been +// fetched, and again when the favicon has been fetched. +- (void)fetchTabSnapshotAndFavicon:(TabSwitcherItem*)item + completion: + (TabSnapshotAndFaviconFetchingCompletionBlock) + completion; + +@end + +#endif // IOS_CHROME_BROWSER_TAB_SWITCHER_UI_BUNDLED_TAB_SWITCHER_ITEM_SNAPSHOT_AND_FAVICON_DATA_SOURCE_H_
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h b/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h index 36447c6c..45503a6 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h +++ b/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.h
@@ -19,13 +19,12 @@ NS_DESIGNATED_INITIALIZER; - (instancetype)initWithIdentifier:(web::WebStateID)identifier NS_UNAVAILABLE; +// The web state represented by this item. +@property(nonatomic, readonly) web::WebState* webState; + #pragma mark - Favicons -// Default favicon to use if the tab has no favicon available yet. Default is -// `kGlobeAmericasSymbol`. -- (UIImage*)defaultFavicon; - -// Favicon to use for NTP. Default is nil. +// Favicon to use for NTP. Default is an empty image. // Subclasses can override this method to customize it. - (UIImage*)NTPFavicon;
diff --git a/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.mm b/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.mm index 34d10c0..35c34100 100644 --- a/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.mm +++ b/ios/chrome/browser/tab_switcher/ui_bundled/web_state_tab_switcher_item.mm
@@ -8,15 +8,9 @@ #import "base/memory/weak_ptr.h" #import "components/favicon/ios/web_favicon_driver.h" #import "ios/chrome/browser/shared/model/url/url_util.h" -#import "ios/chrome/browser/shared/ui/symbols/symbols.h" -#import "ios/chrome/browser/snapshots/model/snapshot_tab_helper.h" #import "ios/chrome/browser/tabs/model/tab_title_util.h" #import "ios/web/public/web_state.h" -namespace { -const CGFloat kSymbolSize = 16; -} - @implementation WebStateTabSwitcherItem { // The web state represented by this item. base::WeakPtr<web::WebState> _webState; @@ -31,6 +25,10 @@ return self; } +- (web::WebState*)webState { + return _webState.get(); +} + - (GURL)URL { if (!_webState) { return GURL(); @@ -59,66 +57,10 @@ return _webState->IsLoading(); } -#pragma mark - Image Fetching - -- (void)fetchFavicon:(TabSwitcherImageFetchingCompletionBlock)completion { - web::WebState* webState = _webState.get(); - if (!webState) { - completion(self, nil); - return; - } - - // NTP tabs have special treatment. - if (IsUrlNtp(webState->GetVisibleURL())) { - completion(self, [self NTPFavicon]); - return; - } - - // Use the page favicon. - favicon::FaviconDriver* faviconDriver = - favicon::WebFaviconDriver::FromWebState(webState); - // The favicon driver may be null during testing. - if (faviconDriver) { - gfx::Image favicon = faviconDriver->GetFavicon(); - if (!favicon.IsEmpty()) { - completion(self, favicon.ToUIImage()); - return; - } - } - - // Otherwise, set a default favicon. - completion(self, [self defaultFavicon]); -} - -- (void)fetchSnapshot:(TabSwitcherImageFetchingCompletionBlock)completion { - web::WebState* webState = _webState.get(); - if (!webState) { - completion(self, nil); - return; - } - - __weak __typeof(self) weakSelf = self; - SnapshotTabHelper::FromWebState(webState)->RetrieveColorSnapshot( - ^(UIImage* snapshot) { - if (weakSelf) { - completion(weakSelf, snapshot); - } - }); -} - #pragma mark - Favicons -- (UIImage*)defaultFavicon { - UIImageConfiguration* configuration = [UIImageSymbolConfiguration - configurationWithPointSize:kSymbolSize - weight:UIImageSymbolWeightBold - scale:UIImageSymbolScaleMedium]; - return DefaultSymbolWithConfiguration(kGlobeAmericasSymbol, configuration); -} - - (UIImage*)NTPFavicon { - // By default NTP tabs gets no favicon. - return nil; + return [[UIImage alloc] init]; } #pragma mark - NSObject @@ -130,9 +72,9 @@ if (![object isKindOfClass:[WebStateTabSwitcherItem class]]) { return NO; } - WebStateTabSwitcherItem* otherTabStrip = + WebStateTabSwitcherItem* otherItem = base::apple::ObjCCastStrict<WebStateTabSwitcherItem>(object); - return self.identifier == otherTabStrip.identifier; + return self.identifier == otherItem.identifier; } - (NSUInteger)hash {
diff --git a/ios/chrome/browser/web/model/font_size/font_size_tab_helper.mm b/ios/chrome/browser/web/model/font_size/font_size_tab_helper.mm index 90936bb..3b8e708 100644 --- a/ios/chrome/browser/web/model/font_size/font_size_tab_helper.mm +++ b/ios/chrome/browser/web/model/font_size/font_size_tab_helper.mm
@@ -260,7 +260,7 @@ } void FontSizeTabHelper::WebStateRealized(web::WebState* web_state) { - CHECK(!notification_observer_, base::NotFatalUntil::M125); + CHECK(!notification_observer_); CreateNotificationObserver(); }
diff --git a/ios/chrome/browser/web/model/sad_tab_tab_helper.mm b/ios/chrome/browser/web/model/sad_tab_tab_helper.mm index e999c4b..2791b10 100644 --- a/ios/chrome/browser/web/model/sad_tab_tab_helper.mm +++ b/ios/chrome/browser/web/model/sad_tab_tab_helper.mm
@@ -134,7 +134,7 @@ } void SadTabTabHelper::WebStateRealized(web::WebState* web_state) { - CHECK(!background_notification_observer_, base::NotFatalUntil::M125); + CHECK(!background_notification_observer_); CreateNotificationObserver(); }
diff --git a/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.h b/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.h index 1e86c1b..7bd018d 100644 --- a/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.h +++ b/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.h
@@ -71,9 +71,6 @@ void WebStateRealized(web::WebState* web_state) override; void WebStateDestroyed(web::WebState* web_state) override; - // The browser whose WebStates' web usage is being managed. - raw_ptr<Browser> browser_ = nullptr; - // Whether web usage is enabled for the WebState in `web_state_list_`. bool web_usage_enabled_ = false;
diff --git a/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.mm b/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.mm index d9044403..2cc845e3 100644 --- a/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.mm +++ b/ios/chrome/browser/web_state_list/model/web_usage_enabler/web_usage_enabler_browser_agent.mm
@@ -8,7 +8,7 @@ #import "ios/web/public/navigation/navigation_manager.h" WebUsageEnablerBrowserAgent::WebUsageEnablerBrowserAgent(Browser* browser) - : BrowserUserData(browser), browser_(browser) { + : BrowserUserData(browser) { browser_observation_.Observe(browser_.get()); WebStateList* web_state_list = browser_->GetWebStateList();
diff --git a/ios_internal b/ios_internal index caa545d..a5c6f36 160000 --- a/ios_internal +++ b/ios_internal
@@ -1 +1 @@ -Subproject commit caa545d88ae49b674a6d9542f80c5514d0cfc18e +Subproject commit a5c6f36c55a93150abaf43134d5c40dc42112f9d
diff --git a/media/audio/win/audio_low_latency_input_win.cc b/media/audio/win/audio_low_latency_input_win.cc index 123a527..2271e41 100644 --- a/media/audio/win/audio_low_latency_input_win.cc +++ b/media/audio/win/audio_low_latency_input_win.cc
@@ -32,6 +32,7 @@ #include "base/strings/stringprintf.h" #include "base/strings/utf_string_conversions.h" #include "base/synchronization/waitable_event.h" +#include "base/timer/elapsed_timer.h" #include "base/trace_event/common/trace_event_common.h" #include "base/trace_event/trace_event.h" #include "base/win/core_winrt_util.h" @@ -77,6 +78,10 @@ // device) being played out. constexpr uint32_t kWindowsSystemProcessId = 4; +// HRESULT_FROM_WIN32(WAIT_TIMEOUT) yields 0x80070102, which is a well-known COM +// error for timeouts. +constexpr HRESULT kActivationTimeoutHr = HRESULT_FROM_WIN32(WAIT_TIMEOUT); + // Converts a COM error into a human-readable string. std::string ErrorToString(HRESULT hresult) { return CoreAudioUtil::ErrorToString(hresult); @@ -522,7 +527,7 @@ base::TimeDelta async_activation_timeout_ms) { // Wait for a maximum of 10 seconds for the activation to complete. if (!wait_event_.TimedWait(async_activation_timeout_ms)) { - return E_FAIL; + return kActivationTimeoutHr; } // If the activation was successful, move the audio client to the output @@ -1526,6 +1531,8 @@ }, }; + TRACE_EVENT("audio", "AudioClientActivation"); + base::ElapsedTimer timer; ComPtr<AudioClientActivationHandler> completion_handler = Microsoft::WRL::Make<AudioClientActivationHandler>(); ComPtr<IActivateAudioInterfaceAsyncOperation> async_op; @@ -1533,11 +1540,25 @@ VIRTUAL_AUDIO_DEVICE_PROCESS_LOOPBACK, __uuidof(IAudioClient), &propvariant, completion_handler.Get(), &async_op); if (FAILED(hr)) { + TRACE_EVENT_INSTANT0("audio", "ActivateAudioInterfaceAsync failed", + TRACE_EVENT_SCOPE_THREAD); return hr; } - return completion_handler->WaitAndGetAudioClient( - &audio_client_, async_activation_timeout_ms_); + hr = completion_handler->WaitAndGetAudioClient(&audio_client_, + async_activation_timeout_ms_); + const bool timed_out = (hr == kActivationTimeoutHr); + base::UmaHistogramBoolean("Media.Audio.Capture.Win.GetAudioClientTimedOut", + timed_out); + if (!timed_out) { + base::UmaHistogramTimes("Media.Audio.Capture.Win.TimeToGetAudioClient", + timer.Elapsed()); + } else { + TRACE_EVENT_INSTANT0("audio", "GetAudioClient timed out", + TRACE_EVENT_SCOPE_THREAD); + } + + return hr; } bool WASAPIAudioInputStream::RawProcessingSupported() {
diff --git a/media/audio/win/audio_low_latency_input_win.h b/media/audio/win/audio_low_latency_input_win.h index 482fd72..7ab264e 100644 --- a/media/audio/win/audio_low_latency_input_win.h +++ b/media/audio/win/audio_low_latency_input_win.h
@@ -379,8 +379,6 @@ // Timeout period for waiting on the OS to activate the audio interface for // application loopback capture. - // TODO(crbug.com/40947205): Add UMA stats to track the actual wait time in - // the field base::TimeDelta async_activation_timeout_ms_ = base::Seconds(10); SEQUENCE_CHECKER(sequence_checker_);
diff --git a/media/audio/win/audio_low_latency_input_win_unittest.cc b/media/audio/win/audio_low_latency_input_win_unittest.cc index cb15f8c0..6e7f74ac 100644 --- a/media/audio/win/audio_low_latency_input_win_unittest.cc +++ b/media/audio/win/audio_low_latency_input_win_unittest.cc
@@ -879,10 +879,15 @@ AudioParameters params_; ScopedAudioInputStream stream_; FakeWinWASAPIEnvironment fake_wasapi_environment_; + base::HistogramTester histogram_tester_; }; TEST_P(WinAudioProcessLoopbackTest, OpenStreamSuccess) { ASSERT_THAT(stream_->Open(), Eq(AudioInputStream::OpenOutcome::kSuccess)); + histogram_tester_.ExpectTotalCount( + "Media.Audio.Capture.Win.TimeToGetAudioClient", 1); + histogram_tester_.ExpectBucketCount( + "Media.Audio.Capture.Win.GetAudioClientTimedOut", false, 1); } TEST_P(WinAudioProcessLoopbackTest, @@ -890,6 +895,10 @@ fake_wasapi_environment_.SimulateError( WASAPITestErrorCode::kActivateAudioInterfaceAsyncFailed); EXPECT_EQ(stream_->Open(), AudioInputStream::OpenOutcome::kFailed); + histogram_tester_.ExpectTotalCount( + "Media.Audio.Capture.Win.TimeToGetAudioClient", 0); + histogram_tester_.ExpectTotalCount( + "Media.Audio.Capture.Win.GetAudioClientTimedOut", 0); } TEST_P(WinAudioProcessLoopbackTest, @@ -900,6 +909,10 @@ // timeout is 10 seconds. OverrideAsyncActivationTimeout(kShortAsyncActivationTimeoutMs); EXPECT_EQ(stream_->Open(), AudioInputStream::OpenOutcome::kFailed); + histogram_tester_.ExpectTotalCount( + "Media.Audio.Capture.Win.TimeToGetAudioClient", 0); + histogram_tester_.ExpectBucketCount( + "Media.Audio.Capture.Win.GetAudioClientTimedOut", true, 1); } TEST_P(WinAudioProcessLoopbackTest, @@ -910,12 +923,20 @@ // timeout is 10 seconds. OverrideAsyncActivationTimeout(kShortAsyncActivationTimeoutMs); EXPECT_EQ(stream_->Open(), AudioInputStream::OpenOutcome::kFailed); + histogram_tester_.ExpectTotalCount( + "Media.Audio.Capture.Win.TimeToGetAudioClient", 0); + histogram_tester_.ExpectBucketCount( + "Media.Audio.Capture.Win.GetAudioClientTimedOut", true, 1); } TEST_P(WinAudioProcessLoopbackTest, OpenStreamAudioClientActivationFailed) { fake_wasapi_environment_.SimulateError( WASAPITestErrorCode::kAudioClientActivationFailed); EXPECT_EQ(stream_->Open(), AudioInputStream::OpenOutcome::kFailed); + histogram_tester_.ExpectTotalCount( + "Media.Audio.Capture.Win.TimeToGetAudioClient", 1); + histogram_tester_.ExpectBucketCount( + "Media.Audio.Capture.Win.GetAudioClientTimedOut", false, 1); } TEST_P(WinAudioProcessLoopbackTest, SuccessfulCapture) { @@ -931,6 +952,10 @@ EXPECT_EQ(sink.num_callbacks(), 2); EXPECT_GT(sink.num_received_audio_frames(), 0); EXPECT_FALSE(sink.error()); + histogram_tester_.ExpectTotalCount( + "Media.Audio.Capture.Win.TimeToGetAudioClient", 1); + histogram_tester_.ExpectBucketCount( + "Media.Audio.Capture.Win.GetAudioClientTimedOut", false, 1); } INSTANTIATE_TEST_SUITE_P(
diff --git a/net/cookies/cookie_monster.cc b/net/cookies/cookie_monster.cc index b914ce3..e1090c3 100644 --- a/net/cookies/cookie_monster.cc +++ b/net/cookies/cookie_monster.cc
@@ -1735,7 +1735,7 @@ // source type to kOther (or kHTTP/kScript where applicable). See // CookieSourceType in net/cookies/cookie_constants.h for more. if (cc->SourceType() == CookieSourceType::kUnknown) { - CHECK_IS_TEST(base::NotFatalUntil::M126); + CHECK_IS_TEST(); } #endif
diff --git a/net/http/transport_security_state_static.pins b/net/http/transport_security_state_static.pins index 41a0418..a4c0a57 100644 --- a/net/http/transport_security_state_static.pins +++ b/net/http/transport_security_state_static.pins
@@ -43,9 +43,9 @@ # hash function for preloaded entries again (we have already done so once). # -# Last updated: 2025-05-25 12:54 UTC +# Last updated: 2025-05-26 12:53 UTC PinsListTimestamp -1748177688 +1748264017 TestSPKI sha256/AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=
diff --git a/net/http/transport_security_state_static_pins.json b/net/http/transport_security_state_static_pins.json index e91b8bc9..b5ec592 100644 --- a/net/http/transport_security_state_static_pins.json +++ b/net/http/transport_security_state_static_pins.json
@@ -31,7 +31,7 @@ // the 'static_spki_hashes' and 'bad_static_spki_hashes' fields in 'pinsets' // refer to, and the timestamp at which the pins list was last updated. // -// Last updated: 2025-05-25 12:54 UTC +// Last updated: 2025-05-26 12:53 UTC // { "pinsets": [
diff --git a/testing/variations/fieldtrial_testing_config.json b/testing/variations/fieldtrial_testing_config.json index b04abba..9310c544 100644 --- a/testing/variations/fieldtrial_testing_config.json +++ b/testing/variations/fieldtrial_testing_config.json
@@ -7776,21 +7776,6 @@ ] } ], - "DeviceIdValidation": [ - { - "platforms": [ - "chromeos" - ], - "experiments": [ - { - "name": "Enabled", - "enable_features": [ - "DeviceIdValidation" - ] - } - ] - } - ], "DexFixer": [ { "platforms": [ @@ -11660,21 +11645,6 @@ ] } ], - "IOSDeleteAllSavedCredentials": [ - { - "platforms": [ - "ios" - ], - "experiments": [ - { - "name": "Enabled", - "enable_features": [ - "IOSEnableDeleteAllSavedCredentials" - ] - } - ] - } - ], "IOSDeprecateFeedHeader": [ { "platforms": [ @@ -16887,14 +16857,14 @@ ], "experiments": [ { - "name": "Enabled_Uniform_20250520", + "name": "Enabled_Uniform_20250526", "params": { "en_site_id": "N5wFxEDQr0ugnJ3q1cK0SNopqcEc", "hats_histogram_name": "Feedback.HappinessTrackingSurvey.PerformanceControlsPPMSurvey", "hats_survey_ukm_id": "1027171324", "ppm_survey_segment_name1": "ChromeOS", "ppm_survey_uniform_sample": "true", - "probability": "0.108", + "probability": "1.0", "survey": "performance-ppm" }, "enable_features": [ @@ -16909,7 +16879,7 @@ ], "experiments": [ { - "name": "Enabled_Uniform_20250520", + "name": "Enabled_Uniform_20250526", "params": { "en_site_id": "N5wFxEDQr0ugnJ3q1cK0SNopqcEc", "hats_histogram_name": "Feedback.HappinessTrackingSurvey.PerformanceControlsPPMSurvey", @@ -16931,7 +16901,7 @@ ], "experiments": [ { - "name": "Enabled_Uniform_20250520", + "name": "Enabled_Uniform_20250526", "params": { "en_site_id": "N5wFxEDQr0ugnJ3q1cK0SNopqcEc", "hats_histogram_name": "Feedback.HappinessTrackingSurvey.PerformanceControlsPPMSurvey", @@ -16948,32 +16918,6 @@ ] } ] - }, - { - "platforms": [ - "windows" - ], - "experiments": [ - { - "name": "Enabled_Uniform_20250520", - "params": { - "en_site_id": "N5wFxEDQr0ugnJ3q1cK0SNopqcEc", - "hats_histogram_name": "Feedback.HappinessTrackingSurvey.PerformanceControlsPPMSurvey", - "hats_survey_ukm_id": "1027171324", - "ppm_survey_segment_max_memory_gb1": "4", - "ppm_survey_segment_max_memory_gb2": "8", - "ppm_survey_segment_name1": "Windows, up to 4 GB", - "ppm_survey_segment_name2": "", - "ppm_survey_segment_name3": "", - "ppm_survey_uniform_sample": "true", - "probability": "0.088", - "survey": "performance-ppm" - }, - "enable_features": [ - "PerformanceControlsPPMSurvey" - ] - } - ] } ], "PerformanceInterventionAlgorithm": [
diff --git a/third_party/angle b/third_party/angle index a38ac25..2a18fdb 160000 --- a/third_party/angle +++ b/third_party/angle
@@ -1 +1 @@ -Subproject commit a38ac25bd93c1fdaf393e2513f9c254b493e18bb +Subproject commit 2a18fdbf4c8c20e37734611064d21a83658f6236
diff --git a/third_party/blink/common/features.cc b/third_party/blink/common/features.cc index cf912d0..d79907cf 100644 --- a/third_party/blink/common/features.cc +++ b/third_party/blink/common/features.cc
@@ -1933,6 +1933,10 @@ "memory_cache_strong_ref_resource_size_threshold", 3 * 1024 * 1024); +BASE_FEATURE(kMemoryPurgeOnFreezeLimit, + "MemoryPurgeOnFreezeLimit", + base::FEATURE_DISABLED_BY_DEFAULT); + BASE_FEATURE(kMemorySaverModeRenderTuning, "MemorySaverModeRenderTuning", base::FEATURE_DISABLED_BY_DEFAULT);
diff --git a/third_party/blink/public/blink_resources.grd b/third_party/blink/public/blink_resources.grd index 38d5b1b..3ae770d 100644 --- a/third_party/blink/public/blink_resources.grd +++ b/third_party/blink/public/blink_resources.grd
@@ -56,6 +56,11 @@ </if> <include name="IDR_AUDIO_SPATIALIZATION_COMPOSITE" file="../renderer/platform/audio/resources/Composite.flac" type="BINDATA"/> <include name="IDR_UASTYLE_JSON_DOCUMENT_CSS" file="../renderer/core/css/json-document.css" type="BINDATA" compress="brotli"/> + <include name="IDR_PERMISSION_ICON_CAMERA_SVG" file="../renderer/core/html/resources/images/permission_icon_camera.svg" type="BINDATA" compress="brotli"/> + <include name="IDR_PERMISSION_ICON_MICROPHONE_SVG" file="../renderer/core/html/resources/images/permission_icon_microphone.svg" type="BINDATA" compress="brotli"/> + <include name="IDR_PERMISSION_ICON_LOCATION_SVG" file="../renderer/core/html/resources/images/permission_icon_location.svg" type="BINDATA" compress="brotli"/> + <include name="IDR_PERMISSION_ICON_LOCATION_PRECISE_SVG" file="../renderer/core/html/resources/images/permission_icon_location_precise.svg" type="BINDATA" compress="brotli"/> + </includes> </release> </grit>
diff --git a/third_party/blink/public/common/features.h b/third_party/blink/public/common/features.h index 97923fb..b65eb508 100644 --- a/third_party/blink/public/common/features.h +++ b/third_party/blink/public/common/features.h
@@ -1298,6 +1298,12 @@ int, kMemoryCacheStrongReferenceResourceSizeThresholdParam); +// Limits the number of memory purge performed on page freezing to 1 per +// interval in which the renderer is backgrounded. Without this, memory purge is +// performed every time all pages in a renderer become frozen, which can happen +// periodically with periodic unfreezing. +BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kMemoryPurgeOnFreezeLimit); + // Enables v8 memory saver mode on low memory thresholds. BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kMemorySaverModeRenderTuning); BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE_PARAM(
diff --git a/third_party/blink/public/devtools_protocol/browser_protocol.pdl b/third_party/blink/public/devtools_protocol/browser_protocol.pdl index acc83701..f5bc1b95 100644 --- a/third_party/blink/public/devtools_protocol/browser_protocol.pdl +++ b/third_party/blink/public/devtools_protocol/browser_protocol.pdl
@@ -3012,6 +3012,7 @@ file-selector-button details-content picker + permission-icon # Shadow root type. type ShadowRootType extends string
diff --git a/third_party/blink/public/mojom/webid/federated_auth_request.mojom b/third_party/blink/public/mojom/webid/federated_auth_request.mojom index 093c5ab..b192ce2 100644 --- a/third_party/blink/public/mojom/webid/federated_auth_request.mojom +++ b/third_party/blink/public/mojom/webid/federated_auth_request.mojom
@@ -4,10 +4,10 @@ module blink.mojom; -import "third_party/blink/public/mojom/credentialmanagement/credential_manager.mojom"; -import "url/mojom/url.mojom"; -import "url/mojom/origin.mojom"; import "mojo/public/mojom/base/time.mojom"; +import "third_party/blink/public/mojom/credentialmanagement/credential_manager.mojom"; +import "url/mojom/origin.mojom"; +import "url/mojom/url.mojom"; // Implementation of the proposed FedCM API. // @@ -39,26 +39,26 @@ enum DisconnectStatus { kSuccess, kErrorTooManyRequests, - kError + kError, }; enum IdpSigninStatus { kSignedIn, - kSignedOut + kSignedOut, }; enum RpContext { kSignIn, kSignUp, kUse, - kContinue + kContinue, }; // Don't change the meaning or the order of these values because they are // being recorded in metrics and in sync with the counterpart in enums.xml. enum RpMode { kActive, - kPassive + kPassive, }; // The result of a call to IdentityProvider.register(). @@ -67,7 +67,8 @@ kErrorFeatureDisabled, kErrorCrossOriginConfig, kErrorNoTransientActivation, - kErrorDeclined + kErrorDeclined, + kErrorInvalidConfig, }; // The details of a federated identity provider. @@ -136,7 +137,8 @@ string account_hint; }; -// The list of user information that can be returned to an identity provider during a UserInfo API call. +// The list of user information that can be returned to an identity provider +// during a UserInfo API call. struct IdentityUserInfo { string email; string given_name; @@ -196,17 +198,17 @@ // - The error which occurred during the retrieval of a token. // - Whether the account was automatically selected. RequestToken(array<IdentityProviderGetParameters> idp_get_params, - CredentialMediationRequirement requirement) => - (RequestTokenStatus status, - url.mojom.Url? selected_identity_provider_config_url, - string? token, - TokenError? error, - bool is_auto_selected); + CredentialMediationRequirement requirement) + => (RequestTokenStatus status, + url.mojom.Url? selected_identity_provider_config_url, + string? token, + TokenError? error, + bool is_auto_selected); // Requests user info to be generated, given an IDP config. // Returns an IdentityUserInfo for each of the user's accounts. - RequestUserInfo(IdentityProviderConfig provider) => - (RequestUserInfoStatus status, array<IdentityUserInfo>? user_info); + RequestUserInfo(IdentityProviderConfig provider) + => (RequestUserInfoStatus status, array<IdentityUserInfo>? user_info); // Cancels the pending token request, if any. CancelTokenRequest(); @@ -220,7 +222,8 @@ // Marks the user as logged in/out to the IDP on this origin. 'origin' must // not be opaque. - SetIdpSigninStatus(url.mojom.Origin origin, IdpSigninStatus status, + SetIdpSigninStatus(url.mojom.Origin origin, + IdpSigninStatus status, LoginStatusOptions? options); // Registers the url as an IdP's configURL of the user's preference. @@ -233,7 +236,8 @@ CloseModalDialogView(); // Require user mediation with navigator.credentials.preventSilentAccess() as - // defined in https://w3c.github.io/webappsec-credential-management/#user-mediation + // defined in + // https://w3c.github.io/webappsec-credential-management/#user-mediation // TODO(https://crbug.com/1441075): There's `PreventSilentAccess` in // credential_manager.mojom but that's specific to PasswordManager and it's // hard to reuse it as-is. We should unify the implementation for different @@ -242,6 +246,6 @@ // Disconnects the sharing permission for the specified |account_id| from // |provider| for the RP identified by |client_id|. - Disconnect(IdentityCredentialDisconnectOptions options) => - (DisconnectStatus status); + Disconnect(IdentityCredentialDisconnectOptions options) + => (DisconnectStatus status); };
diff --git a/third_party/blink/renderer/bindings/generated_in_modules.gni b/third_party/blink/renderer/bindings/generated_in_modules.gni index 5e89373f..3e985636 100644 --- a/third_party/blink/renderer/bindings/generated_in_modules.gni +++ b/third_party/blink/renderer/bindings/generated_in_modules.gni
@@ -3314,8 +3314,8 @@ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_filesystemhandle_wellknowndirectory.h", "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuautolayoutmode_gpupipelinelayout.cc", "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuautolayoutmode_gpupipelinelayout.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpubufferbinding_gpuexternaltexture_gpusampler_gputextureview.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpubufferbinding_gpuexternaltexture_gpusampler_gputextureview.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpubuffer_gpubufferbinding_gpuexternaltexture_gpusampler_gputextureview.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpubuffer_gpubufferbinding_gpuexternaltexture_gpusampler_gputextureview.h", "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_offscreen_rendering_context.cc", "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_offscreen_rendering_context.h", "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuextent3ddict_unsignedlongenforcerangesequence.cc",
diff --git a/third_party/blink/renderer/core/css/css_selector.cc b/third_party/blink/renderer/core/css/css_selector.cc index 9990bda..1851536 100644 --- a/third_party/blink/renderer/core/css/css_selector.cc +++ b/third_party/blink/renderer/core/css/css_selector.cc
@@ -379,6 +379,8 @@ return kPseudoIdFileSelectorButton; case kPseudoDetailsContent: return kPseudoIdDetailsContent; + case kPseudoPermissionIcon: + return kPseudoIdPermissionIcon; case kPseudoPicker: // NOTE: When we support more than one argument to ::picker() we will // need to refactor something here (possibly the callers of this method) @@ -643,6 +645,7 @@ {"out-of-range", CSSSelector::kPseudoOutOfRange}, {"past", CSSSelector::kPseudoPastCue}, {"paused", CSSSelector::kPseudoPaused}, + {"permission-icon", CSSSelector::kPseudoPermissionIcon}, {"picker-icon", CSSSelector::kPseudoPickerIcon}, {"picture-in-picture", CSSSelector::kPseudoPictureInPicture}, {"placeholder", CSSSelector::kPseudoPlaceholder}, @@ -927,6 +930,11 @@ bits_.set<PseudoTypeField>(kPseudoUnknown); } break; + case kPseudoPermissionIcon: + if (Match() != kPseudoElement) { + bits_.set<PseudoTypeField>(kPseudoUnknown); + } + break; case kPseudoBlinkInternalElement: if (Match() != kPseudoElement || mode != kUASheetMode) { bits_.set<PseudoTypeField>(kPseudoUnknown); @@ -1635,7 +1643,8 @@ /* static */ bool CSSSelector::IsElementBackedPseudoElement( CSSSelector::PseudoType pseudo) { - return pseudo == kPseudoDetailsContent || pseudo == kPseudoPicker; + return pseudo == kPseudoDetailsContent || pseudo == kPseudoPicker || + pseudo == kPseudoPermissionIcon; } bool CSSSelector::IsElementBackedPseudoElement() const { @@ -1685,6 +1694,7 @@ case kPseudoWebKitCustomElement: case kPseudoBlinkInternalElement: case kPseudoDetailsContent: + case kPseudoPermissionIcon: case kPseudoViewTransition: case kPseudoViewTransitionGroup: case kPseudoViewTransitionImagePair:
diff --git a/third_party/blink/renderer/core/css/css_selector.h b/third_party/blink/renderer/core/css/css_selector.h index 0e6a24fb..df6655b 100644 --- a/third_party/blink/renderer/core/css/css_selector.h +++ b/third_party/blink/renderer/core/css/css_selector.h
@@ -289,6 +289,7 @@ kPseudoPermissionElementInvalidStyle, kPseudoPermissionElementOccluded, kPseudoPermissionGranted, + kPseudoPermissionIcon, kPseudoPlaceholder, kPseudoPlaceholderShown, kPseudoReadOnly,
diff --git a/third_party/blink/renderer/core/css/css_syntax_definition.cc b/third_party/blink/renderer/core/css/css_syntax_definition.cc index 8ce5455..6ea37f21 100644 --- a/third_party/blink/renderer/core/css/css_syntax_definition.cc +++ b/third_party/blink/renderer/core/css/css_syntax_definition.cc
@@ -362,4 +362,13 @@ return builder.ToString(); } +CSSSyntaxDefinition CSSSyntaxDefinition::CreateNumericSyntax() { + CSSParserTokenStream stream( + "<number> | <length> | <percentage> | <angle> | <time> | <resolution>"); + std::optional<CSSSyntaxDefinition> syntax_definition = + CSSSyntaxDefinition::Consume(stream); + DCHECK(syntax_definition.has_value()); + return *syntax_definition; +} + } // namespace blink
diff --git a/third_party/blink/renderer/core/css/css_syntax_definition.h b/third_party/blink/renderer/core/css/css_syntax_definition.h index d7f23dfd..2d11faf 100644 --- a/third_party/blink/renderer/core/css/css_syntax_definition.h +++ b/third_party/blink/renderer/core/css/css_syntax_definition.h
@@ -57,6 +57,12 @@ // https://drafts.css-houdini.org/css-properties-values-api-1/#universal-syntax-descriptor static CSSSyntaxDefinition CreateUniversal(); + // Returns syntax: <number> | <length> | <percentage> | <angle> | <time> | + // <resolution>. + // Used for container style range queries, + // https://github.com/w3c/csswg-drafts/issues/8376#issuecomment-2751161553. + static CSSSyntaxDefinition CreateNumericSyntax(); + private: friend class CSSSyntaxStringParser; friend class CSSSyntaxStringParserTest;
diff --git a/third_party/blink/renderer/core/css/invalidation/rule_invalidation_data_visitor.cc b/third_party/blink/renderer/core/css/invalidation/rule_invalidation_data_visitor.cc index 95698854c..40fad2e 100644 --- a/third_party/blink/renderer/core/css/invalidation/rule_invalidation_data_visitor.cc +++ b/third_party/blink/renderer/core/css/invalidation/rule_invalidation_data_visitor.cc
@@ -100,6 +100,7 @@ case CSSSelector::kPseudoNot: case CSSSelector::kPseudoPlaceholder: case CSSSelector::kPseudoDetailsContent: + case CSSSelector::kPseudoPermissionIcon: case CSSSelector::kPseudoFileSelectorButton: case CSSSelector::kPseudoResizer: case CSSSelector::kPseudoRoot:
diff --git a/third_party/blink/renderer/core/css/media_query_evaluator.cc b/third_party/blink/renderer/core/css/media_query_evaluator.cc index 4d29caa1..6487f3c 100644 --- a/third_party/blink/renderer/core/css/media_query_evaluator.cc +++ b/third_party/blink/renderer/core/css/media_query_evaluator.cc
@@ -1726,13 +1726,8 @@ return KleeneValue::kUnknown; } - if (feature.HasStyleRange()) { - // TODO(crbug.com/408011559): Add support for container style queries - // ranges. - return KleeneValue::kFalse; - } - - if (CSSVariableParser::IsValidVariableName(feature.Name())) { + if (feature.HasStyleRange() || + CSSVariableParser::IsValidVariableName(feature.Name())) { return EvalStyleFeature(feature, result_flags); } @@ -1819,6 +1814,8 @@ const MediaQueryExpBounds& bounds = feature.Bounds(); if (bounds.IsRange()) { + DCHECK(feature.HasStyleRange()); + DCHECK(RuntimeEnabledFeatures::CSSContainerStyleQueriesRangeEnabled()); // TODO(crbug.com/408011559): Add support for container style queries // ranges. return KleeneValue::kFalse; @@ -1874,4 +1871,28 @@ return KleeneValue::kFalse; } +KleeneValue MediaQueryEvaluator::EvalIfRange(const CSSValue& reference_value, + const CSSValue& query_value, + MediaQueryOperator op, + bool reverse_op) { + const CSSNumericLiteralValue* reference_numeric = + DynamicTo<CSSNumericLiteralValue>(reference_value); + const CSSNumericLiteralValue* query_numeric = + DynamicTo<CSSNumericLiteralValue>(query_value); + + if (!reference_numeric || !query_numeric || + reference_numeric->GetType() != query_numeric->GetType()) { + return KleeneValue::kFalse; + } + + if (reverse_op) { + op = ReverseOperator(op); + } + + return CompareDoubleValue(reference_numeric->DoubleValue(), + query_numeric->DoubleValue(), op) + ? KleeneValue::kTrue + : KleeneValue::kFalse; +} + } // namespace blink
diff --git a/third_party/blink/renderer/core/css/media_query_evaluator.h b/third_party/blink/renderer/core/css/media_query_evaluator.h index 4845479..28d09f3 100644 --- a/third_party/blink/renderer/core/css/media_query_evaluator.h +++ b/third_party/blink/renderer/core/css/media_query_evaluator.h
@@ -38,10 +38,12 @@ namespace blink { +class CSSValue; class LocalFrame; class MediaQuery; class MediaQueryExpNode; class MediaQueryFeatureExpNode; +enum class MediaQueryOperator; class MediaQuerySet; class MediaQuerySetResult; class MediaValues; @@ -97,6 +99,11 @@ KleeneValue Eval(const MediaQueryExpNode&) const; KleeneValue Eval(const MediaQueryExpNode&, MediaQueryResultFlags*) const; + static KleeneValue EvalIfRange(const CSSValue& reference_value, + const CSSValue& query_value, + MediaQueryOperator op, + bool reverse_op); + // Returns true if any of the media queries in the results lists changed its // evaluation. bool DidResultsChange(const HeapVector<MediaQuerySetResult>& results) const;
diff --git a/third_party/blink/renderer/core/css/media_query_exp.h b/third_party/blink/renderer/core/css/media_query_exp.h index b9326c3..db63af8 100644 --- a/third_party/blink/renderer/core/css/media_query_exp.h +++ b/third_party/blink/renderer/core/css/media_query_exp.h
@@ -410,6 +410,11 @@ return exp_.MediaFeature(); } + const CSSUnparsedDeclarationValue& ReferenceValue() const { + DCHECK(HasStyleRange()); + return exp_.ReferenceValue(); + } + bool HasMediaFeature() const { return exp_.HasMediaFeature(); } bool HasStyleRange() const { return exp_.HasStyleRange(); }
diff --git a/third_party/blink/renderer/core/css/parser/css_selector_parser.cc b/third_party/blink/renderer/core/css/parser/css_selector_parser.cc index eb02917..99e5729e 100644 --- a/third_party/blink/renderer/core/css/parser/css_selector_parser.cc +++ b/third_party/blink/renderer/core/css/parser/css_selector_parser.cc
@@ -69,6 +69,7 @@ case CSSSelector::PseudoType::kPseudoPlaceholder: case CSSSelector::PseudoType::kPseudoFileSelectorButton: case CSSSelector::PseudoType::kPseudoPicker: + case CSSSelector::PseudoType::kPseudoPermissionIcon: return CSSSelector::RelationType::kUAShadow; case CSSSelector::PseudoType::kPseudoPart: return CSSSelector::RelationType::kShadowPart;
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 020899e5..8f9e76f4 100644 --- a/third_party/blink/renderer/core/css/resolver/style_cascade.cc +++ b/third_party/blink/renderer/core/css/resolver/style_cascade.cc
@@ -243,6 +243,18 @@ return evaluator.EvalAndAdd(query, change, match_result); } +bool IsVariableNameOnly(StringView str) { + if (!CSSVariableParser::IsValidVariableName(str)) { + return false; + } + CSSParserTokenStream stream(str); + if (stream.Peek().GetType() != kIdentToken) { + return false; + } + stream.ConsumeIncludingWhitespace(); + return stream.AtEnd(); +} + } // namespace MatchResult& StyleCascade::MutableMatchResult() { @@ -2319,6 +2331,88 @@ return false; } +const CSSValue* StyleCascade::CoerceIntoNumericValue( + const CSSUnparsedDeclarationValue& unparsed_value, + const TreeScope* tree_scope, + CascadeResolver& resolver, + const CSSParserContext& context, + FunctionContext* function_context) { + StringView unparsed_value_str( + unparsed_value.VariableDataValue()->OriginalText()); + CSSVariableData* data = nullptr; + if (IsVariableNameOnly(unparsed_value_str)) { + data = ResolveLikeVar(AtomicString(unparsed_value_str), resolver, context, + function_context); + } else { + CSSParserTokenStream decl_value_stream(unparsed_value_str); + TokenSequence substituted_token_sequence; + if (ResolveTokensInto( + decl_value_stream, tree_scope, resolver, context, function_context, + /* stop_type */ kEOFToken, substituted_token_sequence)) { + data = substituted_token_sequence.BuildVariableData(); + } + } + + if (!data) { + return nullptr; + } + + CSSSyntaxDefinition syntax_definition = + CSSSyntaxDefinition::CreateNumericSyntax(); + const CSSValue* parsed_value = syntax_definition.Parse( + data->OriginalText(), context, + /* is_animation_tainted= */ data->IsAnimationTainted(), + /* is_attr_tainted= */ data->IsAttrTainted()); + + if (!parsed_value) { + return nullptr; + } + + const auto* primitive_value = DynamicTo<CSSPrimitiveValue>(parsed_value); + + if (!primitive_value) { + return nullptr; + } + + if (!primitive_value->IsCalculated() && + (primitive_value->IsPx() || primitive_value->IsPercentage())) { + return parsed_value; + } + + if (primitive_value->IsLength() || primitive_value->IsPercentage() || + !primitive_value->IsResolvableBeforeLayout()) { + Length length = primitive_value->ConvertToLength( + state_.CssToLengthConversionData().Unzoomed()); + return CSSPrimitiveValue::CreateFromLength(length, 1); + } + + if (primitive_value->IsNumber()) { + return CSSNumericLiteralValue::Create( + primitive_value->ComputeNumber(state_.CssToLengthConversionData()), + CSSPrimitiveValue::UnitType::kNumber); + } + + if (primitive_value->IsAngle()) { + return CSSNumericLiteralValue::Create( + primitive_value->ComputeDegrees(state_.CssToLengthConversionData()), + CSSPrimitiveValue::UnitType::kDegrees); + } + + if (primitive_value->IsTime()) { + return CSSNumericLiteralValue::Create( + primitive_value->ComputeSeconds(state_.CssToLengthConversionData()), + CSSPrimitiveValue::UnitType::kSeconds); + } + + if (primitive_value->IsResolution()) { + return CSSNumericLiteralValue::Create( + primitive_value->ComputeDotsPerPixel( + state_.CssToLengthConversionData()), + CSSPrimitiveValue::UnitType::kDotsPerPixel); + } + return nullptr; +} + KleeneValue StyleCascade::EvalIfStyleFeature( const MediaQueryFeatureExpNode& feature, const TreeScope* tree_scope, @@ -2328,10 +2422,41 @@ bool& is_attr_tainted) { const MediaQueryExpBounds& bounds = feature.Bounds(); - if (feature.HasStyleRange() || bounds.IsRange()) { - // TODO(crbug.com/408011559): Add support for container style queries - // ranges. - return KleeneValue::kFalse; + if (bounds.IsRange()) { + DCHECK(RuntimeEnabledFeatures::CSSContainerStyleQueriesRangeEnabled()); + DCHECK(feature.HasStyleRange()); + KleeneValue result = KleeneValue::kTrue; + const CSSValue* reference = + CoerceIntoNumericValue(feature.ReferenceValue(), tree_scope, resolver, + context, function_context); + if (!reference) { + return KleeneValue::kFalse; + } + if (bounds.left.IsValid()) { + const auto& left = + To<CSSUnparsedDeclarationValue>(bounds.left.value.GetCSSValue()); + const CSSValue* left_resolved = CoerceIntoNumericValue( + left, tree_scope, resolver, context, function_context); + if (!left_resolved) { + return KleeneValue::kFalse; + } + result = KleeneAnd( + result, MediaQueryEvaluator::EvalIfRange(*reference, *left_resolved, + bounds.left.op, true)); + } + if (bounds.right.IsValid()) { + const auto& right = + To<CSSUnparsedDeclarationValue>(bounds.right.value.GetCSSValue()); + const CSSValue* right_resolved = CoerceIntoNumericValue( + right, tree_scope, resolver, context, function_context); + if (!right_resolved) { + return KleeneValue::kFalse; + } + result = KleeneAnd( + result, MediaQueryEvaluator::EvalIfRange(*reference, *right_resolved, + bounds.right.op, false)); + } + return result; } DCHECK(bounds.right.op == MediaQueryOperator::kNone);
diff --git a/third_party/blink/renderer/core/css/resolver/style_cascade.h b/third_party/blink/renderer/core/css/resolver/style_cascade.h index fe29719..727b04e 100644 --- a/third_party/blink/renderer/core/css/resolver/style_cascade.h +++ b/third_party/blink/renderer/core/css/resolver/style_cascade.h
@@ -523,6 +523,11 @@ const CSSParserContext&, FunctionContext*); + const CSSValue* CoerceIntoNumericValue(const CSSUnparsedDeclarationValue&, + const TreeScope*, + CascadeResolver&, + const CSSParserContext&, + FunctionContext*); KleeneValue EvalIfTest(const IfCondition& node, const TreeScope* tree_scope, CascadeResolver& resolver,
diff --git a/third_party/blink/renderer/core/css/rule_set.cc b/third_party/blink/renderer/core/css/rule_set.cc index acb67fb..6cf3e861 100644 --- a/third_party/blink/renderer/core/css/rule_set.cc +++ b/third_party/blink/renderer/core/css/rule_set.cc
@@ -298,6 +298,7 @@ case CSSSelector::kPseudoPlaceholder: case CSSSelector::kPseudoFileSelectorButton: case CSSSelector::kPseudoDetailsContent: + case CSSSelector::kPseudoPermissionIcon: case CSSSelector::kPseudoPicker: case CSSSelector::kPseudoWebKitCustomElement: case CSSSelector::kPseudoBlinkInternalElement: @@ -358,6 +359,7 @@ case CSSSelector::kPseudoFocusVisible: case CSSSelector::kPseudoPlaceholder: case CSSSelector::kPseudoDetailsContent: + case CSSSelector::kPseudoPermissionIcon: case CSSSelector::kPseudoFileSelectorButton: case CSSSelector::kPseudoHost: case CSSSelector::kPseudoHostContext:
diff --git a/third_party/blink/renderer/core/css/selector_checker.cc b/third_party/blink/renderer/core/css/selector_checker.cc index ddcd99a..da0e0a7 100644 --- a/third_party/blink/renderer/core/css/selector_checker.cc +++ b/third_party/blink/renderer/core/css/selector_checker.cc
@@ -2568,6 +2568,9 @@ case CSSSelector::kPseudoDetailsContent: return MatchesUAShadowElement(element, shadow_element_names::kIdDetailsContent); + case CSSSelector::kPseudoPermissionIcon: + return MatchesUAShadowElement(element, + shadow_element_names::kIdPermissionIcon); case CSSSelector::kPseudoWebKitCustomElement: return MatchesUAShadowElement(element, selector.Value()); case CSSSelector::kPseudoBlinkInternalElement:
diff --git a/third_party/blink/renderer/core/dom/element.cc b/third_party/blink/renderer/core/dom/element.cc index 23a07e44..f7f8c07f 100644 --- a/third_party/blink/renderer/core/dom/element.cc +++ b/third_party/blink/renderer/core/dom/element.cc
@@ -8420,6 +8420,7 @@ DCHECK(type == CSSSelector::kPseudoWebKitCustomElement || type == CSSSelector::kPseudoBlinkInternalElement || type == CSSSelector::kPseudoDetailsContent || + type == CSSSelector::kPseudoPermissionIcon || id == shadow_element_names::kPickerSelect) << "type: " << type << ", id: " << id; }
diff --git a/third_party/blink/renderer/core/html/build.gni b/third_party/blink/renderer/core/html/build.gni index dc1c04a3..5fc5aa7 100644 --- a/third_party/blink/renderer/core/html/build.gni +++ b/third_party/blink/renderer/core/html/build.gni
@@ -371,6 +371,8 @@ "html_param_element.h", "html_permission_element.cc", "html_permission_element.h", + "html_permission_icon_element.cc", + "html_permission_icon_element.h", "html_permission_element_strings_map.h", "html_picture_element.cc", "html_picture_element.h",
diff --git a/third_party/blink/renderer/core/html/canvas/canvas_rendering_context_host.cc b/third_party/blink/renderer/core/html/canvas/canvas_rendering_context_host.cc index 5e399256..814e71c 100644 --- a/third_party/blink/renderer/core/html/canvas/canvas_rendering_context_host.cc +++ b/third_party/blink/renderer/core/html/canvas/canvas_rendering_context_host.cc
@@ -235,9 +235,6 @@ : !!dispatcher; if (!provider && use_software_shared_image_provider) { - CHECK(format == viz::SharedImageFormat::N32Format() || - format == viz::SinglePlaneFormat::kRGBA_F16); - provider = CanvasResourceProvider::CreateSharedImageProviderForSoftwareCompositor( Size(), format, alpha_type, color_space, kShouldInitialize, @@ -333,8 +330,6 @@ : !!dispatcher; if (!provider && use_software_shared_image_provider) { - CHECK(format == viz::SharedImageFormat::N32Format() || - format == viz::SinglePlaneFormat::kRGBA_F16); // In this case, we are using CPU raster and CPU compositing. Create a // CanvasResourceProvider that uses a SharedImage backed by a shared-memory // buffer that can be written by canvas raster and read by the compositor.
diff --git a/third_party/blink/renderer/core/html/html_permission_element.cc b/third_party/blink/renderer/core/html/html_permission_element.cc index 6d0efa4e..3e0a29d8 100644 --- a/third_party/blink/renderer/core/html/html_permission_element.cc +++ b/third_party/blink/renderer/core/html/html_permission_element.cc
@@ -450,6 +450,7 @@ visitor->Trace(permission_service_); visitor->Trace(embedded_permission_control_receiver_); visitor->Trace(permission_text_span_); + visitor->Trace(permission_internal_icon_); visitor->Trace(intersection_observer_); visitor->Trace(disable_reason_expire_timer_); HTMLElement::Trace(visitor); @@ -783,6 +784,12 @@ } void HTMLPermissionElement::DidAddUserAgentShadowRoot(ShadowRoot& root) { + if (RuntimeEnabledFeatures::PermissionElementIconEnabled( + GetDocument().GetExecutionContext())) { + permission_internal_icon_ = + MakeGarbageCollected<HTMLPermissionIconElement>(GetDocument()); + root.AppendChild(permission_internal_icon_); + } permission_text_span_ = MakeGarbageCollected<HTMLSpanElement>(GetDocument()); permission_text_span_->SetShadowPseudoId( shadow_element_names::kPseudoInternalPermissionTextSpan); @@ -1398,7 +1405,16 @@ permission_name = permission_status_map_.begin()->key; permission_count = permission_status_map_.size(); } - + if (RuntimeEnabledFeatures::PermissionElementIconEnabled( + GetDocument().GetExecutionContext())) { + GetTaskRunner()->PostTask( + FROM_HERE, + WTF::BindOnce(&HTMLPermissionIconElement::SetIcon, + WrapWeakPersistent(permission_internal_icon_.Get()), + permission_count == 1 ? permission_name + : PermissionName::VIDEO_CAPTURE, + is_precise_location_)); + } AtomicString language_string = ComputeInheritedLanguage().LowerASCII(); uint16_t untranslated_message_id = @@ -1727,7 +1743,10 @@ UserAgentShadowRoot()->AppendChild( MakeGarbageCollected<HTMLSlotElement>(GetDocument())); UserAgentShadowRoot()->RemoveChild(permission_text_span_); - + if (RuntimeEnabledFeatures::PermissionElementIconEnabled( + GetDocument().GetExecutionContext())) { + UserAgentShadowRoot()->RemoveChild(permission_internal_icon_); + } MaybeDispatchValidationChangeEvent(); }
diff --git a/third_party/blink/renderer/core/html/html_permission_element.h b/third_party/blink/renderer/core/html/html_permission_element.h index 0f64c4f..7341cd1 100644 --- a/third_party/blink/renderer/core/html/html_permission_element.h +++ b/third_party/blink/renderer/core/html/html_permission_element.h
@@ -18,6 +18,7 @@ #include "third_party/blink/renderer/core/frame/cached_permission_status.h" #include "third_party/blink/renderer/core/frame/local_frame_view.h" #include "third_party/blink/renderer/core/html/html_element.h" +#include "third_party/blink/renderer/core/html/html_permission_icon_element.h" #include "third_party/blink/renderer/core/intersection_observer/intersection_observer.h" #include "third_party/blink/renderer/core/scroll/scroll_snapshot_client.h" #include "third_party/blink/renderer/platform/heap/collection_support/heap_vector.h" @@ -535,6 +536,7 @@ HashMap<DisableReason, base::TimeTicks> clicking_disabled_reasons_; Member<HTMLSpanElement> permission_text_span_; + Member<HTMLPermissionIconElement> permission_internal_icon_; Member<IntersectionObserver> intersection_observer_; // Keeps track of the time a request was created.
diff --git a/third_party/blink/renderer/core/html/html_permission_icon_element.cc b/third_party/blink/renderer/core/html/html_permission_icon_element.cc new file mode 100644 index 0000000..91673d5 --- /dev/null +++ b/third_party/blink/renderer/core/html/html_permission_icon_element.cc
@@ -0,0 +1,45 @@ +// Copyright 2025 The Chromium Authors +// 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/html/html_permission_icon_element.h" + +#include "third_party/blink/public/resources/grit/blink_resources.h" +#include "third_party/blink/renderer/core/html/shadow/shadow_element_names.h" +#include "third_party/blink/renderer/platform/data_resource_helper.h" + +namespace blink { + +using mojom::blink::PermissionName; + +HTMLPermissionIconElement::HTMLPermissionIconElement(Document& document) + : HTMLSpanElement(document) { + SetIdAttribute(shadow_element_names::kIdPermissionIcon); + SetShadowPseudoId(shadow_element_names::kIdPermissionIcon); +} + +void HTMLPermissionIconElement::SetIcon(PermissionName permission_type, + bool is_precise_location) { + if (is_icon_set_) { + return; + } + switch (permission_type) { + case PermissionName::GEOLOCATION: + setInnerHTML(UncompressResourceAsASCIIString( + is_precise_location ? IDR_PERMISSION_ICON_LOCATION_PRECISE_SVG + : IDR_PERMISSION_ICON_LOCATION_SVG)); + break; + case PermissionName::VIDEO_CAPTURE: + setInnerHTML(String( + UncompressResourceAsASCIIString(IDR_PERMISSION_ICON_CAMERA_SVG))); + break; + case PermissionName::AUDIO_CAPTURE: + setInnerHTML( + UncompressResourceAsASCIIString(IDR_PERMISSION_ICON_MICROPHONE_SVG)); + break; + default: + return; + } + is_icon_set_ = true; +} +} // namespace blink
diff --git a/third_party/blink/renderer/core/html/html_permission_icon_element.h b/third_party/blink/renderer/core/html/html_permission_icon_element.h new file mode 100644 index 0000000..f7f392a --- /dev/null +++ b/third_party/blink/renderer/core/html/html_permission_icon_element.h
@@ -0,0 +1,29 @@ +// Copyright 2025 The Chromium Authors +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef THIRD_PARTY_BLINK_RENDERER_CORE_HTML_HTML_PERMISSION_ICON_ELEMENT_H_ +#define THIRD_PARTY_BLINK_RENDERER_CORE_HTML_HTML_PERMISSION_ICON_ELEMENT_H_ + +#include "third_party/blink/public/mojom/permissions/permission.mojom-blink.h" +#include "third_party/blink/renderer/core/html/html_span_element.h" + +namespace blink { +// Internal element for the Permission element. This element holds the icon +// of the permission element. +class HTMLPermissionIconElement final : public HTMLSpanElement { + public: + explicit HTMLPermissionIconElement(Document&); + + void SetIcon(mojom::blink::PermissionName permission_type, + bool is_precise_location); + + private: + // Guard used to prevent re-setting the icon on the permission element. The + // state of the element can change, and the text changes with it, but the icon + // is always the same. There is no need to set it again. + bool is_icon_set_ = false; +}; +} // namespace blink + +#endif // THIRD_PARTY_BLINK_RENDERER_CORE_HTML_HTML_PERMISSION_ICON_ELEMENT_H_
diff --git a/third_party/blink/renderer/core/html/resources/images/permission_icon_camera.svg b/third_party/blink/renderer/core/html/resources/images/permission_icon_camera.svg new file mode 100644 index 0000000..e0418a7 --- /dev/null +++ b/third_party/blink/renderer/core/html/resources/images/permission_icon_camera.svg
@@ -0,0 +1,3 @@ +<svg xmlns="http://www.w3.org/2000/svg" height="100%" viewBox="0 -960 960 960" width="100%"> + <path d="M160-160q-33 0-56.5-23.5T80-240v-480q0-33 23.5-56.5T160-800h480q33 0 56.5 23.5T720-720v180l160-160v440L720-420v180q0 33-23.5 56.5T640-160H160Zm0-80h480v-480H160v480Zm0 0v-480 480Z"/> +</svg>
diff --git a/third_party/blink/renderer/core/html/resources/images/permission_icon_location.svg b/third_party/blink/renderer/core/html/resources/images/permission_icon_location.svg new file mode 100644 index 0000000..a43bb56 --- /dev/null +++ b/third_party/blink/renderer/core/html/resources/images/permission_icon_location.svg
@@ -0,0 +1,3 @@ +<svg xmlns="http://www.w3.org/2000/svg" height="100%" viewBox="0 -960 960 960" width="100%"> + <path d="M480-480q33 0 56.5-23.5T560-560q0-33-23.5-56.5T480-640q-33 0-56.5 23.5T400-560q0 33 23.5 56.5T480-480Zm0 294q122-112 181-203.5T720-552q0-109-69.5-178.5T480-800q-101 0-170.5 69.5T240-552q0 71 59 162.5T480-186Zm0 106Q319-217 239.5-334.5T160-552q0-150 96.5-239T480-880q127 0 223.5 89T800-552q0 100-79.5 217.5T480-80Zm0-480Z"/> +</svg>
diff --git a/third_party/blink/renderer/core/html/resources/images/permission_icon_location_precise.svg b/third_party/blink/renderer/core/html/resources/images/permission_icon_location_precise.svg new file mode 100644 index 0000000..15123c9 --- /dev/null +++ b/third_party/blink/renderer/core/html/resources/images/permission_icon_location_precise.svg
@@ -0,0 +1,3 @@ +<svg xmlns="http://www.w3.org/2000/svg" height="100%" viewBox="0 -960 960 960" width="100%"> + <path d="M440-42v-80q-125-14-214.5-103.5T122-440H42v-80h80q14-125 103.5-214.5T440-838v-80h80v80q125 14 214.5 103.5T838-520h80v80h-80q-14 125-103.5 214.5T520-122v80h-80Zm40-158q116 0 198-82t82-198q0-116-82-198t-198-82q-116 0-198 82t-82 198q0 116 82 198t198 82Zm0-120q-66 0-113-47t-47-113q0-66 47-113t113-47q66 0 113 47t47 113q0 66-47 113t-113 47Zm0-80q33 0 56.5-23.5T560-480q0-33-23.5-56.5T480-560q-33 0-56.5 23.5T400-480q0 33 23.5 56.5T480-400Zm0-80Z"/> +</svg>
diff --git a/third_party/blink/renderer/core/html/resources/images/permission_icon_microphone.svg b/third_party/blink/renderer/core/html/resources/images/permission_icon_microphone.svg new file mode 100644 index 0000000..1ff62b7f --- /dev/null +++ b/third_party/blink/renderer/core/html/resources/images/permission_icon_microphone.svg
@@ -0,0 +1,3 @@ +<svg xmlns="http://www.w3.org/2000/svg" height="100%" viewBox="0 -960 960 960" width="100%"> + <path d="M480-400q-50 0-85-35t-35-85v-240q0-50 35-85t85-35q50 0 85 35t35 85v240q0 50-35 85t-85 35Zm0-240Zm-40 520v-123q-104-14-172-93t-68-184h80q0 83 58.5 141.5T480-320q83 0 141.5-58.5T680-520h80q0 105-68 184t-172 93v123h-80Zm40-360q17 0 28.5-11.5T520-520v-240q0-17-11.5-28.5T480-800q-17 0-28.5 11.5T440-760v240q0 17 11.5 28.5T480-480Z"/> +</svg>
diff --git a/third_party/blink/renderer/core/html/resources/permission.css b/third_party/blink/renderer/core/html/resources/permission.css index 0094d0e..40c9121 100644 --- a/third_party/blink/renderer/core/html/resources/permission.css +++ b/third_party/blink/renderer/core/html/resources/permission.css
@@ -49,3 +49,11 @@ word-wrap: normal; word-spacing: inherit; } + +::permission-icon { + display: flex; + width: 1.3em; + height: 1.3em; + margin: auto; + float: inline-start; +}
diff --git a/third_party/blink/renderer/core/html/shadow/shadow_element_names.json5 b/third_party/blink/renderer/core/html/shadow/shadow_element_names.json5 index dcd6864..3b14b04 100644 --- a/third_party/blink/renderer/core/html/shadow/shadow_element_names.json5 +++ b/third_party/blink/renderer/core/html/shadow/shadow_element_names.json5
@@ -18,6 +18,10 @@ Symbol: "kIdDetailsContent", }, { + name: "permission-icon", + Symbol: "kIdPermissionIcon", + }, + { name: "details-summary", Symbol: "kIdDetailsSummary", },
diff --git a/third_party/blink/renderer/core/html/shadow/shadow_element_utils.cc b/third_party/blink/renderer/core/html/shadow/shadow_element_utils.cc index 1870bdb..7032dd6 100644 --- a/third_party/blink/renderer/core/html/shadow/shadow_element_utils.cc +++ b/third_party/blink/renderer/core/html/shadow/shadow_element_utils.cc
@@ -57,6 +57,8 @@ return shadow_element_names::kPseudoFileUploadButton; case kPseudoIdDetailsContent: return shadow_element_names::kIdDetailsContent; + case kPseudoIdPermissionIcon: + return shadow_element_names::kIdPermissionIcon; case kPseudoIdPickerSelect: return shadow_element_names::kPickerSelect; default:
diff --git a/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc b/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc index 5c0f702..3f696f2 100644 --- a/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc +++ b/third_party/blink/renderer/core/inspector/inspector_dom_agent.cc
@@ -270,6 +270,8 @@ return protocol::DOM::PseudoTypeEnum::FileSelectorButton; case kPseudoIdDetailsContent: return protocol::DOM::PseudoTypeEnum::DetailsContent; + case kPseudoIdPermissionIcon: + return protocol::DOM::PseudoTypeEnum::PermissionIcon; case kPseudoIdPickerSelect: return protocol::DOM::PseudoTypeEnum::Picker; case kPseudoIdViewTransition: @@ -393,6 +395,9 @@ if (type == protocol::DOM::PseudoTypeEnum::DetailsContent) { return kPseudoIdDetailsContent; } + if (type == protocol::DOM::PseudoTypeEnum::PermissionIcon) { + return kPseudoIdPermissionIcon; + } if (type == protocol::DOM::PseudoTypeEnum::Picker) { return kPseudoIdPickerSelect; }
diff --git a/third_party/blink/renderer/core/style/computed_style_constants.h b/third_party/blink/renderer/core/style/computed_style_constants.h index a496633..afabc9b 100644 --- a/third_party/blink/renderer/core/style/computed_style_constants.h +++ b/third_party/blink/renderer/core/style/computed_style_constants.h
@@ -107,6 +107,7 @@ kPseudoIdFileSelectorButton, kPseudoIdDetailsContent, kPseudoIdPickerSelect, + kPseudoIdPermissionIcon, // Special values follow: kAfterLastInternalPseudoId, kPseudoIdInvalid,
diff --git a/third_party/blink/renderer/modules/accessibility/blink_ax_tree_source.cc b/third_party/blink/renderer/modules/accessibility/blink_ax_tree_source.cc index a1124a53..3b54f1d 100644 --- a/third_party/blink/renderer/modules/accessibility/blink_ax_tree_source.cc +++ b/third_party/blink/renderer/modules/accessibility/blink_ax_tree_source.cc
@@ -241,18 +241,15 @@ // The child may be invalid due to issues in blink accessibility code. CHECK(child); if (child->IsDetached()) { - NOTREACHED(base::NotFatalUntil::M127) - << "Should not try to serialize an invalid child:" << "\nParent: " - << node->ToString().Utf8() << "\nChild: " << child->ToString().Utf8(); - return nullptr; + NOTREACHED() << "Should not try to serialize an invalid child:" + << "\nParent: " << node->ToString().Utf8() + << "\nChild: " << child->ToString().Utf8(); } if (!child->IsIncludedInTree()) { - NOTREACHED(base::NotFatalUntil::M127) - << "Should not receive unincluded child." - << "\nChild: " << child->ToString().Utf8() - << "\nParent: " << node->ToString().Utf8(); - return nullptr; + NOTREACHED() << "Should not receive unincluded child." + << "\nChild: " << child->ToString().Utf8() + << "\nParent: " << node->ToString().Utf8(); } // These should not be produced by Blink. They are only needed on Mac and
diff --git a/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_test.cc b/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_test.cc index 64409da..34ea6e9 100644 --- a/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_test.cc +++ b/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_test.cc
@@ -225,7 +225,7 @@ const bool context_alpha = GetParam().alpha; auto canvas_resource = CanvasResourceSharedImage::CreateSoftware( - offscreen_canvas().Size(), viz::SinglePlaneFormat::kRGBA_8888, + offscreen_canvas().Size(), viz::SinglePlaneFormat::kBGRA_8888, kPremul_SkAlphaType, gfx::ColorSpace::CreateSRGB(), /*provider=*/nullptr, shared_image_interface_provider()); EXPECT_TRUE(!!canvas_resource); @@ -251,7 +251,7 @@ platform->RunUntilIdle(); auto canvas_resource2 = CanvasResourceSharedImage::CreateSoftware( - offscreen_canvas().Size(), viz::SinglePlaneFormat::kRGBA_8888, + offscreen_canvas().Size(), viz::SinglePlaneFormat::kBGRA_8888, kPremul_SkAlphaType, gfx::ColorSpace::CreateSRGB(), /*provider=*/nullptr, shared_image_interface_provider()); EXPECT_CALL(mock_embedded_frame_sink_provider.mock_compositor_frame_sink(),
diff --git a/third_party/blink/renderer/modules/credentialmanagement/identity_provider.cc b/third_party/blink/renderer/modules/credentialmanagement/identity_provider.cc index 7b941ca6..fb34a32 100644 --- a/third_party/blink/renderer/modules/credentialmanagement/identity_provider.cc +++ b/third_party/blink/renderer/modules/credentialmanagement/identity_provider.cc
@@ -164,7 +164,13 @@ "User declined the permission to register the identity provider.")); return; } - }; + case RegisterIdpStatus::kErrorInvalidConfig: { + resolver->Reject(MakeGarbageCollected<DOMException>( + DOMExceptionCode::kNotAllowedError, + "Invalid identity provider registration config.")); + return; + } + } } ScriptPromise<IDLBoolean> IdentityProvider::registerIdentityProvider(
diff --git a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl b/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl index ac76ded..899056c 100644 --- a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl +++ b/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl
@@ -8,6 +8,12 @@ ActiveScriptWrappable, Exposed=(Window,Worker), RuntimeEnabled=WebGLOnWebGPU -] interface WebGL2RenderingContextWebGPU { }; +] interface WebGL2RenderingContextWebGPU { + // TODO(https://issues.chromium.org/413078308): Asynchronous initialization + // is needed because it is not possible to synchronously wait for WebGPU + // requestAdapter/Device in the renderer process. Once this capability is + // added, the initAsync should be removed. + [CallWith=ScriptState] Promise<undefined> initAsync(); +}; WebGL2RenderingContextWebGPU includes WebGLRenderingContextBase; WebGL2RenderingContextWebGPU includes WebGL2RenderingContextBase;
diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl index 2f4c23c..88fde368 100644 --- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl +++ b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl
@@ -12,5 +12,10 @@ [RuntimeEnabled=WebGLDrawingBufferStorage] const GLenum RGB8 = 0x8051; [RuntimeEnabled=WebGLDrawingBufferStorage] const GLenum RGBA8 = 0x8058; + // TODO(https://issues.chromium.org/413078308): Asynchronous initialization + // is needed because it is not possible to synchronously wait for WebGPU + // requestAdapter/Device in the renderer process. Once this capability is + // added, the initAsync should be removed. + [CallWith=ScriptState] Promise<undefined> initAsync(); }; WebGLRenderingContextWebGPU includes WebGLRenderingContextBase;
diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.cc b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.cc index 8d6c118..a323216 100644 --- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.cc +++ b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.cc
@@ -1,10 +1,19 @@ -// Copyright 2025 The Chromium Authors -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. +// Copyright 2025 The Chromium Authors 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/modules/webgl/webgl_rendering_context_webgpu_base.h" #include "base/notimplemented.h" +#include "third_party/blink/public/platform/web_url.h" +#include "third_party/blink/renderer/core/execution_context/execution_context.h" +#include "third_party/blink/renderer/core/frame/local_dom_window.h" +#include "third_party/blink/renderer/platform/graphics/gpu/dawn_control_client_holder.h" +#include "third_party/blink/renderer/platform/graphics/gpu/webgpu_callback.h" +#include "third_party/blink/renderer/platform/graphics/skia/skia_utils.h" +#include "third_party/blink/renderer/platform/graphics/web_graphics_context_3d_provider_util.h" +#include "third_party/blink/renderer/platform/weborigin/kurl.h" +#include "third_party/blink/renderer/platform/wtf/functional.h" +#include "third_party/blink/renderer/platform/wtf/text/wtf_string.h" namespace blink { @@ -19,6 +28,122 @@ WebGLRenderingContextWebGPUBase::~WebGLRenderingContextWebGPUBase() {} +ScriptPromise<IDLUndefined> WebGLRenderingContextWebGPUBase::initAsync( + ScriptState* script_state) { + auto* resolver = + MakeGarbageCollected<ScriptPromiseResolver<IDLUndefined>>(script_state); + auto promise = resolver->Promise(); + + // Synchronously connect to the GPU process to use WebGPU. + ExecutionContext* execution_context = ExecutionContext::From(script_state); + std::unique_ptr<WebGraphicsContext3DProvider> context_provider = + Platform::Current()->CreateWebGPUGraphicsContext3DProvider( + execution_context->Url()); + + if (context_provider == nullptr) { + resolver->RejectWithDOMException( + DOMExceptionCode::kOperationError, + "Failed to create a WebGPU context provider"); + return promise; + } + + // The context provider requires being bound on a single thread because it was + // initially designed only for GL. + context_provider->BindToCurrentSequence(); + // Send the execution token to the GPU process, it won't return devices until + // it receives it. + context_provider->WebGPUInterface()->SetWebGPUExecutionContextToken( + To<LocalDOMWindow>(execution_context)->document()->Token()); + + // Create the wgpu::Instance (as part of the DawnControlClientHolder). + dawn_control_client_ = DawnControlClientHolder::Create( + std::move(context_provider), + execution_context->GetTaskRunner(TaskType::kWebGPU)); + + // Request the adapter, making it resolve the result promise when it is done. + auto* callback = + MakeWGPUOnceCallback(resolver->WrapCallbackInScriptScope(WTF::BindOnce( + &WebGLRenderingContextWebGPUBase::InitRequestAdapterCallback, + WrapPersistent(this), WrapPersistent(script_state)))); + + dawn_control_client_->GetWGPUInstance().RequestAdapter( + nullptr, wgpu::CallbackMode::AllowSpontaneous, + callback->UnboundCallback(), callback->AsUserdata()); + dawn_control_client_->EnsureFlush(ToEventLoop(script_state)); + + return promise; +} + +void WebGLRenderingContextWebGPUBase::InitRequestAdapterCallback( + ScriptState* script_state, + ScriptPromiseResolver<IDLUndefined>* resolver, + wgpu::RequestAdapterStatus status, + wgpu::Adapter adapter, + wgpu::StringView error_message) { + if (status != wgpu::RequestAdapterStatus::Success) { + resolver->RejectWithDOMException( + DOMExceptionCode::kOperationError, + WTF::String::FromUTF8WithLatin1Fallback(error_message)); + return; + } + + adapter_ = std::move(adapter); + + // Request the device. + auto* callback = MakeWGPUOnceCallback( + WTF::BindOnce(&WebGLRenderingContextWebGPUBase::InitRequestDeviceCallback, + WrapPersistent(this), WrapPersistent(script_state), + WrapPersistent(resolver))); + + adapter_.RequestDevice(nullptr, wgpu::CallbackMode::AllowSpontaneous, + callback->UnboundCallback(), callback->AsUserdata()); + dawn_control_client_->EnsureFlush(ToEventLoop(script_state)); +} + +void WebGLRenderingContextWebGPUBase::InitRequestDeviceCallback( + ScriptState* script_state, + ScriptPromiseResolver<IDLUndefined>* resolver, + wgpu::RequestDeviceStatus status, + wgpu::Device device, + wgpu::StringView error_message) { + if (status != wgpu::RequestDeviceStatus::Success) { + resolver->RejectWithDOMException( + DOMExceptionCode::kOperationError, + WTF::String::FromUTF8WithLatin1Fallback(error_message)); + return; + } + + device_ = std::move(device); + + // TODO(413078308): Fill in with a GLES2Interface that will be used by WebGL + // objects. + WebGLContextObjectSupport::OnContextRestored(nullptr); + + // Create the underlying WebGPUSwapBufferProvider. + constexpr wgpu::TextureUsage kDefaultFBOUsages = + wgpu::TextureUsage::RenderAttachment | wgpu::TextureUsage::CopySrc | + wgpu::TextureUsage::CopySrc; +#if BUILDFLAG(IS_ANDROID) + constexpr wgpu::TextureFormat kDefaultFBON32Format = + wgpu::TextureFormat::RGBA8Unorm; +#else + constexpr wgpu::TextureFormat kDefaultFBON32Format = + wgpu::TextureFormat::BGRA8Unorm; +#endif + + // TODO(413078308): Add support for non-SRGB color spaces and HDR metadata. + // TODO(413078308): Add support for RGBA16Float drawing buffer. + swap_buffers_ = base::AdoptRef(new WebGPUSwapBufferProvider( + this, dawn_control_client_, device_, kDefaultFBOUsages, + wgpu::TextureUsage::None, kDefaultFBON32Format, + PredefinedColorSpace::kSRGB, gfx::HDRMetadata{})); + + // We are required to present to the compositor on context creation. + ShouldPresentToCompositor(); + + resolver->Resolve(); +} + // **************************************************************************** // Start of WebGLRenderingContextBase's IDL methods // **************************************************************************** @@ -2381,24 +2506,34 @@ // Start of CanvasRenderingContext implementation // **************************************************************************** SkAlphaType WebGLRenderingContextWebGPUBase::GetAlphaType() const { - NOTIMPLEMENTED(); - return SkAlphaType::kUnknown_SkAlphaType; + // WebGL spec section 2.2 The Drawing Buffer + // + // If defined, the alpha channel is used by the HTML compositor to combine + // the color buffer with the rest of the page. + return CreationAttributes().alpha ? kPremul_SkAlphaType : kOpaque_SkAlphaType; } viz::SharedImageFormat WebGLRenderingContextWebGPUBase::GetSharedImageFormat() const { - NOTIMPLEMENTED(); - return {}; + // TODO(413078308): Add support for RGBA16Float drawing buffer. + if (swap_buffers_) { + return swap_buffers_->Format(); + } + return GetN32FormatForCanvas(); } gfx::ColorSpace WebGLRenderingContextWebGPUBase::GetColorSpace() const { - NOTIMPLEMENTED(); - return {}; + // TODO(413078308): Add support for non-SRGB color spaces. + return gfx::ColorSpace::CreateSRGB(); +} + +int WebGLRenderingContextWebGPUBase::ExternallyAllocatedBufferCountPerPixel() { + // TODO(413078308): Add support configuring MSAA and depth-stencil. + return 2; } bool WebGLRenderingContextWebGPUBase::isContextLost() const { - NOTIMPLEMENTED(); - return false; + return IsLost(); } scoped_refptr<StaticBitmapImage> WebGLRenderingContextWebGPUBase::GetImage( @@ -2413,18 +2548,11 @@ } bool WebGLRenderingContextWebGPUBase::IsComposited() const { - NOTIMPLEMENTED(); - return false; + return true; } bool WebGLRenderingContextWebGPUBase::IsPaintable() const { - NOTIMPLEMENTED(); - return false; -} - -bool WebGLRenderingContextWebGPUBase::UsingSwapChain() const { - NOTIMPLEMENTED(); - return false; + return true; } void WebGLRenderingContextWebGPUBase::PageVisibilityChanged() { @@ -2448,10 +2576,16 @@ } cc::Layer* WebGLRenderingContextWebGPUBase::CcLayer() const { - NOTIMPLEMENTED(); + if (swap_buffers_) { + return swap_buffers_->CcLayer(); + } return nullptr; } +void WebGLRenderingContextWebGPUBase::Reshape(int width, int height) { + NOTIMPLEMENTED(); +} + void WebGLRenderingContextWebGPUBase::Stop() { NOTIMPLEMENTED(); } @@ -2469,8 +2603,47 @@ // End of CanvasRenderingContext implementation // **************************************************************************** +void WebGLRenderingContextWebGPUBase::OnTextureTransferred() { + current_swap_buffer_ = nullptr; +} + +void WebGLRenderingContextWebGPUBase::InitializeLayer(cc::Layer* layer) { + if (Host()) { + Host()->InitializeLayerWithCSSProperties(layer); + } +} + +void WebGLRenderingContextWebGPUBase::SetNeedsCompositingUpdate() { + if (Host()) { + Host()->SetNeedsCompositingUpdate(); + } +} + +bool WebGLRenderingContextWebGPUBase::IsGPUDeviceDestroyed() { + return IsLost(); +} + void WebGLRenderingContextWebGPUBase::Trace(Visitor* visitor) const { WebGLContextObjectSupport::Trace(visitor); CanvasRenderingContext::Trace(visitor); } + +void WebGLRenderingContextWebGPUBase::ShouldPresentToCompositor() { + if (current_swap_buffer_) { + return; + } + wgpu::TextureDescriptor texDesc; + texDesc.size.width = std::max(1, Host()->Size().width()); + texDesc.size.height = std::max(1, Host()->Size().height()); + texDesc.usage = swap_buffers_->TextureUsage(); + texDesc.format = swap_buffers_->TextureFormat(); + texDesc.dimension = wgpu::TextureDimension::e2D; + + scoped_refptr<WebGPUMailboxTexture> mailbox_texture = + swap_buffers_->GetNewTexture(texDesc, GetAlphaType()); + mailbox_texture->SetNeedsPresent(true); + + current_swap_buffer_ = mailbox_texture->GetTexture(); +} + } // namespace blink
diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h index 42470446..e20a746 100644 --- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h +++ b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h
@@ -12,6 +12,7 @@ #include "third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h" #include "third_party/blink/renderer/modules/webgl/webgl_context_object_support.h" #include "third_party/blink/renderer/platform/bindings/script_wrappable.h" +#include "third_party/blink/renderer/platform/graphics/gpu/webgpu_swap_buffer_provider.h" #include "third_party/blink/renderer/platform/wtf/text/wtf_string.h" namespace blink { @@ -42,7 +43,8 @@ class MODULES_EXPORT WebGLRenderingContextWebGPUBase : public WebGLContextObjectSupport, - public CanvasRenderingContext { + public CanvasRenderingContext, + public WebGPUSwapBufferProvider::Client { public: WebGLRenderingContextWebGPUBase( CanvasRenderingContextHost* host, @@ -55,6 +57,10 @@ WebGLRenderingContextWebGPUBase& operator=( const WebGLRenderingContextWebGPUBase&) = delete; + // Extra Web-exposed initAsync while until Dawn operations can be made + // blocking in the renderer process. + ScriptPromise<IDLUndefined> initAsync(ScriptState* script_state); + // ************************************************************************** // Start of WebGLRenderingContextBase's IDL methods // ************************************************************************** @@ -1251,13 +1257,13 @@ SkAlphaType GetAlphaType() const override; viz::SharedImageFormat GetSharedImageFormat() const override; gfx::ColorSpace GetColorSpace() const override; + int ExternallyAllocatedBufferCountPerPixel() override; bool isContextLost() const override; scoped_refptr<StaticBitmapImage> GetImage(FlushReason) override; void SetHdrMetadata(const gfx::HDRMetadata& hdr_metadata) override; bool IsComposited() const override; bool IsPaintable() const override; - bool UsingSwapChain() const override; void PageVisibilityChanged() override; CanvasResourceProvider* PaintRenderingResultsToCanvas( SourceDrawingBuffer) override; @@ -1268,6 +1274,7 @@ VideoFrameCopyCompletedCallback) override; cc::Layer* CcLayer() const override; + void Reshape(int width, int height) override; void Stop() override; void FinalizeFrame(FlushReason) override; bool PushFrame() override; @@ -1276,9 +1283,37 @@ // End of CanvasRenderingContext implementation // ************************************************************************** + // WebGPUSwapBufferProvider::Client implementation + void OnTextureTransferred() override; + void InitializeLayer(cc::Layer* layer) override; + void SetNeedsCompositingUpdate() override; + bool IsGPUDeviceDestroyed() override; + void Trace(Visitor*) const override; private: + void InitRequestAdapterCallback(ScriptState* script_state, + ScriptPromiseResolver<IDLUndefined>* resolver, + wgpu::RequestAdapterStatus status, + wgpu::Adapter adapter, + wgpu::StringView error_message); + void InitRequestDeviceCallback(ScriptState* script_state, + ScriptPromiseResolver<IDLUndefined>* resolver, + wgpu::RequestDeviceStatus status, + wgpu::Device device, + wgpu::StringView error_message); + + // Must be called when an operation happens that should cause the drawing + // buffer to be present to the compositor. See WebGL spec Section 2.2 The + // Drawing Buffer. + void ShouldPresentToCompositor(); + + scoped_refptr<DawnControlClientHolder> dawn_control_client_; + wgpu::Adapter adapter_; + wgpu::Device device_; + + scoped_refptr<WebGPUSwapBufferProvider> swap_buffers_; + wgpu::Texture current_swap_buffer_; }; } // namespace blink
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc b/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc index 8117f15..6e2ebb0 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc +++ b/third_party/blink/renderer/modules/webgpu/gpu_bind_group.cc
@@ -7,7 +7,7 @@ #include "third_party/blink/renderer/bindings/modules/v8/v8_gpu_bind_group_descriptor.h" #include "third_party/blink/renderer/bindings/modules/v8/v8_gpu_bind_group_entry.h" #include "third_party/blink/renderer/bindings/modules/v8/v8_gpu_buffer_binding.h" -#include "third_party/blink/renderer/bindings/modules/v8/v8_union_gpubufferbinding_gpuexternaltexture_gpusampler_gputextureview.h" +#include "third_party/blink/renderer/bindings/modules/v8/v8_union_gpubuffer_gpubufferbinding_gpuexternaltexture_gpusampler_gputextureview.h" #include "third_party/blink/renderer/modules/webgpu/dawn_conversions.h" #include "third_party/blink/renderer/modules/webgpu/gpu_bind_group_layout.h" #include "third_party/blink/renderer/modules/webgpu/gpu_buffer.h" @@ -28,6 +28,11 @@ }; switch (webgpu_binding->resource()->GetContentType()) { + case V8GPUBindingResource::ContentType::kGPUBuffer: { + GPUBuffer* buffer = webgpu_binding->resource()->GetAsGPUBuffer(); + dawn_binding.buffer = AsDawnType(buffer); + break; + } case V8GPUBindingResource::ContentType::kGPUBufferBinding: { GPUBufferBinding* buffer = webgpu_binding->resource()->GetAsGPUBufferBinding();
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_bind_group_entry.idl b/third_party/blink/renderer/modules/webgpu/gpu_bind_group_entry.idl index 75392081..41754ea 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_bind_group_entry.idl +++ b/third_party/blink/renderer/modules/webgpu/gpu_bind_group_entry.idl
@@ -4,7 +4,7 @@ // https://gpuweb.github.io/gpuweb/ -typedef (GPUSampler or GPUTextureView or GPUBufferBinding or GPUExternalTexture) GPUBindingResource; +typedef (GPUSampler or GPUTextureView or GPUBuffer or GPUBufferBinding or GPUExternalTexture) GPUBindingResource; dictionary GPUBindGroupEntry { required GPUIndex32 binding;
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.cc b/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.cc index 95d1929..081f55c 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.cc +++ b/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.cc
@@ -318,15 +318,14 @@ DCHECK(release_callback); auto format = client_si->format(); + auto size = client_si->size(); return MakeGarbageCollected<ImageBitmap>( AcceleratedStaticBitmapImage::CreateFromCanvasSharedImage( std::move(client_si), sk_image_sync_token, - /* shared_image_texture_id = */ 0, - gfx::Size(texture_descriptor_.size.width, - texture_descriptor_.size.height), - format, kPremul_SkAlphaType, gfx::ColorSpace::CreateSRGB(), - GetContextProviderWeakPtr(), base::PlatformThread::CurrentRef(), + /* shared_image_texture_id = */ 0, size, format, kPremul_SkAlphaType, + gfx::ColorSpace::CreateSRGB(), GetContextProviderWeakPtr(), + base::PlatformThread::CurrentRef(), ThreadScheduler::Current()->CleanupTaskRunner(), std::move(release_callback))); }
diff --git a/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.h b/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.h index af900ba..3334442 100644 --- a/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.h +++ b/third_party/blink/renderer/modules/webgpu/gpu_canvas_context.h
@@ -79,7 +79,6 @@ bool isContextLost() const override { return false; } bool IsComposited() const final { return true; } bool IsPaintable() const final { return true; } - int ExternallyAllocatedBufferCountPerPixel() final { return 1; } void Stop() final; cc::Layer* CcLayer() const final; void Reshape(int width, int height) override;
diff --git a/third_party/blink/renderer/modules/xr/xr_rigid_transform.cc b/third_party/blink/renderer/modules/xr/xr_rigid_transform.cc index 3bd0098c..4b9776c 100644 --- a/third_party/blink/renderer/modules/xr/xr_rigid_transform.cc +++ b/third_party/blink/renderer/modules/xr/xr_rigid_transform.cc
@@ -7,7 +7,6 @@ #include <cmath> #include <utility> -#include "base/not_fatal_until.h" #include "third_party/blink/renderer/bindings/core/v8/v8_dom_point_init.h" #include "third_party/blink/renderer/core/geometry/dom_point_read_only.h" #include "third_party/blink/renderer/modules/xr/xr_utils.h" @@ -35,8 +34,7 @@ void XRRigidTransform::DecomposeMatrix() { // decompose matrix to position and orientation std::optional<gfx::DecomposedTransform> decomp = matrix_->Decompose(); - CHECK(decomp, base::NotFatalUntil::M129) - << "Matrix decompose failed for " << matrix_->ToString(); + CHECK(decomp) << "Matrix decompose failed for " << matrix_->ToString(); position_ = DOMPointReadOnly::Create( decomp->translate[0], decomp->translate[1], decomp->translate[2], 1.0);
diff --git a/third_party/blink/renderer/platform/graphics/canvas_resource.cc b/third_party/blink/renderer/platform/graphics/canvas_resource.cc index 08137b3..ba73b75 100644 --- a/third_party/blink/renderer/platform/graphics/canvas_resource.cc +++ b/third_party/blink/renderer/platform/graphics/canvas_resource.cc
@@ -58,16 +58,12 @@ namespace blink { CanvasResource::CanvasResource(base::WeakPtr<CanvasResourceProvider> provider, - gfx::Size size, - viz::SharedImageFormat format, SkAlphaType alpha_type, const gfx::ColorSpace& color_space) : owning_thread_ref_(base::PlatformThread::CurrentRef()), owning_thread_task_runner_( ThreadScheduler::Current()->CleanupTaskRunner()), provider_(std::move(provider)), - size_(size), - format_(format), alpha_type_(alpha_type), color_space_(color_space) {} @@ -202,8 +198,10 @@ } SkImageInfo CanvasResource::CreateSkImageInfo() const { - return SkImageInfo::Make(SkISize::Make(size_.width(), size_.height()), - viz::ToClosestSkColorType(format_), alpha_type_, + auto size = GetClientSharedImage()->size(); + auto format = GetClientSharedImage()->format(); + return SkImageInfo::Make(SkISize::Make(size.width(), size.height()), + viz::ToClosestSkColorType(format), alpha_type_, color_space_.ToSkColorSpace()); } @@ -219,8 +217,6 @@ base::WeakPtr<WebGraphicsSharedImageInterfaceProvider> shared_image_interface_provider) : CanvasResource(std::move(provider), - size, - format, alpha_type, color_space), is_accelerated_(false), @@ -236,8 +232,7 @@ owning_thread_data().client_shared_image = shared_image_interface->CreateSharedImageForSoftwareCompositor( - {viz::SinglePlaneFormat::kBGRA_8888, size, color_space, - gpu::SHARED_IMAGE_USAGE_CPU_WRITE_ONLY, + {format, size, color_space, gpu::SHARED_IMAGE_USAGE_CPU_WRITE_ONLY, "CanvasResourceSharedImage"}); // This class doesn't currently have a way of verifying the sync token for @@ -274,8 +269,6 @@ bool is_accelerated, gpu::SharedImageUsageSet shared_image_usage_flags) : CanvasResource(std::move(provider), - size, - format, alpha_type, color_space), context_provider_wrapper_(std::move(context_provider_wrapper)), @@ -576,25 +569,20 @@ has_read_ref_on_texture); scoped_refptr<StaticBitmapImage> image; - auto client_shared_image = GetClientSharedImage(); + const auto& client_shared_image = GetClientSharedImage(); // If its cross thread, then the sync token was already verified. image = AcceleratedStaticBitmapImage::CreateFromCanvasSharedImage( - std::move(client_shared_image), GetSyncToken(), texture_id_for_image, - Size(), GetFormat(), GetAlphaType(), GetColorSpace(), - context_provider_wrapper_, owning_thread_ref_, owning_thread_task_runner_, + client_shared_image, GetSyncToken(), texture_id_for_image, + client_shared_image->size(), client_shared_image->format(), + GetAlphaType(), GetColorSpace(), context_provider_wrapper_, + owning_thread_ref_, owning_thread_task_runner_, std::move(release_callback)); DCHECK(image); return image; } -scoped_refptr<gpu::ClientSharedImage> -CanvasResourceSharedImage::GetClientSharedImage() { - CHECK(owning_thread_data_.client_shared_image); - return owning_thread_data_.client_shared_image; -} - const scoped_refptr<gpu::ClientSharedImage>& CanvasResourceSharedImage::GetClientSharedImage() const { CHECK(owning_thread_data_.client_shared_image); @@ -789,9 +777,9 @@ base::RetainedRef(this)); return AcceleratedStaticBitmapImage::CreateFromCanvasSharedImage( - client_si_, GetSyncToken(), /*shared_image_texture_id=*/0u, Size(), - GetFormat(), GetAlphaType(), GetColorSpace(), context_provider_wrapper_, - owning_thread_ref_, owning_thread_task_runner_, + client_si_, GetSyncToken(), /*shared_image_texture_id=*/0u, + client_si_->size(), client_si_->format(), GetAlphaType(), GetColorSpace(), + context_provider_wrapper_, owning_thread_ref_, owning_thread_task_runner_, std::move(release_callback)); } @@ -835,8 +823,6 @@ base::WeakPtr<WebGraphicsContext3DProviderWrapper> context_provider_wrapper, base::WeakPtr<CanvasResourceProvider> provider) : CanvasResource(std::move(provider), - client_si->size(), - client_si->format(), kPremul_SkAlphaType, client_si->color_space()), client_si_(std::move(client_si)), @@ -922,14 +908,15 @@ base::RetainedRef(this)); return AcceleratedStaticBitmapImage::CreateFromCanvasSharedImage( - back_buffer_shared_image_, GetSyncToken(), shared_texture_id, Size(), - GetFormat(), GetAlphaType(), GetColorSpace(), context_provider_wrapper_, + back_buffer_shared_image_, GetSyncToken(), shared_texture_id, + back_buffer_shared_image_->size(), back_buffer_shared_image_->format(), + GetAlphaType(), GetColorSpace(), context_provider_wrapper_, owning_thread_ref_, owning_thread_task_runner_, std::move(release_callback)); } -scoped_refptr<gpu::ClientSharedImage> -CanvasResourceSwapChain::GetClientSharedImage() { +const scoped_refptr<gpu::ClientSharedImage>& +CanvasResourceSwapChain::GetClientSharedImage() const { return front_buffer_shared_image_; } @@ -998,8 +985,6 @@ base::WeakPtr<WebGraphicsContext3DProviderWrapper> context_provider_wrapper, base::WeakPtr<CanvasResourceProvider> provider) : CanvasResource(std::move(provider), - size, - format, alpha_type, color_space), context_provider_wrapper_(std::move(context_provider_wrapper)),
diff --git a/third_party/blink/renderer/platform/graphics/canvas_resource.h b/third_party/blink/renderer/platform/graphics/canvas_resource.h index b0c43775..8065e68 100644 --- a/third_party/blink/renderer/platform/graphics/canvas_resource.h +++ b/third_party/blink/renderer/platform/graphics/canvas_resource.h
@@ -86,9 +86,7 @@ virtual bool IsValid() const = 0; // The bounds for this resource. - gfx::Size Size() const { return size_; } - - viz::SharedImageFormat GetFormat() const { return format_; } + gfx::Size Size() const { return GetClientSharedImage()->size(); } const gfx::ColorSpace& GetColorSpace() const { return color_space_; } @@ -96,7 +94,8 @@ // The ClientSharedImage containing information on the SharedImage // attached to the resource. - virtual scoped_refptr<gpu::ClientSharedImage> GetClientSharedImage() = 0; + virtual const scoped_refptr<gpu::ClientSharedImage>& GetClientSharedImage() + const = 0; // A CanvasResource is not thread-safe and does not allow concurrent usage // from multiple threads. But it maybe used from any thread. It remains bound @@ -146,8 +145,6 @@ protected: CanvasResource(base::WeakPtr<CanvasResourceProvider>, - gfx::Size size, - viz::SharedImageFormat format, SkAlphaType alpha_type, const gfx::ColorSpace& color_space); @@ -188,8 +185,6 @@ } base::WeakPtr<CanvasResourceProvider> provider_; - gfx::Size size_; - viz::SharedImageFormat format_; SkAlphaType alpha_type_; gfx::ColorSpace color_space_; bool is_origin_clean_ = true; @@ -240,8 +235,8 @@ void WillDraw(); bool IsLost() const { return owning_thread_data().is_lost; } - scoped_refptr<gpu::ClientSharedImage> GetClientSharedImage() override; - const scoped_refptr<gpu::ClientSharedImage>& GetClientSharedImage() const; + const scoped_refptr<gpu::ClientSharedImage>& GetClientSharedImage() + const override; void OnMemoryDump(base::trace_event::ProcessMemoryDump* pmd, const std::string& parent_path) const; @@ -351,7 +346,8 @@ bool IsValid() const override; bool CreatesAcceleratedTransferableResources() const override { return true; } void NotifyResourceLost() override { resource_is_lost_ = true; } - scoped_refptr<gpu::ClientSharedImage> GetClientSharedImage() final { + const scoped_refptr<gpu::ClientSharedImage>& GetClientSharedImage() + const final { return client_si_; } @@ -414,7 +410,8 @@ return back_buffer_shared_image_; } void PresentSwapChain(); - scoped_refptr<gpu::ClientSharedImage> GetClientSharedImage() override; + const scoped_refptr<gpu::ClientSharedImage>& GetClientSharedImage() + const override; private: bool UsesAcceleratedRaster() const final { return true; }
diff --git a/third_party/blink/renderer/platform/graphics/canvas_resource_dispatcher_test.cc b/third_party/blink/renderer/platform/graphics/canvas_resource_dispatcher_test.cc index 8977325..8532ba3 100644 --- a/third_party/blink/renderer/platform/graphics/canvas_resource_dispatcher_test.cc +++ b/third_party/blink/renderer/platform/graphics/canvas_resource_dispatcher_test.cc
@@ -383,7 +383,7 @@ platform->RunUntilIdle(); auto canvas_resource = CanvasResourceSharedImage::CreateSoftware( - GetSize(), viz::SinglePlaneFormat::kRGBA_8888, kPremul_SkAlphaType, + GetSize(), viz::SinglePlaneFormat::kBGRA_8888, kPremul_SkAlphaType, gfx::ColorSpace::CreateSRGB(), /*provider=*/nullptr, shared_image_interface_provider()); EXPECT_TRUE(!!canvas_resource);
diff --git a/third_party/blink/renderer/platform/graphics/canvas_resource_provider.cc b/third_party/blink/renderer/platform/graphics/canvas_resource_provider.cc index 5ae28c1..a49d161f 100644 --- a/third_party/blink/renderer/platform/graphics/canvas_resource_provider.cc +++ b/third_party/blink/renderer/platform/graphics/canvas_resource_provider.cc
@@ -414,16 +414,9 @@ TRACE_EVENT0("blink", "CanvasResourceProviderSharedImage::CreateResource"); if (is_software_) { - auto format = GetSharedImageFormat(); - if (!format.IsBitmapFormatSupported()) { - // If the rendering format is not supported, downgrade to 8-bits. - // TODO(junov): Should we try 12-12-12-12 and 10-10-10-2? - format = GetN32FormatForCanvas(); - } - return CanvasResourceSharedImage::CreateSoftware( - Size(), format, GetAlphaType(), GetColorSpace(), CreateWeakPtr(), - shared_image_interface_provider_); + Size(), viz::SinglePlaneFormat::kBGRA_8888, GetAlphaType(), + GetColorSpace(), CreateWeakPtr(), shared_image_interface_provider_); } if (IsGpuContextLost()) @@ -1276,6 +1269,9 @@ return nullptr; } + CHECK(format == viz::SharedImageFormat::N32Format() || + format == viz::SinglePlaneFormat::kRGBA_F16); + auto provider = std::make_unique<CanvasResourceProviderSharedImage>( size, format, alpha_type, color_space, shared_image_interface_provider, resource_host);
diff --git a/third_party/blink/renderer/platform/graphics/canvas_resource_test.cc b/third_party/blink/renderer/platform/graphics/canvas_resource_test.cc index ef1d85cc..163e19eb 100644 --- a/third_party/blink/renderer/platform/graphics/canvas_resource_test.cc +++ b/third_party/blink/renderer/platform/graphics/canvas_resource_test.cc
@@ -45,7 +45,7 @@ scoped_refptr<CanvasResource> canvas_resource = CanvasResourceSharedImage::CreateSoftware( - gfx::Size(10, 10), viz::SinglePlaneFormat::kRGBA_8888, + gfx::Size(10, 10), viz::SinglePlaneFormat::kBGRA_8888, kPremul_SkAlphaType, gfx::ColorSpace::CreateSRGB(), /*CanvasResourceProvider=*/nullptr, shared_image_interface_provider); EXPECT_TRUE(!!canvas_resource);
diff --git a/third_party/blink/renderer/platform/graphics/gpu/webgpu_swap_buffer_provider.h b/third_party/blink/renderer/platform/graphics/gpu/webgpu_swap_buffer_provider.h index 3c050d2..1ba4d14 100644 --- a/third_party/blink/renderer/platform/graphics/gpu/webgpu_swap_buffer_provider.h +++ b/third_party/blink/renderer/platform/graphics/gpu/webgpu_swap_buffer_provider.h
@@ -64,6 +64,7 @@ viz::SharedImageFormat Format() const; wgpu::TextureFormat TextureFormat() const { return format_; } + wgpu::TextureUsage TextureUsage() const { return usage_; } gfx::Size Size() const; cc::Layer* CcLayer(); void Neuter();
diff --git a/third_party/blink/renderer/platform/runtime_enabled_features.json5 b/third_party/blink/renderer/platform/runtime_enabled_features.json5 index 7044f4e0..a1ed4e1c 100644 --- a/third_party/blink/renderer/platform/runtime_enabled_features.json5 +++ b/third_party/blink/renderer/platform/runtime_enabled_features.json5
@@ -3607,6 +3607,8 @@ // The flag will enable us to land the feature over multiple CLs, and will // be enabled after the feature has been fully implemented. name: "PermissionElementIcon", + status: "test", + depends_on: ["PermissionElement"], }, { name: "Permissions",
diff --git a/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.cc b/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.cc index a8e195e..010beb4 100644 --- a/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.cc +++ b/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.cc
@@ -17,6 +17,7 @@ #include "base/task/single_thread_task_runner.h" #include "base/time/time.h" #include "base/trace_event/trace_event.h" +#include "third_party/blink/public/common/features.h" #include "third_party/blink/public/platform/platform.h" namespace blink { @@ -88,7 +89,9 @@ if (CanPurge()) { if (called_from == base::MemoryReductionTaskContext::kProactive) { PerformMemoryPurge(); - } else { + } else if (!did_purge_with_page_frozen_since_backgrounded_ || + !base::FeatureList::IsEnabled( + features::kMemoryPurgeOnFreezeLimit)) { RequestMemoryPurgeWithDelay(kFreezePurgeDelay); } } @@ -143,6 +146,7 @@ void MemoryPurgeManager::OnRendererForegrounded() { backgrounded_purge_pending_ = false; + did_purge_with_page_frozen_since_backgrounded_ = false; purge_timer_.Stop(); } @@ -171,6 +175,11 @@ base::android::PreFreezeBackgroundMemoryTrimmer::OnRunningCompact(); #endif } + + if (frozen_page_count_ > 0) { + did_purge_with_page_frozen_since_backgrounded_ = true; + } + backgrounded_purge_pending_ = false; }
diff --git a/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.h b/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.h index 4d9c657..228aa683 100644 --- a/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.h +++ b/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.h
@@ -137,6 +137,10 @@ int total_page_count_ = 0; int frozen_page_count_ = 0; + // Whether a memory purge was performed with at least one page frozen since + // the renderer was backgrounded. Reset when the renderer is foregrounded. + bool did_purge_with_page_frozen_since_backgrounded_ = false; + base::OneShotTimer purge_timer_; #if BUILDFLAG(IS_ANDROID)
diff --git a/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager_unittest.cc b/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager_unittest.cc index a5ce0aec..3e3f1a9 100644 --- a/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager_unittest.cc +++ b/third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager_unittest.cc
@@ -5,6 +5,7 @@ #include "third_party/blink/renderer/platform/scheduler/main_thread/memory_purge_manager.h" #include "base/memory/memory_pressure_listener.h" +#include "base/test/scoped_feature_list.h" #include "base/test/task_environment.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" @@ -253,6 +254,34 @@ EXPECT_EQ(0U, MemoryPressureCount()); } +TEST_F(MemoryPurgeManagerTest, MemoryPurgeOnFreezeLimitEnabled) { + base::test::ScopedFeatureList feature_list{ + features::kMemoryPurgeOnFreezeLimit}; + + memory_purge_manager_.SetPurgeDisabledForTesting(true); + memory_purge_manager_.SetRendererBackgrounded(true); + + // The initial freeze should trigger a memory purge. + memory_purge_manager_.OnPageCreated(); + memory_purge_manager_.OnPageFrozen(); + FastForwardBy(base::Seconds(1)); + EXPECT_EQ(1U, MemoryPressureCount()); + + // The second freeze should not trigger a memory purge. + memory_purge_manager_.OnPageResumed(); + memory_purge_manager_.OnPageFrozen(); + FastForwardBy(base::Seconds(1)); + EXPECT_EQ(1U, MemoryPressureCount()); + + // Another freeze after foregrounding the renderer triggers a memory purge. + memory_purge_manager_.SetRendererBackgrounded(false); + memory_purge_manager_.OnPageResumed(); + memory_purge_manager_.SetRendererBackgrounded(true); + memory_purge_manager_.OnPageFrozen(); + FastForwardBy(base::Seconds(1)); + EXPECT_EQ(2U, MemoryPressureCount()); +} + } // namespace } // namespace blink
diff --git a/third_party/blink/web_tests/TestExpectations b/third_party/blink/web_tests/TestExpectations index e403adf..b6c7737 100644 --- a/third_party/blink/web_tests/TestExpectations +++ b/third_party/blink/web_tests/TestExpectations
@@ -9418,3 +9418,6 @@ crbug.com/418345234 [ Win ] external/wpt/fetch/fetch-later/quota/max-payload.tentative.https.window.html [ Failure ] crbug.com/418572857 external/wpt/background-fetch/fetch.https.window.html [ Failure Pass Timeout ] crbug.com/418362694 [ Linux ] external/wpt/geolocation/enabled-by-permission-policy-attribute-redirect-on-load.https.sub.html [ Crash Timeout ] + +# Skipped due to feature implementation in progress +crbug.com/420393952 external/wpt/html/semantics/permission-element/quirks-mode-no-height-is-still-bounded.tentative.html [ Failure Skip ]
diff --git a/third_party/blink/web_tests/VirtualTestSuites b/third_party/blink/web_tests/VirtualTestSuites index 2cef160..54911f1 100644 --- a/third_party/blink/web_tests/VirtualTestSuites +++ b/third_party/blink/web_tests/VirtualTestSuites
@@ -4416,7 +4416,8 @@ "owners": ["moonira@google.com"], "platforms": ["Linux"], "bases": [ - "external/wpt/css/css-conditional/container-queries/" + "external/wpt/css/css-conditional/container-queries/", + "external/wpt/css/css-values/if-conditionals.html" ], "args": [ "--disable-features=CSSContainerStyleQueriesRange"
diff --git a/third_party/blink/web_tests/external/wpt/css/css-values/if-conditionals.html b/third_party/blink/web_tests/external/wpt/css/css-values/if-conditionals.html index caead78..f6d9817 100644 --- a/third_party/blink/web_tests/external/wpt/css/css-values/if-conditionals.html +++ b/third_party/blink/web_tests/external/wpt/css/css-values/if-conditionals.html
@@ -37,6 +37,21 @@ inherits: true; initial-value: 3; } + @property --angle { + syntax: "<angle>"; + inherits: true; + initial-value: 3deg; + } + @property --time { + syntax: "<time>"; + inherits: true; + initial-value: 3s; + } + @property --resolution { + syntax: "<resolution>"; + inherits: true; + initial-value: 3dpi; + } div { font-size: 30px; } @@ -511,6 +526,122 @@ [['--length', 'attr(data-foo type(<length>))']], 'false_value'); + // style() queries with range syntax in the condition, literals on both sides of equation + test_if_with_custom_properties('if(style(10em > 3px): true_value; else: false_value)', [], 'true_value'); + test_if_with_custom_properties('if(style(1em > 1px): true_value; else: false_value)', [], 'true_value'); + test_if_with_custom_properties('if(style(7px > 3px): true_value; else: false_value)', [], 'true_value'); + test_if_with_custom_properties('if(style(3px > 3px): true_value; else: false_value)', [], 'false_value'); + test_if_with_custom_properties('if(style(3turn > 3deg): true_value; else: false_value)', [], 'true_value'); + test_if_with_custom_properties('if(style(3turn <= 3deg): true_value; else: false_value)', [], 'false_value'); + test_if_with_custom_properties('if(style(3% >= 3%): true_value; else: false_value)', [], 'true_value'); + test_if_with_custom_properties('if(style(3s > 3ms): true_value; else: false_value)', [], 'true_value'); + test_if_with_custom_properties('if(style(3dppx > 96dpi): true_value; else: false_value)', [], 'true_value'); + + // style() queries with range syntax in the condition, simple custom properties in the condition + test_if_with_custom_properties('if(style(--x <= 3): true_value; else: false_value)', + [['--x', '3']], + 'true_value'); + test_if_with_custom_properties('if(style(--x >= --y): true_value; else: false_value)', + [['--x', '3'], ['--y', '3']], + 'true_value'); + test_if_with_custom_properties('if(style(--length > 3px): true_value; else: false_value)', + [['--length', '11px']], + 'true_value'); + test_if_with_custom_properties('if(style(--x > 3px): true_value; else: false_value)', + [['--x', '11px']], + 'true_value'); + test_if_with_custom_properties('if(style(--number >= 3): true_value; else: false_value)', + [['--number', '3']], + 'true_value'); + test_if_with_custom_properties('if(style(--x >= 3): true_value; else: false_value)', + [['--x', '3']], + 'true_value'); + test_if_with_custom_properties('if(style(--percentage > 3%): true_value; else: false_value)', + [['--percentage', '5%']], + 'true_value'); + test_if_with_custom_properties('if(style(--x > 3%): true_value; else: false_value)', + [['--x', '5%']], + 'true_value'); + test_if_with_custom_properties('if(style(--angle < 1turn): true_value; else: false_value)', + [['--angle', '1deg']], + 'true_value'); + test_if_with_custom_properties('if(style(--x < 1turn): true_value; else: false_value)', + [['--x', '1deg']], + 'true_value'); + test_if_with_custom_properties('if(style(--time <= 1000ms): true_value; else: false_value)', + [['--time', '1s']], + 'true_value'); + test_if_with_custom_properties('if(style(--x <= 1000ms): true_value; else: false_value)', + [['--x', '1s']], + 'true_value'); + test_if_with_custom_properties('if(style(3dppx > --resolution): true_value; else: false_value)', + [['--resolution', '96dpi']], + 'true_value'); + test_if_with_custom_properties('if(style(3dppx > --x): true_value; else: false_value)', + [['--x', '96dpi']], + 'true_value'); + + // style() queries with range syntax in the condition, invalid custom properties in the condition + test_if_with_custom_properties('if(style(--x + 1 >= --y): true_value; else: false_value)', + [['--x', '5'], ['--y', '3']], + 'false_value'); + test_if_with_custom_properties('if(style(--x >= --y + 1): true_value; else: false_value)', + [['--x', '5'], ['--y', '3']], + 'false_value'); + test_if_with_custom_properties('if(style(calc(--x + 1) >= --y): true_value; else: false_value)', + [['--x', '5'], ['--y', '3']], + 'false_value'); + test_if_with_custom_properties('if(style(--x >= calc(--y + 1)): true_value; else: false_value)', + [['--x', '5'], ['--y', '3']], + 'false_value'); + + // style() queries with range syntax in the condition, custom properties with functions in the condition + test_if_with_custom_properties('if(style(--x >= calc(3px + 3px)): true_value; else: false_value)', + [['--x', '7px']], + 'true_value'); + test_if_with_custom_properties('if(style(calc(var(--x) + 1) >= var(--y)): true_value; else: false_value)', + [['--x', '5'], ['--y', '3']], + 'true_value'); + test_if_with_custom_properties('if(style(var(--x) >= --x): true_value; else: false_value)', + [['--x', '3']], + 'true_value'); + + // style() queries with range syntax in the condition, incompatible types in the range. + test_if_with_custom_properties('if(style(3px > 3): true_value; else: false_value)', + [], + 'false_value'); + test_if_with_custom_properties('if(style(3em > 3deg): true_value; else: false_value)', + [], + 'false_value'); + test_if_with_custom_properties('if(style(1px >= 1%) or style(1px <= 1%): true_value; else: false_value)', + [], + 'false_value'); + test_if_with_custom_properties('if(style(--length > 3): true_value; else: false_value)', + [['--length', '11em']], + 'false_value'); + test_if_with_custom_properties('if(style(--number > 3px): true_value; else: false_value)', + [['--number', '11']], + 'false_value'); + test_if_with_custom_properties('if(style(--x >= 3): true_value; else: false_value)', + [['--x', '3px']], + 'false_value'); + test_if_with_custom_properties(`if(style(--length >= 30px): true_value; + else: false_value)`, + [['--length', 'attr(data-foo type(<length>))']], + 'true_value'); + + // style() queries with range syntax in the condition, double range + test_if_with_custom_properties('if(style(10px <= 10px < 11px): true_value; else: false_value)', [], 'true_value'); + test_if_with_custom_properties('if(style(3 < --x <= 5): true_value; else: false_value)', + [['--x', '5']], + 'true_value'); + test_if_with_custom_properties('if(style(--x >= --y > --z): true_value; else: false_value)', + [['--x', '3'], ['--y', '3'], ['--z', '3']], + 'false_value'); + test_if_with_custom_properties('if(style(--x >= --y > --z): true_value; else: false_value)', + [['--x', '3'], ['--y', '3'], ['--z', '1']], + 'true_value'); + // media() queries in the condition test_if(`if(media(max-width: 1px): true_value; else: false_value)`,
diff --git a/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/icon-hidden-reftest.html b/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/icon-hidden-reftest.html new file mode 100644 index 0000000..79055da --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/icon-hidden-reftest.html
@@ -0,0 +1,11 @@ +<!doctype html> +<title>The icon of the location permission element should not be visibe if it is set to display:none</title> +<!-- TODO: Update the link to the permission icon spec --> +<link rel="help" href="https://github.com/WICG/PEPC/blob/main/explainer.md"> +<link rel="mismatch" href="standard-location-permission-element-ref.html"> +<style> + ::permission-icon { + display: none; + } +</style> +<permission id="geolocation" type="geolocation"/>
diff --git a/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/icon-unique-per-type-reftest.html b/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/icon-unique-per-type-reftest.html new file mode 100644 index 0000000..d51b1c4 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/icon-unique-per-type-reftest.html
@@ -0,0 +1,6 @@ +<!doctype html> +<title>The camera permission element icon should be different to the location permission element</title> +<!-- TODO: Update the link to the permission icon spec --> +<link rel="help" href="https://github.com/WICG/PEPC/blob/main/explainer.md"> +<link rel="mismatch" href="standard-location-permission-element-ref.html"> +<permission id="camera" type="camera"/>
diff --git a/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/standard-location-permission-element-ref.html b/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/standard-location-permission-element-ref.html new file mode 100644 index 0000000..15ffe75 --- /dev/null +++ b/third_party/blink/web_tests/external/wpt/html/semantics/permission-element/permission-icon/standard-location-permission-element-ref.html
@@ -0,0 +1,4 @@ +<!DOCTYPE html> +<meta charset="utf-8"> +<title>A standard permission element of type location, without any non-default styling</title> +<permission id="geolocation" type="geolocation"/>
diff --git a/third_party/blink/web_tests/virtual/container-style-queries-range/external/wpt/css/css-values/if-conditionals-expected.txt b/third_party/blink/web_tests/virtual/container-style-queries-range/external/wpt/css/css-values/if-conditionals-expected.txt new file mode 100644 index 0000000..80bbd08 --- /dev/null +++ b/third_party/blink/web_tests/virtual/container-style-queries-range/external/wpt/css/css-values/if-conditionals-expected.txt
@@ -0,0 +1,62 @@ +This is a testharness.js-based test. +Found 29 FAIL, 0 TIMEOUT, 0 NOTRUN. +[FAIL] CSS Values and Units Test: CSS inline if() function 112 + assert_equals: "if(style(10em > 3px): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 113 + assert_equals: "if(style(1em > 1px): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 114 + assert_equals: "if(style(7px > 3px): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 116 + assert_equals: "if(style(3turn > 3deg): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 118 + assert_equals: "if(style(3% >= 3%): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 119 + assert_equals: "if(style(3s > 3ms): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 120 + assert_equals: "if(style(3dppx > 96dpi): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 121 + assert_equals: "if(style(--x <= 3): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 122 + assert_equals: "if(style(--x >= --y): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 123 + assert_equals: "if(style(--length > 3px): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 124 + assert_equals: "if(style(--x > 3px): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 125 + assert_equals: "if(style(--number >= 3): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 126 + assert_equals: "if(style(--x >= 3): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 127 + assert_equals: "if(style(--percentage > 3%): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 128 + assert_equals: "if(style(--x > 3%): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 129 + assert_equals: "if(style(--angle < 1turn): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 130 + assert_equals: "if(style(--x < 1turn): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 131 + assert_equals: "if(style(--time <= 1000ms): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 132 + assert_equals: "if(style(--x <= 1000ms): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 133 + assert_equals: "if(style(3dppx > --resolution): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 134 + assert_equals: "if(style(3dppx > --x): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 137 + assert_equals: "if(style(calc(--x + 1) >= --y): true_value; else: false_value)" should be substituted to "false_value". expected "false_value" but got "" +[FAIL] CSS Values and Units Test: CSS inline if() function 139 + assert_equals: "if(style(--x >= calc(3px + 3px)): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 140 + assert_equals: "if(style(calc(var(--x) + 1) >= var(--y)): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "" +[FAIL] CSS Values and Units Test: CSS inline if() function 141 + assert_equals: "if(style(var(--x) >= --x): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "" +[FAIL] CSS Values and Units Test: CSS inline if() function 148 + assert_equals: "if(style(--length >= 30px): true_value;\n else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 149 + assert_equals: "if(style(10px <= 10px < 11px): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 150 + assert_equals: "if(style(3 < --x <= 5): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +[FAIL] CSS Values and Units Test: CSS inline if() function 152 + assert_equals: "if(style(--x >= --y > --z): true_value; else: false_value)" should be substituted to "true_value". expected "true_value" but got "false_value" +Harness: the test ran to completion. +
diff --git a/third_party/compiler-rt/src b/third_party/compiler-rt/src index 9c6d38a..57196dd 160000 --- a/third_party/compiler-rt/src +++ b/third_party/compiler-rt/src
@@ -1 +1 @@ -Subproject commit 9c6d38aa28100761bc2d6dcd2a590a37f8519adf +Subproject commit 57196dd146582915c955f6d388e31aea93220c51
diff --git a/third_party/dawn b/third_party/dawn index 156136e..45b5634 160000 --- a/third_party/dawn +++ b/third_party/dawn
@@ -1 +1 @@ -Subproject commit 156136ebb43d383a3833545598023dd366085166 +Subproject commit 45b5634e70a3a6d61f3704f308d7a419e7db532d
diff --git a/third_party/devtools-frontend/src b/third_party/devtools-frontend/src index 5515443..acd68d2 160000 --- a/third_party/devtools-frontend/src +++ b/third_party/devtools-frontend/src
@@ -1 +1 @@ -Subproject commit 55154436a9c71fc62179638710b405c99e80ef54 +Subproject commit acd68d2f092a2e674894c9d389c96e39beec1aa2
diff --git a/third_party/freetype/README.chromium b/third_party/freetype/README.chromium index 9b791fd..705f487 100644 --- a/third_party/freetype/README.chromium +++ b/third_party/freetype/README.chromium
@@ -1,7 +1,7 @@ Name: FreeType URL: http://www.freetype.org/ -Version: VER-2-13-3-225-g57a873045 -Revision: 57a873045016c7866a298f5e9faa830e6ec24cf9 +Version: VER-2-13-3-230-ge07e56c7f +Revision: e07e56c7f106b600262ab653d696b7b57f320127 CPEPrefix: cpe:/a:freetype:freetype:2.13.3 License: FTL License File: src/docs/FTL.TXT
diff --git a/third_party/freetype/src b/third_party/freetype/src index 57a8730..e07e56c 160000 --- a/third_party/freetype/src +++ b/third_party/freetype/src
@@ -1 +1 @@ -Subproject commit 57a873045016c7866a298f5e9faa830e6ec24cf9 +Subproject commit e07e56c7f106b600262ab653d696b7b57f320127
diff --git a/third_party/skia b/third_party/skia index 1e07a4b..3ba7657 160000 --- a/third_party/skia +++ b/third_party/skia
@@ -1 +1 @@ -Subproject commit 1e07a4b16973cf716cb40b72dd969e961f4dd950 +Subproject commit 3ba7657e8745bffd1c6263d5555be935afbc0df9
diff --git a/third_party/vulkan-deps b/third_party/vulkan-deps index bf02428..5912cbd 160000 --- a/third_party/vulkan-deps +++ b/third_party/vulkan-deps
@@ -1 +1 @@ -Subproject commit bf024288c340597e8421df8db06c2de12c25bf31 +Subproject commit 5912cbdd295c2bacb5798432a7b1cac9d20c0725
diff --git a/third_party/vulkan-utility-libraries/src b/third_party/vulkan-utility-libraries/src index ae56bd6..49ac289 160000 --- a/third_party/vulkan-utility-libraries/src +++ b/third_party/vulkan-utility-libraries/src
@@ -1 +1 @@ -Subproject commit ae56bd6e65d9faa731150e931cb35f0d895223bc +Subproject commit 49ac28931f28bffaa3cd73dc4ad997284d574962
diff --git a/third_party/vulkan-validation-layers/src b/third_party/vulkan-validation-layers/src index 84b023a..f7ceb1d0 160000 --- a/third_party/vulkan-validation-layers/src +++ b/third_party/vulkan-validation-layers/src
@@ -1 +1 @@ -Subproject commit 84b023ac42601ff51ea6094dc2c18ca62960b25d +Subproject commit f7ceb1d01a292846db77ec87786be84d6fd568d9
diff --git a/third_party/webrtc b/third_party/webrtc index 2fe2d51..9909b30 160000 --- a/third_party/webrtc +++ b/third_party/webrtc
@@ -1 +1 @@ -Subproject commit 2fe2d5190bd3d8766759e3a7de2b648d5ce96aee +Subproject commit 9909b30d5e3c104d4dce7d066fc8422eef1dcc59
diff --git a/tools/binary_size/libsupersize/native.py b/tools/binary_size/libsupersize/native.py index ada8cc4..e6bcec6 100644 --- a/tools/binary_size/libsupersize/native.py +++ b/tools/binary_size/libsupersize/native.py
@@ -670,7 +670,7 @@ args = [path_util.GetReadElfPath(), '-r', elf_path] stdout = subprocess.check_output(args).decode('ascii') relocations = re.findall( - 'Relocation section .* at offset .* contains (\d+) entries', stdout) + r'Relocation section .* at offset .* contains (\d+) entries', stdout) return sum([int(i) for i in relocations])
diff --git a/tools/binary_size/libsupersize/readelf.py b/tools/binary_size/libsupersize/readelf.py index f3d7cc5..b78362e6 100644 --- a/tools/binary_size/libsupersize/readelf.py +++ b/tools/binary_size/libsupersize/readelf.py
@@ -22,7 +22,7 @@ """Returns the GN architecture for the given binary.""" args = [path_util.GetReadElfPath(), '-h', elf_path] stdout = subprocess.check_output(args, encoding='ascii') - machine = re.search('Machine:\s*(.+)', stdout).group(1) + machine = re.search(r'Machine:\s*(.+)', stdout).group(1) if machine == 'Intel 80386': return 'x86' if machine == 'Advanced Micro Devices X86-64':
diff --git a/tools/binary_size/libsupersize/viewer/caspian/BUILD.gn b/tools/binary_size/libsupersize/viewer/caspian/BUILD.gn index 90dc22c..9f2d40a 100644 --- a/tools/binary_size/libsupersize/viewer/caspian/BUILD.gn +++ b/tools/binary_size/libsupersize/viewer/caspian/BUILD.gn
@@ -4,11 +4,9 @@ import("//testing/test.gni") -# Enable wasm target that depends on foo.patch being applied. -if (!defined(is_wasm)) { - is_wasm = current_os == "wasm" +declare_args() { + enable_caspian = false } - assert(is_linux || is_chromeos || is_wasm) source_set("caspian-lib") { @@ -61,18 +59,26 @@ cflags = [ "-Wall" ] } -if (is_wasm) { - executable("caspian_web") { - sources = [ "caspian_web.cc" ] - deps = [ - ":caspian-lib", - "//third_party/re2:re2", - ] - ldflags = [ - "-s", - "EXPORTED_FUNCTIONS=['_BuildTree','_GetMetadata','_LoadBeforeSizeFile','_LoadSizeFile','_Open','_QueryAncestryById','_QueryProperty','_free','_malloc']", - "-s", - "EXPORTED_RUNTIME_METHODS=['ccall','cwrap','UTF8ToString']", - ] +if (enable_caspian) { + if (is_wasm) { + executable("caspian_web") { + sources = [ "caspian_web.cc" ] + deps = [ + ":caspian-lib", + "//third_party/re2:re2", + ] + ldflags = [ + "-s", + "EXPORTED_FUNCTIONS=['_BuildTree','_GetMetadata','_LoadBeforeSizeFile','_LoadSizeFile','_Open','_QueryAncestryById','_QueryProperty','_free','_malloc']", + "-s", + "EXPORTED_RUNTIME_METHODS=['HEAPU8','ccall','cwrap','UTF8ToString']", + "-s", + "MAXIMUM_MEMORY=4GB", + ] + } + } else { + group("caspian_web") { + public_deps = [ ":caspian_web(//build/toolchain/wasm)" ] + } } }
diff --git a/tools/binary_size/libsupersize/viewer/caspian/README.md b/tools/binary_size/libsupersize/viewer/caspian/README.md index f4f4756..a350b68e 100644 --- a/tools/binary_size/libsupersize/viewer/caspian/README.md +++ b/tools/binary_size/libsupersize/viewer/caspian/README.md
@@ -9,42 +9,24 @@ ## Building the WASM Module -### 1. Install Emscripten +### Install Emscripten -This step needs to be only once. - -1. `git clone` emscripten: -https://emscripten.org/docs/getting_started/downloads.html -2. Install the known working version: - ```sh - cd $EMSDK; ./emsdk install 3.1.9 && ./emsdk activate 3.1.9 - ``` -3. Activate it via environment variables: - ```sh - cd $EMSDK; source emsdk_env.sh - ``` - -### 2. Apply Local Patches - -Caspian needs some minor edits that we don't want to commit: +This step needs to be only once. Docs: https://emscripten.org/docs/getting_started/downloads.html ```sh -git apply -3 tools/binary_size/libsupersize/viewer/caspian/wasmbuild.patch +cd /usr/local/google/code +git clone https://github.com/emscripten-core/emsdk.git +cd emsdk +./emsdk install 4.0.9 +./emsdk activate 4.0.9 +source emsdk_env.sh ``` -To re-create .patch file: -```sh -git add ...files to include in patch... -git diff --staged > tools/binary_size/libsupersize/viewer/caspian/wasmbuild.patch -# Double check that only expected files are included in the patch: -grep +++ tools/binary_size/libsupersize/viewer/caspian/wasmbuild.patch -``` - -### 3. Build +### Build ```sh # Omit is_official_build=true if developing locally. -gn gen out/caspian --args='is_official_build=true treat_warnings_as_errors=false fatal_linker_warnings=false chrome_pgo_phase=0 enable_rust=false' +gn gen out/caspian --args='enable_caspian=true is_official_build=true treat_warnings_as_errors=false fatal_linker_warnings=false emscripten_path="/usr/local/google/code/emsdk/upstream/emscripten"' # Build and copy into static/ directory: ( cd out/caspian; autoninja caspian_web && cp wasm/caspian_web.* ../../tools/binary_size/libsupersize/viewer/static/ ) ``` @@ -90,6 +72,9 @@ ``` cd $PATH_TO_EMSDK git pull origin main --tags + ./emsdk install latest + ./emsdk activate latest + source ./emsdk_env.sh ``` 2. Update this README's Emscripten version above, then follow its steps.
diff --git a/tools/binary_size/libsupersize/viewer/caspian/wasmbuild.patch b/tools/binary_size/libsupersize/viewer/caspian/wasmbuild.patch deleted file mode 100644 index 1d24e9e..0000000 --- a/tools/binary_size/libsupersize/viewer/caspian/wasmbuild.patch +++ /dev/null
@@ -1,129 +0,0 @@ -diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn -index cc7e92ddb67cd..f9212d2e81c63 100644 ---- a/build/config/BUILDCONFIG.gn -+++ b/build/config/BUILDCONFIG.gn -@@ -305,10 +305,11 @@ is_ios = current_os == "ios" - is_linux = current_os == "linux" - is_mac = current_os == "mac" - is_nacl = current_os == "nacl" -+is_wasm = current_os == "wasm" - is_win = current_os == "win" || current_os == "winuwp" - - is_apple = is_ios || is_mac --is_posix = !is_win && !is_fuchsia -+is_posix = !is_win && !is_fuchsia && !is_wasm - - # ============================================================================= - # TARGET DEFAULTS -diff --git a/build/config/compiler/BUILD.gn b/build/config/compiler/BUILD.gn -index 6119aa066a982..a77ca7e4a2ab8 100644 ---- a/build/config/compiler/BUILD.gn -+++ b/build/config/compiler/BUILD.gn -@@ -647,6 +647,20 @@ config("compiler") { - ldflags += [ "-fexperimental-relative-c++-abi-vtables" ] - } - -+ if (is_wasm) { -+ ldflags += [ -+ "-s", -+ "ALLOW_MEMORY_GROWTH=1", -+ "-s", -+ "LLD_REPORT_UNDEFINED=1", -+ ] -+ -+ if (is_official_build) { -+ cflags += ["-flto=full"] -+ ldflags += ["-flto=full"] -+ } -+ } -+ - # Add flags for link-time optimization. These flags enable - # optimizations/transformations that require whole-program visibility at link - # time, so they need to be applied to all translation units, and we may end up -@@ -766,7 +780,7 @@ config("compiler") { - - # TODO(crbug.com/40242425): Cleanup undefined symbol errors caught by - # --no-undefined-version. -- if (use_lld && !is_win && !is_mac && !is_ios) { -+ if (use_lld && !is_win && !is_mac && !is_ios && !is_wasm) { - ldflags += [ "-Wl,--undefined-version" ] - } - -@@ -777,7 +791,7 @@ config("compiler") { - if (use_lld && !enable_call_graph_profile_sort) { - if (is_win) { - ldflags += [ "/call-graph-profile-sort:no" ] -- } else { -+ } else if (!is_wasm) { - ldflags += [ "-Wl,--no-call-graph-profile-sort" ] - } - } -@@ -1615,7 +1629,7 @@ config("default_warnings") { - "-Wno-ignored-pragma-optimize", - ] - -- if (!is_nacl) { -+ if (!is_nacl && !is_wasm) { - cflags += [ - # TODO(crbug.com/40231599) Evaluate and possibly enable. - "-Wno-deprecated-builtins", -@@ -2380,6 +2394,9 @@ config("symbols") { - - # All configs using /DEBUG should include this: - configs = [ ":win_pdbaltpath" ] -+ } else if (is_wasm) { -+ cflags = [ "-gseparate-dwarf" ] -+ ldflags = [ "-gseparate-dwarf" ] - } else { - cflags = [] - if (is_mac && enable_dsyms) { -diff --git a/build/toolchain/toolchain.gni b/build/toolchain/toolchain.gni -index 844bc8e540bcc..93e6e0c437fab 100644 ---- a/build/toolchain/toolchain.gni -+++ b/build/toolchain/toolchain.gni -@@ -47,6 +47,9 @@ if (is_apple) { - shlib_extension = ".so" - } else if (is_win) { - shlib_extension = ".dll" -+} else if (is_wasm) { -+ # WebAssembly does not stably support shared libraries. (as of Oct 2019) -+ shlib_extension = ".wasm" - } else { - assert(false, "Platform not supported") - } -diff --git a/build/toolchain/wasm/BUILD.gn b/build/toolchain/wasm/BUILD.gn -new file mode 100644 -index 0000000000000..4aed5264eae15 ---- /dev/null -+++ b/build/toolchain/wasm/BUILD.gn -@@ -0,0 +1,30 @@ -+# Copyright 2019 The Chromium Authors -+# Use of this source code is governed by a BSD-style license that can be -+# found in the LICENSE file. -+ -+import("//build/toolchain/gcc_toolchain.gni") -+ -+gcc_toolchain("wasm") { -+ cc = "emcc" -+ cxx = "em++" -+ nm = "emcc" -+ ar = "emar" -+ ld = cxx -+ -+ toolchain_args = { -+ current_cpu = "wasm" -+ current_os = "wasm" -+ -+ is_clang = true -+ use_remoteexec = false -+ use_debug_fission = false -+ clang_use_chrome_plugins = false -+ use_allocator_shim = false -+ is_component_build = false -+ } -+ executable_extension = ".js" -+ link_outputs = [ -+ "{{output_dir}}/{{target_output_name}}.wasm", -+ "{{output_dir}}/{{target_output_name}}.wasm.debug.wasm", -+ ] -+}
diff --git a/tools/metrics/histograms/enums.xml b/tools/metrics/histograms/enums.xml index 1c05f9b6..7a9d74e 100644 --- a/tools/metrics/histograms/enums.xml +++ b/tools/metrics/histograms/enums.xml
@@ -13098,6 +13098,7 @@ <int value="-300817167" label="CrosSwitcher:enabled"/> <int value="-300018686" label="disable-cloud-import"/> <int value="-299841473" label="top-document-isolation:enabled"/> + <int value="-299332162" label="PageActionsMigration:enabled"/> <int value="-299116652" label="CCTResizable90MaximumHeight:enabled"/> <int value="-298647219" label="OmniboxContextualSearchOnFocusSuggestions:enabled"/> @@ -13384,6 +13385,7 @@ <int value="-190449995" label="CommerceLocalPDPDetection:enabled"/> <int value="-189740492" label="PolicyIndicationForManagedDefaultSearch:disabled"/> + <int value="-189543840" label="PageActionsMigration:disabled"/> <int value="-189478545" label="ArcCustomTabsExperiment:enabled"/> <int value="-188439713" label="disable-video-capture-use-gpu-memory-buffer"/> <int value="-187536302" label="TabstripComboButton:enabled"/> @@ -13800,6 +13802,7 @@ <int value="-35256214" label="InterestFeedNoticeCardAutoDismiss:enabled"/> <int value="-35002051" label="DefaultBucketUsesRelaxedDurability:enabled"/> <int value="-34898620" label="RendererSideContentDecoding:disabled"/> + <int value="-33771076" label="MemoryPurgeOnFreezeLimit:disabled"/> <int value="-33240310" label="AppShimNotificationAttribution:enabled"/> <int value="-32712825" label="CrOSEnforceSystemAec:disabled"/> <int value="-31484570" @@ -14672,6 +14675,7 @@ <int value="296066418" label="CCTResizableForThirdParties:disabled"/> <int value="296215399" label="WindowsMixedReality:disabled"/> <int value="296296761" label="MediaFoundationVideoCapture:disabled"/> + <int value="296729972" label="MvcUpdateViewWhenModelChanged:enabled"/> <int value="297095559" label="ShowBluetoothDebugLogToggle:disabled"/> <int value="297750703" label="DesktopPWAsAppIconShortcutsMenu:enabled"/> <int value="299270348" label="EnablePixPaymentsInLandscapeMode:disabled"/> @@ -15122,6 +15126,7 @@ <int value="455698038" label="disable-gesture-requirement-for-media-playback"/> <int value="455754036" label="MirroringService:disabled"/> + <int value="456095041" label="MvcUpdateViewWhenModelChanged:disabled"/> <int value="456908798" label="WebViewSupervisedUserSiteBlock:enabled"/> <int value="457265823" label="NtpWideModules:enabled"/> <int value="457301531" label="SiteIsolationForGuests:disabled"/> @@ -15214,6 +15219,7 @@ <int value="494939785" label="InsecureFormSubmissionInterstitial:disabled"/> <int value="495177253" label="CastStreamingWinHardwareH264:enabled"/> <int value="495435958" label="PageInfoAboutThisSiteMoreInfo:enabled"/> + <int value="495620535" label="MemoryPurgeOnFreezeLimit:enabled"/> <int value="496491728" label="SiteSearchSettingsPolicy:enabled"/> <int value="496667708" label="ArcInputOverlay:disabled"/> <int value="497039057" label="AdaptiveChargingForTesting:disabled"/>
diff --git a/tools/metrics/histograms/metadata/enterprise/histograms.xml b/tools/metrics/histograms/metadata/enterprise/histograms.xml index 192d436a..1b95fb1 100644 --- a/tools/metrics/histograms/metadata/enterprise/histograms.xml +++ b/tools/metrics/histograms/metadata/enterprise/histograms.xml
@@ -544,7 +544,7 @@ </histogram> <histogram name="Enterprise.CloudExtensionRequestUpdated" - enum="EnterpriseCloudExtensionRequestListUpdate" expires_after="2025-10-01"> + enum="EnterpriseCloudExtensionRequestListUpdate" expires_after="2025-12-01"> <owner>zmin@chromium.org</owner> <owner>src/chrome/browser/enterprise/reporting/OWNERS</owner> <summary> @@ -1835,7 +1835,7 @@ name="Enterprise.DMServerCloudPolicyRequestStatus{EnterpriseDMServerCloudPolicyRequest}" enum="EnterpriseDeviceManagementStatus" expires_after="2025-12-01"> <owner>vincb@google.com</owner> - <owner>zmin@google.com</owner> + <owner>zmin@chromium.com</owner> <summary> Records the returned status of fetching cloud policies from the dmserver. @@ -3661,7 +3661,7 @@ </histogram> <histogram name="Enterprise.UserInfoFetch.HttpErrorCode" - enum="CombinedHttpResponseAndNetErrorCode" expires_after="2025-10-19"> + enum="CombinedHttpResponseAndNetErrorCode" expires_after="2025-12-19"> <owner>vincb@google.com</owner> <owner>zmin@chromium.org</owner> <summary> @@ -3674,7 +3674,7 @@ </histogram> <histogram name="Enterprise.UserInfoFetch.Status" - enum="EnterpriseUserInfoFetchStatus" expires_after="2025-10-26"> + enum="EnterpriseUserInfoFetchStatus" expires_after="2025-12-26"> <owner>vincb@google.com</owner> <owner>zmin@chromium.org</owner> <summary> @@ -3850,7 +3850,7 @@ </histogram> <histogram name="EnterpriseCheck.AzureADJoinStatusCheckTime" units="ms" - expires_after="2025-07-01"> + expires_after="2025-12-01"> <owner>igorruvinov@chromium.org</owner> <owner>ydago@chromium.org</owner> <owner>pastarmovj@chromium.org</owner> @@ -3862,7 +3862,7 @@ </histogram> <histogram name="EnterpriseCheck.InDomain" enum="BooleanEnabled" - expires_after="2025-07-01"> + expires_after="2025-12-01"> <owner>ydago@chromium.org</owner> <owner>pastarmovj@chromium.org</owner> <summary> @@ -3909,7 +3909,7 @@ </histogram> <histogram name="EnterpriseCheck.IsDomainJoined" enum="BooleanEnabled" - expires_after="2025-06-08"> + expires_after="2025-12-10"> <owner>pastarmovj@chromium.org</owner> <owner>zmin@chromium.org</owner> <summary> @@ -3919,7 +3919,7 @@ </histogram> <histogram name="EnterpriseCheck.IsEnterpriseUser" enum="BooleanEnabled" - expires_after="2025-10-26"> + expires_after="2025-12-01"> <owner>pastarmovj@chromium.org</owner> <owner>zmin@chromium.org</owner> <summary> @@ -3930,7 +3930,7 @@ </histogram> <histogram name="EnterpriseCheck.IsFullyManaged2" enum="IsFullyManagedBoolean" - expires_after="2025-10-19"> + expires_after="2025-12-01"> <owner>twellington@google.com</owner> <owner>tedchcoc@chromium.org</owner> <summary> @@ -3941,7 +3941,7 @@ </histogram> <histogram name="EnterpriseCheck.IsJoinedToAzureAD" enum="BooleanEnabled" - expires_after="2025-07-01"> + expires_after="2025-12-01"> <owner>igorruvinov@chromium.org</owner> <owner>ydago@chromium.org</owner> <owner>pastarmovj@chromium.org</owner> @@ -4030,7 +4030,7 @@ </histogram> <histogram name="EnterpriseCheck.OSType" enum="OsSuite" - expires_after="2025-07-01"> + expires_after="2025-12-01"> <owner>ydago@chromium.org</owner> <owner>pastarmovj@chromium.org</owner> <summary> @@ -4040,7 +4040,7 @@ </histogram> <histogram name="EnterpriseCheck.WindowsProfileType" enum="WindowsProfileType" - expires_after="2025-11-02"> + expires_after="2025-12-01"> <owner>wfh@chromium.org</owner> <owner>chrome-platform-security-core@google.com</owner> <summary>
diff --git a/tools/metrics/histograms/metadata/glic/histograms.xml b/tools/metrics/histograms/metadata/glic/histograms.xml index e8f8a53..e3aa62d 100644 --- a/tools/metrics/histograms/metadata/glic/histograms.xml +++ b/tools/metrics/histograms/metadata/glic/histograms.xml
@@ -84,8 +84,10 @@ <variant name="OnUserInputSubmitted"/> <variant name="OpenGlicSettingsPage"/> <variant name="OpenOsPermissionSettingsMenu"/> + <variant name="PauseActorTask"/> <variant name="RefreshSignInCookies"/> <variant name="ResizeWindow"/> + <variant name="ResumeActorTask"/> <variant name="ScrollTo"/> <variant name="SetAudioDucking"/> <variant name="SetClosedCaptioningState"/>
diff --git a/tools/metrics/histograms/metadata/media/histograms.xml b/tools/metrics/histograms/metadata/media/histograms.xml index 3ea80b0d9..a28f697 100644 --- a/tools/metrics/histograms/metadata/media/histograms.xml +++ b/tools/metrics/histograms/metadata/media/histograms.xml
@@ -857,6 +857,19 @@ </summary> </histogram> +<histogram name="Media.Audio.Capture.Win.GetAudioClientTimedOut" enum="Boolean" + expires_after="2026-05-30"> + <owner>henrika@chromium.org</owner> + <owner>olka@chromium.org</owner> + <owner>webrtc-audio-uma@google.com</owner> + <summary> + Logs whether the attempt to acquire an input audio client asynchronously + timed out or not. A timeout corresponds to a waiting time which exceeds 10 + seconds. Logged once when an input audio stream is opened and the specified + device ID is a process loopback device. Only supported on Windows. + </summary> +</histogram> + <histogram name="Media.Audio.Capture.Win.Glitches2" units="glitches" expires_after="2026-05-11"> <owner>olka@chromium.org</owner> @@ -909,6 +922,21 @@ </summary> </histogram> +<histogram name="Media.Audio.Capture.Win.TimeToGetAudioClient" units="ms" + expires_after="2026-05-30"> + <owner>henrika@chromium.org</owner> + <owner>olka@chromium.org</owner> + <owner>webrtc-audio-uma@google.com</owner> + <summary> + This histogram records the time it takes to activate an audio client + asynchronously, which occurs on the audio.CrUtilityMain thread in the + AudioService process. Logged once when an input audio stream is successfully + opened and the specified device ID is a process loopback device. Only + supported on Windows and when Media.Audio.Capture.Win.GetAudioClientTimedOut + is false. + </summary> +</histogram> + <histogram name="Media.Audio.Capture.Win.VoiceProcessingEffects" enum="AudioEffectType" expires_after="2025-12-30"> <owner>henrika@chromium.org</owner>
diff --git a/tools/metrics/histograms/metadata/web_rtc/enums.xml b/tools/metrics/histograms/metadata/web_rtc/enums.xml index 5a05346..5665576 100644 --- a/tools/metrics/histograms/metadata/web_rtc/enums.xml +++ b/tools/metrics/histograms/metadata/web_rtc/enums.xml
@@ -219,8 +219,6 @@ <int value="2" label="WithoutCreateAnswer"/> <int value="3" label="WithoutCreateOffer"/> <int value="4" label="NumberOfContents"/> - <int value="5" label="NumberOfTransports"/> - <int value="6" label="OrderOfContents"/> <int value="20" label="IceOptions"/> <int value="21" label="IcePwd"/> <int value="22" label="IceUfrag"/> @@ -230,6 +228,7 @@ <int value="26" label="PayloadTypes"/> <int value="27" label="Ssrcs"/> <int value="28" label="IceOptionsRenomination"/> + <int value="29" label="Direction"/> <int value="40" label="RtpHeaderExtensionsRemoved"/> <int value="41" label="RtpHeaderExtensionsAdded"/> <int value="42" label="RtpHeaderExtensionsModified"/> @@ -253,6 +252,8 @@ <int value="84" label="VideoCodecsFmtpH264SpsPpsIdrInKeyframe"/> <int value="85" label="VideoCodecsFmtp"/> <int value="86" label="VideoCodecsRtcpFb"/> + <int value="87" label="VideoCodecsAddedWithRawPacketization"/> + <int value="88" label="VideoCodecsModifiedWithRawPacketization"/> </enum> <enum name="SrtpErrorCode">
diff --git a/tools/metrics/structured/sync/structured.xml b/tools/metrics/structured/sync/structured.xml index a7a86dc..3b8b451 100644 --- a/tools/metrics/structured/sync/structured.xml +++ b/tools/metrics/structured/sync/structured.xml
@@ -3466,6 +3466,33 @@ </summary> </metric> </event> + + <event name="FunctionCall"> + <summary> + Recorded when an instrumented function is called. + </summary> + <metric name="Name" type="int"> + <summary> + Hash of the function name + </summary> + </metric> + <metric name="Context" type="int"> + <summary> + Hash of the function's context. + </summary> + </metric> + <metric name="TimeSinceSessionStart" type="int"> + <summary> + Time in milliseconds since DevTools sessions start. + </summary> + </metric> + <metric name="SessionId" type="int"> + <summary> + Unique ID of this debugging session. If DevTools is opened on multiple tabs, + each instance would have a unique ID. + </summary> + </metric> + </event> </project> <project name="TestProjectOne">
diff --git a/ui/base/models/dialog_model.cc b/ui/base/models/dialog_model.cc index c11dc4f..5a6b01a 100644 --- a/ui/base/models/dialog_model.cc +++ b/ui/base/models/dialog_model.cc
@@ -24,23 +24,23 @@ DialogModel::Button::Params& DialogModel::Button::Params::SetId( ElementIdentifier id) { - CHECK(!id_, base::NotFatalUntil::M123); - CHECK(id, base::NotFatalUntil::M123); + CHECK(!id_); + CHECK(id); id_ = id; return *this; } DialogModel::Button::Params& DialogModel::Button::Params::SetLabel( std::u16string label) { - CHECK(label_.empty(), base::NotFatalUntil::M123); - CHECK(!label.empty(), base::NotFatalUntil::M123); + CHECK(label_.empty()); + CHECK(!label.empty()); label_ = label; return *this; } DialogModel::Button::Params& DialogModel::Button::Params::SetStyle( std::optional<ButtonStyle> style) { - CHECK(style_ != style, base::NotFatalUntil::M123); + CHECK(style_ != style); style_ = style; return *this; } @@ -65,7 +65,7 @@ style_(params.style_), is_enabled_(params.is_enabled_), callback_(std::move(callback)) { - CHECK(callback_, base::NotFatalUntil::M123); + CHECK(callback_); } DialogModel::Button::~Button() = default; @@ -82,11 +82,11 @@ DialogModel::Builder::Builder() : Builder(nullptr) {} DialogModel::Builder::~Builder() { - CHECK(!model_, base::NotFatalUntil::M123) << "Model should've been built."; + CHECK(!model_) << "Model should've been built."; } std::unique_ptr<DialogModel> DialogModel::Builder::Build() { - CHECK(model_, base::NotFatalUntil::M123); + CHECK(model_); return std::move(model_); } @@ -133,18 +133,18 @@ base::RepeatingCallback<void(const Event&)> callback, const DialogModel::Button::Params& params) { CHECK(params.is_visible_); - CHECK(!model_->extra_button_, base::NotFatalUntil::M123); - CHECK(!model_->extra_link_, base::NotFatalUntil::M123); + CHECK(!model_->extra_button_); + CHECK(!model_->extra_link_); // Extra buttons are required to have labels. - CHECK(!params.label_.empty(), base::NotFatalUntil::M123); + CHECK(!params.label_.empty()); model_->extra_button_.emplace(std::move(callback), params); return *this; } DialogModel::Builder& DialogModel::Builder::AddExtraLink( DialogModelLabel::TextReplacement link) { - CHECK(!model_->extra_button_, base::NotFatalUntil::M123); - CHECK(!model_->extra_link_, base::NotFatalUntil::M123); + CHECK(!model_->extra_button_); + CHECK(!model_->extra_link_); model_->extra_link_.emplace(std::move(link)); return *this; } @@ -152,16 +152,16 @@ DialogModel::Builder& DialogModel::Builder::OverrideDefaultButton( mojom::DialogButton button) { // This can only be called once. - CHECK(!model_->override_default_button_, base::NotFatalUntil::M123); + CHECK(!model_->override_default_button_); // Confirm the button exists. switch (button) { case mojom::DialogButton::kNone: break; case mojom::DialogButton::kOk: - CHECK(model_->ok_button_, base::NotFatalUntil::M123); + CHECK(model_->ok_button_); break; case mojom::DialogButton::kCancel: - CHECK(model_->cancel_button_, base::NotFatalUntil::M123); + CHECK(model_->cancel_button_); break; } model_->override_default_button_ = button; @@ -171,9 +171,9 @@ DialogModel::Builder& DialogModel::Builder::SetInitiallyFocusedField( ElementIdentifier id) { // This must be called with a non-null id - CHECK(id, base::NotFatalUntil::M123); + CHECK(id); // This can only be called once. - CHECK(!model_->initially_focused_field_, base::NotFatalUntil::M123); + CHECK(!model_->initially_focused_field_); model_->initially_focused_field_ = id; return *this; }
diff --git a/ui/base/models/dialog_model_field.cc b/ui/base/models/dialog_model_field.cc index 0aa11de..4375fc7 100644 --- a/ui/base/models/dialog_model_field.cc +++ b/ui/base/models/dialog_model_field.cc
@@ -45,7 +45,7 @@ : message_id_(-1), string_(std::move(fixed_string)) {} const std::u16string& DialogModelLabel::GetString() const { - CHECK(replacements_.empty(), base::NotFatalUntil::M123); + CHECK(replacements_.empty()); return string_; } @@ -116,17 +116,17 @@ } DialogModelParagraph* DialogModelField::AsParagraph() { - CHECK_EQ(type_, kParagraph, base::NotFatalUntil::M123); + CHECK_EQ(type_, kParagraph); return static_cast<DialogModelParagraph*>(this); } DialogModelCheckbox* DialogModelField::AsCheckbox() { - CHECK_EQ(type_, kCheckbox, base::NotFatalUntil::M123); + CHECK_EQ(type_, kCheckbox); return static_cast<DialogModelCheckbox*>(this); } DialogModelCombobox* DialogModelField::AsCombobox() { - CHECK_EQ(type_, kCombobox, base::NotFatalUntil::M123); + CHECK_EQ(type_, kCombobox); return static_cast<DialogModelCombobox*>(this); } @@ -135,17 +135,17 @@ } const DialogModelMenuItem* DialogModelField::AsMenuItem() const { - CHECK_EQ(type_, kMenuItem, base::NotFatalUntil::M123); + CHECK_EQ(type_, kMenuItem); return static_cast<const DialogModelMenuItem*>(this); } const DialogModelTitleItem* DialogModelField::AsTitleItem() const { - CHECK_EQ(type_, kTitleItem, base::NotFatalUntil::M123); + CHECK_EQ(type_, kTitleItem); return static_cast<const DialogModelTitleItem*>(this); } DialogModelTextfield* DialogModelField::AsTextfield() { - CHECK_EQ(type_, kTextfield, base::NotFatalUntil::M123); + CHECK_EQ(type_, kTextfield); return static_cast<DialogModelTextfield*>(this); } @@ -155,7 +155,7 @@ } DialogModelCustomField* DialogModelField::AsCustomField() { - CHECK_EQ(type_, kCustom, base::NotFatalUntil::M123); + CHECK_EQ(type_, kCustom); return static_cast<DialogModelCustomField*>(this); } @@ -238,8 +238,8 @@ DialogModelMenuItem::Params& DialogModelMenuItem::Params::SetId( ElementIdentifier id) { - CHECK(!id_, base::NotFatalUntil::M123); - CHECK(id, base::NotFatalUntil::M123); + CHECK(!id_); + CHECK(id); id_ = id; return *this; } @@ -259,7 +259,7 @@ void DialogModelMenuItem::OnActivated(base::PassKey<DialogModelFieldHost>, int event_flags) { - CHECK(callback_, base::NotFatalUntil::M123); + CHECK(callback_); callback_.Run(event_flags); } @@ -298,8 +298,7 @@ text_(std::move(text)) { // Textfields need either an accessible name or label or the screenreader will // not be able to announce anything sensible. - CHECK(!label_.empty() || !accessible_name_.empty(), - base::NotFatalUntil::M123); + CHECK(!label_.empty() || !accessible_name_.empty()); } DialogModelTextfield::~DialogModelTextfield() = default;
diff --git a/ui/base/models/dialog_model_menu_model_adapter.cc b/ui/base/models/dialog_model_menu_model_adapter.cc index 5f5440cc..a33ce2d9 100644 --- a/ui/base/models/dialog_model_menu_model_adapter.cc +++ b/ui/base/models/dialog_model_menu_model_adapter.cc
@@ -44,8 +44,7 @@ MenuSeparatorType DialogModelMenuModelAdapter::GetSeparatorTypeAt( size_t index) const { - CHECK_EQ(GetField(index)->type(), DialogModelField::kSeparator, - base::NotFatalUntil::M123); + CHECK_EQ(GetField(index)->type(), DialogModelField::kSeparator); return MenuSeparatorType::NORMAL_SEPARATOR; } @@ -101,7 +100,7 @@ } bool DialogModelMenuModelAdapter::IsEnabledAt(size_t index) const { - CHECK_LT(index, GetItemCount(), base::NotFatalUntil::M123); + CHECK_LT(index, GetItemCount()); const DialogModelField* const field = GetField(index); // Non-interactive title should be disabled. @@ -114,7 +113,7 @@ ui::ElementIdentifier DialogModelMenuModelAdapter::GetElementIdentifierAt( size_t index) const { - CHECK_LT(index, GetItemCount(), base::NotFatalUntil::M123); + CHECK_LT(index, GetItemCount()); const DialogModelField* const field = GetField(index); if (field->type() == DialogModelField::kTitleItem) { @@ -140,7 +139,7 @@ const DialogModelField* DialogModelMenuModelAdapter::GetField( size_t index) const { - CHECK_LT(index, GetItemCount(), base::NotFatalUntil::M123); + CHECK_LT(index, GetItemCount()); return model_->fields(DialogModelHost::GetPassKey())[index].get(); }
diff --git a/ui/base/resource/resource_bundle_android.cc b/ui/base/resource/resource_bundle_android.cc index 7d9b624..8a1580e0 100644 --- a/ui/base/resource/resource_bundle_android.cc +++ b/ui/base/resource/resource_bundle_android.cc
@@ -28,14 +28,16 @@ namespace { +using FileDescriptor = int; + bool g_locale_paks_in_apk = false; bool g_load_secondary_locale_paks = false; // It is okay to cache and share these file descriptors since the // ResourceBundle singleton never closes the handles. -int g_chrome_100_percent_fd = -1; -int g_resources_pack_fd = -1; -int g_locale_pack_fd = -1; -int g_secondary_locale_pack_fd = -1; +FileDescriptor g_chrome_100_percent_fd = -1; +FileDescriptor g_resources_pack_fd = -1; +FileDescriptor g_locale_pack_fd = -1; +FileDescriptor g_secondary_locale_pack_fd = -1; base::MemoryMappedFile::Region g_chrome_100_percent_region; base::MemoryMappedFile::Region g_resources_pack_region; base::MemoryMappedFile::Region g_locale_pack_region; @@ -43,7 +45,7 @@ bool LoadFromApkOrFile(const char* apk_path, const base::FilePath* disk_path, - int* out_fd, + FileDescriptor* out_fd, base::MemoryMappedFile::Region* out_region) { DCHECK_EQ(*out_fd, -1) << "Attempt to load " << apk_path << " twice."; if (apk_path != nullptr) { @@ -64,9 +66,31 @@ return success; } -int LoadLocalePakFromApk(const std::string& app_locale, - bool in_split, - base::MemoryMappedFile::Region* out_region) { +// Returns the path within the apk for the given locale's .pak file, or an +// empty string if it doesn't exist. +// Only locale paks for the active Android language can be retrieved. +// If |in_split| is true, look into bundle split-specific location (e.g. +// 'assets/locales#lang_<lang>/<locale>.pak', otherwise use the default +// WebView-related location, i.e. 'assets/stored-locales/<locale>.pak'. +// If |log_error|, logs the path to logcat, but does not abort. +std::string GetPathForAndroidLocalePakWithinApk(const std::string& locale, + bool in_bundle, + bool log_error) { + JNIEnv* env = base::android::AttachCurrentThread(); + base::android::ScopedJavaLocalRef<jstring> ret = + Java_ResourceBundle_getLocalePakResourcePath( + env, base::android::ConvertUTF8ToJavaString(env, locale), in_bundle, + log_error); + if (ret.obj() == nullptr) { + return std::string(); + } + return base::android::ConvertJavaStringToUTF8(env, ret.obj()); +} + +FileDescriptor LoadLocalePakFromApk( + const std::string& app_locale, + bool in_split, + base::MemoryMappedFile::Region* out_region) { bool log_error = true; std::string locale_path_within_apk = GetPathForAndroidLocalePakWithinApk(app_locale, in_split, log_error); @@ -77,7 +101,7 @@ } std::unique_ptr<DataPack> LoadDataPackFromLocalePak( - int locale_pack_fd, + FileDescriptor locale_pack_fd, const base::MemoryMappedFile::Region& region) { auto data_pack = std::make_unique<DataPack>(k100Percent); CHECK(data_pack->LoadFromFileRegion(base::File(locale_pack_fd), region)) @@ -85,6 +109,13 @@ return data_pack; } +bool LocaleDataPakExists(const std::string& locale, + bool in_split, + bool log_error) { + return !GetPathForAndroidLocalePakWithinApk(locale, in_split, log_error) + .empty(); +} + } // namespace void ResourceBundle::LoadCommonResources() { @@ -102,14 +133,12 @@ // static bool ResourceBundle::LocaleDataPakExists(const std::string& locale) { - bool log_error = false; - bool in_split = !g_locale_paks_in_apk; - if (!in_split) { - return !GetPathForAndroidLocalePakWithinApk(locale, in_split, log_error) - .empty(); + const bool in_split = !g_locale_paks_in_apk; + const bool exists = + ::ui::LocaleDataPakExists(locale, in_split, false /* log_error */); + if (exists || !in_split) { + return exists; } - if (!GetPathForAndroidLocalePakWithinApk(locale, in_split, log_error).empty()) - return true; // Fall back to checking on disk, which is necessary only for tests. const auto path = GetLocaleFilePath(locale); @@ -120,7 +149,7 @@ bool crash_on_failure) { DCHECK(!locale_resources_data_.get() && !secondary_locale_resources_data_.get()) - << "locale.pak already loaded"; + << "locale.pak already loaded"; std::string app_locale = l10n_util::GetApplicationLocale(pref_locale); // Some Chromium apps have two sets of .pak files for their UI strings, i.e.: @@ -153,9 +182,9 @@ // as the secondary locale pak file. Otherwise don't load a secondary // locale at all. // - // This is set by SetLoadSecondaryLocalePaks() which is called - // during ChromeMainDelegate::PostEarlyInitialization() with a value - // that is true iff there are stored-locale/ .pak files. + // This is set by DetectAndSetLoadSecondaryLocalePaks() which is called + // during ChromeMainDelegate::PostEarlyInitialization(). It will set the + // value to true iff there are stored-locale/ .pak files. // // In other words, if both |g_locale_paks_in_apk| and // |g_load_secondary_locale_paks| are true, the stored-locales file will be @@ -194,11 +223,12 @@ } } - locale_resources_data_ = LoadDataPackFromLocalePak( - g_locale_pack_fd, g_locale_pack_region); + locale_resources_data_ = + LoadDataPackFromLocalePak(g_locale_pack_fd, g_locale_pack_region); - if (!locale_resources_data_.get()) + if (!locale_resources_data_.get()) { return std::string(); + } // Load secondary locale .pak file if it exists. For debug build monochrome, // a secondary locale pak will always be loaded; however, it should be @@ -211,8 +241,9 @@ secondary_locale_resources_data_ = LoadDataPackFromLocalePak( g_secondary_locale_pack_fd, g_secondary_locale_pack_region); - if (!secondary_locale_resources_data_.get()) + if (!secondary_locale_resources_data_.get()) { return std::string(); + } } return app_locale; @@ -226,8 +257,10 @@ g_locale_paks_in_apk = value; } -void SetLoadSecondaryLocalePaks(bool value) { - g_load_secondary_locale_paks = value; +void DetectAndSetLoadSecondaryLocalePaks() { + // Auto-detect based on en-US whether secondary locale .pak files exist. + g_load_secondary_locale_paks = + LocaleDataPakExists("en-US", false /* in_split */, false /* log_error */); } void LoadMainAndroidPackFile(const char* path_within_apk, @@ -245,49 +278,38 @@ void LoadPackFileFromApk(const std::string& path, const std::string& split_name) { base::MemoryMappedFile::Region region; - int fd = base::android::OpenApkAsset(path, split_name, ®ion); + FileDescriptor fd = base::android::OpenApkAsset(path, split_name, ®ion); CHECK_GE(fd, 0) << "Could not find " << path << " in APK."; ui::ResourceBundle::GetSharedInstance().AddDataPackFromFileRegion( base::File(fd), region, ui::kScaleFactorNone); } -int GetMainAndroidPackFd(base::MemoryMappedFile::Region* out_region) { +FileDescriptor GetMainAndroidPackFd( + base::MemoryMappedFile::Region* out_region) { DCHECK_GE(g_resources_pack_fd, 0); *out_region = g_resources_pack_region; return g_resources_pack_fd; } -int GetCommonResourcesPackFd(base::MemoryMappedFile::Region* out_region) { +FileDescriptor GetCommonResourcesPackFd( + base::MemoryMappedFile::Region* out_region) { DCHECK_GE(g_chrome_100_percent_fd, 0); *out_region = g_chrome_100_percent_region; return g_chrome_100_percent_fd; } -int GetLocalePackFd(base::MemoryMappedFile::Region* out_region) { +FileDescriptor GetLocalePackFd(base::MemoryMappedFile::Region* out_region) { DCHECK_GE(g_locale_pack_fd, 0); *out_region = g_locale_pack_region; return g_locale_pack_fd; } -int GetSecondaryLocalePackFd(base::MemoryMappedFile::Region* out_region) { +FileDescriptor GetSecondaryLocalePackFd( + base::MemoryMappedFile::Region* out_region) { *out_region = g_secondary_locale_pack_region; return g_secondary_locale_pack_fd; } -std::string GetPathForAndroidLocalePakWithinApk(const std::string& locale, - bool in_bundle, - bool log_error) { - JNIEnv* env = base::android::AttachCurrentThread(); - base::android::ScopedJavaLocalRef<jstring> ret = - Java_ResourceBundle_getLocalePakResourcePath( - env, base::android::ConvertUTF8ToJavaString(env, locale), in_bundle, - log_error); - if (ret.obj() == nullptr) { - return std::string(); - } - return base::android::ConvertJavaStringToUTF8(env, ret.obj()); -} - void SetNoAvailableLocalePaksForTest() { Java_ResourceBundle_setNoAvailableLocalePaks( base::android::AttachCurrentThread());
diff --git a/ui/base/resource/resource_bundle_android.h b/ui/base/resource/resource_bundle_android.h index ba8610e8..06ca565b 100644 --- a/ui/base/resource/resource_bundle_android.h +++ b/ui/base/resource/resource_bundle_android.h
@@ -44,20 +44,9 @@ // GetPathForAndroidLocalePakWithinApk rather than looking for them on disk. COMPONENT_EXPORT(UI_BASE) void SetLocalePaksStoredInApk(bool value); -// Tell ResourceBundle to load secondary locale .pak files. -COMPONENT_EXPORT(UI_BASE) void SetLoadSecondaryLocalePaks(bool value); - -// Returns the path within the apk for the given locale's .pak file, or an -// empty string if it doesn't exist. -// Only locale paks for the active Android language can be retrieved. -// If |in_split| is true, look into bundle split-specific location (e.g. -// 'assets/locales#lang_<lang>/<locale>.pak', otherwise use the default -// WebView-related location, i.e. 'assets/stored-locales/<locale>.pak'. -// If |log_error|, logs the path to logcat, but does not abort. -COMPONENT_EXPORT(UI_BASE) -std::string GetPathForAndroidLocalePakWithinApk(const std::string& locale, - bool in_split, - bool log_error); +// Tell ResourceBundle to determine whether load secondary locale .pak files +// based on whether secondary locale .pak files exist. +COMPONENT_EXPORT(UI_BASE) void DetectAndSetLoadSecondaryLocalePaks(); // Called in test when there are no locale pak files available. COMPONENT_EXPORT(UI_BASE) void SetNoAvailableLocalePaksForTest();
diff --git a/ui/base/ui_features.gni b/ui/base/ui_features.gni index 6e7ff9e..da4746e1c 100644 --- a/ui/base/ui_features.gni +++ b/ui/base/ui_features.gni
@@ -2,6 +2,7 @@ # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. +import("//build/config/features.gni") import("//build/config/ui.gni") declare_args() {
diff --git a/ui/events/ozone/chromeos/cursor_controller.cc b/ui/events/ozone/chromeos/cursor_controller.cc index b2f8007..6409c50 100644 --- a/ui/events/ozone/chromeos/cursor_controller.cc +++ b/ui/events/ozone/chromeos/cursor_controller.cc
@@ -49,8 +49,7 @@ void CursorController::AddCursorObserver(CursorObserver* observer) { base::AutoLock lock(cursor_observers_lock_); - CHECK(!base::Contains(cursor_observers_, observer), - base::NotFatalUntil::M126); + CHECK(!base::Contains(cursor_observers_, observer)); cursor_observers_.push_back(observer); }
diff --git a/ui/gl/gl_switches.cc b/ui/gl/gl_switches.cc index 3da4914..544c948c 100644 --- a/ui/gl/gl_switches.cc +++ b/ui/gl/gl_switches.cc
@@ -349,9 +349,17 @@ return false; #if BUILDFLAG(IS_ANDROID) + // Samsung GPUs already use ANGLE as the GLES driver. Always choose + // ANGLE/Vulkan on these GPUs to avoid the inefficiencies of translating + // over ANGLE twice. + if (active_gpu.driverId == VK_DRIVER_ID_SAMSUNG_PROPRIETARY) { + return true; + } + // Exclude SwiftShader-based Android emulators for now. - if (active_gpu.driverId == VK_DRIVER_ID_GOOGLE_SWIFTSHADER) + if (active_gpu.driverId == VK_DRIVER_ID_GOOGLE_SWIFTSHADER) { return false; + } // Encountered bugs with older Imagination drivers. New drivers seem fixed, // but disabled for the sake of experiment for now. crbug.com/371512561
diff --git a/ui/ozone/platform/wayland/wayland.gni b/ui/ozone/platform/wayland/wayland.gni index a966dea6..01e5517 100644 --- a/ui/ozone/platform/wayland/wayland.gni +++ b/ui/ozone/platform/wayland/wayland.gni
@@ -2,6 +2,7 @@ # Use of this source code is governed by a BSD-style license that can be # found in the LICENSE file. +import("//build/config/gclient_args.gni") import("//build/config/ozone.gni") import("//build/config/ui.gni")
diff --git a/ui/views/background.cc b/ui/views/background.cc index b63e5df..8714d51d 100644 --- a/ui/views/background.cc +++ b/ui/views/background.cc
@@ -54,8 +54,8 @@ public: RoundedRectBackground(ui::ColorVariant color, const gfx::RoundedCornersF& radii, - int for_border_thickness) - : radii_(radii), half_thickness_(for_border_thickness / 2.0f) { + const gfx::Insets& insets) + : radii_(radii), insets_(insets) { SetColor(color); } @@ -64,7 +64,7 @@ void Paint(gfx::Canvas* canvas, View* view) const override { gfx::Rect rect(view->GetLocalBounds()); - rect.Inset(half_thickness_); + rect.Inset(insets_); SkPath path; SkScalar radii[8] = {radii_.upper_left(), radii_.upper_left(), radii_.upper_right(), radii_.upper_right(), @@ -91,7 +91,7 @@ private: const gfx::RoundedCornersF radii_; - const float half_thickness_; + const gfx::Insets insets_; }; // ThemedVectorIconBackground is an image drawn on the view's background using @@ -188,14 +188,20 @@ ui::ColorVariant color, const gfx::RoundedCornersF& radii, int for_border_thickness) { + return CreateRoundedRectBackground(color, radii, + gfx::Insets(for_border_thickness / 2.0f)); +} + +std::unique_ptr<Background> CreateRoundedRectBackground( + ui::ColorVariant color, + const gfx::RoundedCornersF& radii, + const gfx::Insets& insets) { // If the radii is not set, fallback to SolidBackground since it results in // more efficient tiling by cc. See crbug.com/1464128. - if (radii.IsEmpty() && for_border_thickness == 0) { + if (radii.IsEmpty() && insets.IsEmpty()) { return CreateSolidBackground(color); } - - return std::make_unique<RoundedRectBackground>(color, radii, - for_border_thickness); + return std::make_unique<RoundedRectBackground>(color, radii, insets); } std::unique_ptr<Background> CreateThemedVectorIconBackground(
diff --git a/ui/views/background.h b/ui/views/background.h index 52cf4793..0beb41c 100644 --- a/ui/views/background.h +++ b/ui/views/background.h
@@ -16,6 +16,7 @@ #include "ui/color/color_id.h" #include "ui/color/color_variant.h" #include "ui/gfx/color_palette.h" +#include "ui/gfx/geometry/insets.h" #include "ui/gfx/geometry/rounded_corners_f.h" #include "ui/views/views_export.h" @@ -101,6 +102,12 @@ const gfx::RoundedCornersF& radii, int for_border_thickness = 0); +// Same as above except the background is inset by the specified insets. +VIEWS_EXPORT std::unique_ptr<Background> CreateRoundedRectBackground( + ui::ColorVariant color, + const gfx::RoundedCornersF& radii, + const gfx::Insets& insets); + // Creates a background from the specified Painter. VIEWS_EXPORT std::unique_ptr<Background> CreateBackgroundFromPainter( std::unique_ptr<Painter> painter);