From 6696b98eccd10d23b8a8ca74cc3fab4ac2195097 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 1 May 2025 11:41:45 -0500 Subject: [PATCH 001/186] refactor: add EmitDeprecationWarning helper (#46878) * refactor: add EmitDeprecationWarning helper Also switches EmitWarning to using Node's ProcessEmitWarningGeneric Co-authored-by: David Sanders * chore: use node namespace for function call Co-authored-by: David Sanders --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- shell/browser/api/electron_api_web_request.cc | 5 ++-- shell/browser/native_window_mac.mm | 5 ++-- shell/common/api/electron_api_native_image.cc | 5 ++-- shell/common/node_util.cc | 26 ++++++++++++------- shell/common/node_util.h | 12 ++++++++- 5 files changed, 34 insertions(+), 19 deletions(-) diff --git a/shell/browser/api/electron_api_web_request.cc b/shell/browser/api/electron_api_web_request.cc index 32e68a8a6c997..d2e58f9a23525 100644 --- a/shell/browser/api/electron_api_web_request.cc +++ b/shell/browser/api/electron_api_web_request.cc @@ -666,10 +666,9 @@ void WebRequest::SetListener(Event event, } if (filter_include_patterns.empty()) { - util::EmitWarning( + util::EmitDeprecationWarning( "The urls array in WebRequestFilter is empty, which is deprecated. " - "Please use '' to match all URLs.", - "DeprecationWarning"); + "Please use '' to match all URLs."); filter_include_patterns.insert(""); } diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 3fef4cba6c24e..2ebb32fa4d183 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -182,9 +182,8 @@ static bool FromV8(v8::Isolate* isolate, #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wdeprecated-declarations" if (windowType == "textured" && (transparent() || !has_frame())) { - util::EmitWarning( - "The 'textured' window type is deprecated and will be removed", - "DeprecationWarning"); + util::EmitDeprecationWarning( + "The 'textured' window type is deprecated and will be removed"); styleMask |= NSWindowStyleMaskTexturedBackground; } #pragma clang diagnostic pop diff --git a/shell/common/api/electron_api_native_image.cc b/shell/common/api/electron_api_native_image.cc index da34a3158c3fe..ffe3267b2999a 100644 --- a/shell/common/api/electron_api_native_image.cc +++ b/shell/common/api/electron_api_native_image.cc @@ -286,9 +286,8 @@ v8::Local NativeImage::GetBitmap(gin::Arguments* args) { if (!deprecated_warning_issued) { deprecated_warning_issued = true; - util::EmitWarning(isolate_, - "getBitmap() is deprecated, use toBitmap() instead.", - "DeprecationWarning"); + util::EmitDeprecationWarning( + isolate_, "getBitmap() is deprecated, use toBitmap() instead."); } return ToBitmap(args); diff --git a/shell/common/node_util.cc b/shell/common/node_util.cc index 055670cc4ddfb..89eaf88942194 100644 --- a/shell/common/node_util.cc +++ b/shell/common/node_util.cc @@ -12,10 +12,10 @@ #include "base/strings/string_number_conversions.h" #include "base/values.h" #include "gin/converter.h" -#include "gin/dictionary.h" #include "shell/browser/javascript_environment.h" #include "shell/common/gin_converters/callback_converter.h" #include "shell/common/node_includes.h" +#include "third_party/electron_node/src/node_process-inl.h" namespace electron::util { @@ -65,14 +65,22 @@ void EmitWarning(const std::string_view warning_msg, void EmitWarning(v8::Isolate* isolate, const std::string_view warning_msg, const std::string_view warning_type) { - v8::HandleScope scope{isolate}; - gin::Dictionary process{ - isolate, node::Environment::GetCurrent(isolate)->process_object()}; - base::RepeatingCallback - emit_warning; - process.Get("emitWarning", &emit_warning); - emit_warning.Run(warning_msg, warning_type, ""); + node::ProcessEmitWarningGeneric(node::Environment::GetCurrent(isolate), + warning_msg, warning_type); +} + +void EmitDeprecationWarning(const std::string_view warning_msg, + const std::string_view deprecation_code) { + EmitDeprecationWarning(JavascriptEnvironment::GetIsolate(), warning_msg, + deprecation_code); +} + +void EmitDeprecationWarning(v8::Isolate* isolate, + const std::string_view warning_msg, + const std::string_view deprecation_code) { + node::ProcessEmitWarningGeneric(node::Environment::GetCurrent(isolate), + warning_msg, "DeprecationWarning", + deprecation_code); } node::Environment* CreateEnvironment(v8::Isolate* isolate, diff --git a/shell/common/node_util.h b/shell/common/node_util.h index 36fcfdf940ba4..fdc92c0f6b9e5 100644 --- a/shell/common/node_util.h +++ b/shell/common/node_util.h @@ -30,9 +30,19 @@ void EmitWarning(v8::Isolate* isolate, std::string_view warning_type); // Emit a warning via node's process.emitWarning(), -// using JavscriptEnvironment's isolate +// using JavascriptEnvironment's isolate void EmitWarning(std::string_view warning_msg, std::string_view warning_type); +// Emit a deprecation warning via node's process.emitWarning() +void EmitDeprecationWarning(v8::Isolate* isolate, + std::string_view warning_msg, + std::string_view deprecation_code = ""); + +// Emit a deprecation warning via node's process.emitWarning(), +// using JavascriptEnvironment's isolate +void EmitDeprecationWarning(std::string_view warning_msg, + std::string_view deprecation_code = ""); + // Run a script with JS source bundled inside the binary as if it's wrapped // in a function called with a null receiver and arguments specified in C++. // The returned value is empty if an exception is encountered. From 7c77018b1974afb14467f002f1947363d91e0bed Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 1 May 2025 23:52:19 -0500 Subject: [PATCH 002/186] refactor: don't call deprecated `WidgetDelegate` API in `NativeWindowViews` (#46885) * refactor: don't call RegisterDeleteDelegateCallback() move NativeWindowViews' on-widget-delegate-destroyed callback logic to the NativeWindowViews destructor. Since NativeWindowViews subclasses from WidgetDelegate and |this| *is* the delegate being destroyed, we can handle this more cleanly in ~NativeWindowViews() instead of in a separate callback. Co-authored-by: Charles Kerr * chore: remove NativeWindowViews from the grandfathered-classes-that-can-call-deprecated-views-behavior patch Co-authored-by: Charles Kerr * refactor: don't call RegisterDeleteDelegateCallback() RegisterDeleteDelegateCallback() is private upstream API, so we shouldn't be using it. Move the on-widget-delegate-destroyed callback logic over to our methods NativeWindowViews::OnWidgetDestroying() and NativeWindowViews::OnWidgetDestroyed(). Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- ...ther_in_electron_views_and_delegates.patch | 12 ++++---- shell/browser/native_window_views.cc | 29 +++++++------------ 2 files changed, 16 insertions(+), 25 deletions(-) diff --git a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch index c19db7f2b7c6c..ee30ed47b66ac 100644 --- a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch +++ b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch @@ -49,10 +49,10 @@ index ae7eab37f12ba80ec423d229cf048021e9ba6765..507a75dc7947295db221b01356fa57ba // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop class. diff --git a/ui/views/widget/widget_delegate.h b/ui/views/widget/widget_delegate.h -index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..0d5c63e7efbe42d5352abdeb594175904af30c41 100644 +index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..e79beefddbd815e1ba7d9be86256e49d3ee7c619 100644 --- a/ui/views/widget/widget_delegate.h +++ b/ui/views/widget/widget_delegate.h -@@ -169,6 +169,13 @@ namespace data_controls { +@@ -169,6 +169,12 @@ namespace data_controls { class DesktopDataControlsDialog; } @@ -60,13 +60,12 @@ index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..0d5c63e7efbe42d5352abdeb59417590 +class AutofillPopupView; +class DevToolsWindowDelegate; +class NativeWindowMac; -+class NativeWindowViews; +} + namespace enterprise_connectors { class ContentAnalysisDialog; class ContentAnalysisDialogBehaviorBrowserTest; -@@ -371,6 +378,7 @@ class VIEWS_EXPORT WidgetDelegate { +@@ -371,6 +377,7 @@ class VIEWS_EXPORT WidgetDelegate { class OwnedByWidgetPassKey { private: @@ -74,16 +73,15 @@ index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..0d5c63e7efbe42d5352abdeb59417590 // DO NOT ADD TO THIS LIST! // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop `SetOwnedByWidget()`. -@@ -468,6 +476,8 @@ class VIEWS_EXPORT WidgetDelegate { +@@ -468,6 +475,7 @@ class VIEWS_EXPORT WidgetDelegate { }; class RegisterDeleteCallbackPassKey { private: + friend class electron::NativeWindowMac; -+ friend class electron::NativeWindowViews; // DO NOT ADD TO THIS LIST! // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop `RegisterDeleteDelegateCallback()`. -@@ -918,6 +928,7 @@ class VIEWS_EXPORT WidgetDelegateView : public WidgetDelegate, public View { +@@ -918,6 +926,7 @@ class VIEWS_EXPORT WidgetDelegateView : public WidgetDelegate, public View { View* GetContentsView() override; private: diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 610ecc7ecad82..fead4bf7c7c13 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -435,22 +435,6 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, // bounds if the bounds are smaller than the current display SetBounds(gfx::Rect(GetPosition(), bounds.size()), false); #endif - - RegisterDeleteDelegateCallback( - RegisterDeleteCallbackPassKey(), - base::BindOnce( - [](NativeWindowViews* window) { - if (window->is_modal() && window->parent()) { - auto* parent = window->parent(); - // Enable parent window after current window gets closed. - static_cast(parent)->DecrementChildModals(); - // Focus on parent window. - parent->Focus(true); - } - - window->NotifyWindowClosed(); - }, - this)); } NativeWindowViews::~NativeWindowViews() { @@ -1725,13 +1709,22 @@ void NativeWindowViews::OnWidgetBoundsChanged(views::Widget* changed_widget, } void NativeWindowViews::OnWidgetDestroying(views::Widget* widget) { - aura::Window* window = GetNativeWindow(); - if (window) + if (aura::Window* window = GetNativeWindow()) window->RemovePreTargetHandler(this); + + if (is_modal()) { + if (NativeWindow* const parent = this->parent()) { + // Enable parent window after current window gets closed. + static_cast(parent)->DecrementChildModals(); + // Focus on parent window. + parent->Focus(true); + } + } } void NativeWindowViews::OnWidgetDestroyed(views::Widget* changed_widget) { widget_destroyed_ = true; + NotifyWindowClosed(); } views::View* NativeWindowViews::GetInitiallyFocusedView() { From 534ad05cf288ecdf409080b7013d8f578480224f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 13:18:46 +0200 Subject: [PATCH 003/186] fix: revert macOS content protection logic refactor (#46891) Revert "refactor: use upstream content protection logic on macOS (#46813)" This reverts commit 34adb976b632157379de34cc1a71bdf6cc089714. Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Keeley Hammond --- shell/browser/native_window.cc | 15 --------------- shell/browser/native_window.h | 4 ++-- shell/browser/native_window_mac.h | 2 ++ shell/browser/native_window_mac.mm | 9 +++++++++ shell/browser/native_window_views.cc | 15 +++++++++++++++ shell/browser/native_window_views.h | 2 ++ 6 files changed, 30 insertions(+), 17 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 9a6db49f0763a..2bbd1ede039ea 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -26,7 +26,6 @@ #include "shell/common/options_switches.h" #include "ui/base/hit_test.h" #include "ui/compositor/compositor.h" -#include "ui/views/widget/native_widget_private.h" #include "ui/views/widget/widget.h" #if !BUILDFLAG(IS_MAC) @@ -823,20 +822,6 @@ void NativeWindow::HandlePendingFullscreenTransitions() { SetFullScreen(next_transition); } -void NativeWindow::SetContentProtection(bool enable) { -#if !BUILDFLAG(IS_LINUX) - widget()->native_widget_private()->SetAllowScreenshots(!enable); -#endif -} - -bool NativeWindow::IsContentProtected() const { -#if !BUILDFLAG(IS_LINUX) - return !widget()->native_widget_private()->AreScreenshotsAllowed(); -#else // Not implemented on Linux - return false; -#endif -} - bool NativeWindow::IsTranslucent() const { // Transparent windows are translucent if (transparent()) { diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index 7a9b762c60b2c..831cf8947aa85 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -186,8 +186,8 @@ class NativeWindow : public base::SupportsUserData, virtual void SetDocumentEdited(bool edited) {} virtual bool IsDocumentEdited() const; virtual void SetIgnoreMouseEvents(bool ignore, bool forward) = 0; - void SetContentProtection(bool enable); - bool IsContentProtected() const; + virtual void SetContentProtection(bool enable) = 0; + virtual bool IsContentProtected() const = 0; virtual void SetFocusable(bool focusable) {} virtual bool IsFocusable() const; virtual void SetMenu(ElectronMenuModel* menu) {} diff --git a/shell/browser/native_window_mac.h b/shell/browser/native_window_mac.h index fa51e9ee447d2..5420e14aecd7d 100644 --- a/shell/browser/native_window_mac.h +++ b/shell/browser/native_window_mac.h @@ -109,6 +109,8 @@ class NativeWindowMac : public NativeWindow, void SetIgnoreMouseEvents(bool ignore, bool forward) override; bool IsHiddenInMissionControl() const override; void SetHiddenInMissionControl(bool hidden) override; + void SetContentProtection(bool enable) override; + bool IsContentProtected() const override; void SetFocusable(bool focusable) override; bool IsFocusable() const override; void SetParentWindow(NativeWindow* parent) override; diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 2ebb32fa4d183..6d8a2712420be 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -1171,6 +1171,15 @@ static bool FromV8(v8::Isolate* isolate, } } +void NativeWindowMac::SetContentProtection(bool enable) { + [window_ + setSharingType:enable ? NSWindowSharingNone : NSWindowSharingReadOnly]; +} + +bool NativeWindowMac::IsContentProtected() const { + return [window_ sharingType] == NSWindowSharingNone; +} + void NativeWindowMac::SetFocusable(bool focusable) { // No known way to unfocus the window if it had the focus. Here we do not // want to call Focus(false) because it moves the window to the back, i.e. diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index fead4bf7c7c13..f9c659a9ddd0b 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -44,6 +44,7 @@ #include "ui/ozone/public/ozone_platform.h" #include "ui/views/background.h" #include "ui/views/controls/webview/webview.h" +#include "ui/views/widget/native_widget_private.h" #include "ui/views/widget/widget.h" #include "ui/views/window/client_view.h" #include "ui/wm/core/shadow_types.h" @@ -1310,6 +1311,20 @@ void NativeWindowViews::SetIgnoreMouseEvents(bool ignore, bool forward) { #endif } +void NativeWindowViews::SetContentProtection(bool enable) { +#if BUILDFLAG(IS_WIN) + widget()->native_widget_private()->SetAllowScreenshots(!enable); +#endif +} + +bool NativeWindowViews::IsContentProtected() const { +#if BUILDFLAG(IS_WIN) + return !widget()->native_widget_private()->AreScreenshotsAllowed(); +#else // Not implemented on Linux + return false; +#endif +} + void NativeWindowViews::SetFocusable(bool focusable) { widget()->widget_delegate()->SetCanActivate(focusable); #if BUILDFLAG(IS_WIN) diff --git a/shell/browser/native_window_views.h b/shell/browser/native_window_views.h index 5bc9db1ea7bb8..8ef7d2b783a2f 100644 --- a/shell/browser/native_window_views.h +++ b/shell/browser/native_window_views.h @@ -115,6 +115,8 @@ class NativeWindowViews : public NativeWindow, void SetOpacity(const double opacity) override; double GetOpacity() const override; void SetIgnoreMouseEvents(bool ignore, bool forward) override; + void SetContentProtection(bool enable) override; + bool IsContentProtected() const override; void SetFocusable(bool focusable) override; bool IsFocusable() const override; void SetMenu(ElectronMenuModel* menu_model) override; From 620f3a57dd4c0695b3d129328f60593d33c0c633 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 13:19:52 +0200 Subject: [PATCH 004/186] docs: clarified usage of createFromPath() (#46898) * docs: clarified usage of createFromPath() Co-authored-by: Yuri * Update docs/api/native-image.md Co-authored-by: Niklas Wenzel Co-authored-by: Yuri --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Yuri --- docs/api/native-image.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/api/native-image.md b/docs/api/native-image.md index 14ee825618c30..58c9dadfd3c01 100644 --- a/docs/api/native-image.md +++ b/docs/api/native-image.md @@ -142,8 +142,8 @@ Note: The Windows implementation will ignore `size.height` and scale the height Returns `NativeImage` -Creates a new `NativeImage` instance from a file located at `path`. This method -returns an empty image if the `path` does not exist, cannot be read, or is not +Creates a new `NativeImage` instance from an image file (e.g., PNG or JPEG) located at `path`. +This method returns an empty image if the `path` does not exist, cannot be read, or is not a valid image. ```js From 46e3ab63530a6288064d6f1fb5eba6d70e5968e4 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 07:50:47 -0500 Subject: [PATCH 005/186] refactor: use `base::ObserverList::Notify()` (#46896) * refactor: use ObserverList::Notify() in shell/browser/window_list.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/web_contents_zoom_controller.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/usb/usb_chooser_context.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/usb/electron_usb_delegate.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/ui/views/menu_delegate.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/ui/tray_icon.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/ui/electron_menu_model.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/serial/serial_chooser_context.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/native_window.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/serial/electron_serial_delegate.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/browser.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/api/electron_api_web_contents.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/hid/electron_hid_delegate.cc Co-authored-by: Charles Kerr * refactor: use ObserverList::Notify() in shell/browser/hid/hid_chooser_context.cc Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- .../browser/api/electron_api_web_contents.cc | 13 +- shell/browser/browser.cc | 48 +++---- shell/browser/hid/electron_hid_delegate.cc | 16 +-- shell/browser/hid/hid_chooser_context.cc | 12 +- shell/browser/native_window.cc | 120 +++++++----------- .../serial/electron_serial_delegate.cc | 11 +- .../browser/serial/serial_chooser_context.cc | 7 +- shell/browser/ui/electron_menu_model.cc | 8 +- shell/browser/ui/tray_icon.cc | 54 +++----- shell/browser/ui/views/menu_delegate.cc | 9 +- shell/browser/usb/electron_usb_delegate.cc | 12 +- shell/browser/usb/usb_chooser_context.cc | 9 +- shell/browser/web_contents_zoom_controller.cc | 35 +++-- shell/browser/window_list.cc | 9 +- 14 files changed, 134 insertions(+), 229 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index 487f2461a25d2..71b4733a34b61 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -1299,8 +1299,7 @@ void WebContents::BeforeUnloadFired(content::WebContents* tab, void WebContents::SetContentsBounds(content::WebContents* source, const gfx::Rect& rect) { if (!Emit("content-bounds-updated", rect)) - for (ExtendedWebContentsObserver& observer : observers_) - observer.OnSetContentBounds(rect); + observers_.Notify(&ExtendedWebContentsObserver::OnSetContentBounds, rect); } void WebContents::CloseContents(content::WebContents* source) { @@ -1316,8 +1315,7 @@ void WebContents::CloseContents(content::WebContents* source) { } void WebContents::ActivateContents(content::WebContents* source) { - for (ExtendedWebContentsObserver& observer : observers_) - observer.OnActivateContents(); + observers_.Notify(&ExtendedWebContentsObserver::OnActivateContents); } void WebContents::UpdateTargetURL(content::WebContents* source, @@ -2112,8 +2110,8 @@ void WebContents::TitleWasSet(content::NavigationEntry* entry) { } else { final_title = web_contents()->GetTitle(); } - for (ExtendedWebContentsObserver& observer : observers_) - observer.OnPageTitleUpdated(final_title, explicit_set); + observers_.Notify(&ExtendedWebContentsObserver::OnPageTitleUpdated, + final_title, explicit_set); Emit("page-title-updated", final_title, explicit_set); } @@ -2169,8 +2167,7 @@ void WebContents::DevToolsClosed() { } void WebContents::DevToolsResized() { - for (ExtendedWebContentsObserver& observer : observers_) - observer.OnDevToolsResized(); + observers_.Notify(&ExtendedWebContentsObserver::OnDevToolsResized); } void WebContents::SetOwnerWindow(NativeWindow* owner_window) { diff --git a/shell/browser/browser.cc b/shell/browser/browser.cc index 711aa4c2b9c44..0c0e7c8c5076f 100644 --- a/shell/browser/browser.cc +++ b/shell/browser/browser.cc @@ -129,8 +129,7 @@ void Browser::Shutdown() { is_shutdown_ = true; is_quitting_ = true; - for (BrowserObserver& observer : observers_) - observer.OnQuit(); + observers_.Notify(&BrowserObserver::OnQuit); if (quit_main_message_loop_) { RunQuitClosure(std::move(quit_main_message_loop_)); @@ -165,25 +164,20 @@ void Browser::SetName(const std::string& name) { bool Browser::OpenFile(const std::string& file_path) { bool prevent_default = false; - for (BrowserObserver& observer : observers_) - observer.OnOpenFile(&prevent_default, file_path); - + observers_.Notify(&BrowserObserver::OnOpenFile, &prevent_default, file_path); return prevent_default; } void Browser::OpenURL(const std::string& url) { - for (BrowserObserver& observer : observers_) - observer.OnOpenURL(url); + observers_.Notify(&BrowserObserver::OnOpenURL, url); } void Browser::Activate(bool has_visible_windows) { - for (BrowserObserver& observer : observers_) - observer.OnActivate(has_visible_windows); + observers_.Notify(&BrowserObserver::OnActivate, has_visible_windows); } void Browser::WillFinishLaunching() { - for (BrowserObserver& observer : observers_) - observer.OnWillFinishLaunching(); + observers_.Notify(&BrowserObserver::OnWillFinishLaunching); } void Browser::DidFinishLaunching(base::Value::Dict launch_info) { @@ -201,6 +195,7 @@ void Browser::DidFinishLaunching(base::Value::Dict launch_info) { if (ready_promise_) { ready_promise_->Resolve(); } + for (BrowserObserver& observer : observers_) observer.OnFinishLaunching(launch_info.Clone()); } @@ -216,20 +211,15 @@ v8::Local Browser::WhenReady(v8::Isolate* isolate) { } void Browser::OnAccessibilitySupportChanged() { - for (BrowserObserver& observer : observers_) - observer.OnAccessibilitySupportChanged(); + observers_.Notify(&BrowserObserver::OnAccessibilitySupportChanged); } void Browser::PreMainMessageLoopRun() { - for (BrowserObserver& observer : observers_) { - observer.OnPreMainMessageLoopRun(); - } + observers_.Notify(&BrowserObserver::OnPreMainMessageLoopRun); } void Browser::PreCreateThreads() { - for (BrowserObserver& observer : observers_) { - observer.OnPreCreateThreads(); - } + observers_.Notify(&BrowserObserver::OnPreCreateThreads); } void Browser::SetMainMessageLoopQuitClosure(base::OnceClosure quit_closure) { @@ -244,9 +234,7 @@ void Browser::NotifyAndShutdown() { return; bool prevent_default = false; - for (BrowserObserver& observer : observers_) - observer.OnWillQuit(&prevent_default); - + observers_.Notify(&BrowserObserver::OnWillQuit, &prevent_default); if (prevent_default) { is_quitting_ = false; return; @@ -257,9 +245,7 @@ void Browser::NotifyAndShutdown() { bool Browser::HandleBeforeQuit() { bool prevent_default = false; - for (BrowserObserver& observer : observers_) - observer.OnBeforeQuit(&prevent_default); - + observers_.Notify(&BrowserObserver::OnBeforeQuit, &prevent_default); return !prevent_default; } @@ -276,25 +262,21 @@ void Browser::OnWindowAllClosed() { } else if (is_quitting_) { NotifyAndShutdown(); } else { - for (BrowserObserver& observer : observers_) - observer.OnWindowAllClosed(); + observers_.Notify(&BrowserObserver::OnWindowAllClosed); } } #if BUILDFLAG(IS_MAC) void Browser::NewWindowForTab() { - for (BrowserObserver& observer : observers_) - observer.OnNewWindowForTab(); + observers_.Notify(&BrowserObserver::OnNewWindowForTab); } void Browser::DidBecomeActive() { - for (BrowserObserver& observer : observers_) - observer.OnDidBecomeActive(); + observers_.Notify(&BrowserObserver::OnDidBecomeActive); } void Browser::DidResignActive() { - for (BrowserObserver& observer : observers_) - observer.OnDidResignActive(); + observers_.Notify(&BrowserObserver::OnDidResignActive); } #endif diff --git a/shell/browser/hid/electron_hid_delegate.cc b/shell/browser/hid/electron_hid_delegate.cc index aea69296dbfa2..2d235845e821f 100644 --- a/shell/browser/hid/electron_hid_delegate.cc +++ b/shell/browser/hid/electron_hid_delegate.cc @@ -56,25 +56,25 @@ class ElectronHidDelegate::ContextObservation // HidChooserContext::DeviceObserver: void OnDeviceAdded(const device::mojom::HidDeviceInfo& device_info) override { - for (auto& observer : observer_list_) - observer.OnDeviceAdded(device_info); + observer_list_.Notify(&content::HidDelegate::Observer::OnDeviceAdded, + device_info); } void OnDeviceRemoved( const device::mojom::HidDeviceInfo& device_info) override { - for (auto& observer : observer_list_) - observer.OnDeviceRemoved(device_info); + observer_list_.Notify(&content::HidDelegate::Observer::OnDeviceRemoved, + device_info); } void OnDeviceChanged( const device::mojom::HidDeviceInfo& device_info) override { - for (auto& observer : observer_list_) - observer.OnDeviceChanged(device_info); + observer_list_.Notify(&content::HidDelegate::Observer::OnDeviceChanged, + device_info); } void OnHidManagerConnectionError() override { - for (auto& observer : observer_list_) - observer.OnHidManagerConnectionError(); + observer_list_.Notify( + &content::HidDelegate::Observer::OnHidManagerConnectionError); } void OnHidChooserContextShutdown() override { diff --git a/shell/browser/hid/hid_chooser_context.cc b/shell/browser/hid/hid_chooser_context.cc index e135dd1c762e5..c1ad43c8f97f8 100644 --- a/shell/browser/hid/hid_chooser_context.cc +++ b/shell/browser/hid/hid_chooser_context.cc @@ -244,8 +244,7 @@ void HidChooserContext::DeviceAdded(device::mojom::HidDeviceInfoPtr device) { devices_.insert({device->guid, device->Clone()}); // Notify all observers. - for (auto& observer : device_observer_list_) - observer.OnDeviceAdded(*device); + device_observer_list_.Notify(&DeviceObserver::OnDeviceAdded, *device); } void HidChooserContext::DeviceRemoved(device::mojom::HidDeviceInfoPtr device) { @@ -256,8 +255,7 @@ void HidChooserContext::DeviceRemoved(device::mojom::HidDeviceInfoPtr device) { DCHECK_EQ(n_erased, 1U); // Notify all device observers. - for (auto& observer : device_observer_list_) - observer.OnDeviceRemoved(*device); + device_observer_list_.Notify(&DeviceObserver::OnDeviceRemoved, *device); // Next we'll notify observers for revoked permissions. If the device does not // support persistent permissions then device permissions are revoked on @@ -278,8 +276,7 @@ void HidChooserContext::DeviceChanged(device::mojom::HidDeviceInfoPtr device) { mapped = device->Clone(); // Notify all observers. - for (auto& observer : device_observer_list_) - observer.OnDeviceChanged(*device); + device_observer_list_.Notify(&DeviceObserver::OnDeviceChanged, *device); } void HidChooserContext::EnsureHidManagerConnection() { @@ -329,8 +326,7 @@ void HidChooserContext::OnHidManagerConnectionError() { ephemeral_devices_.clear(); // Notify all device observers. - for (auto& observer : device_observer_list_) - observer.OnHidManagerConnectionError(); + device_observer_list_.Notify(&DeviceObserver::OnHidManagerConnectionError); } } // namespace electron diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 2bbd1ede039ea..19232b6259b0b 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -504,23 +504,21 @@ void NativeWindow::SetWindowControlsOverlayRect(const gfx::Rect& overlay_rect) { } void NativeWindow::NotifyWindowRequestPreferredWidth(int* width) { - for (NativeWindowObserver& observer : observers_) - observer.RequestPreferredWidth(width); + observers_.Notify(&NativeWindowObserver::RequestPreferredWidth, width); } void NativeWindow::NotifyWindowCloseButtonClicked() { // First ask the observers whether we want to close. bool prevent_default = false; - for (NativeWindowObserver& observer : observers_) - observer.WillCloseWindow(&prevent_default); + observers_.Notify(&NativeWindowObserver::WillCloseWindow, &prevent_default); if (prevent_default) { WindowList::WindowCloseCancelled(this); return; } // Then ask the observers how should we close the window. - for (NativeWindowObserver& observer : observers_) - observer.OnCloseButtonClicked(&prevent_default); + observers_.Notify(&NativeWindowObserver::OnCloseButtonClicked, + &prevent_default); if (prevent_default) return; @@ -532,8 +530,7 @@ void NativeWindow::NotifyWindowClosed() { return; is_closed_ = true; - for (NativeWindowObserver& observer : observers_) - observer.OnWindowClosed(); + observers_.Notify(&NativeWindowObserver::OnWindowClosed); WindowList::RemoveWindow(this); } @@ -541,180 +538,153 @@ void NativeWindow::NotifyWindowClosed() { void NativeWindow::NotifyWindowQueryEndSession( const std::vector& reasons, bool* prevent_default) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowQueryEndSession(reasons, prevent_default); + observers_.Notify(&NativeWindowObserver::OnWindowQueryEndSession, reasons, + prevent_default); } void NativeWindow::NotifyWindowEndSession( const std::vector& reasons) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowEndSession(reasons); + observers_.Notify(&NativeWindowObserver::OnWindowEndSession, reasons); } void NativeWindow::NotifyWindowBlur() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowBlur(); + observers_.Notify(&NativeWindowObserver::OnWindowBlur); } void NativeWindow::NotifyWindowFocus() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowFocus(); + observers_.Notify(&NativeWindowObserver::OnWindowFocus); } void NativeWindow::NotifyWindowIsKeyChanged(bool is_key) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowIsKeyChanged(is_key); + observers_.Notify(&NativeWindowObserver::OnWindowIsKeyChanged, is_key); } void NativeWindow::NotifyWindowShow() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowShow(); + observers_.Notify(&NativeWindowObserver::OnWindowShow); } void NativeWindow::NotifyWindowHide() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowHide(); + observers_.Notify(&NativeWindowObserver::OnWindowHide); } void NativeWindow::NotifyWindowMaximize() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowMaximize(); + observers_.Notify(&NativeWindowObserver::OnWindowMaximize); } void NativeWindow::NotifyWindowUnmaximize() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowUnmaximize(); + observers_.Notify(&NativeWindowObserver::OnWindowUnmaximize); } void NativeWindow::NotifyWindowMinimize() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowMinimize(); + observers_.Notify(&NativeWindowObserver::OnWindowMinimize); } void NativeWindow::NotifyWindowRestore() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowRestore(); + observers_.Notify(&NativeWindowObserver::OnWindowRestore); } void NativeWindow::NotifyWindowWillResize(const gfx::Rect& new_bounds, const gfx::ResizeEdge& edge, bool* prevent_default) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowWillResize(new_bounds, edge, prevent_default); + observers_.Notify(&NativeWindowObserver::OnWindowWillResize, new_bounds, edge, + prevent_default); } void NativeWindow::NotifyWindowWillMove(const gfx::Rect& new_bounds, bool* prevent_default) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowWillMove(new_bounds, prevent_default); + observers_.Notify(&NativeWindowObserver::OnWindowWillMove, new_bounds, + prevent_default); } void NativeWindow::NotifyWindowResize() { NotifyLayoutWindowControlsOverlay(); - for (NativeWindowObserver& observer : observers_) - observer.OnWindowResize(); + observers_.Notify(&NativeWindowObserver::OnWindowResize); } void NativeWindow::NotifyWindowResized() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowResized(); + observers_.Notify(&NativeWindowObserver::OnWindowResized); } void NativeWindow::NotifyWindowMove() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowMove(); + observers_.Notify(&NativeWindowObserver::OnWindowMove); } void NativeWindow::NotifyWindowMoved() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowMoved(); + observers_.Notify(&NativeWindowObserver::OnWindowMoved); } void NativeWindow::NotifyWindowEnterFullScreen() { NotifyLayoutWindowControlsOverlay(); - for (NativeWindowObserver& observer : observers_) - observer.OnWindowEnterFullScreen(); + observers_.Notify(&NativeWindowObserver::OnWindowEnterFullScreen); } void NativeWindow::NotifyWindowSwipe(const std::string& direction) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowSwipe(direction); + observers_.Notify(&NativeWindowObserver::OnWindowSwipe, direction); } void NativeWindow::NotifyWindowRotateGesture(float rotation) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowRotateGesture(rotation); + observers_.Notify(&NativeWindowObserver::OnWindowRotateGesture, rotation); } void NativeWindow::NotifyWindowSheetBegin() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowSheetBegin(); + observers_.Notify(&NativeWindowObserver::OnWindowSheetBegin); } void NativeWindow::NotifyWindowSheetEnd() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowSheetEnd(); + observers_.Notify(&NativeWindowObserver::OnWindowSheetEnd); } void NativeWindow::NotifyWindowLeaveFullScreen() { NotifyLayoutWindowControlsOverlay(); - for (NativeWindowObserver& observer : observers_) - observer.OnWindowLeaveFullScreen(); + observers_.Notify(&NativeWindowObserver::OnWindowLeaveFullScreen); } void NativeWindow::NotifyWindowEnterHtmlFullScreen() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowEnterHtmlFullScreen(); + observers_.Notify(&NativeWindowObserver::OnWindowEnterHtmlFullScreen); } void NativeWindow::NotifyWindowLeaveHtmlFullScreen() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowLeaveHtmlFullScreen(); + observers_.Notify(&NativeWindowObserver::OnWindowLeaveHtmlFullScreen); } void NativeWindow::NotifyWindowAlwaysOnTopChanged() { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowAlwaysOnTopChanged(); + observers_.Notify(&NativeWindowObserver::OnWindowAlwaysOnTopChanged); } void NativeWindow::NotifyWindowExecuteAppCommand( const std::string_view command_name) { - for (NativeWindowObserver& observer : observers_) - observer.OnExecuteAppCommand(command_name); + observers_.Notify(&NativeWindowObserver::OnExecuteAppCommand, command_name); } void NativeWindow::NotifyTouchBarItemInteraction(const std::string& item_id, base::Value::Dict details) { - for (NativeWindowObserver& observer : observers_) - observer.OnTouchBarItemResult(item_id, details); + observers_.Notify(&NativeWindowObserver::OnTouchBarItemResult, item_id, + details); } void NativeWindow::NotifyNewWindowForTab() { - for (NativeWindowObserver& observer : observers_) - observer.OnNewWindowForTab(); + observers_.Notify(&NativeWindowObserver::OnNewWindowForTab); } void NativeWindow::NotifyWindowSystemContextMenu(int x, int y, bool* prevent_default) { - for (NativeWindowObserver& observer : observers_) - observer.OnSystemContextMenu(x, y, prevent_default); + observers_.Notify(&NativeWindowObserver::OnSystemContextMenu, x, y, + prevent_default); } void NativeWindow::NotifyLayoutWindowControlsOverlay() { - auto bounding_rect = GetWindowControlsOverlayRect(); - if (bounding_rect.has_value()) { - for (NativeWindowObserver& observer : observers_) - observer.UpdateWindowControlsOverlay(bounding_rect.value()); - } + if (const auto bounds = GetWindowControlsOverlayRect()) + observers_.Notify(&NativeWindowObserver::UpdateWindowControlsOverlay, + *bounds); } #if BUILDFLAG(IS_WIN) void NativeWindow::NotifyWindowMessage(UINT message, WPARAM w_param, LPARAM l_param) { - for (NativeWindowObserver& observer : observers_) - observer.OnWindowMessage(message, w_param, l_param); + observers_.Notify(&NativeWindowObserver::OnWindowMessage, message, w_param, + l_param); } #endif diff --git a/shell/browser/serial/electron_serial_delegate.cc b/shell/browser/serial/electron_serial_delegate.cc index bd8f5c5a85c6c..5b6821d26522d 100644 --- a/shell/browser/serial/electron_serial_delegate.cc +++ b/shell/browser/serial/electron_serial_delegate.cc @@ -128,20 +128,19 @@ void ElectronSerialDelegate::DeleteControllerForFrame( // SerialChooserContext::PortObserver: void ElectronSerialDelegate::OnPortAdded( const device::mojom::SerialPortInfo& port) { - for (auto& observer : observer_list_) - observer.OnPortAdded(port); + observer_list_.Notify(&content::SerialDelegate::Observer::OnPortAdded, port); } void ElectronSerialDelegate::OnPortRemoved( const device::mojom::SerialPortInfo& port) { - for (auto& observer : observer_list_) - observer.OnPortRemoved(port); + observer_list_.Notify(&content::SerialDelegate::Observer::OnPortRemoved, + port); } void ElectronSerialDelegate::OnPortManagerConnectionError() { port_observation_.Reset(); - for (auto& observer : observer_list_) - observer.OnPortManagerConnectionError(); + observer_list_.Notify( + &content::SerialDelegate::Observer::OnPortManagerConnectionError); } void ElectronSerialDelegate::OnSerialChooserContextShutdown() { diff --git a/shell/browser/serial/serial_chooser_context.cc b/shell/browser/serial/serial_chooser_context.cc index 5d096743d8541..22b09744a8f5f 100644 --- a/shell/browser/serial/serial_chooser_context.cc +++ b/shell/browser/serial/serial_chooser_context.cc @@ -238,15 +238,12 @@ void SerialChooserContext::OnPortAdded(device::mojom::SerialPortInfoPtr port) { ports.erase(port->token); } - for (auto& observer : port_observer_list_) - observer.OnPortAdded(*port); + port_observer_list_.Notify(&PortObserver::OnPortAdded, *port); } void SerialChooserContext::OnPortRemoved( device::mojom::SerialPortInfoPtr port) { - for (auto& observer : port_observer_list_) - observer.OnPortRemoved(*port); - + port_observer_list_.Notify(&PortObserver::OnPortRemoved, *port); port_info_.erase(port->token); } diff --git a/shell/browser/ui/electron_menu_model.cc b/shell/browser/ui/electron_menu_model.cc index e926d24e3bd19..fd854a6313bb3 100644 --- a/shell/browser/ui/electron_menu_model.cc +++ b/shell/browser/ui/electron_menu_model.cc @@ -101,16 +101,12 @@ void ElectronMenuModel::SetSharingItem(SharingItem item) { void ElectronMenuModel::MenuWillClose() { ui::SimpleMenuModel::MenuWillClose(); - for (Observer& observer : observers_) { - observer.OnMenuWillClose(); - } + observers_.Notify(&Observer::OnMenuWillClose); } void ElectronMenuModel::MenuWillShow() { ui::SimpleMenuModel::MenuWillShow(); - for (Observer& observer : observers_) { - observer.OnMenuWillShow(); - } + observers_.Notify(&Observer::OnMenuWillShow); } ElectronMenuModel* ElectronMenuModel::GetSubmenuModelAt(size_t index) { diff --git a/shell/browser/ui/tray_icon.cc b/shell/browser/ui/tray_icon.cc index 22de23fb65c5c..acb1b2fe5c19c 100644 --- a/shell/browser/ui/tray_icon.cc +++ b/shell/browser/ui/tray_icon.cc @@ -19,93 +19,75 @@ gfx::Rect TrayIcon::GetBounds() { void TrayIcon::NotifyClicked(const gfx::Rect& bounds, const gfx::Point& location, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnClicked(bounds, location, modifiers); + observers_.Notify(&TrayIconObserver::OnClicked, bounds, location, modifiers); } void TrayIcon::NotifyDoubleClicked(const gfx::Rect& bounds, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnDoubleClicked(bounds, modifiers); + observers_.Notify(&TrayIconObserver::OnDoubleClicked, bounds, modifiers); } void TrayIcon::NotifyMiddleClicked(const gfx::Rect& bounds, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnMiddleClicked(bounds, modifiers); + observers_.Notify(&TrayIconObserver::OnMiddleClicked, bounds, modifiers); } void TrayIcon::NotifyBalloonShow() { - for (TrayIconObserver& observer : observers_) - observer.OnBalloonShow(); + observers_.Notify(&TrayIconObserver::OnBalloonShow); } void TrayIcon::NotifyBalloonClicked() { - for (TrayIconObserver& observer : observers_) - observer.OnBalloonClicked(); + observers_.Notify(&TrayIconObserver::OnBalloonClicked); } void TrayIcon::NotifyBalloonClosed() { - for (TrayIconObserver& observer : observers_) - observer.OnBalloonClosed(); + observers_.Notify(&TrayIconObserver::OnBalloonClosed); } void TrayIcon::NotifyRightClicked(const gfx::Rect& bounds, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnRightClicked(bounds, modifiers); + observers_.Notify(&TrayIconObserver::OnRightClicked, bounds, modifiers); } void TrayIcon::NotifyDrop() { - for (TrayIconObserver& observer : observers_) - observer.OnDrop(); + observers_.Notify(&TrayIconObserver::OnDrop); } void TrayIcon::NotifyDropFiles(const std::vector& files) { - for (TrayIconObserver& observer : observers_) - observer.OnDropFiles(files); + observers_.Notify(&TrayIconObserver::OnDropFiles, files); } void TrayIcon::NotifyDropText(const std::string& text) { - for (TrayIconObserver& observer : observers_) - observer.OnDropText(text); + observers_.Notify(&TrayIconObserver::OnDropText, text); } void TrayIcon::NotifyMouseUp(const gfx::Point& location, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnMouseUp(location, modifiers); + observers_.Notify(&TrayIconObserver::OnMouseUp, location, modifiers); } void TrayIcon::NotifyMouseDown(const gfx::Point& location, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnMouseDown(location, modifiers); + observers_.Notify(&TrayIconObserver::OnMouseDown, location, modifiers); } void TrayIcon::NotifyMouseEntered(const gfx::Point& location, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnMouseEntered(location, modifiers); + observers_.Notify(&TrayIconObserver::OnMouseEntered, location, modifiers); } void TrayIcon::NotifyMouseExited(const gfx::Point& location, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnMouseExited(location, modifiers); + observers_.Notify(&TrayIconObserver::OnMouseExited, location, modifiers); } void TrayIcon::NotifyMouseMoved(const gfx::Point& location, int modifiers) { - for (TrayIconObserver& observer : observers_) - observer.OnMouseMoved(location, modifiers); + observers_.Notify(&TrayIconObserver::OnMouseMoved, location, modifiers); } void TrayIcon::NotifyDragEntered() { - for (TrayIconObserver& observer : observers_) - observer.OnDragEntered(); + observers_.Notify(&TrayIconObserver::OnDragEntered); } void TrayIcon::NotifyDragExited() { - for (TrayIconObserver& observer : observers_) - observer.OnDragExited(); + observers_.Notify(&TrayIconObserver::OnDragExited); } void TrayIcon::NotifyDragEnded() { - for (TrayIconObserver& observer : observers_) - observer.OnDragEnded(); + observers_.Notify(&TrayIconObserver::OnDragEnded); } } // namespace electron diff --git a/shell/browser/ui/views/menu_delegate.cc b/shell/browser/ui/views/menu_delegate.cc index 2d7ca15f2a86e..cf79c26f5ad3a 100644 --- a/shell/browser/ui/views/menu_delegate.cc +++ b/shell/browser/ui/views/menu_delegate.cc @@ -51,14 +51,12 @@ void MenuDelegate::RunMenu(ElectronMenuModel* model, } void MenuDelegate::ExecuteCommand(int id) { - for (Observer& obs : observers_) - obs.OnBeforeExecuteCommand(); + observers_.Notify(&Observer::OnBeforeExecuteCommand); adapter_->ExecuteCommand(id); } void MenuDelegate::ExecuteCommand(int id, int mouse_event_flags) { - for (Observer& obs : observers_) - obs.OnBeforeExecuteCommand(); + observers_.Notify(&Observer::OnBeforeExecuteCommand); adapter_->ExecuteCommand(id, mouse_event_flags); } @@ -104,8 +102,7 @@ void MenuDelegate::WillHideMenu(views::MenuItemView* menu) { } void MenuDelegate::OnMenuClosed(views::MenuItemView* menu) { - for (Observer& obs : observers_) - obs.OnMenuClosed(); + observers_.Notify(&Observer::OnMenuClosed); // Only switch to new menu when current menu is closed. if (button_to_open_) diff --git a/shell/browser/usb/electron_usb_delegate.cc b/shell/browser/usb/electron_usb_delegate.cc index 7cc8ffabec915..446b68fb4bfc2 100644 --- a/shell/browser/usb/electron_usb_delegate.cc +++ b/shell/browser/usb/electron_usb_delegate.cc @@ -102,19 +102,19 @@ class ElectronUsbDelegate::ContextObservation // UsbChooserContext::DeviceObserver: void OnDeviceAdded(const device::mojom::UsbDeviceInfo& device_info) override { - for (auto& observer : observer_list_) - observer.OnDeviceAdded(device_info); + observer_list_.Notify(&content::UsbDelegate::Observer::OnDeviceAdded, + device_info); } void OnDeviceRemoved( const device::mojom::UsbDeviceInfo& device_info) override { - for (auto& observer : observer_list_) - observer.OnDeviceRemoved(device_info); + observer_list_.Notify(&content::UsbDelegate::Observer::OnDeviceRemoved, + device_info); } void OnDeviceManagerConnectionError() override { - for (auto& observer : observer_list_) - observer.OnDeviceManagerConnectionError(); + observer_list_.Notify( + &content::UsbDelegate::Observer::OnDeviceManagerConnectionError); } void OnBrowserContextShutdown() override { diff --git a/shell/browser/usb/usb_chooser_context.cc b/shell/browser/usb/usb_chooser_context.cc index ae4a086f5b3fd..d807e916f2b6c 100644 --- a/shell/browser/usb/usb_chooser_context.cc +++ b/shell/browser/usb/usb_chooser_context.cc @@ -290,8 +290,7 @@ void UsbChooserContext::OnDeviceAdded( devices_.try_emplace(device_info->guid, device_info->Clone()); // Notify all observers. - for (auto& observer : device_observer_list_) - observer.OnDeviceAdded(*device_info); + device_observer_list_.Notify(&DeviceObserver::OnDeviceAdded, *device_info); } void UsbChooserContext::OnDeviceRemoved( @@ -308,8 +307,7 @@ void UsbChooserContext::OnDeviceRemoved( DCHECK_EQ(n_erased, 1U); // Notify all device observers. - for (auto& observer : device_observer_list_) - observer.OnDeviceRemoved(*device_info); + device_observer_list_.Notify(&DeviceObserver::OnDeviceRemoved, *device_info); // If the device was persistent, return. Otherwise, notify all permission // observers that its permissions were revoked. @@ -331,8 +329,7 @@ void UsbChooserContext::OnDeviceManagerConnectionError() { ephemeral_devices_.clear(); // Notify all device observers. - for (auto& observer : device_observer_list_) - observer.OnDeviceManagerConnectionError(); + device_observer_list_.Notify(&DeviceObserver::OnDeviceManagerConnectionError); } } // namespace electron diff --git a/shell/browser/web_contents_zoom_controller.cc b/shell/browser/web_contents_zoom_controller.cc index 64933e192d043..b4c237d68f7ac 100644 --- a/shell/browser/web_contents_zoom_controller.cc +++ b/shell/browser/web_contents_zoom_controller.cc @@ -48,9 +48,7 @@ WebContentsZoomController::WebContentsZoomController( WebContentsZoomController::~WebContentsZoomController() { DCHECK_CURRENTLY_ON(BrowserThread::UI); - for (auto& observer : observers_) { - observer.OnZoomControllerDestroyed(this); - } + observers_.Notify(&WebContentsZoomObserver::OnZoomControllerDestroyed, this); } void WebContentsZoomController::AddObserver(WebContentsZoomObserver* observer) { @@ -90,8 +88,8 @@ bool WebContentsZoomController::SetZoomLevel(double level) { ZoomChangedEventData zoom_change_data(web_contents(), old_zoom_level, zoom_level_, true /* temporary */, zoom_mode_); - for (auto& observer : observers_) - observer.OnZoomChanged(zoom_change_data); + observers_.Notify(&WebContentsZoomObserver::OnZoomChanged, + zoom_change_data); return true; } @@ -110,8 +108,8 @@ bool WebContentsZoomController::SetZoomLevel(double level) { zoom_map->SetTemporaryZoomLevel(rfh_id, level); ZoomChangedEventData zoom_change_data(web_contents(), zoom_level_, level, true /* temporary */, zoom_mode_); - for (auto& observer : observers_) - observer.OnZoomChanged(zoom_change_data); + observers_.Notify(&WebContentsZoomObserver::OnZoomChanged, + zoom_change_data); } else { const GURL url = content::HostZoomMap::GetURLForRenderFrameHost(rfh_id); if (url.is_empty()) { @@ -148,8 +146,7 @@ void WebContentsZoomController::SetTemporaryZoomLevel(double level) { // Notify observers of zoom level changes. ZoomChangedEventData zoom_change_data(web_contents(), zoom_level_, level, true /* temporary */, zoom_mode_); - for (auto& observer : observers_) - observer.OnZoomChanged(zoom_change_data); + observers_.Notify(&WebContentsZoomObserver::OnZoomChanged, zoom_change_data); } bool WebContentsZoomController::UsesTemporaryZoomLevel() { @@ -213,8 +210,8 @@ void WebContentsZoomController::SetZoomMode(ZoomMode new_mode) { } else { // When we don't call any HostZoomMap set functions, we send the event // manually. - for (auto& observer : observers_) - observer.OnZoomChanged(*event_data_); + observers_.Notify(&WebContentsZoomObserver::OnZoomChanged, + *event_data_); event_data_.reset(); } break; @@ -229,8 +226,8 @@ void WebContentsZoomController::SetZoomMode(ZoomMode new_mode) { } else { // When we don't call any HostZoomMap set functions, we send the event // manually. - for (auto& observer : observers_) - observer.OnZoomChanged(*event_data_); + observers_.Notify(&WebContentsZoomObserver::OnZoomChanged, + *event_data_); event_data_.reset(); } break; @@ -303,9 +300,7 @@ void WebContentsZoomController::WebContentsDestroyed() { DCHECK_CURRENTLY_ON(BrowserThread::UI); // At this point we should no longer be sending any zoom events with this // WebContents. - for (auto& observer : observers_) { - observer.OnZoomControllerDestroyed(this); - } + observers_.Notify(&WebContentsZoomObserver::OnZoomControllerDestroyed, this); embedder_zoom_controller_ = nullptr; } @@ -389,14 +384,14 @@ void WebContentsZoomController::UpdateState(const std::string& host) { // the change should be sent. ZoomChangedEventData zoom_change_data = *event_data_; event_data_.reset(); - for (auto& observer : observers_) - observer.OnZoomChanged(zoom_change_data); + observers_.Notify(&WebContentsZoomObserver::OnZoomChanged, + zoom_change_data); } else { double zoom_level = GetZoomLevel(); ZoomChangedEventData zoom_change_data(web_contents(), zoom_level, zoom_level, false, zoom_mode_); - for (auto& observer : observers_) - observer.OnZoomChanged(zoom_change_data); + observers_.Notify(&WebContentsZoomObserver::OnZoomChanged, + zoom_change_data); } } diff --git a/shell/browser/window_list.cc b/shell/browser/window_list.cc index 89a3ab1d4b9e2..188402d0e6bb1 100644 --- a/shell/browser/window_list.cc +++ b/shell/browser/window_list.cc @@ -57,16 +57,13 @@ void WindowList::RemoveWindow(NativeWindow* window) { WindowVector& windows = GetInstance()->windows_; std::erase(windows, window); - if (windows.empty()) { - for (WindowListObserver& observer : GetObservers()) - observer.OnWindowAllClosed(); - } + if (windows.empty()) + GetObservers().Notify(&WindowListObserver::OnWindowAllClosed); } // static void WindowList::WindowCloseCancelled(NativeWindow* window) { - for (WindowListObserver& observer : GetObservers()) - observer.OnWindowCloseCancelled(window); + GetObservers().Notify(&WindowListObserver::OnWindowCloseCancelled, window); } // static From 03d83c293f3f9f824259c16f519e1acbb15f2a60 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 10:08:04 -0400 Subject: [PATCH 006/186] chore: bump chromium to 138.0.7154.0 (37-x-y) (#46894) * chore: bump chromium in DEPS to 138.0.7152.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: update patches Co-authored-by: John Kleinschmidt * chore: bump chromium in DEPS to 138.0.7154.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: update patches Co-authored-by: John Kleinschmidt * ozone/wayland: Fix bookmark dropdown right click context menu https://chromium-review.googlesource.com/c/chromium/src/+/6488801 Co-authored-by: John Kleinschmidt * Use base::cstring_view in base::Environment https://chromium-review.googlesource.com/c/chromium/src/+/6494292 Co-authored-by: John Kleinschmidt * Remove Add/Remove AXMode methods https://chromium-review.googlesource.com/c/chromium/src/+/6418444 xref: https://chromium-review.googlesource.com/c/chromium/src/+/6383275 Co-authored-by: John Kleinschmidt * build: update filenames.libcxx.gni Co-authored-by: John Kleinschmidt * Use base::cstring_view in base::Environment https://chromium-review.googlesource.com/c/chromium/src/+/6494292 Co-authored-by: John Kleinschmidt * Use getters to expose NativePixmapHandle from GpuMemoryBufferHandle https://chromium-review.googlesource.com/c/chromium/src/+/6374406 Co-authored-by: John Kleinschmidt --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- DEPS | 2 +- filenames.libcxx.gni | 1 - patches/chromium/.patches | 1 - ...client_precreatemessageloop_callback.patch | 4 +- .../add_didinstallconditionalfeatures.patch | 4 +- ...adjust_accessibility_ui_for_electron.patch | 24 +++++------ ..._depend_on_packed_resource_integrity.patch | 12 +++--- patches/chromium/can_create_window.patch | 22 +++++----- .../chromium/chore_partial_revert_of.patch | 4 +- ...screationoverridden_with_full_params.patch | 14 +++---- ...e_browser_v8_snapshot_file_name_fuse.patch | 4 +- ...le_freezing_flags_after_init_in_node.patch | 4 +- patches/chromium/disable_unload_metrics.patch | 6 +-- ...e_launch_options_for_service_process.patch | 2 +- ...screen_rendering_with_viz_compositor.patch | 2 +- ...g_exit_code_on_service_process_crash.patch | 2 +- ..._raw_response_headers_from_urlloader.patch | 12 +++--- ...allback_for_sync_and_async_clipboard.patch | 2 +- ...ding_non-standard_schemes_in_iframes.patch | 4 +- ...king_and_message_bubbling_on_windows.patch | 2 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ...from_localframe_requestexecutescript.patch | 12 +++--- ...t_menu_item_when_opened_via_keyboard.patch | 10 +++-- patches/chromium/frame_host_manager.patch | 2 +- .../load_v8_snapshot_in_browser_process.patch | 2 +- ..._avoid_private_macos_api_usage.patch.patch | 18 ++++----- ...eated_to_allow_for_browser_initiated.patch | 2 +- patches/chromium/printing.patch | 4 +- ...r_changes_to_the_webcontentsobserver.patch | 8 ++-- ..._electron_permissiontypes_into_blink.patch | 2 +- ...efactor_unfilter_unresponsive_events.patch | 4 +- .../render_widget_host_view_mac.patch | 10 ++--- ...ean_up_stale_macwebcontentsocclusion.patch | 8 ++-- ...revert_enable_crel_for_arm32_targets.patch | 23 ----------- patches/chromium/web_contents.patch | 10 ++--- patches/chromium/webview_fullscreen.patch | 10 ++--- ...i_to_allow_electron_to_set_dock_side.patch | 4 +- ...8_object_setinternalfieldfornodecore.patch | 2 +- shell/app/electron_main_delegate.cc | 6 ++- shell/app/node_main.cc | 6 ++- shell/browser/api/electron_api_app.cc | 13 +++--- shell/browser/api/electron_api_app.h | 3 ++ .../electron_browser_main_parts_linux.cc | 5 +-- shell/browser/mac/electron_application.mm | 40 ++++++++++++------- shell/browser/native_window_views.h | 3 ++ shell/browser/native_window_views_win.cc | 6 +-- shell/browser/osr/osr_video_consumer.cc | 2 +- shell/common/logging.cc | 6 +-- 48 files changed, 174 insertions(+), 179 deletions(-) delete mode 100644 patches/chromium/revert_enable_crel_for_arm32_targets.patch diff --git a/DEPS b/DEPS index 58aeaa902adb6..62e2af28abae0 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '137.0.7151.0', + '138.0.7154.0', 'node_version': 'v22.14.0', 'nan_version': diff --git a/filenames.libcxx.gni b/filenames.libcxx.gni index f6b15202a0860..0bf4fcacfa2c9 100644 --- a/filenames.libcxx.gni +++ b/filenames.libcxx.gni @@ -1421,7 +1421,6 @@ libcxx_headers = [ "//third_party/libc++/src/include/__type_traits/is_member_pointer.h", "//third_party/libc++/src/include/__type_traits/is_nothrow_assignable.h", "//third_party/libc++/src/include/__type_traits/is_nothrow_constructible.h", - "//third_party/libc++/src/include/__type_traits/is_nothrow_convertible.h", "//third_party/libc++/src/include/__type_traits/is_nothrow_destructible.h", "//third_party/libc++/src/include/__type_traits/is_null_pointer.h", "//third_party/libc++/src/include/__type_traits/is_object.h", diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 794d878745ce3..5489765e6d4d8 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -144,6 +144,5 @@ feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch fix_win32_synchronous_spellcheck.patch fix_enable_wrap_iter_in_string_view_and_array.patch fix_linter_error.patch -revert_enable_crel_for_arm32_targets.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch diff --git a/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch b/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch index d0f00ff10f09e..0f9ffc477fbe0 100644 --- a/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch +++ b/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch @@ -10,7 +10,7 @@ Allows Electron to restore WER when ELECTRON_DEFAULT_ERROR_MODE is set. This should be upstreamed. diff --git a/content/gpu/gpu_main.cc b/content/gpu/gpu_main.cc -index f78e6732f4a154b6a479bcfcdb237f0679a7fde3..c95b699fe2d37421ae589a14d51c5ffd4465860f 100644 +index cadb96febde3fb3fe90929873b1db452a6d8fb8f..09f5504127b5a5ec3d0d69d9eb6d0cd93e0e75cd 100644 --- a/content/gpu/gpu_main.cc +++ b/content/gpu/gpu_main.cc @@ -254,6 +254,10 @@ int GpuMain(MainFunctionParams parameters) { @@ -24,7 +24,7 @@ index f78e6732f4a154b6a479bcfcdb237f0679a7fde3..c95b699fe2d37421ae589a14d51c5ffd // We are experiencing what appear to be memory-stomp issues in the GPU // process. These issues seem to be impacting the task executor and listeners // registered to it. Create the task executor on the heap to guard against -@@ -364,7 +368,6 @@ int GpuMain(MainFunctionParams parameters) { +@@ -363,7 +367,6 @@ int GpuMain(MainFunctionParams parameters) { #endif const bool dead_on_arrival = !init_success; diff --git a/patches/chromium/add_didinstallconditionalfeatures.patch b/patches/chromium/add_didinstallconditionalfeatures.patch index aef67c03af1d1..e88cb145424d1 100644 --- a/patches/chromium/add_didinstallconditionalfeatures.patch +++ b/patches/chromium/add_didinstallconditionalfeatures.patch @@ -23,10 +23,10 @@ index 44da0544b778d6ff4c14b6f4e8463cb8260d2f0d..8ae8939af4141a684b7a6d50a43e1abb int32_t world_id) {} virtual void DidClearWindowObject() {} diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index e3f9f9406f51d4d4cb48fd35d33ee3d694933038..6bcbbd6f746e00344e78447ebdaf59edc80a2b79 100644 +index c0ee479cea4f34fcfac502a20130fbb4c8becc15..3be4b5225fe791901ba27b9fbb7a21ea1ae5d4ff 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc -@@ -4810,6 +4810,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, +@@ -4811,6 +4811,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, observer.DidCreateScriptContext(context, world_id); } diff --git a/patches/chromium/adjust_accessibility_ui_for_electron.patch b/patches/chromium/adjust_accessibility_ui_for_electron.patch index 331d0cfeb85e2..a01f7c96e67e6 100644 --- a/patches/chromium/adjust_accessibility_ui_for_electron.patch +++ b/patches/chromium/adjust_accessibility_ui_for_electron.patch @@ -10,7 +10,7 @@ usage of BrowserList and Browser as we subclass related methods and use our WindowList. diff --git a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc -index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4590c16b0 100644 +index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df13aa0649 100644 --- a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc +++ b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc @@ -48,6 +48,7 @@ @@ -21,7 +21,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 #include "ui/accessibility/accessibility_features.h" #include "ui/accessibility/ax_updates_and_events.h" #include "ui/accessibility/platform/ax_platform_node.h" -@@ -167,7 +168,7 @@ base::Value::Dict BuildTargetDescriptor(content::RenderViewHost* rvh) { +@@ -168,7 +169,7 @@ base::Value::Dict BuildTargetDescriptor(content::RenderViewHost* rvh) { rvh->GetRoutingID(), accessibility_mode); } @@ -30,7 +30,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 base::Value::Dict BuildTargetDescriptor(Browser* browser) { base::Value::Dict target_data; target_data.Set(kSessionIdField, browser->session_id().id()); -@@ -190,7 +191,7 @@ void HandleAccessibilityRequestCallback( +@@ -192,7 +193,7 @@ void HandleAccessibilityRequestCallback( auto& browser_accessibility_state = *content::BrowserAccessibilityState::GetInstance(); base::Value::Dict data; @@ -39,8 +39,8 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 ui::AXMode mode = browser_accessibility_state.GetAccessibilityMode(); bool native = mode.has_mode(ui::AXMode::kNativeAPIs); bool web = mode.has_mode(ui::AXMode::kWebContents); -@@ -214,7 +215,7 @@ void HandleAccessibilityRequestCallback( - data.Set(kPDFPrinting, pdf_printing); +@@ -240,7 +241,7 @@ void HandleAccessibilityRequestCallback( + initial_process_mode.has_mode(ui::AXMode::kHTML))); std::string pref_api_type = - pref->GetString(prefs::kShownAccessibilityApiType); @@ -48,7 +48,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 bool pref_api_type_supported = false; std::vector supported_api_types = -@@ -282,11 +283,11 @@ void HandleAccessibilityRequestCallback( +@@ -307,11 +308,11 @@ void HandleAccessibilityRequestCallback( data.Set(kPagesField, std::move(page_list)); base::Value::List browser_list; @@ -62,7 +62,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 data.Set(kBrowsersField, std::move(browser_list)); std::string json_string; -@@ -762,7 +763,8 @@ void AccessibilityUIMessageHandler::SetGlobalString( +@@ -783,7 +784,8 @@ void AccessibilityUIMessageHandler::SetGlobalString( const std::string value = CheckJSValue(data.FindString(kValueField)); if (string_name == kApiTypeField) { @@ -72,7 +72,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 pref->SetString(prefs::kShownAccessibilityApiType, value); } } -@@ -816,7 +818,8 @@ void AccessibilityUIMessageHandler::RequestWebContentsTree( +@@ -837,7 +839,8 @@ void AccessibilityUIMessageHandler::RequestWebContentsTree( AXPropertyFilter::ALLOW_EMPTY); AddPropertyFilters(property_filters, deny, AXPropertyFilter::DENY); @@ -82,7 +82,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 ui::AXApiType::Type api_type = ui::AXApiType::From(pref->GetString(prefs::kShownAccessibilityApiType)); std::string accessibility_contents = -@@ -843,6 +846,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( +@@ -864,6 +867,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( AXPropertyFilter::ALLOW_EMPTY); AddPropertyFilters(property_filters, deny, AXPropertyFilter::DENY); @@ -90,7 +90,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 for (Browser* browser : *BrowserList::GetInstance()) { if (browser->session_id().id() == session_id) { base::Value::Dict result = BuildTargetDescriptor(browser); -@@ -855,6 +859,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( +@@ -876,6 +880,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( return; } } @@ -98,7 +98,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 #endif // !BUILDFLAG(IS_ANDROID) // No browser with the specified |session_id| was found. base::Value::Dict result; -@@ -898,11 +903,13 @@ void AccessibilityUIMessageHandler::StopRecording( +@@ -919,11 +924,13 @@ void AccessibilityUIMessageHandler::StopRecording( } ui::AXApiType::Type AccessibilityUIMessageHandler::GetRecordingApiType() { @@ -115,7 +115,7 @@ index 09027b5c273a209519a1c9268c604b3cf1ca0d3c..00511a4558dbc907f752b4c602cc97b4 // Check to see if it is in the supported types list. if (std::find(supported_types.begin(), supported_types.end(), api_type) == supported_types.end()) { -@@ -972,8 +979,11 @@ void AccessibilityUIMessageHandler::RequestAccessibilityEvents( +@@ -993,8 +1000,11 @@ void AccessibilityUIMessageHandler::RequestAccessibilityEvents( // static void AccessibilityUIMessageHandler::RegisterProfilePrefs( user_prefs::PrefRegistrySyncable* registry) { diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index cee7fdd1fc1af..8dd738f4a9b92 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -33,10 +33,10 @@ index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index ad39862fdd9a5a4f827f36e6a9778223a638d831..518ab769287525b1977387df56d1f50d1f0778f2 100644 +index 4e84a91033465438d8510ba532ba795a2eb6bcf6..b9f60071a41de560a36214a6490d206382d9d6cb 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4627,7 +4627,7 @@ static_library("browser") { +@@ -4631,7 +4631,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,10 +46,10 @@ index ad39862fdd9a5a4f827f36e6a9778223a638d831..518ab769287525b1977387df56d1f50d # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 1b52a0d1a249c5d8beb205358c2003202c9253a0..4fbf2f66adfccb3580176be8d25598cf9ffcb616 100644 +index 05073b10cb0c86b63f50071ef7e04225ef0627ec..de6c65e2ada9696c9a6c183f02493ea446e8bd3d 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7187,9 +7187,12 @@ test("unit_tests") { +@@ -7184,9 +7184,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index 1b52a0d1a249c5d8beb205358c2003202c9253a0..4fbf2f66adfccb3580176be8d25598cf "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8155,6 +8158,10 @@ test("unit_tests") { +@@ -8153,6 +8156,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index 1b52a0d1a249c5d8beb205358c2003202c9253a0..4fbf2f66adfccb3580176be8d25598cf sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8210,7 +8217,6 @@ test("unit_tests") { +@@ -8208,7 +8215,6 @@ test("unit_tests") { # Non-android deps for "unit_tests" target. deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 81b4b4e651753..5ed6f79b92779 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,10 +9,10 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index ebf407904b9b9bc7f60a9c13a5c39ce64640189d..7b45a0006af60400f5d8ba5b925f971cb5cf393e 100644 +index ad821a07ad808b392633f0e8e774b6082cc3b184..df50b84cca214a9b6a85afe2fd677a45e2529cdc 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -9778,6 +9778,7 @@ void RenderFrameHostImpl::CreateNewWindow( +@@ -9775,6 +9775,7 @@ void RenderFrameHostImpl::CreateNewWindow( last_committed_origin_, params->window_container_type, params->target_url, params->referrer.To(), params->frame_name, params->disposition, *params->features, @@ -21,10 +21,10 @@ index ebf407904b9b9bc7f60a9c13a5c39ce64640189d..7b45a0006af60400f5d8ba5b925f971c &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index fe352434dd26ebbde72145df335520ff9d026e80..4f87894219452e736311ad25a62b71b8aec4d158 100644 +index 2039ac799297183b16fb4795b63c6c5b76dac478..fec569763d3ba8b171ca65a9ea523ada5f729f41 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5126,6 +5126,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5131,6 +5131,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( SetPartitionedPopinOpenerOnNewWindowIfNeeded(new_contents_impl, params, opener); @@ -37,7 +37,7 @@ index fe352434dd26ebbde72145df335520ff9d026e80..4f87894219452e736311ad25a62b71b8 // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5167,12 +5173,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5172,12 +5178,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -66,10 +66,10 @@ index 55bb4ae3bab4cdf20b3e1dde9450a5c0e4e62b37..fe444c7fa140166a1b65c7a8a2676e2d // Operation result when the renderer asks the browser to create a new window. diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc -index 9c36ad70531bd8c31158c741ab23763ea00bc068..6909f75fb4cbd0e7b4f3067cda52a5f67dc100de 100644 +index b3975f65bfbcff7bc9eb0815a0ac5e97d1ff3548..2b219ccfdbef82f9e4075243da48c4b1e53158c2 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc -@@ -821,6 +821,8 @@ bool ContentBrowserClient::CanCreateWindow( +@@ -823,6 +823,8 @@ bool ContentBrowserClient::CanCreateWindow( const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -79,7 +79,7 @@ index 9c36ad70531bd8c31158c741ab23763ea00bc068..6909f75fb4cbd0e7b4f3067cda52a5f6 bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index f1fee091b84aec20f1e15dcc90917e50bb47d1c6..3a7a6dc0a4e75c151379f8488d371439a808f1a9 100644 +index 77b3e5c0fe47e5ed0139d3e54394f7d96fc69d21..cabdb73fa092683cdd2dad38f7b62b6bac974d0d 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -199,6 +199,7 @@ class NetworkService; @@ -90,7 +90,7 @@ index f1fee091b84aec20f1e15dcc90917e50bb47d1c6..3a7a6dc0a4e75c151379f8488d371439 } // namespace network namespace sandbox { -@@ -1377,6 +1378,8 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -1378,6 +1379,8 @@ class CONTENT_EXPORT ContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -148,10 +148,10 @@ index da319cb20733150366d85bee95609f0f2d9def7f..8a18958035cc1dd26be558349f64f772 // typically happens when popups are created. virtual void WebContentsCreated(WebContents* source_contents, diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index 5af26eef19c2f7ce082af02cff6d8f919c4d245d..e3f9f9406f51d4d4cb48fd35d33ee3d694933038 100644 +index 6dd63dbd96ce5c941790f97929b2826a03cabbcc..c0ee479cea4f34fcfac502a20130fbb4c8becc15 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc -@@ -6936,6 +6936,10 @@ WebView* RenderFrameImpl::CreateNewWindow( +@@ -6942,6 +6942,10 @@ WebView* RenderFrameImpl::CreateNewWindow( request.HasUserGesture(), GetWebFrame()->IsAdFrame(), GetWebFrame()->IsAdScriptInStack()); diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 5b1a9db22a741..579c06513d717 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 4c30f71ced0da645637c989c08ccc93e463e755f..56b2fb93d5d85f520081de9e42e26ef3f8f6090e 100644 +index 05859e343a6c1fa58f3fb847ad6e97982804f910..5fef3e077072ee9dc3ff22110b7818503c8b4e4b 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5045,7 +5045,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5050,7 +5050,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index bde95238b2ffa..1bd9e98ea3434 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -80,10 +80,10 @@ index 4fd8dff1089cd6afa6a66dc185734d7671657281..0a1f4268ea771a3d5d4a2668928c6e5d content::WebContents* source, const content::OpenURLParams& params, diff --git a/chrome/browser/ui/browser.cc b/chrome/browser/ui/browser.cc -index 435235c067f70f7f3d219dfc0bf91c9be40d1389..cc6c860ec51075fc047a77c26c5b42296bb6ab19 100644 +index de3f9f56b47628e1104b5f64b3c17cc35e10bfc7..3a19c28386fd3a0b8755a06510895c685f2c0cdb 100644 --- a/chrome/browser/ui/browser.cc +++ b/chrome/browser/ui/browser.cc -@@ -2323,12 +2323,11 @@ bool Browser::IsWebContentsCreationOverridden( +@@ -2327,12 +2327,11 @@ bool Browser::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -99,10 +99,10 @@ index 435235c067f70f7f3d219dfc0bf91c9be40d1389..cc6c860ec51075fc047a77c26c5b4229 WebContents* Browser::CreateCustomWebContents( diff --git a/chrome/browser/ui/browser.h b/chrome/browser/ui/browser.h -index c4cea0b6e8c4c95ebcddf5497d731d1d63934f22..7686b75c5504d093dcd9dd8a7ffd28e0c2fd036c 100644 +index 0bcb2fc072e47c2c259b724209b4814486329fe1..db674988cf87f198ed1af7e0f4def24776fbaa89 100644 --- a/chrome/browser/ui/browser.h +++ b/chrome/browser/ui/browser.h -@@ -1026,8 +1026,7 @@ class Browser : public TabStripModelObserver, +@@ -1027,8 +1027,7 @@ class Browser : public TabStripModelObserver, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -218,10 +218,10 @@ index c6838c83ef971b88769b1f3fba8095025ae25464..2da6a4e08340e72ba7de5d03444c2f17 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 7a8d7ce6f628123f5288d693046ca7602eeccac1..f73f2ac411c0af45d7c0a4ba94222b2bd1d4841c 100644 +index e236eb74db68a6c11892e1ea16cab05b8c47afbf..b2d5733ff8c47f497af03171d9dfac68b2013e4d 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5008,8 +5008,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5013,8 +5013,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( // TODO(crbug.com/40202416): Support a way for MPArch guests to support this. if (delegate_ && delegate_->IsWebContentsCreationOverridden( source_site_instance, params.window_container_type, @@ -274,7 +274,7 @@ index 8d6fc67cb9b1d653bce64d1ba22aa7ec2d79257c..d5ce746373a1a4310e1eb530aee011a7 return true; diff --git a/extensions/browser/guest_view/app_view/app_view_guest.h b/extensions/browser/guest_view/app_view/app_view_guest.h -index 136448c9df06b9704e95d2797a60907d7ec5170a..21cc7b08dd8f9e4a32d29dd35c42ec2ce9f6cd53 100644 +index 775cfbf5adac0017f343bc091daee1b8883c75bb..dc97e5d60d3663ef7f7c78c28603f9e1c5aea4ff 100644 --- a/extensions/browser/guest_view/app_view/app_view_guest.h +++ b/extensions/browser/guest_view/app_view/app_view_guest.h @@ -10,6 +10,7 @@ diff --git a/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch b/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch index 98c7b5e9aa338..0e39852cbd01a 100644 --- a/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch +++ b/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch @@ -7,7 +7,7 @@ By default, chromium sets up one v8 snapshot to be used in all v8 contexts. This to have a dedicated browser process v8 snapshot defined by the file `browser_v8_context_snapshot.bin`. diff --git a/content/app/content_main_runner_impl.cc b/content/app/content_main_runner_impl.cc -index a23d9b8fc451078708fd1a39f3d74357de7c244f..f619f8a360b43b43174647cd596ab9c75c8ea1f1 100644 +index d55c408557e15650897c9ed6d5b6bd83178a551f..f1c54919990af204004380b0d84ee750de5e3c35 100644 --- a/content/app/content_main_runner_impl.cc +++ b/content/app/content_main_runner_impl.cc @@ -275,8 +275,13 @@ void AsanProcessInfoCB(const char*, bool*) { @@ -40,7 +40,7 @@ index a23d9b8fc451078708fd1a39f3d74357de7c244f..f619f8a360b43b43174647cd596ab9c7 #endif // V8_USE_EXTERNAL_STARTUP_DATA } -@@ -982,7 +988,7 @@ int ContentMainRunnerImpl::Initialize(ContentMainParams params) { +@@ -1005,7 +1011,7 @@ int ContentMainRunnerImpl::Initialize(ContentMainParams params) { return TerminateForFatalInitializationError(); #endif // BUILDFLAG(IS_ANDROID) && (ICU_UTIL_DATA_IMPL == ICU_UTIL_DATA_FILE) diff --git a/patches/chromium/disable_freezing_flags_after_init_in_node.patch b/patches/chromium/disable_freezing_flags_after_init_in_node.patch index fa6e951731d35..39e2e7efaf509 100644 --- a/patches/chromium/disable_freezing_flags_after_init_in_node.patch +++ b/patches/chromium/disable_freezing_flags_after_init_in_node.patch @@ -15,10 +15,10 @@ at some point be an API to "unfreeze" the flags, or we may be able to refactor node initialization to not update flags after V8 initialization. diff --git a/content/renderer/render_process_impl.cc b/content/renderer/render_process_impl.cc -index eb11068e932b7b94cbf215d6f84ae427ce77fcd5..9744e45974af215bfbe9e5feb2db7274f8efebf0 100644 +index 7a20f5199bd6cb5d13f31ec5db3e3cc03821bc3a..22167f808cb7b27d5b2a8e517cdeee63205ab9ad 100644 --- a/content/renderer/render_process_impl.cc +++ b/content/renderer/render_process_impl.cc -@@ -208,6 +208,9 @@ RenderProcessImpl::RenderProcessImpl() +@@ -212,6 +212,9 @@ RenderProcessImpl::RenderProcessImpl() v8::V8::SetFlagsFromString(kSABPerContextFlag, sizeof(kSABPerContextFlag)); } diff --git a/patches/chromium/disable_unload_metrics.patch b/patches/chromium/disable_unload_metrics.patch index b81c1f68b7d16..4e43463b8aecb 100644 --- a/patches/chromium/disable_unload_metrics.patch +++ b/patches/chromium/disable_unload_metrics.patch @@ -24,10 +24,10 @@ This patch temporarily disables the metrics so we can have green CI, and we should continue seeking for a real fix. diff --git a/content/browser/renderer_host/navigator.cc b/content/browser/renderer_host/navigator.cc -index ed7d7512c7112eedcbbddf30ed4a0a0cff4b7e34..fbdf54a1003f30e5113309fa74e851a4eebea85d 100644 +index 9cc3ae76503699417e8b7a2bd18d0b899e20d790..cba63c2eacdb1c02391941854f94dd5e2ddc2776 100644 --- a/content/browser/renderer_host/navigator.cc +++ b/content/browser/renderer_host/navigator.cc -@@ -1476,6 +1476,7 @@ void Navigator::RecordNavigationMetrics( +@@ -1470,6 +1470,7 @@ void Navigator::RecordNavigationMetrics( .InMilliseconds()); } @@ -35,7 +35,7 @@ index ed7d7512c7112eedcbbddf30ed4a0a0cff4b7e34..fbdf54a1003f30e5113309fa74e851a4 // If this is a same-process navigation and we have timestamps for unload // durations, fill those metrics out as well. if (params.unload_start && params.unload_end && -@@ -1525,6 +1526,7 @@ void Navigator::RecordNavigationMetrics( +@@ -1519,6 +1520,7 @@ void Navigator::RecordNavigationMetrics( first_before_unload_start_time) .InMilliseconds()); } diff --git a/patches/chromium/feat_configure_launch_options_for_service_process.patch b/patches/chromium/feat_configure_launch_options_for_service_process.patch index 558d8392f093f..41b88cc8254f9 100644 --- a/patches/chromium/feat_configure_launch_options_for_service_process.patch +++ b/patches/chromium/feat_configure_launch_options_for_service_process.patch @@ -187,7 +187,7 @@ index 96c9563aac5847e742de5d9c9236f78bcb6cfd9c..73c9d585579ad5bdc407687b8becd0b7 host->GetChildProcess()->BindServiceInterface(std::move(receiver)); } diff --git a/content/browser/service_host/utility_process_host.cc b/content/browser/service_host/utility_process_host.cc -index 9e01e61bf1fce448a93eaa3d5f363fc835b78538..d210af6fb317c922a8415a67a7ccd1d8a4a88ea1 100644 +index e2c72b43f75b57ef1f49b82d3ecdfb425f8596de..51f8ff9b8424d098979a24c2e8628cdf7c4b758d 100644 --- a/content/browser/service_host/utility_process_host.cc +++ b/content/browser/service_host/utility_process_host.cc @@ -190,11 +190,13 @@ const ChildProcessData& UtilityProcessHost::GetData() { diff --git a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch index 4622d4483e9a2..e503e5e8ab6b7 100644 --- a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch +++ b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch @@ -522,7 +522,7 @@ index f0aca972c4a81c3dfb536e14244daafae21ee716..a15afbc1a3519e657121b4952444d2f4 waiting_on_draw_ack_ = true; diff --git a/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc b/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc -index ed921225298fbb4f6d12d7c49be825ee586d009c..78a393d96ddf4dc3bf8d1af297ed2642eacac495 100644 +index 391004b202e6f20ad06eb6a53a6d55f5e8981c75..acb849f4e737de45e7aa4640b6866791424f010b 100644 --- a/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc +++ b/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc @@ -130,7 +130,8 @@ RootCompositorFrameSinkImpl::Create( diff --git a/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch b/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch index de4299dc23aca..0c133fce18816 100644 --- a/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch +++ b/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch @@ -80,7 +80,7 @@ index 801db538979ba62facdcf3a472dade56723ca639..7abac9a5b13b393713534ae51664c2e5 private: const std::string service_interface_name_; diff --git a/content/browser/service_host/utility_process_host.cc b/content/browser/service_host/utility_process_host.cc -index d210af6fb317c922a8415a67a7ccd1d8a4a88ea1..0de01879f618555030e87ea79a94d41232811c2c 100644 +index 51f8ff9b8424d098979a24c2e8628cdf7c4b758d..19d8ed89211402e93632c4d83dbf452d4194a14c 100644 --- a/content/browser/service_host/utility_process_host.cc +++ b/content/browser/service_host/utility_process_host.cc @@ -541,7 +541,7 @@ void UtilityProcessHost::OnProcessCrashed(int exit_code) { diff --git a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch index cd77c50fe3ed6..f5bf6d35ca68f 100644 --- a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch +++ b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch @@ -112,10 +112,10 @@ index 99bf736ebe303d46ab1ced924ba929a0cd258909..e10c8782d2704ff9cff8062d201a4339 string mime_type; diff --git a/services/network/url_loader.cc b/services/network/url_loader.cc -index 937a7b2ba05c11514d2d980a6fb2eaa9102c2774..6ffe746744beccbf224ad1a36ad102da5164580f 100644 +index 35d3acb1a088a7b4cba7b062a62e8033c31dfe52..9770306449b39f26c047ed0c15cba9feae55c5d3 100644 --- a/services/network/url_loader.cc +++ b/services/network/url_loader.cc -@@ -387,6 +387,9 @@ URLLoader::URLLoader( +@@ -386,6 +386,9 @@ URLLoader::URLLoader( mojo::SimpleWatcher::ArmingPolicy::MANUAL, base::SequencedTaskRunner::GetCurrentDefault()), per_factory_orb_state_(context.GetMutableOrbState()), @@ -125,7 +125,7 @@ index 937a7b2ba05c11514d2d980a6fb2eaa9102c2774..6ffe746744beccbf224ad1a36ad102da devtools_request_id_(request.devtools_request_id), options_(PopulateOptions(options, factory_params_->is_orb_enabled, -@@ -544,7 +547,7 @@ void URLLoader::SetUpUrlRequestCallbacks( +@@ -521,7 +524,7 @@ void URLLoader::SetUpUrlRequestCallbacks( &URLLoader::IsSharedDictionaryReadAllowed, base::Unretained(this))); } @@ -134,7 +134,7 @@ index 937a7b2ba05c11514d2d980a6fb2eaa9102c2774..6ffe746744beccbf224ad1a36ad102da url_request_->SetResponseHeadersCallback(base::BindRepeating( &URLLoader::SetRawResponseHeaders, base::Unretained(this))); } -@@ -1225,6 +1228,19 @@ void URLLoader::OnResponseStarted(net::URLRequest* url_request, int net_error) { +@@ -1126,6 +1129,19 @@ void URLLoader::OnResponseStarted(net::URLRequest* url_request, int net_error) { } response_ = BuildResponseHead(); @@ -155,10 +155,10 @@ index 937a7b2ba05c11514d2d980a6fb2eaa9102c2774..6ffe746744beccbf224ad1a36ad102da ad_auction_event_record_request_helper_.HandleResponse( diff --git a/services/network/url_loader.h b/services/network/url_loader.h -index 6832aca0d487d5cbf2fc445f1f07a17565cf9d45..78618a2c3d79455ff685d58d11b61d3d8468b7e1 100644 +index f4d16508d4a34f9991b1b2f4e519e6cb2a7f5a73..099e146bc04bb4eb768c79099c5646ad7a029382 100644 --- a/services/network/url_loader.h +++ b/services/network/url_loader.h -@@ -625,6 +625,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) URLLoader +@@ -599,6 +599,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) URLLoader std::unique_ptr resource_scheduler_request_handle_; diff --git a/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch b/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch index e15e46d03be52..fe27ef5e7f68f 100644 --- a/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch +++ b/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch @@ -32,7 +32,7 @@ index 0aae1d3b2777d5f6db711d1ade99b4bde24e76bf..e350f6789c710826e0885ccdc19e66e2 break; } diff --git a/content/browser/permissions/permission_controller_impl.cc b/content/browser/permissions/permission_controller_impl.cc -index f53158596f935545afde6a175138347a752f73e7..b267734bf2273253aa921728e12c753adfade02e 100644 +index bc4dd4c643f2aa4cba07c0560e14f65f3c6aa291..b1c9f2d59559ed33cd32ad1f22b221029018cf0f 100644 --- a/content/browser/permissions/permission_controller_impl.cc +++ b/content/browser/permissions/permission_controller_impl.cc @@ -87,6 +87,7 @@ PermissionToSchedulingFeature(PermissionType permission_name) { diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index e0b0fcecac502..c1e844182bae8 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -28,10 +28,10 @@ The patch should be removed in favor of either: Upstream bug https://bugs.chromium.org/p/chromium/issues/detail?id=1081397. diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc -index 4c78563c29ce92c8217d288ed03f73fb482c6b49..aee0097df986cb4b3b75112fab828c59803e28d1 100644 +index 8a0e2b9520654002578a673bb22c9def4caa0d26..b2a28eb0276211d2949fb1b8b74cf098ae5aba41 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc -@@ -11159,6 +11159,12 @@ NavigationRequest::GetOriginForURLLoaderFactoryUncheckedWithDebugInfo() { +@@ -11151,6 +11151,12 @@ NavigationRequest::GetOriginForURLLoaderFactoryUncheckedWithDebugInfo() { "blob"); } diff --git a/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch b/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch index 47bf154ae0ec0..d33a5c4458fee 100644 --- a/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch +++ b/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch @@ -13,7 +13,7 @@ messages in the legacy window handle layer. These conditions are regularly hit with WCO-enabled windows on Windows. diff --git a/content/browser/renderer_host/legacy_render_widget_host_win.cc b/content/browser/renderer_host/legacy_render_widget_host_win.cc -index c6e88cee8640c56aad01721ab667b4255bd64a60..2742df0532c890fe97adf4a0c430c7718e5e73b5 100644 +index 1c03162fbcda8ab75dcd53722f92e10403fbae08..a21c58d3f13fadf3a7888f4fe16c0e6cf6c215b0 100644 --- a/content/browser/renderer_host/legacy_render_widget_host_win.cc +++ b/content/browser/renderer_host/legacy_render_widget_host_win.cc @@ -328,12 +328,12 @@ LRESULT LegacyRenderWidgetHostHWND::OnMouseRange(UINT message, diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 2a5e9b721b6ba..94d0f1cb79268 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 3b9e634245986b1ef22e8bf4e116470343f5ff60..4c30f71ced0da645637c989c08ccc93e463e755f 100644 +index d0f80de98c2bd3cf686b05ef972c89a8c2276935..05859e343a6c1fa58f3fb847ad6e97982804f910 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -9992,7 +9992,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -9997,7 +9997,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch index e6c9ded3d7ace..3469f2110bfd4 100644 --- a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch +++ b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch @@ -20,10 +20,10 @@ index fc9cb7e68bdad4c40fab63f70243e09ad005ab80..199fbceda530da31aab9126d78b4bd21 injector_->ExpectsResults(), injector_->ShouldWaitForPromise()); } diff --git a/third_party/blink/public/web/web_local_frame.h b/third_party/blink/public/web/web_local_frame.h -index 7934e6a8a2498acbe822df05e6087b885384c6d7..3026ebee29af3ead9f505292317160409a190b29 100644 +index 8db7be4dbc924c719783ceb667e4f5708ea0133e..d8622012721795c76831bf33c62ce393e81badbb 100644 --- a/third_party/blink/public/web/web_local_frame.h +++ b/third_party/blink/public/web/web_local_frame.h -@@ -460,6 +460,7 @@ class BLINK_EXPORT WebLocalFrame : public WebFrame { +@@ -461,6 +461,7 @@ class BLINK_EXPORT WebLocalFrame : public WebFrame { mojom::EvaluationTiming, mojom::LoadEventBlockingOption, WebScriptExecutionCallback, @@ -215,10 +215,10 @@ index 5e12b61ba14cd1afb07b71ff15e73e905da0addc..685a2ebb6694c173471d045014932125 mojom::blink::WantResultOption::kWantResult, wait_for_promise); } diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc -index f5adaadb9058e5fcad69d131f54ea06cb298b514..3315b02953685503d49a7e871fedf04262e80b71 100644 +index dcab8b2d4adcf14b285b558d85f69c303dc0818a..c998cba53d57dda9c32e7f75a9de3dcf0b974f58 100644 --- a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc +++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc -@@ -1109,14 +1109,15 @@ void WebLocalFrameImpl::RequestExecuteScript( +@@ -1111,14 +1111,15 @@ void WebLocalFrameImpl::RequestExecuteScript( mojom::blink::EvaluationTiming evaluation_timing, mojom::blink::LoadEventBlockingOption blocking_option, WebScriptExecutionCallback callback, @@ -237,10 +237,10 @@ index f5adaadb9058e5fcad69d131f54ea06cb298b514..3315b02953685503d49a7e871fedf042 bool WebLocalFrameImpl::IsInspectorConnected() { diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.h b/third_party/blink/renderer/core/frame/web_local_frame_impl.h -index 1b5e7a1a2bb5eb0b986dd6c61b4915d29a9a5667..19c8fdb320cbc84ba00b5e0b4b33a385b61b0db1 100644 +index 1d50260fb58eb439d68506de7de04b78c616b6ee..3699e331d5cb15ca12b6fa2d2ba058f7ca74df40 100644 --- a/third_party/blink/renderer/core/frame/web_local_frame_impl.h +++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.h -@@ -196,6 +196,7 @@ class CORE_EXPORT WebLocalFrameImpl final +@@ -198,6 +198,7 @@ class CORE_EXPORT WebLocalFrameImpl final mojom::blink::EvaluationTiming, mojom::blink::LoadEventBlockingOption, WebScriptExecutionCallback, diff --git a/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch b/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch index e72c5c7f4855a..5ab66964901ef 100644 --- a/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch +++ b/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch @@ -6,14 +6,16 @@ Subject: fix: select the first menu item when opened via keyboard This fixes an accessibility issue where the root view is 'focused' to the screen reader instead of the first menu item as with all other native menus. This patch will be upstreamed. diff --git a/ui/views/controls/menu/menu_controller.cc b/ui/views/controls/menu/menu_controller.cc -index a777b6b4c61c24cd2885134cccd5ada7d035cd5e..1a41b716ce5366497e60a691c23c7e62627b5748 100644 +index d3e06148b22f06e6676bcda5fd8907595389887e..35f22b679494940ae1b1d64fa4eb17c41c0cc623 100644 --- a/ui/views/controls/menu/menu_controller.cc +++ b/ui/views/controls/menu/menu_controller.cc -@@ -701,6 +701,14 @@ void MenuController::Run(Widget* parent, +@@ -711,6 +711,16 @@ void MenuController::Run(Widget* parent, SetSelection(root, SELECTION_OPEN_SUBMENU | SELECTION_UPDATE_IMMEDIATELY); } -+ if (source_type == ui::mojom::MenuSourceType::kKeyboard && context_menu && root->HasSubmenu()) { ++ if (source_type == ui::mojom::MenuSourceType::kKeyboard && ++ (menu_type == MenuType::kContextMenu || menu_type == MenuType::kMenuItemContextMenu) && ++ root->HasSubmenu()) { + // For context menus opened via the keyboard we select the first item by default + // to match accessibility expectations + MenuItemView* first_item = FindInitialSelectableMenuItem(root, INCREMENT_SELECTION_DOWN); @@ -24,7 +26,7 @@ index a777b6b4c61c24cd2885134cccd5ada7d035cd5e..1a41b716ce5366497e60a691c23c7e62 if (button_controller) { pressed_lock_ = button_controller->TakeLock( false, ui::LocatedEvent::FromIfValid(event)); -@@ -2407,19 +2415,15 @@ void MenuController::OpenMenuImpl(MenuItemView* item, bool show) { +@@ -2426,19 +2436,15 @@ void MenuController::OpenMenuImpl(MenuItemView* item, bool show) { } item->GetSubmenu()->ShowAt(params); diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index 9364009c8107f..f66769ab5b3cb 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -20,7 +20,7 @@ index d26c850e28b7df6992bf07fda2abe260ed4da769..008c131e5b4f84daeaee5ffe6ab7ae88 } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 3a7a6dc0a4e75c151379f8488d371439a808f1a9..0869aef8fce2829f7827d36c73af65ad71f7fdd3 100644 +index cabdb73fa092683cdd2dad38f7b62b6bac974d0d..6bd13985764981ccbc547faccdec78bce18600a0 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -340,6 +340,11 @@ class CONTENT_EXPORT ContentBrowserClient { diff --git a/patches/chromium/load_v8_snapshot_in_browser_process.patch b/patches/chromium/load_v8_snapshot_in_browser_process.patch index 8e703a02704b6..3768dd1e3766a 100644 --- a/patches/chromium/load_v8_snapshot_in_browser_process.patch +++ b/patches/chromium/load_v8_snapshot_in_browser_process.patch @@ -9,7 +9,7 @@ but due to the nature of electron, we need to load the v8 snapshot in the browser process. diff --git a/content/app/content_main_runner_impl.cc b/content/app/content_main_runner_impl.cc -index 24f6f89cfa430ed26476e1a3f79a8ed9464c45f3..a23d9b8fc451078708fd1a39f3d74357de7c244f 100644 +index 48363b920c780064a6d49f4a521b476bda5ac27b..d55c408557e15650897c9ed6d5b6bd83178a551f 100644 --- a/content/app/content_main_runner_impl.cc +++ b/content/app/content_main_runner_impl.cc @@ -296,11 +296,8 @@ void LoadV8SnapshotFile(const base::CommandLine& command_line) { diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 2f4cc22ce20a1..3cfbbc9f20f8a 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,7 +35,7 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index 59721ed3c9e26fd83c553d82030f3e76af0c3dfd..e8a9715e9004e5d10aa96298332237c78796bf5b 100644 +index a6cbbaa18ab6631aff7d76873077d2e15cbedeb6..db6fac3683f2737d05c5bc2dabfcc4b669a8a6d1 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn @@ -1045,6 +1045,7 @@ component("base") { @@ -548,18 +548,18 @@ index dbf334caa3a6d10017b69ad76802e389a011436b..da828823e8195cc9e497866363c9af93 void ForwardKeyboardEvent(const input::NativeWebKeyboardEvent& key_event, diff --git a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -index eca43bf620111c27c400ae2d95880e47c34fbc59..12ee7e75e437426f28002c7c9f4d5f5b5016ec53 100644 +index 371b7b3ba73ee7b88027fcc31cb0a346cae40eea..c4b0654a56f4f2b4ab57ef05a119e38862b5fd2d 100644 --- a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm +++ b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -@@ -35,6 +35,7 @@ - #include "content/public/browser/browser_accessibility_state.h" +@@ -36,6 +36,7 @@ #import "content/public/browser/render_widget_host_view_mac_delegate.h" + #include "content/public/browser/scoped_accessibility_mode.h" #include "content/public/common/content_features.h" +#include "electron/mas.h" #include "skia/ext/skia_utils_mac.h" #include "third_party/blink/public/common/features.h" #include "third_party/blink/public/mojom/input/input_handler.mojom.h" -@@ -2136,15 +2137,21 @@ - (NSAccessibilityRole)accessibilityRole { +@@ -2138,15 +2139,21 @@ - (NSAccessibilityRole)accessibilityRole { // Since this implementation doesn't have to wait any IPC calls, this doesn't // make any key-typing jank. --hbono 7/23/09 // @@ -582,7 +582,7 @@ index eca43bf620111c27c400ae2d95880e47c34fbc59..12ee7e75e437426f28002c7c9f4d5f5b return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 3256304fe1bfb80af0312f9046b1a78a2469956e..29281a0d8a4383ed4b2d5d8bac934acd54040aa8 100644 +index bdc48f4549ce6f82c5558b3c9e70c5c5a92c4faa..d10a5afe9da445b6fb940a46252efa8e0c36bcb4 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn @@ -342,6 +342,7 @@ source_set("browser") { @@ -797,7 +797,7 @@ index a1068589ad844518038ee7bc15a3de9bc5cba525..1ff781c49f086ec8015c7d3c44567dbe } // namespace content diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn -index 126c0d51647ef46a12b2c47930f7bd49e55dd736..d61474fb3478a27450a037f50d2a734097eb4ca9 100644 +index 4c59b6c62ad3fed9717b0330c7b46b8dc83a51a1..1c88c8f449387258259bcd65c13709d70f03117b 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn @@ -662,6 +662,7 @@ static_library("test_support") { @@ -824,7 +824,7 @@ index 126c0d51647ef46a12b2c47930f7bd49e55dd736..d61474fb3478a27450a037f50d2a7340 ] if (!(is_chromeos && target_cpu == "arm64" && current_cpu == "arm")) { -@@ -3283,6 +3286,7 @@ test("content_unittests") { +@@ -3284,6 +3287,7 @@ test("content_unittests") { "//ui/shell_dialogs:shell_dialogs", "//ui/webui:test_support", "//url", @@ -1848,7 +1848,7 @@ index 874ac9d572931fe175ccab8beb7738fe0a7b3c1b..b70e2a8a7be9e00a379f47c77589dde6 // Query the display's refresh rate. if (@available(macos 12.0, *)) { diff --git a/ui/gfx/BUILD.gn b/ui/gfx/BUILD.gn -index e531cb42cde9863ff1c4a13150f35877b564226c..0c0ec308be02297b090d08b52cc713c22652da36 100644 +index c8f01a88e0d1797baf53c517341c735d9c6e6b4a..345743dd19f862cf2b4304d70cb47ce68e6895d1 100644 --- a/ui/gfx/BUILD.gn +++ b/ui/gfx/BUILD.gn @@ -337,6 +337,12 @@ component("gfx") { diff --git a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch index 487d331ce98c7..01b9cb3d386b9 100644 --- a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch +++ b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch @@ -10,7 +10,7 @@ an about:blank check to this area. Ref: https://chromium-review.googlesource.com/c/chromium/src/+/5403876 diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 5870b90b02ba5cf4b197e91ae9c9dc8fa3ebf7e4..bab3c9fdb1a90dd42394ab77732976e0b444a4e5 100644 +index 78b55aa09b6db29119a0f47e11ea157e8b0c6d3b..deb02736cf52536d1c65255146ee077650d18095 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc @@ -807,8 +807,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index b0a9a4b666db3..3020f2fb1702e 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -881,10 +881,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 29281a0d8a4383ed4b2d5d8bac934acd54040aa8..0b943e7a4324b8ce9524d76f1cf4c6a2f187c595 100644 +index d10a5afe9da445b6fb940a46252efa8e0c36bcb4..6cfd8d6e9a38da8adfa05075097cc491962bd8f7 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3159,8 +3159,9 @@ source_set("browser") { +@@ -3157,8 +3157,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 7e702832e1450..2575b051ad0a1 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -44,10 +44,10 @@ index 8637d83c1d3a912bbc48effcc095b426640351ad..3419628c08b62a16c62778cc124c365a void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 4f87894219452e736311ad25a62b71b8aec4d158..7a8d7ce6f628123f5288d693046ca7602eeccac1 100644 +index fec569763d3ba8b171ca65a9ea523ada5f729f41..e236eb74db68a6c11892e1ea16cab05b8c47afbf 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5878,6 +5878,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -5883,6 +5883,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,7 +60,7 @@ index 4f87894219452e736311ad25a62b71b8aec4d158..7a8d7ce6f628123f5288d693046ca760 RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index ff2a3cc31a9c8e24222d3614c58d0884c1fde260..641840c371a76a729d62d59703a5d5566ef76b3c 100644 +index c0a0400ae804dca3679bf8e98dc06effcc96dfe0..2e305bca22ed140a8fe28077f611b845c5478a88 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h @@ -1186,6 +1186,7 @@ class CONTENT_EXPORT WebContentsImpl @@ -72,7 +72,7 @@ index ff2a3cc31a9c8e24222d3614c58d0884c1fde260..641840c371a76a729d62d59703a5d556 RenderWidgetHostImpl* render_widget_host) override; bool IsShowingContextMenuOnPage() const override; diff --git a/content/public/browser/web_contents_observer.h b/content/public/browser/web_contents_observer.h -index 4f97e13f9125e653f44acad78f8f35ee38e90b6d..f3c712e3f970dcccaac37e4dd407f14b52871269 100644 +index 7e0dd469a7059ea38120cfd6cd17469a3c06c1fa..4fd3ab75b462cf169443473b968db64c765930b8 100644 --- a/content/public/browser/web_contents_observer.h +++ b/content/public/browser/web_contents_observer.h @@ -37,6 +37,7 @@ diff --git a/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch b/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch index e31a8e462260f..6f67a6ed9ce64 100644 --- a/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch +++ b/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch @@ -28,7 +28,7 @@ index e350f6789c710826e0885ccdc19e66e2213820df..b8ba008470f39f6f3559d29b9eff0a23 break; } diff --git a/content/browser/permissions/permission_controller_impl.cc b/content/browser/permissions/permission_controller_impl.cc -index b267734bf2273253aa921728e12c753adfade02e..fd72e7d62ac45f51b2e7e295930ed25bb376056b 100644 +index b1c9f2d59559ed33cd32ad1f22b221029018cf0f..81deda95c71f025b723571ca9a6ac20bc7bb4b0c 100644 --- a/content/browser/permissions/permission_controller_impl.cc +++ b/content/browser/permissions/permission_controller_impl.cc @@ -87,7 +87,15 @@ PermissionToSchedulingFeature(PermissionType permission_name) { diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index 4a599baed0995..dbfa5f17c7b95 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 56b2fb93d5d85f520081de9e42e26ef3f8f6090e..b32e75e7c1922e63fdca891dfd7d4bcb27c5096e 100644 +index 5fef3e077072ee9dc3ff22110b7818503c8b4e4b..2d3fc900a04e6ddc291548a37aaf2322ccbc4846 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10129,25 +10129,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10134,25 +10134,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/render_widget_host_view_mac.patch b/patches/chromium/render_widget_host_view_mac.patch index 75be54bf20830..f79f8356bd8ad 100644 --- a/patches/chromium/render_widget_host_view_mac.patch +++ b/patches/chromium/render_widget_host_view_mac.patch @@ -8,10 +8,10 @@ respond to the first mouse click in their window, which is desirable for some kinds of utility windows. Similarly for `disableAutoHideCursor`. diff --git a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -index a6b6917ee2c02c091aa51b55449d93fa55e06ac2..eca43bf620111c27c400ae2d95880e47c34fbc59 100644 +index 91e5beaa68fc0b8231fce4bf195efa924744a532..371b7b3ba73ee7b88027fcc31cb0a346cae40eea 100644 --- a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm +++ b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -@@ -170,6 +170,15 @@ void ExtractUnderlines(NSAttributedString* string, +@@ -171,6 +171,15 @@ void ExtractUnderlines(NSAttributedString* string, } // namespace @@ -27,7 +27,7 @@ index a6b6917ee2c02c091aa51b55449d93fa55e06ac2..eca43bf620111c27c400ae2d95880e47 // RenderWidgetHostViewCocoa --------------------------------------------------- // Private methods: -@@ -774,6 +783,9 @@ - (AcceptMouseEventsOption)acceptsMouseEventsOption { +@@ -776,6 +785,9 @@ - (AcceptMouseEventsOption)acceptsMouseEventsOption { } - (BOOL)acceptsFirstMouse:(NSEvent*)theEvent { @@ -37,7 +37,7 @@ index a6b6917ee2c02c091aa51b55449d93fa55e06ac2..eca43bf620111c27c400ae2d95880e47 // Enable "click-through" if mouse clicks are accepted in inactive windows return [self acceptsMouseEventsOption] > kAcceptMouseEventsInActiveWindow; } -@@ -919,6 +931,10 @@ - (BOOL)shouldIgnoreMouseEvent:(NSEvent*)theEvent { +@@ -921,6 +933,10 @@ - (BOOL)shouldIgnoreMouseEvent:(NSEvent*)theEvent { // its parent view. BOOL hitSelf = NO; while (view) { @@ -48,7 +48,7 @@ index a6b6917ee2c02c091aa51b55449d93fa55e06ac2..eca43bf620111c27c400ae2d95880e47 if (view == self) hitSelf = YES; if ([view isKindOfClass:[self class]] && ![view isEqual:self] && -@@ -1253,6 +1269,10 @@ - (void)keyEvent:(NSEvent*)theEvent wasKeyEquivalent:(BOOL)equiv { +@@ -1255,6 +1271,10 @@ - (void)keyEvent:(NSEvent*)theEvent wasKeyEquivalent:(BOOL)equiv { eventType == NSEventTypeKeyDown && !(modifierFlags & NSEventModifierFlagCommand); diff --git a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch index b5dace2e08657..49cfde7de2e25 100644 --- a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch +++ b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch @@ -233,10 +233,10 @@ index 7c99a9512e6f65713fe8483cef7b7c9b494b4491..8fb6cf252961c9773d1a6a09d47bec6a } diff --git a/content/common/features.cc b/content/common/features.cc -index 9a619bf9a4e2801d7a67bd26104066d03dcfb465..6aa5f4cb75bc8e22048b6b9bb8456a958ad7b80d 100644 +index 9119155650ed4249c699cc57eaef9149b99e7297..13e2c0da07938d73b5a689cea19df4a445c4e5e5 100644 --- a/content/common/features.cc +++ b/content/common/features.cc -@@ -300,6 +300,14 @@ BASE_FEATURE(kIOSurfaceCapturer, +@@ -294,6 +294,14 @@ BASE_FEATURE(kIOSurfaceCapturer, base::FEATURE_ENABLED_BY_DEFAULT); #endif @@ -252,10 +252,10 @@ index 9a619bf9a4e2801d7a67bd26104066d03dcfb465..6aa5f4cb75bc8e22048b6b9bb8456a95 // invalidated upon notifications sent by base::SystemMonitor. If disabled, the // cache is considered invalid on every enumeration request. diff --git a/content/common/features.h b/content/common/features.h -index 7bc79ead73e5e51d7735d6964cf96990120670ca..83b5666e735aa99a8e2300b37154da1769baa2b0 100644 +index 0764c2fd1086bb0da16df91c95b171eea0a06bb1..3bc7a54999ec5e1f3afa45fe59d43ba12ec10286 100644 --- a/content/common/features.h +++ b/content/common/features.h -@@ -100,6 +100,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); +@@ -99,6 +99,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); #if BUILDFLAG(IS_MAC) CONTENT_EXPORT BASE_DECLARE_FEATURE(kIOSurfaceCapturer); #endif diff --git a/patches/chromium/revert_enable_crel_for_arm32_targets.patch b/patches/chromium/revert_enable_crel_for_arm32_targets.patch deleted file mode 100644 index 534abda4bf67a..0000000000000 --- a/patches/chromium/revert_enable_crel_for_arm32_targets.patch +++ /dev/null @@ -1,23 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Samuel Maddock -Date: Fri, 28 Mar 2025 20:22:26 -0400 -Subject: revert: Enable CREL for arm32 targets - -Enabling CREL on Linux ARM64 seems to cause it to segfault. Disable for Electron -as its one of our supported platforms. -https://chromium-review.googlesource.com/q/I3a62f02f564f07be63173b0773b4ecaffbe939b9 - -diff --git a/build/config/compiler/BUILD.gn b/build/config/compiler/BUILD.gn -index e579cc9a9d1fd01d390a64886f649dc53102166e..de1f3b7b1a33bf5ab4f6922f0cb2d305a8af7550 100644 ---- a/build/config/compiler/BUILD.gn -+++ b/build/config/compiler/BUILD.gn -@@ -619,7 +619,8 @@ config("compiler") { - - # Enable ELF CREL (see crbug.com/357878242) for all platforms that use ELF - # (excluding toolchains that use an older version of LLVM). -- if (is_linux && use_lld && !llvm_android_mainline && -+ # TODO(crbug.com/376278218): This causes segfault on Linux ARM builds. -+ if (is_linux && use_lld && !llvm_android_mainline && current_cpu != "arm" && - default_toolchain != "//build/toolchain/cros:target") { - cflags += [ "-Wa,--crel,--allow-experimental-crel" ] - } diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index a8dabf6dbbf7b..feafb0097d40a 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index f73f2ac411c0af45d7c0a4ba94222b2bd1d4841c..3ec3dd8f89bb167ed82c0da95a0f1d3d9738ac72 100644 +index b2d5733ff8c47f497af03171d9dfac68b2013e4d..52b782a40724ab6d8cd9abf2193aeb1a14a5d8e9 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -3947,6 +3947,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3952,6 +3952,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index f73f2ac411c0af45d7c0a4ba94222b2bd1d4841c..3ec3dd8f89bb167ed82c0da95a0f1d3d std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -3957,6 +3964,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3962,6 +3969,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } @@ -35,7 +35,7 @@ index f73f2ac411c0af45d7c0a4ba94222b2bd1d4841c..3ec3dd8f89bb167ed82c0da95a0f1d3d CHECK(view_.get()); diff --git a/content/public/browser/web_contents.h b/content/public/browser/web_contents.h -index 437060750090e974a3257979c215d13d036afa4e..5dce8d4e37845e1bb1922d7c4da3208939549b27 100644 +index 9360a2b080ebe4d6c0a475b0a536a5d7212c8a86..6e5eebfb199d322028f6b2bc72d666c24f334bba 100644 --- a/content/public/browser/web_contents.h +++ b/content/public/browser/web_contents.h @@ -121,10 +121,13 @@ class BrowserPluginGuestDelegate; @@ -52,7 +52,7 @@ index 437060750090e974a3257979c215d13d036afa4e..5dce8d4e37845e1bb1922d7c4da32089 class WebUI; struct DropData; struct MHTMLGenerationParams; -@@ -270,6 +273,10 @@ class WebContents : public PageNavigator, public base::SupportsUserData { +@@ -274,6 +277,10 @@ class WebContents : public PageNavigator, public base::SupportsUserData { network::mojom::WebSandboxFlags starting_sandbox_flags = network::mojom::WebSandboxFlags::kNone; diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index 5f02dfdcf5fd5..b194903626de5 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,10 +15,10 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 7b45a0006af60400f5d8ba5b925f971cb5cf393e..5870b90b02ba5cf4b197e91ae9c9dc8fa3ebf7e4 100644 +index df50b84cca214a9b6a85afe2fd677a45e2529cdc..78b55aa09b6db29119a0f47e11ea157e8b0c6d3b 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -8884,6 +8884,17 @@ void RenderFrameHostImpl::EnterFullscreen( +@@ -8881,6 +8881,17 @@ void RenderFrameHostImpl::EnterFullscreen( } } @@ -37,10 +37,10 @@ index 7b45a0006af60400f5d8ba5b925f971cb5cf393e..5870b90b02ba5cf4b197e91ae9c9dc8f if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 3ec3dd8f89bb167ed82c0da95a0f1d3d9738ac72..3b9e634245986b1ef22e8bf4e116470343f5ff60 100644 +index 52b782a40724ab6d8cd9abf2193aeb1a14a5d8e9..d0f80de98c2bd3cf686b05ef972c89a8c2276935 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4222,21 +4222,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4227,21 +4227,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index 3ec3dd8f89bb167ed82c0da95a0f1d3d9738ac72..3b9e634245986b1ef22e8bf4e1164703 } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4395,7 +4399,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4400,7 +4404,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch index 1d08b29cd92e7..68185410f669e 100644 --- a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch +++ b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch @@ -10,10 +10,10 @@ to handle this without patching, but this is fairly clean for now and no longer patching legacy devtools code. diff --git a/front_end/entrypoints/main/MainImpl.ts b/front_end/entrypoints/main/MainImpl.ts -index 0f3a5d69bef697a7787b68cd1c8261c67993edf3..1d49c1190ba7d47a76993b7f291119be243d189e 100644 +index 20ffe01d89e65b3eb6dc97b75761166ae3c9acb9..0444f2d81e53a01a81861c158713336a8062434f 100644 --- a/front_end/entrypoints/main/MainImpl.ts +++ b/front_end/entrypoints/main/MainImpl.ts -@@ -741,6 +741,8 @@ export class MainImpl { +@@ -736,6 +736,8 @@ export class MainImpl { globalThis.Main = globalThis.Main || {}; // @ts-expect-error Exported for Tests.js globalThis.Main.Main = MainImpl; diff --git a/patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch b/patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch index 1205dd0f509eb..b682b49f0e1ea 100644 --- a/patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch +++ b/patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch @@ -46,7 +46,7 @@ index 3e57ae8efe33f326ef0e5d609c311d4be5b8afd6..dc521d39c2280dfc3217e97c1e413b2b V8_INLINE static void* GetAlignedPointerFromInternalField( const BasicTracedReference& object, int index) { diff --git a/src/api/api.cc b/src/api/api.cc -index 0ab95ba54d1829ea0fda9a5678a906850b4b509b..2a01241d7db654098720f00a9130996e79d63261 100644 +index 62a71b9cb7594e5fcc86f32d7af160c32b8e8944..0b2d5bfa9480ea90eb0adb89132505b8cabafc08 100644 --- a/src/api/api.cc +++ b/src/api/api.cc @@ -6313,14 +6313,33 @@ Local v8::Object::SlowGetInternalField(int index) { diff --git a/shell/app/electron_main_delegate.cc b/shell/app/electron_main_delegate.cc index 9c34d5ca7b77f..fb58a1e8370c2 100644 --- a/shell/app/electron_main_delegate.cc +++ b/shell/app/electron_main_delegate.cc @@ -18,6 +18,7 @@ #include "base/files/file_util.h" #include "base/logging.h" #include "base/path_service.h" +#include "base/strings/cstring_view.h" #include "chrome/common/chrome_paths.h" #include "chrome/common/chrome_switches.h" #include "components/content_settings/core/common/content_settings_pattern.h" @@ -81,8 +82,9 @@ namespace { constexpr std::string_view kRelauncherProcess = "relauncher"; -constexpr std::string_view kElectronDisableSandbox{"ELECTRON_DISABLE_SANDBOX"}; -constexpr std::string_view kElectronEnableStackDumping{ +constexpr base::cstring_view kElectronDisableSandbox{ + "ELECTRON_DISABLE_SANDBOX"}; +constexpr base::cstring_view kElectronEnableStackDumping{ "ELECTRON_ENABLE_STACK_DUMPING"}; // Returns true if this subprocess type needs the ResourceBundle initialized diff --git a/shell/app/node_main.cc b/shell/app/node_main.cc index 7e9c493f8c01d..da539a86d30ab 100644 --- a/shell/app/node_main.cc +++ b/shell/app/node_main.cc @@ -17,6 +17,7 @@ #include "base/containers/fixed_flat_set.h" #include "base/environment.h" #include "base/feature_list.h" +#include "base/strings/cstring_view.h" #include "base/task/single_thread_task_runner.h" #include "base/task/thread_pool/thread_pool_instance.h" #include "content/public/common/content_switches.h" @@ -85,12 +86,13 @@ void ExitIfContainsDisallowedFlags(const std::vector& argv) { #if BUILDFLAG(IS_MAC) // A list of node envs that may be used to inject scripts. -const char* kHijackableEnvs[] = {"NODE_OPTIONS", "NODE_REPL_EXTERNAL_MODULE"}; +constexpr base::cstring_view kHijackableEnvs[] = {"NODE_OPTIONS", + "NODE_REPL_EXTERNAL_MODULE"}; // Return true if there is any env in kHijackableEnvs. bool UnsetHijackableEnvs(base::Environment* env) { bool has = false; - for (const char* name : kHijackableEnvs) { + for (base::cstring_view name : kHijackableEnvs) { if (env->HasVar(name)) { env->UnSetVar(name); has = true; diff --git a/shell/browser/api/electron_api_app.cc b/shell/browser/api/electron_api_app.cc index f6d639dc82a9d..7ff15cacc5b9a 100644 --- a/shell/browser/api/electron_api_app.cc +++ b/shell/browser/api/electron_api_app.cc @@ -1167,13 +1167,12 @@ void App::SetAccessibilitySupportEnabled(gin_helper::ErrorThrower thrower, return; } - // TODO(wg-upgrades): crbug.com/1470199 remove use of deprecated - // AddAccessibilityModeFlags() and RemoveAccessibilityModeFlags() - auto* ax_state = content::BrowserAccessibilityState::GetInstance(); - if (enabled) { - ax_state->AddAccessibilityModeFlags(ui::kAXModeComplete); - } else { - ax_state->RemoveAccessibilityModeFlags(ui::kAXModeComplete); + if (!enabled) { + scoped_accessibility_mode_.reset(); + } else if (!scoped_accessibility_mode_) { + scoped_accessibility_mode_ = + content::BrowserAccessibilityState::GetInstance() + ->CreateScopedModeForProcess(ui::kAXModeComplete); } Browser::Get()->OnAccessibilitySupportChanged(); } diff --git a/shell/browser/api/electron_api_app.h b/shell/browser/api/electron_api_app.h index d19e5270e9034..8c591df0819dc 100644 --- a/shell/browser/api/electron_api_app.h +++ b/shell/browser/api/electron_api_app.h @@ -16,6 +16,7 @@ #include "content/public/browser/browser_child_process_observer.h" #include "content/public/browser/gpu_data_manager_observer.h" #include "content/public/browser/render_process_host.h" +#include "content/public/browser/scoped_accessibility_mode.h" #include "crypto/crypto_buildflags.h" #include "electron/mas.h" #include "net/base/completion_once_callback.h" @@ -276,6 +277,8 @@ class App final : public ElectronBrowserClient::Delegate, bool disable_hw_acceleration_ = false; bool disable_domain_blocking_for_3DAPIs_ = false; bool watch_singleton_socket_on_ready_ = false; + + std::unique_ptr scoped_accessibility_mode_; }; } // namespace api diff --git a/shell/browser/electron_browser_main_parts_linux.cc b/shell/browser/electron_browser_main_parts_linux.cc index 1bac78d7c8f8c..87e2f50d2a2eb 100644 --- a/shell/browser/electron_browser_main_parts_linux.cc +++ b/shell/browser/electron_browser_main_parts_linux.cc @@ -4,10 +4,9 @@ #include "shell/browser/electron_browser_main_parts.h" -#include - #include "base/command_line.h" #include "base/environment.h" +#include "base/strings/cstring_view.h" #include "ui/base/ozone_buildflags.h" #include "ui/ozone/public/ozone_switches.h" @@ -22,7 +21,7 @@ namespace electron { namespace { -constexpr std::string_view kElectronOzonePlatformHint{ +constexpr base::cstring_view kElectronOzonePlatformHint{ "ELECTRON_OZONE_PLATFORM_HINT"}; #if BUILDFLAG(IS_OZONE_WAYLAND) diff --git a/shell/browser/mac/electron_application.mm b/shell/browser/mac/electron_application.mm index 350443fb0382f..e4c86aabde3da 100644 --- a/shell/browser/mac/electron_application.mm +++ b/shell/browser/mac/electron_application.mm @@ -13,9 +13,11 @@ #include "content/public/browser/browser_accessibility_state.h" #include "content/public/browser/native_event_processor_mac.h" #include "content/public/browser/native_event_processor_observer_mac.h" +#include "content/public/browser/scoped_accessibility_mode.h" #include "shell/browser/browser.h" #include "shell/browser/mac/dict_util.h" #import "shell/browser/mac/electron_application_delegate.h" +#include "ui/accessibility/ax_mode.h" namespace { @@ -34,7 +36,10 @@ @interface AtomApplication () { } @end -@implementation AtomApplication +@implementation AtomApplication { + std::unique_ptr + _scoped_accessibility_mode_general; +} + (AtomApplication*)sharedApplication { return (AtomApplication*)[super sharedApplication]; @@ -209,13 +214,12 @@ - (id)accessibilityAttributeValue:(NSString*)attribute { - (void)accessibilitySetValue:(id)value forAttribute:(NSString*)attribute { bool is_manual_ax = [attribute isEqualToString:@"AXManualAccessibility"]; if ([attribute isEqualToString:@"AXEnhancedUserInterface"] || is_manual_ax) { - auto* ax_state = content::BrowserAccessibilityState::GetInstance(); - // TODO(wg-upgrades): crbug.com/1470199 remove use of deprecated - // AddAccessibilityModeFlags() and RemoveAccessibilityModeFlags() - if ([value boolValue]) { - ax_state->AddAccessibilityModeFlags(ui::kAXModeComplete); - } else { - ax_state->RemoveAccessibilityModeFlags(ui::kAXModeComplete); + if (![value boolValue]) { + _scoped_accessibility_mode_general.reset(); + } else if (!_scoped_accessibility_mode_general) { + _scoped_accessibility_mode_general = + content::BrowserAccessibilityState::GetInstance() + ->CreateScopedModeForProcess(ui::kAXModeComplete); } electron::Browser::Get()->OnAccessibilitySupportChanged(); @@ -230,15 +234,21 @@ - (void)accessibilitySetValue:(id)value forAttribute:(NSString*)attribute { return [super accessibilitySetValue:value forAttribute:attribute]; } +// FROM: +// https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/chrome_browser_application_mac.mm;l=549;drc=4341cc4e529444bd201ad3aeeed0ec561e04103f - (NSAccessibilityRole)accessibilityRole { - // For non-VoiceOver AT, such as Voice Control, Apple recommends turning on - // a11y when an AT accesses the 'accessibilityRole' property. This function - // is accessed frequently so we only change the accessibility state when - // accessibility is disabled. - auto* ax_state = content::BrowserAccessibilityState::GetInstance(); - if (!ax_state->GetAccessibilityMode().has_mode(ui::kAXModeBasic.flags())) { - ax_state->AddAccessibilityModeFlags(ui::kAXModeBasic); + // For non-VoiceOver assistive technology (AT), such as Voice Control, Apple + // recommends turning on a11y when an AT accesses the 'accessibilityRole' + // property. This function is accessed frequently, so we only change the + // accessibility state when accessibility is already disabled. + if (!_scoped_accessibility_mode_general) { + ui::AXMode target_mode = ui::kAXModeBasic; + _scoped_accessibility_mode_general = + content::BrowserAccessibilityState::GetInstance() + ->CreateScopedModeForProcess(target_mode | + ui::AXMode::kFromPlatform); } + return [super accessibilityRole]; } diff --git a/shell/browser/native_window_views.h b/shell/browser/native_window_views.h index 8ef7d2b783a2f..b65221bcdba21 100644 --- a/shell/browser/native_window_views.h +++ b/shell/browser/native_window_views.h @@ -20,6 +20,7 @@ #if BUILDFLAG(IS_WIN) #include "base/win/scoped_gdi_object.h" +#include "content/public/browser/scoped_accessibility_mode.h" #include "shell/browser/ui/win/taskbar_host.h" #endif @@ -309,6 +310,8 @@ class NativeWindowViews : public NativeWindow, // The message ID of the "TaskbarCreated" message, sent to us when we need to // reset our thumbar buttons. UINT taskbar_created_message_ = 0; + + std::unique_ptr scoped_accessibility_mode_; #endif // Handles unhandled keyboard messages coming back from the renderer process. diff --git a/shell/browser/native_window_views_win.cc b/shell/browser/native_window_views_win.cc index ec11d02baee66..858418af4f8d5 100644 --- a/shell/browser/native_window_views_win.cc +++ b/shell/browser/native_window_views_win.cc @@ -280,11 +280,11 @@ bool NativeWindowViews::PreHandleMSG(UINT message, checked_for_a11y_support_ = true; - // TODO(wg-upgrades): crbug.com/1470199 remove use of deprecated - // AddAccessibilityModeFlags() and RemoveAccessibilityModeFlags() auto* const axState = content::BrowserAccessibilityState::GetInstance(); if (axState && axState->GetAccessibilityMode() != ui::kAXModeComplete) { - axState->AddAccessibilityModeFlags(ui::kAXModeComplete); + scoped_accessibility_mode_ = + content::BrowserAccessibilityState::GetInstance() + ->CreateScopedModeForProcess(ui::kAXModeComplete); Browser::Get()->OnAccessibilitySupportChanged(); } diff --git a/shell/browser/osr/osr_video_consumer.cc b/shell/browser/osr/osr_video_consumer.cc index 85c9286e18fc6..f1307bb62fb0d 100644 --- a/shell/browser/osr/osr_video_consumer.cc +++ b/shell/browser/osr/osr_video_consumer.cc @@ -109,7 +109,7 @@ void OffScreenVideoConsumer::OnFrameCaptured( texture.shared_texture_handle = reinterpret_cast(gmb_handle.io_surface.get()); #elif BUILDFLAG(IS_LINUX) - const auto& native_pixmap = gmb_handle.native_pixmap_handle; + const auto& native_pixmap = gmb_handle.native_pixmap_handle(); texture.modifier = native_pixmap.modifier; for (const auto& plane : native_pixmap.planes) { texture.planes.emplace_back(plane.stride, plane.offset, plane.size, diff --git a/shell/common/logging.cc b/shell/common/logging.cc index 7204dfd4f8480..093f9cdaa38e1 100644 --- a/shell/common/logging.cc +++ b/shell/common/logging.cc @@ -5,7 +5,6 @@ #include "shell/common/logging.h" #include -#include #include "base/base_switches.h" #include "base/command_line.h" @@ -13,14 +12,15 @@ #include "base/files/file_path.h" #include "base/logging.h" #include "base/path_service.h" +#include "base/strings/cstring_view.h" #include "base/strings/string_number_conversions.h" #include "chrome/common/chrome_paths.h" #include "content/public/common/content_switches.h" namespace logging { -constexpr std::string_view kLogFileName{"ELECTRON_LOG_FILE"}; -constexpr std::string_view kElectronEnableLogging{"ELECTRON_ENABLE_LOGGING"}; +constexpr base::cstring_view kLogFileName{"ELECTRON_LOG_FILE"}; +constexpr base::cstring_view kElectronEnableLogging{"ELECTRON_ENABLE_LOGGING"}; base::FilePath GetLogFileName(const base::CommandLine& command_line) { std::string filename = command_line.GetSwitchValueASCII(switches::kLogFile); From 47e25dfd57514471065c54baf8d4aa63d2bcf71f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 19:08:00 -0500 Subject: [PATCH 007/186] fix: prevent log files being written to current directory on Windows (#46910) * fix: prevent log files being written to current directory on Windows Co-authored-by: Derek Cicerone * Update shell/common/logging.cc Co-authored-by: Robo Co-authored-by: Derek Cicerone <120135886+derekcicerone@users.noreply.github.com> * chore: add test Co-authored-by: deepak1556 * chore: update includes Refs https://chromium-review.googlesource.com/c/chromium/src/+/6418805 Co-authored-by: deepak1556 * chore: address review feedback Co-authored-by: deepak1556 --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Derek Cicerone Co-authored-by: Derek Cicerone <120135886+derekcicerone@users.noreply.github.com> Co-authored-by: deepak1556 --- shell/common/api/electron_api_testing.cc | 8 +++ shell/common/logging.cc | 78 +++++++++++++++++++++--- spec/fixtures/log-test.js | 3 + spec/logging-spec.ts | 30 ++++++++- 4 files changed, 110 insertions(+), 9 deletions(-) create mode 100644 spec/fixtures/log-test.js diff --git a/shell/common/api/electron_api_testing.cc b/shell/common/api/electron_api_testing.cc index 8d88fca564186..097da88e158b6 100644 --- a/shell/common/api/electron_api_testing.cc +++ b/shell/common/api/electron_api_testing.cc @@ -2,8 +2,10 @@ // Use of this source code is governed by the MIT license that can be // found in the LICENSE file. +#include "base/command_line.h" #include "base/dcheck_is_on.h" #include "base/logging.h" +#include "content/public/common/content_switches.h" #include "shell/common/gin_helper/dictionary.h" #include "shell/common/node_includes.h" #include "v8/include/v8.h" @@ -34,12 +36,18 @@ void Log(int severity, std::string text) { } } +std::string GetLoggingDestination() { + const auto* command_line = base::CommandLine::ForCurrentProcess(); + return command_line->GetSwitchValueASCII(switches::kEnableLogging); +} + void Initialize(v8::Local exports, v8::Local unused, v8::Local context, void* priv) { gin_helper::Dictionary dict(context->GetIsolate(), exports); dict.SetMethod("log", &Log); + dict.SetMethod("getLoggingDestination", &GetLoggingDestination); } } // namespace diff --git a/shell/common/logging.cc b/shell/common/logging.cc index 093f9cdaa38e1..3969d5a9bd67a 100644 --- a/shell/common/logging.cc +++ b/shell/common/logging.cc @@ -17,11 +17,41 @@ #include "chrome/common/chrome_paths.h" #include "content/public/common/content_switches.h" +#if BUILDFLAG(IS_WIN) +#include +#include "base/win/scoped_handle.h" +#include "base/win/windows_handle_util.h" +#include "sandbox/policy/switches.h" +#endif + namespace logging { constexpr base::cstring_view kLogFileName{"ELECTRON_LOG_FILE"}; constexpr base::cstring_view kElectronEnableLogging{"ELECTRON_ENABLE_LOGGING"}; +#if BUILDFLAG(IS_WIN) +base::win::ScopedHandle GetLogInheritedHandle( + const base::CommandLine& command_line) { + auto handle_str = command_line.GetSwitchValueNative(::switches::kLogFile); + uint32_t handle_value = 0; + if (!base::StringToUint(handle_str, &handle_value)) { + return {}; + } + // Duplicate the handle from the command line so that different things can + // init logging. This means the handle from the parent is never closed, but + // there will only be one of these in the process. + HANDLE log_handle = nullptr; + if (!::DuplicateHandle(::GetCurrentProcess(), + base::win::Uint32ToHandle(handle_value), + ::GetCurrentProcess(), &log_handle, 0, + /*bInheritHandle=*/FALSE, DUPLICATE_SAME_ACCESS)) { + return {}; + } + // Transfer ownership to the caller. + return base::win::ScopedHandle(log_handle); +} +#endif + base::FilePath GetLogFileName(const base::CommandLine& command_line) { std::string filename = command_line.GetSwitchValueASCII(switches::kLogFile); if (filename.empty()) @@ -47,9 +77,9 @@ bool HasExplicitLogFile(const base::CommandLine& command_line) { return !filename.empty(); } -LoggingDestination DetermineLoggingDestination( - const base::CommandLine& command_line, - bool is_preinit) { +std::pair +DetermineLoggingDestination(const base::CommandLine& command_line, + bool is_preinit) { bool enable_logging = false; std::string logging_destination; if (command_line.HasSwitch(::switches::kEnableLogging)) { @@ -64,7 +94,7 @@ LoggingDestination DetermineLoggingDestination( } } if (!enable_logging) - return LOG_NONE; + return {LOG_NONE, false}; bool also_log_to_stderr = false; #if !defined(NDEBUG) @@ -73,6 +103,16 @@ LoggingDestination DetermineLoggingDestination( also_log_to_stderr = !also_log_to_stderr_str->empty(); #endif +#if BUILDFLAG(IS_WIN) + if (logging_destination == "handle" && + command_line.HasSwitch(::switches::kProcessType) && + command_line.HasSwitch(::switches::kLogFile)) { + // Child processes can log to a handle duplicated from the parent, and + // provided in the log-file switch value. + return {LOG_TO_FILE, true}; + } +#endif // BUILDFLAG(IS_WIN) + // --enable-logging logs to stderr, --enable-logging=file logs to a file. // NB. this differs from Chromium, in which --enable-logging logs to a file // and --enable-logging=stderr logs to stderr, because that's how Electron @@ -88,8 +128,8 @@ LoggingDestination DetermineLoggingDestination( // given. if (HasExplicitLogFile(command_line) || (logging_destination == "file" && !is_preinit)) - return LOG_TO_FILE | (also_log_to_stderr ? LOG_TO_STDERR : 0); - return LOG_TO_SYSTEM_DEBUG_LOG | LOG_TO_STDERR; + return {LOG_TO_FILE | (also_log_to_stderr ? LOG_TO_STDERR : 0), false}; + return {LOG_TO_SYSTEM_DEBUG_LOG | LOG_TO_STDERR, false}; } } // namespace @@ -98,10 +138,13 @@ void InitElectronLogging(const base::CommandLine& command_line, bool is_preinit) { const std::string process_type = command_line.GetSwitchValueASCII(::switches::kProcessType); - LoggingDestination logging_dest = + auto [logging_dest, filename_is_handle] = DetermineLoggingDestination(command_line, is_preinit); LogLockingState log_locking_state = LOCK_LOG_FILE; base::FilePath log_path; +#if BUILDFLAG(IS_WIN) + base::win::ScopedHandle log_handle; +#endif if (command_line.HasSwitch(::switches::kLoggingLevel) && GetMinLogLevel() >= 0) { @@ -119,7 +162,19 @@ void InitElectronLogging(const base::CommandLine& command_line, // Don't resolve the log path unless we need to. Otherwise we leave an open // ALPC handle after sandbox lockdown on Windows. if ((logging_dest & LOG_TO_FILE) != 0) { - log_path = GetLogFileName(command_line); + if (filename_is_handle) { +#if BUILDFLAG(IS_WIN) + // Child processes on Windows are provided a file handle if logging is + // enabled as sandboxed processes cannot open files. + log_handle = GetLogInheritedHandle(command_line); + if (!log_handle.is_valid()) { + LOG(ERROR) << "Unable to initialize logging from handle."; + return; + } +#endif + } else { + log_path = GetLogFileName(command_line); + } } else { log_locking_state = DONT_LOCK_LOG_FILE; } @@ -131,6 +186,13 @@ void InitElectronLogging(const base::CommandLine& command_line, LoggingSettings settings; settings.logging_dest = logging_dest; settings.log_file_path = log_path.value().c_str(); +#if BUILDFLAG(IS_WIN) + // Avoid initializing with INVALID_HANDLE_VALUE. + // This handle is owned by the logging framework and is closed when the + // process exits. + // TODO(crbug.com/328285906) Use a ScopedHandle in logging settings. + settings.log_file = log_handle.is_valid() ? log_handle.release() : nullptr; +#endif settings.lock_log = log_locking_state; // If we're logging to an explicit file passed with --log-file, we don't want // to delete the log file on our second initialization. diff --git a/spec/fixtures/log-test.js b/spec/fixtures/log-test.js new file mode 100644 index 0000000000000..840b66791e2dd --- /dev/null +++ b/spec/fixtures/log-test.js @@ -0,0 +1,3 @@ +const binding = process._linkedBinding('electron_common_testing'); +binding.log(1, 'CHILD_PROCESS_TEST_LOG'); +binding.log(1, `CHILD_PROCESS_DESTINATION_${binding.getLoggingDestination()}`); diff --git a/spec/logging-spec.ts b/spec/logging-spec.ts index cde8fdb170d0f..30258f9a7f47e 100644 --- a/spec/logging-spec.ts +++ b/spec/logging-spec.ts @@ -7,7 +7,7 @@ import { once } from 'node:events'; import * as fs from 'node:fs/promises'; import * as path from 'node:path'; -import { startRemoteControlApp, ifdescribe } from './lib/spec-helpers'; +import { startRemoteControlApp, ifdescribe, ifit } from './lib/spec-helpers'; function isTestingBindingAvailable () { try { @@ -127,6 +127,34 @@ ifdescribe(isTestingBindingAvailable())('logging', () => { expect(contents).to.match(/TEST_LOG/); }); + ifit(process.platform === 'win32')('child process logs to the given file when --log-file is passed', async () => { + const logFilePath = path.join(app.getPath('temp'), 'test-log-file-' + uuid.v4()); + const preloadPath = path.resolve(__dirname, 'fixtures', 'log-test.js'); + const rc = await startRemoteControlApp(['--enable-logging', `--log-file=${logFilePath}`, `--boot-eval=preloadPath=${JSON.stringify(preloadPath)}`]); + rc.remotely(() => { + process._linkedBinding('electron_common_testing').log(0, 'MAIN_PROCESS_TEST_LOG'); + const { app, BrowserWindow } = require('electron'); + const w = new BrowserWindow({ + show: false, + webPreferences: { + preload: preloadPath, + additionalArguments: ['--unsafely-expose-electron-internals-for-testing'] + } + }); + w.loadURL('about:blank'); + w.webContents.once('did-finish-load', () => { + setTimeout(() => { app.quit(); }); + }); + }); + await once(rc.process, 'exit'); + const stat = await fs.stat(logFilePath); + expect(stat.isFile()).to.be.true(); + const contents = await fs.readFile(logFilePath, 'utf8'); + expect(contents).to.match(/MAIN_PROCESS_TEST_LOG/); + expect(contents).to.match(/CHILD_PROCESS_TEST_LOG/); + expect(contents).to.match(/CHILD_PROCESS_DESTINATION_handle/); + }); + it('logs to the given file when ELECTRON_LOG_FILE is set', async () => { const logFilePath = path.join(app.getPath('temp'), 'test-log-file-' + uuid.v4()); const rc = await startRemoteControlApp([], { env: { ...process.env, ELECTRON_ENABLE_LOGGING: '1', ELECTRON_LOG_FILE: logFilePath } }); From bf94f8856912d2bfa501e140c09621785e89bc39 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 19:08:28 -0500 Subject: [PATCH 008/186] refactor: move `IsClosed()` and `IsClosable()` tests into `NativeWindow::Close()` (#46907) refactor: devirtualize NativeWindow::IsClosed() Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_base_window.cc | 3 +-- shell/browser/native_window.cc | 21 ++++++++++++++----- shell/browser/native_window.h | 12 ++++++++--- shell/browser/native_window_mac.h | 4 ++-- shell/browser/native_window_mac.mm | 12 +++-------- shell/browser/native_window_views.cc | 10 ++------- shell/browser/native_window_views.h | 4 ++-- shell/browser/window_list.cc | 4 ++-- 8 files changed, 37 insertions(+), 33 deletions(-) diff --git a/shell/browser/api/electron_api_base_window.cc b/shell/browser/api/electron_api_base_window.cc index 506350baa80e1..27d9da1ba7dbd 100644 --- a/shell/browser/api/electron_api_base_window.cc +++ b/shell/browser/api/electron_api_base_window.cc @@ -362,8 +362,7 @@ void BaseWindow::SetContentView(gin::Handle view) { } void BaseWindow::CloseImmediately() { - if (!window_->IsClosed()) - window_->CloseImmediately(); + window_->CloseImmediately(); } void BaseWindow::Close() { diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 19232b6259b0b..b6e7d9a9901c7 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -284,10 +284,6 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { Show(); } -bool NativeWindow::IsClosed() const { - return is_closed_; -} - void NativeWindow::SetSize(const gfx::Size& size, bool animate) { SetBounds(gfx::Rect(GetPosition(), size), animate); } @@ -525,8 +521,23 @@ void NativeWindow::NotifyWindowCloseButtonClicked() { CloseImmediately(); } +void NativeWindow::Close() { + if (!IsClosable()) { + WindowList::WindowCloseCancelled(this); + return; + } + + if (!is_closed()) + CloseImpl(); +} + +void NativeWindow::CloseImmediately() { + if (!is_closed()) + CloseImmediatelyImpl(); +} + void NativeWindow::NotifyWindowClosed() { - if (is_closed_) + if (is_closed()) return; is_closed_ = true; diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index 831cf8947aa85..176931bc2eb4f 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -82,9 +82,10 @@ class NativeWindow : public base::SupportsUserData, virtual void SetContentView(views::View* view) = 0; - virtual void Close() = 0; - virtual void CloseImmediately() = 0; - virtual bool IsClosed() const; + // wrapper around CloseImpl that checks that window_ can be closed + void Close(); + // wrapper around CloseImmediatelyImpl that checks that window_ can be closed + void CloseImmediately(); virtual void Focus(bool focus) = 0; virtual bool IsFocused() const = 0; virtual void Show() = 0; @@ -435,6 +436,8 @@ class NativeWindow : public base::SupportsUserData, protected: friend class api::BrowserView; + [[nodiscard]] constexpr bool is_closed() const { return is_closed_; } + NativeWindow(const gin_helper::Dictionary& options, NativeWindow* parent); // views::WidgetDelegate: @@ -444,6 +447,9 @@ class NativeWindow : public base::SupportsUserData, void set_content_view(views::View* view) { content_view_ = view; } + virtual void CloseImpl() = 0; + virtual void CloseImmediatelyImpl() = 0; + // The boolean parsing of the "titleBarOverlay" option bool titlebar_overlay_ = false; diff --git a/shell/browser/native_window_mac.h b/shell/browser/native_window_mac.h index 5420e14aecd7d..d4c07ba6fc06f 100644 --- a/shell/browser/native_window_mac.h +++ b/shell/browser/native_window_mac.h @@ -38,8 +38,8 @@ class NativeWindowMac : public NativeWindow, // NativeWindow: void SetContentView(views::View* view) override; - void Close() override; - void CloseImmediately() override; + void CloseImpl() override; + void CloseImmediatelyImpl() override; void Focus(bool focus) override; bool IsFocused() const override; void Show() override; diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 6d8a2712420be..2610ddeaf03ca 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -33,7 +33,6 @@ #include "shell/browser/ui/cocoa/root_view_mac.h" #include "shell/browser/ui/cocoa/window_buttons_proxy.h" #include "shell/browser/ui/drag_util.h" -#include "shell/browser/window_list.h" #include "shell/common/gin_converters/gfx_converter.h" #include "shell/common/gin_helper/dictionary.h" #include "shell/common/node_util.h" @@ -331,12 +330,7 @@ static bool FromV8(v8::Isolate* isolate, root_view->DeprecatedLayoutImmediately(); } -void NativeWindowMac::Close() { - if (!IsClosable()) { - WindowList::WindowCloseCancelled(this); - return; - } - +void NativeWindowMac::CloseImpl() { if (fullscreen_transition_state() != FullScreenTransitionState::kNone) { SetHasDeferredWindowClose(true); return; @@ -372,7 +366,7 @@ static bool FromV8(v8::Isolate* isolate, } } -void NativeWindowMac::CloseImmediately() { +void NativeWindowMac::CloseImmediatelyImpl() { // Ensure we're detached from the parent window before closing. RemoveChildFromParentWindow(); @@ -1692,7 +1686,7 @@ static bool FromV8(v8::Isolate* isolate, } void NativeWindowMac::Cleanup() { - DCHECK(!IsClosed()); + DCHECK(!is_closed()); ui::NativeTheme::GetInstanceForNativeUi()->RemoveObserver(this); display::Screen::GetScreen()->RemoveObserver(this); [window_ cleanup]; diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index f9c659a9ddd0b..dd1af72d13c12 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -31,7 +31,6 @@ #include "shell/browser/ui/views/root_view.h" #include "shell/browser/web_contents_preferences.h" #include "shell/browser/web_view_manager.h" -#include "shell/browser/window_list.h" #include "shell/common/electron_constants.h" #include "shell/common/gin_converters/image_converter.h" #include "shell/common/gin_helper/dictionary.h" @@ -473,16 +472,11 @@ void NativeWindowViews::SetContentView(views::View* view) { root_view_.GetMainView()->DeprecatedLayoutImmediately(); } -void NativeWindowViews::Close() { - if (!IsClosable()) { - WindowList::WindowCloseCancelled(this); - return; - } - +void NativeWindowViews::CloseImpl() { widget()->Close(); } -void NativeWindowViews::CloseImmediately() { +void NativeWindowViews::CloseImmediatelyImpl() { widget()->CloseNow(); } diff --git a/shell/browser/native_window_views.h b/shell/browser/native_window_views.h index b65221bcdba21..650a026b4807c 100644 --- a/shell/browser/native_window_views.h +++ b/shell/browser/native_window_views.h @@ -48,8 +48,8 @@ class NativeWindowViews : public NativeWindow, // NativeWindow: void SetContentView(views::View* view) override; - void Close() override; - void CloseImmediately() override; + void CloseImpl() override; + void CloseImmediatelyImpl() override; void Focus(bool focus) override; bool IsFocused() const override; void Show() override; diff --git a/shell/browser/window_list.cc b/shell/browser/window_list.cc index 188402d0e6bb1..bd9cfbfe53e23 100644 --- a/shell/browser/window_list.cc +++ b/shell/browser/window_list.cc @@ -84,7 +84,7 @@ void WindowList::CloseAllWindows() { std::ranges::reverse(weak_windows); #endif for (const auto& window : weak_windows) { - if (window && !window->IsClosed()) + if (window) window->Close(); } } @@ -95,7 +95,7 @@ void WindowList::DestroyAllWindows() { ConvertToWeakPtrVector(GetInstance()->windows_); for (const auto& window : weak_windows) { - if (window && !window->IsClosed()) + if (window) window->CloseImmediately(); } } From d783f134d92036e6ea79e91487c9dfb1c9eb500f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 19:08:50 -0500 Subject: [PATCH 009/186] feat: support dip <-> screen conversion on Linux X11 (#46895) feat: support dip <-> screen conversion on Linux Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- BUILD.gn | 2 + docs/api/base-window.md | 2 +- docs/api/browser-window.md | 2 +- docs/api/screen.md | 9 +++- shell/browser/api/electron_api_screen.cc | 59 ++++++++++++++++++++---- shell/browser/api/electron_api_screen.h | 4 ++ shell/browser/linux/x11_util.cc | 17 +++++++ shell/browser/linux/x11_util.h | 14 ++++++ shell/browser/native_window_views.cc | 28 +++++------ 9 files changed, 106 insertions(+), 31 deletions(-) create mode 100644 shell/browser/linux/x11_util.cc create mode 100644 shell/browser/linux/x11_util.h diff --git a/BUILD.gn b/BUILD.gn index d1a0083474373..fe4fb706f5573 100644 --- a/BUILD.gn +++ b/BUILD.gn @@ -670,6 +670,8 @@ source_set("electron_lib") { sources += [ "shell/browser/certificate_manager_model.cc", "shell/browser/certificate_manager_model.h", + "shell/browser/linux/x11_util.cc", + "shell/browser/linux/x11_util.h", "shell/browser/ui/gtk_util.cc", "shell/browser/ui/gtk_util.h", ] diff --git a/docs/api/base-window.md b/docs/api/base-window.md index 7ad17d045c909..c988ddb4b426d 100644 --- a/docs/api/base-window.md +++ b/docs/api/base-window.md @@ -356,7 +356,7 @@ as `-webkit-app-region: drag` in a frameless window. Calling `event.preventDefault()` will prevent the menu from being displayed. -To convert `point` to DIP, use [`screen.screenToDipPoint(point)`](./screen.md#screenscreentodippointpoint-windows). +To convert `point` to DIP, use [`screen.screenToDipPoint(point)`](./screen.md#screenscreentodippointpoint-windows-linux). ### Static Methods diff --git a/docs/api/browser-window.md b/docs/api/browser-window.md index 95a1baa784450..aba24068dadf5 100644 --- a/docs/api/browser-window.md +++ b/docs/api/browser-window.md @@ -435,7 +435,7 @@ as `-webkit-app-region: drag` in a frameless window. Calling `event.preventDefault()` will prevent the menu from being displayed. -To convert `point` to DIP, use [`screen.screenToDipPoint(point)`](./screen.md#screenscreentodippointpoint-windows). +To convert `point` to DIP, use [`screen.screenToDipPoint(point)`](./screen.md#screenscreentodippointpoint-windows-linux). ### Static Methods diff --git a/docs/api/screen.md b/docs/api/screen.md index 4f68a2018b062..d923b8995f540 100644 --- a/docs/api/screen.md +++ b/docs/api/screen.md @@ -124,7 +124,7 @@ Returns [`Display`](structures/display.md) - The display nearest the specified p Returns [`Display`](structures/display.md) - The display that most closely intersects the provided bounds. -### `screen.screenToDipPoint(point)` _Windows_ +### `screen.screenToDipPoint(point)` _Windows_ _Linux_ * `point` [Point](structures/point.md) @@ -133,7 +133,10 @@ Returns [`Point`](structures/point.md) Converts a screen physical point to a screen DIP point. The DPI scale is performed relative to the display containing the physical point. -### `screen.dipToScreenPoint(point)` _Windows_ +Not currently supported on Wayland - if used there it will return the point passed +in with no changes. + +### `screen.dipToScreenPoint(point)` _Windows_ _Linux_ * `point` [Point](structures/point.md) @@ -142,6 +145,8 @@ Returns [`Point`](structures/point.md) Converts a screen DIP point to a screen physical point. The DPI scale is performed relative to the display containing the DIP point. +Not currently supported on Wayland. + ### `screen.screenToDipRect(window, rect)` _Windows_ * `window` [BrowserWindow](browser-window.md) | null diff --git a/shell/browser/api/electron_api_screen.cc b/shell/browser/api/electron_api_screen.cc index efee699f02bd5..fed1141f25f89 100644 --- a/shell/browser/api/electron_api_screen.cc +++ b/shell/browser/api/electron_api_screen.cc @@ -20,11 +20,18 @@ #include "ui/display/display.h" #include "ui/display/screen.h" #include "ui/gfx/geometry/point.h" +#include "ui/gfx/geometry/point_conversions.h" +#include "ui/gfx/geometry/point_f.h" +#include "ui/gfx/geometry/vector2d_conversions.h" #if BUILDFLAG(IS_WIN) #include "ui/display/win/screen_win.h" #endif +#if BUILDFLAG(IS_LINUX) +#include "shell/browser/linux/x11_util.h" +#endif + #if defined(USE_OZONE) #include "ui/ozone/public/ozone_platform.h" #endif @@ -102,14 +109,6 @@ static gfx::Rect DIPToScreenRect(electron::NativeWindow* window, return display::win::GetScreenWin()->DIPToScreenRect(hwnd, rect); } -static gfx::PointF ScreenToDIPPoint(const gfx::PointF& pixel_point) { - return display::win::GetScreenWin()->ScreenToDIPPoint(pixel_point); -} - -static gfx::Point DIPToScreenPoint(const gfx::Point& dip_point) { - return display::win::GetScreenWin()->DIPToScreenPoint(dip_point); -} - #endif void Screen::OnDisplayAdded(const display::Display& new_display) { @@ -134,6 +133,44 @@ void Screen::OnDisplayMetricsChanged(const display::Display& display, MetricsToArray(changed_metrics))); } +gfx::PointF Screen::ScreenToDIPPoint(const gfx::PointF& point_px) { +#if BUILDFLAG(IS_WIN) + return display::win::GetScreenWin()->ScreenToDIPPoint(point_px); +#elif BUILDFLAG(IS_LINUX) + if (x11_util::IsX11()) { + gfx::Point pt_px = gfx::ToFlooredPoint(point_px); + display::Display display = GetDisplayNearestPoint(pt_px); + gfx::Vector2d delta_px = pt_px - display.native_origin(); + gfx::Vector2dF delta_dip = + gfx::ScaleVector2d(delta_px, 1.0 / display.device_scale_factor()); + return gfx::PointF(display.bounds().origin()) + delta_dip; + } else { + return point_px; + } +#else + return point_px; +#endif +} + +gfx::Point Screen::DIPToScreenPoint(const gfx::Point& point_dip) { +#if BUILDFLAG(IS_WIN) + return display::win::GetScreenWin()->DIPToScreenPoint(point_dip); +#elif BUILDFLAG(IS_LINUX) + if (x11_util::IsX11()) { + display::Display display = GetDisplayNearestPoint(point_dip); + gfx::Rect bounds_dip = display.bounds(); + gfx::Vector2d delta_dip = point_dip - bounds_dip.origin(); + gfx::Vector2d delta_px = gfx::ToFlooredVector2d( + gfx::ScaleVector2d(delta_dip, display.device_scale_factor())); + return display.native_origin() + delta_px; + } else { + return point_dip; + } +#else + return point_dip; +#endif +} + // static v8::Local Screen::Create(gin_helper::ErrorThrower error_thrower) { if (!Browser::Get()->is_ready()) { @@ -161,9 +198,11 @@ gin::ObjectTemplateBuilder Screen::GetObjectTemplateBuilder( .SetMethod("getPrimaryDisplay", &Screen::GetPrimaryDisplay) .SetMethod("getAllDisplays", &Screen::GetAllDisplays) .SetMethod("getDisplayNearestPoint", &Screen::GetDisplayNearestPoint) +#if BUILDFLAG(IS_WIN) || BUILDFLAG(IS_LINUX) + .SetMethod("screenToDipPoint", &Screen::ScreenToDIPPoint) + .SetMethod("dipToScreenPoint", &Screen::DIPToScreenPoint) +#endif #if BUILDFLAG(IS_WIN) - .SetMethod("screenToDipPoint", &ScreenToDIPPoint) - .SetMethod("dipToScreenPoint", &DIPToScreenPoint) .SetMethod("screenToDipRect", &ScreenToDIPRect) .SetMethod("dipToScreenRect", &DIPToScreenRect) #endif diff --git a/shell/browser/api/electron_api_screen.h b/shell/browser/api/electron_api_screen.h index cd5d7f5b5d25c..4b63cd8858890 100644 --- a/shell/browser/api/electron_api_screen.h +++ b/shell/browser/api/electron_api_screen.h @@ -15,6 +15,7 @@ namespace gfx { class Point; +class PointF; class Rect; class Screen; } // namespace gfx @@ -58,6 +59,9 @@ class Screen final : public gin::Wrappable, return screen_->GetDisplayMatching(match_rect); } + gfx::PointF ScreenToDIPPoint(const gfx::PointF& point_px); + gfx::Point DIPToScreenPoint(const gfx::Point& point_dip); + // display::DisplayObserver: void OnDisplayAdded(const display::Display& new_display) override; void OnDisplaysRemoved(const display::Displays& removed_displays) override; diff --git a/shell/browser/linux/x11_util.cc b/shell/browser/linux/x11_util.cc new file mode 100644 index 0000000000000..38a33fe36d15a --- /dev/null +++ b/shell/browser/linux/x11_util.cc @@ -0,0 +1,17 @@ +// Copyright (c) 2025 Microsoft GmbH. +// Use of this source code is governed by the MIT license that can be +// found in the LICENSE file. + +#include "shell/browser/linux/x11_util.h" + +#include "ui/ozone/public/ozone_platform.h" + +namespace x11_util { + +bool IsX11() { + return ui::OzonePlatform::GetInstance() + ->GetPlatformProperties() + .electron_can_call_x11; +} + +} // namespace x11_util diff --git a/shell/browser/linux/x11_util.h b/shell/browser/linux/x11_util.h new file mode 100644 index 0000000000000..246d1b2aa2f5b --- /dev/null +++ b/shell/browser/linux/x11_util.h @@ -0,0 +1,14 @@ +// Copyright (c) 2025 Microsoft GmbH. +// Use of this source code is governed by the MIT license that can be +// found in the LICENSE file. + +#ifndef ELECTRON_SHELL_BROWSER_LINUX_X11_UTIL_H_ +#define ELECTRON_SHELL_BROWSER_LINUX_X11_UTIL_H_ + +namespace x11_util { + +bool IsX11(); + +} // namespace x11_util + +#endif // ELECTRON_SHELL_BROWSER_LINUX_X11_UTIL_H_ diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index dd1af72d13c12..0c5e0fc58f2c5 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -53,6 +53,7 @@ #include "base/strings/string_util.h" #include "shell/browser/browser.h" #include "shell/browser/linux/unity_service.h" +#include "shell/browser/linux/x11_util.h" #include "shell/browser/ui/electron_desktop_window_tree_host_linux.h" #include "shell/browser/ui/views/client_frame_view_linux.h" #include "shell/browser/ui/views/native_frame_view.h" @@ -163,13 +164,6 @@ gfx::Size WindowSizeToContentSizeBuggy(HWND hwnd, const gfx::Size& size) { #endif -[[maybe_unused, nodiscard]] bool IsX11() { - static const bool is_x11 = ui::OzonePlatform::GetInstance() - ->GetPlatformProperties() - .electron_can_call_x11; - return is_x11; -} - class NativeWindowClientView : public views::ClientView { public: NativeWindowClientView(views::Widget* widget, @@ -331,7 +325,7 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, if (parent) SetParentWindow(parent); - if (IsX11()) { + if (x11_util::IsX11()) { // Before the window is mapped the SetWMSpecState can not work, so we have // to manually set the _NET_WM_STATE. std::vector state_atom_list; @@ -452,7 +446,7 @@ NativeWindowViews::~NativeWindowViews() { void NativeWindowViews::SetGTKDarkThemeEnabled(bool use_dark_theme) { #if BUILDFLAG(IS_LINUX) - if (IsX11()) { + if (x11_util::IsX11()) { const std::string color = use_dark_theme ? "dark" : "light"; auto* connection = x11::Connection::Get(); connection->SetStringProperty( @@ -514,7 +508,7 @@ void NativeWindowViews::Show() { // On X11, setting Z order before showing the window doesn't take effect, // so we have to call it again. - if (IsX11()) + if (x11_util::IsX11()) widget()->SetZOrderLevel(widget()->GetZOrderLevel()); #endif } @@ -530,7 +524,7 @@ void NativeWindowViews::ShowInactive() { // On X11, setting Z order before showing the window doesn't take effect, // so we have to call it again. - if (IsX11()) + if (x11_util::IsX11()) widget()->SetZOrderLevel(widget()->GetZOrderLevel()); #endif } @@ -575,7 +569,7 @@ bool NativeWindowViews::IsEnabled() const { #if BUILDFLAG(IS_WIN) return ::IsWindowEnabled(GetAcceleratedWidget()); #elif BUILDFLAG(IS_LINUX) - if (IsX11()) + if (x11_util::IsX11()) return !event_disabler_.get(); NOTIMPLEMENTED(); return true; @@ -612,7 +606,7 @@ void NativeWindowViews::SetEnabledInternal(bool enable) { #if BUILDFLAG(IS_WIN) ::EnableWindow(GetAcceleratedWidget(), enable); #else - if (IsX11()) { + if (x11_util::IsX11()) { views::DesktopWindowTreeHostPlatform* tree_host = views::DesktopWindowTreeHostLinux::GetHostForWidget( GetAcceleratedWidget()); @@ -944,7 +938,7 @@ bool NativeWindowViews::MoveAbove(const std::string& sourceId) { 0, 0, 0, SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE | SWP_SHOWWINDOW); #else - if (IsX11()) { + if (x11_util::IsX11()) { if (!IsWindowValid(static_cast(id.id))) return false; @@ -966,7 +960,7 @@ void NativeWindowViews::MoveTop() { size.width(), size.height(), SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE | SWP_SHOWWINDOW); #else - if (IsX11()) + if (x11_util::IsX11()) electron::MoveWindowToForeground( static_cast(GetAcceleratedWidget())); #endif @@ -1280,7 +1274,7 @@ void NativeWindowViews::SetIgnoreMouseEvents(bool ignore, bool forward) { SetForwardMouseMessages(forward); } #else - if (IsX11()) { + if (x11_util::IsX11()) { auto* connection = x11::Connection::Get(); if (ignore) { x11::Rectangle r{0, 0, 1, 1}; @@ -1401,7 +1395,7 @@ void NativeWindowViews::SetParentWindow(NativeWindow* parent) { NativeWindow::SetParentWindow(parent); #if BUILDFLAG(IS_LINUX) - if (IsX11()) { + if (x11_util::IsX11()) { auto* connection = x11::Connection::Get(); connection->SetProperty( static_cast(GetAcceleratedWidget()), From 0810fe54d4bd53e4017dc441725ae97f166e8831 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 2 May 2025 22:46:54 -0500 Subject: [PATCH 010/186] chore: bump chromium to 138.0.7156.0 (37-x-y) (#46913) * chore: bump chromium in DEPS to 138.0.7156.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: update patches Co-authored-by: John Kleinschmidt * chore: ICWYU Co-authored-by: John Kleinschmidt * Allow SecKeychain and SecItem implementations of AppleKeychain to coexist https://chromium-review.googlesource.com/c/chromium/src/+/6444777 Co-authored-by: John Kleinschmidt --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- DEPS | 2 +- patches/chromium/accelerator.patch | 8 +- .../add_didinstallconditionalfeatures.patch | 6 +- ...adjust_accessibility_ui_for_electron.patch | 22 ++--- ..._scheduler_throttling_per_renderview.patch | 4 +- patches/chromium/blink_local_frame.patch | 2 +- ..._depend_on_packed_resource_integrity.patch | 12 +-- patches/chromium/can_create_window.patch | 12 +-- .../chromium/chore_partial_revert_of.patch | 2 +- ...tition_attribute_dcheck_for_webviews.patch | 4 +- ...screationoverridden_with_full_params.patch | 4 +- patches/chromium/command-ismediakey.patch | 8 +- .../custom_protocols_plzserviceworker.patch | 8 +- patches/chromium/disable_unload_metrics.patch | 6 +- ...n_embedder_cleanup_callbacks_run_for.patch | 2 +- ...moothing_css_rule_and_blink_painting.patch | 2 +- ...screen_rendering_with_viz_compositor.patch | 2 +- ...same_application_can_use_safestorage.patch | 86 ++++++++++++++----- ...ding_non-standard_schemes_in_iframes.patch | 4 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ...from_localframe_requestexecutescript.patch | 12 +-- patches/chromium/frame_host_manager.patch | 4 +- ...sync_with_host_os_mac_on_linux_in_ci.patch | 2 +- ..._avoid_private_macos_api_usage.patch.patch | 16 ++-- ...eated_to_allow_for_browser_initiated.patch | 2 +- patches/chromium/printing.patch | 4 +- ...r_changes_to_the_webcontentsobserver.patch | 6 +- ...efactor_unfilter_unresponsive_events.patch | 4 +- patches/chromium/web_contents.patch | 2 +- patches/chromium/webview_fullscreen.patch | 4 +- shell/common/asar/archive.cc | 1 + 31 files changed, 151 insertions(+), 106 deletions(-) diff --git a/DEPS b/DEPS index 62e2af28abae0..127d47a33ff30 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7154.0', + '138.0.7156.0', 'node_version': 'v22.14.0', 'nan_version': diff --git a/patches/chromium/accelerator.patch b/patches/chromium/accelerator.patch index 6f7866e89125b..65aea0d48e53f 100644 --- a/patches/chromium/accelerator.patch +++ b/patches/chromium/accelerator.patch @@ -9,7 +9,7 @@ This patch makes three changes to Accelerator::GetShortcutText to improve shortc 2. Ctrl-Shift-= and Ctrl-Plus show up as such diff --git a/ui/base/accelerators/accelerator.cc b/ui/base/accelerators/accelerator.cc -index 7eb75d87dd3ed03fc6da738a8b397d4d52f5b5ce..8db9f17c2bdcf5378f9a3f3165956c8f1d1c8d61 100644 +index 5ad9332dd27ceda7d67cd3f571b12218a4415a40..ffe083836c39fb60b4bff1f9fbdd6cebb7fa9d1d 100644 --- a/ui/base/accelerators/accelerator.cc +++ b/ui/base/accelerators/accelerator.cc @@ -12,6 +12,7 @@ @@ -20,7 +20,7 @@ index 7eb75d87dd3ed03fc6da738a8b397d4d52f5b5ce..8db9f17c2bdcf5378f9a3f3165956c8f #include "base/strings/utf_string_conversions.h" #include "base/types/cxx23_to_underlying.h" #include "build/build_config.h" -@@ -160,6 +161,11 @@ std::u16string Accelerator::GetKeyCodeStringForShortcut() const { +@@ -164,6 +165,11 @@ std::u16string Accelerator::GetKeyCodeStringForShortcut() const { #endif if (key_string.empty()) { @@ -32,7 +32,7 @@ index 7eb75d87dd3ed03fc6da738a8b397d4d52f5b5ce..8db9f17c2bdcf5378f9a3f3165956c8f #if BUILDFLAG(IS_WIN) // Our fallback is to try translate the key code to a regular character // unless it is one of digits (VK_0 to VK_9). Some keyboard -@@ -186,6 +192,10 @@ std::u16string Accelerator::GetKeyCodeStringForShortcut() const { +@@ -190,6 +196,10 @@ std::u16string Accelerator::GetKeyCodeStringForShortcut() const { static_cast(base::ToUpperASCII(c)); } #endif @@ -43,7 +43,7 @@ index 7eb75d87dd3ed03fc6da738a8b397d4d52f5b5ce..8db9f17c2bdcf5378f9a3f3165956c8f } return key_string; -@@ -346,7 +356,7 @@ std::vector Accelerator::GetLongFormModifiers() const { +@@ -350,7 +360,7 @@ std::vector Accelerator::GetLongFormModifiers() const { modifiers.push_back(l10n_util::GetStringUTF16(IDS_APP_CTRL_KEY)); } diff --git a/patches/chromium/add_didinstallconditionalfeatures.patch b/patches/chromium/add_didinstallconditionalfeatures.patch index e88cb145424d1..7f134c862747b 100644 --- a/patches/chromium/add_didinstallconditionalfeatures.patch +++ b/patches/chromium/add_didinstallconditionalfeatures.patch @@ -10,7 +10,7 @@ DidCreateScriptContext is called, not all JS APIs are available in the context, which can cause some preload scripts to trip. diff --git a/content/public/renderer/render_frame_observer.h b/content/public/renderer/render_frame_observer.h -index 44da0544b778d6ff4c14b6f4e8463cb8260d2f0d..8ae8939af4141a684b7a6d50a43e1abb354ea028 100644 +index db655a7b52eacb74f2a8637db36abd87f6b86792..8014cb08e2090a12ea8b9e92cb8f93c96921d400 100644 --- a/content/public/renderer/render_frame_observer.h +++ b/content/public/renderer/render_frame_observer.h @@ -149,6 +149,8 @@ class CONTENT_EXPORT RenderFrameObserver @@ -23,10 +23,10 @@ index 44da0544b778d6ff4c14b6f4e8463cb8260d2f0d..8ae8939af4141a684b7a6d50a43e1abb int32_t world_id) {} virtual void DidClearWindowObject() {} diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index c0ee479cea4f34fcfac502a20130fbb4c8becc15..3be4b5225fe791901ba27b9fbb7a21ea1ae5d4ff 100644 +index b0aa018f2f4e6865915516ab6b65fac20d9e6f20..c04a544eb8991bfa718322e6e3a090ef4733a50b 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc -@@ -4811,6 +4811,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, +@@ -4807,6 +4807,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, observer.DidCreateScriptContext(context, world_id); } diff --git a/patches/chromium/adjust_accessibility_ui_for_electron.patch b/patches/chromium/adjust_accessibility_ui_for_electron.patch index a01f7c96e67e6..4f89d368bc66f 100644 --- a/patches/chromium/adjust_accessibility_ui_for_electron.patch +++ b/patches/chromium/adjust_accessibility_ui_for_electron.patch @@ -10,7 +10,7 @@ usage of BrowserList and Browser as we subclass related methods and use our WindowList. diff --git a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc -index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df13aa0649 100644 +index ce3840087d3becac116e57ed8c690b73e360f95f..a929b2d4f6c4b34f9e278aada9f8f793477c6d19 100644 --- a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc +++ b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc @@ -48,6 +48,7 @@ @@ -21,7 +21,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df #include "ui/accessibility/accessibility_features.h" #include "ui/accessibility/ax_updates_and_events.h" #include "ui/accessibility/platform/ax_platform_node.h" -@@ -168,7 +169,7 @@ base::Value::Dict BuildTargetDescriptor(content::RenderViewHost* rvh) { +@@ -169,7 +170,7 @@ base::Value::Dict BuildTargetDescriptor(content::RenderViewHost* rvh) { rvh->GetRoutingID(), accessibility_mode); } @@ -30,7 +30,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df base::Value::Dict BuildTargetDescriptor(Browser* browser) { base::Value::Dict target_data; target_data.Set(kSessionIdField, browser->session_id().id()); -@@ -192,7 +193,7 @@ void HandleAccessibilityRequestCallback( +@@ -193,7 +194,7 @@ void HandleAccessibilityRequestCallback( auto& browser_accessibility_state = *content::BrowserAccessibilityState::GetInstance(); base::Value::Dict data; @@ -39,7 +39,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df ui::AXMode mode = browser_accessibility_state.GetAccessibilityMode(); bool native = mode.has_mode(ui::AXMode::kNativeAPIs); bool web = mode.has_mode(ui::AXMode::kWebContents); -@@ -240,7 +241,7 @@ void HandleAccessibilityRequestCallback( +@@ -246,7 +247,7 @@ void HandleAccessibilityRequestCallback( initial_process_mode.has_mode(ui::AXMode::kHTML))); std::string pref_api_type = @@ -48,7 +48,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df bool pref_api_type_supported = false; std::vector supported_api_types = -@@ -307,11 +308,11 @@ void HandleAccessibilityRequestCallback( +@@ -314,11 +315,11 @@ void HandleAccessibilityRequestCallback( data.Set(kPagesField, std::move(page_list)); base::Value::List browser_list; @@ -62,7 +62,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df data.Set(kBrowsersField, std::move(browser_list)); std::string json_string; -@@ -783,7 +784,8 @@ void AccessibilityUIMessageHandler::SetGlobalString( +@@ -792,7 +793,8 @@ void AccessibilityUIMessageHandler::SetGlobalString( const std::string value = CheckJSValue(data.FindString(kValueField)); if (string_name == kApiTypeField) { @@ -72,7 +72,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df pref->SetString(prefs::kShownAccessibilityApiType, value); } } -@@ -837,7 +839,8 @@ void AccessibilityUIMessageHandler::RequestWebContentsTree( +@@ -846,7 +848,8 @@ void AccessibilityUIMessageHandler::RequestWebContentsTree( AXPropertyFilter::ALLOW_EMPTY); AddPropertyFilters(property_filters, deny, AXPropertyFilter::DENY); @@ -82,7 +82,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df ui::AXApiType::Type api_type = ui::AXApiType::From(pref->GetString(prefs::kShownAccessibilityApiType)); std::string accessibility_contents = -@@ -864,6 +867,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( +@@ -873,6 +876,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( AXPropertyFilter::ALLOW_EMPTY); AddPropertyFilters(property_filters, deny, AXPropertyFilter::DENY); @@ -90,7 +90,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df for (Browser* browser : *BrowserList::GetInstance()) { if (browser->session_id().id() == session_id) { base::Value::Dict result = BuildTargetDescriptor(browser); -@@ -876,6 +880,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( +@@ -885,6 +889,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( return; } } @@ -98,7 +98,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df #endif // !BUILDFLAG(IS_ANDROID) // No browser with the specified |session_id| was found. base::Value::Dict result; -@@ -919,11 +924,13 @@ void AccessibilityUIMessageHandler::StopRecording( +@@ -928,11 +933,13 @@ void AccessibilityUIMessageHandler::StopRecording( } ui::AXApiType::Type AccessibilityUIMessageHandler::GetRecordingApiType() { @@ -115,7 +115,7 @@ index 105e84d00ff73357e1fa002ffa605e8ccb67fd71..e576ade293afd158cf5511d53d0bf5df // Check to see if it is in the supported types list. if (std::find(supported_types.begin(), supported_types.end(), api_type) == supported_types.end()) { -@@ -993,8 +1000,11 @@ void AccessibilityUIMessageHandler::RequestAccessibilityEvents( +@@ -1002,8 +1009,11 @@ void AccessibilityUIMessageHandler::RequestAccessibilityEvents( // static void AccessibilityUIMessageHandler::RegisterProfilePrefs( user_prefs::PrefRegistrySyncable* registry) { diff --git a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch index 2dace54ab6ba2..a36161acbffe9 100644 --- a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch +++ b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch @@ -23,10 +23,10 @@ index f9b27264f7e3e1f8de6f088ccb78e4a4693c5e93..85aebec5028fd6b324a1f1d9416fbf99 return receiver_.BindNewEndpointAndPassDedicatedRemote(); } diff --git a/content/browser/renderer_host/render_view_host_impl.cc b/content/browser/renderer_host/render_view_host_impl.cc -index 00b1dc2ab7661d9ab76d0c6787bfe406327039ad..22c2a68428ed881b63e4458d17d5ff542cefe559 100644 +index 9d430ebff1067323f229c3b81b18300e8cb7e8a9..090125bc5a4c485c83d9eaa6b82ed5cf3402cbbd 100644 --- a/content/browser/renderer_host/render_view_host_impl.cc +++ b/content/browser/renderer_host/render_view_host_impl.cc -@@ -763,6 +763,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { +@@ -768,6 +768,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { GetWidget()->GetAssociatedFrameWidget()->SetBackgroundOpaque(opaque); } diff --git a/patches/chromium/blink_local_frame.patch b/patches/chromium/blink_local_frame.patch index fce2a3cae04ec..6dcc64570f651 100644 --- a/patches/chromium/blink_local_frame.patch +++ b/patches/chromium/blink_local_frame.patch @@ -49,7 +49,7 @@ index 2072f6b14289b1f3a76dbccc98f29aa178c1c35c..d7017437a7e7e6ac130677e52731d048 // its owning reference back to our owning LocalFrame. client_->Detached(type); diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index ecaae5e1a2911b122678b2f4f77b5796323ad0bf..fbfd4d96e8082df8c5db5d354ac7c39bc329d4ee 100644 +index a309befcbcb1e7fe667bc1d794141fb90fea1035..dd148eb3cce762d20e9117b4f8030c881057b8bb 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc @@ -753,10 +753,6 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index 8dd738f4a9b92..a2f8cde7b70e7 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -33,10 +33,10 @@ index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index 4e84a91033465438d8510ba532ba795a2eb6bcf6..b9f60071a41de560a36214a6490d206382d9d6cb 100644 +index 5c26efefaa030e5f5b7ba6089e989303795d771c..5df9bd353fe212491e473027a7080854cc5ea738 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4631,7 +4631,7 @@ static_library("browser") { +@@ -4627,7 +4627,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,10 +46,10 @@ index 4e84a91033465438d8510ba532ba795a2eb6bcf6..b9f60071a41de560a36214a6490d2063 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 05073b10cb0c86b63f50071ef7e04225ef0627ec..de6c65e2ada9696c9a6c183f02493ea446e8bd3d 100644 +index 897f91ed0f1fcd386f980fe2073c07915cfc6458..43c6c436a391362173cc3ae562d6cd0fb5191d1b 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7184,9 +7184,12 @@ test("unit_tests") { +@@ -7181,9 +7181,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index 05073b10cb0c86b63f50071ef7e04225ef0627ec..de6c65e2ada9696c9a6c183f02493ea4 "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8153,6 +8156,10 @@ test("unit_tests") { +@@ -8149,6 +8152,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index 05073b10cb0c86b63f50071ef7e04225ef0627ec..de6c65e2ada9696c9a6c183f02493ea4 sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8208,7 +8215,6 @@ test("unit_tests") { +@@ -8204,7 +8211,6 @@ test("unit_tests") { # Non-android deps for "unit_tests" target. deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 5ed6f79b92779..07f617cab8e51 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,7 +9,7 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index ad821a07ad808b392633f0e8e774b6082cc3b184..df50b84cca214a9b6a85afe2fd677a45e2529cdc 100644 +index 66c25476de83a9aabad58a042addc825e27ffd0c..7578b4f9056b9be79645fa0eed9476ab9b80c509 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc @@ -9775,6 +9775,7 @@ void RenderFrameHostImpl::CreateNewWindow( @@ -21,7 +21,7 @@ index ad821a07ad808b392633f0e8e774b6082cc3b184..df50b84cca214a9b6a85afe2fd677a45 &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 2039ac799297183b16fb4795b63c6c5b76dac478..fec569763d3ba8b171ca65a9ea523ada5f729f41 100644 +index d2715008c411519ed6c2491bf093a92e81d8d874..a99621ef317ec59f1368e5c7959f73de8ed32c54 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc @@ -5131,6 +5131,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( @@ -148,10 +148,10 @@ index da319cb20733150366d85bee95609f0f2d9def7f..8a18958035cc1dd26be558349f64f772 // typically happens when popups are created. virtual void WebContentsCreated(WebContents* source_contents, diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index 6dd63dbd96ce5c941790f97929b2826a03cabbcc..c0ee479cea4f34fcfac502a20130fbb4c8becc15 100644 +index 7f33a5452de32f5f4f8a43d0314917f24308d77c..b0aa018f2f4e6865915516ab6b65fac20d9e6f20 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc -@@ -6942,6 +6942,10 @@ WebView* RenderFrameImpl::CreateNewWindow( +@@ -6938,6 +6938,10 @@ WebView* RenderFrameImpl::CreateNewWindow( request.HasUserGesture(), GetWebFrame()->IsAdFrame(), GetWebFrame()->IsAdScriptInStack()); @@ -163,7 +163,7 @@ index 6dd63dbd96ce5c941790f97929b2826a03cabbcc..c0ee479cea4f34fcfac502a20130fbb4 // moved on send. bool is_background_tab = diff --git a/content/web_test/browser/web_test_content_browser_client.cc b/content/web_test/browser/web_test_content_browser_client.cc -index 75bd6c082dbda49bd5ee177105d78b670d147034..bceb8a8acf9a23d0d1df2d6749b94f4c98ee72ec 100644 +index 9af07ab542531bd3354cf28135f36044e88c0dfb..5d763af59aec30cdfb763b8bd5fa1383c4cb5568 100644 --- a/content/web_test/browser/web_test_content_browser_client.cc +++ b/content/web_test/browser/web_test_content_browser_client.cc @@ -535,6 +535,8 @@ bool WebTestContentBrowserClient::CanCreateWindow( @@ -176,7 +176,7 @@ index 75bd6c082dbda49bd5ee177105d78b670d147034..bceb8a8acf9a23d0d1df2d6749b94f4c bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/web_test/browser/web_test_content_browser_client.h b/content/web_test/browser/web_test_content_browser_client.h -index 78eafab336717b7ec8adab23b3bd8baace7b3e09..16cfe915177d812bce5738acf2b1991b7eb1aeb1 100644 +index a7f5f09f9f5147b565f5934c6b467c4a4c04b626..2d44bafc6a7c81f7189934c61d88a5bb3e921266 100644 --- a/content/web_test/browser/web_test_content_browser_client.h +++ b/content/web_test/browser/web_test_content_browser_client.h @@ -94,6 +94,8 @@ class WebTestContentBrowserClient : public ShellContentBrowserClient { diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 579c06513d717..3ca00573ac9c0 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,7 +14,7 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 05859e343a6c1fa58f3fb847ad6e97982804f910..5fef3e077072ee9dc3ff22110b7818503c8b4e4b 100644 +index da05a4f28cc03bc555a99bd4e10097cd175b479c..dd94f88d353eb9291e2a64f0281e3fc1d53b68da 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc @@ -5050,7 +5050,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( diff --git a/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch b/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch index ccad2444864a5..72a66aea141e7 100644 --- a/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch +++ b/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch @@ -14,10 +14,10 @@ This change patches it out to prevent the DCHECK. It can be removed once/if we see a better solution to the problem. diff --git a/content/browser/site_instance_impl.cc b/content/browser/site_instance_impl.cc -index adaa1cd426c138972b088d0d0093b0e1653af231..be4684c94ba2214255c5dbe9cdcf1ea316c60c06 100644 +index 4007e92316a6ac59145fa9bc021904fd1b3b0136..afedeaea7fd419f3374ffeebb7ee931219a90f93 100644 --- a/content/browser/site_instance_impl.cc +++ b/content/browser/site_instance_impl.cc -@@ -229,7 +229,7 @@ scoped_refptr SiteInstanceImpl::CreateForGuest( +@@ -226,7 +226,7 @@ scoped_refptr SiteInstanceImpl::CreateForGuest( BrowserContext* browser_context, const StoragePartitionConfig& partition_config) { DCHECK(browser_context); diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index 1bd9e98ea3434..f3d22875f651e 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -218,7 +218,7 @@ index c6838c83ef971b88769b1f3fba8095025ae25464..2da6a4e08340e72ba7de5d03444c2f17 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index e236eb74db68a6c11892e1ea16cab05b8c47afbf..b2d5733ff8c47f497af03171d9dfac68b2013e4d 100644 +index 5df2433b30213ba5683a864dcf42a07a5deb56e7..7500958c41904c61705d49f75b7a152005ce4890 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc @@ -5013,8 +5013,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( @@ -352,7 +352,7 @@ index 2dcf51f335f5dac39f431c3e0f56f8789f33d40b..2b433624d0604e0b9da5117b9e83cc15 content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, diff --git a/fuchsia_web/webengine/browser/frame_impl.cc b/fuchsia_web/webengine/browser/frame_impl.cc -index 45c7aa83272dfa0d55ac3582a109b376184b389b..2841f550ac1724de4631aae0dd614e2ce3f522f5 100644 +index c10903a8e7e5fb66a1b038eab9015658a93672df..5a3afdb8ababf6e465c6166ca6229af7b4d6941d 100644 --- a/fuchsia_web/webengine/browser/frame_impl.cc +++ b/fuchsia_web/webengine/browser/frame_impl.cc @@ -576,8 +576,7 @@ bool FrameImpl::IsWebContentsCreationOverridden( diff --git a/patches/chromium/command-ismediakey.patch b/patches/chromium/command-ismediakey.patch index 88b195e5c2757..50e25fcbe5e78 100644 --- a/patches/chromium/command-ismediakey.patch +++ b/patches/chromium/command-ismediakey.patch @@ -39,10 +39,10 @@ index e87c180342b967756efeb701c73207fcee8754f1..42e37564e585987d367921568f0f1d2b NOTREACHED(); } diff --git a/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_ozone.cc b/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_ozone.cc -index c98ecc36007185052481b6479b2ba4608e326021..dd0e4553b78997beea0f11242eeb9f759359066f 100644 +index b6985bd63a34c55154fcfae601add6ce6c451704..fb44cc65b1a15c8b69410a2a2cb925a0326bb438 100644 --- a/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_ozone.cc +++ b/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_ozone.cc -@@ -111,7 +111,8 @@ bool GlobalAcceleratorListenerOzone::StartListeningForAccelerator( +@@ -147,7 +147,8 @@ bool GlobalAcceleratorListenerOzone::StartListeningForAccelerator( const bool registered = platform_global_shortcut_listener_->RegisterAccelerator( accelerator.key_code(), accelerator.IsAltDown(), @@ -52,7 +52,7 @@ index c98ecc36007185052481b6479b2ba4608e326021..dd0e4553b78997beea0f11242eeb9f75 if (registered) { registered_hot_keys_.insert(accelerator); } -@@ -126,14 +127,15 @@ void GlobalAcceleratorListenerOzone::StopListeningForAccelerator( +@@ -162,14 +163,15 @@ void GlobalAcceleratorListenerOzone::StopListeningForAccelerator( platform_global_shortcut_listener_->UnregisterAccelerator( accelerator.key_code(), accelerator.IsAltDown(), accelerator.IsCtrlDown(), @@ -70,7 +70,7 @@ index c98ecc36007185052481b6479b2ba4608e326021..dd0e4553b78997beea0f11242eeb9f75 int modifiers = 0; if (is_alt_down) { modifiers |= ui::EF_ALT_DOWN; -@@ -144,6 +146,9 @@ void GlobalAcceleratorListenerOzone::OnKeyPressed(ui::KeyboardCode key_code, +@@ -180,6 +182,9 @@ void GlobalAcceleratorListenerOzone::OnKeyPressed(ui::KeyboardCode key_code, if (is_shift_down) { modifiers |= ui::EF_SHIFT_DOWN; } diff --git a/patches/chromium/custom_protocols_plzserviceworker.patch b/patches/chromium/custom_protocols_plzserviceworker.patch index 9826554101e13..a3d61e14186ff 100644 --- a/patches/chromium/custom_protocols_plzserviceworker.patch +++ b/patches/chromium/custom_protocols_plzserviceworker.patch @@ -8,10 +8,10 @@ Allow registering custom protocols to handle service worker main script fetching Refs https://bugs.chromium.org/p/chromium/issues/detail?id=996511 diff --git a/content/browser/service_worker/service_worker_context_wrapper.cc b/content/browser/service_worker/service_worker_context_wrapper.cc -index aa342545b9e629c4194b8da90380e612ede423d6..3ef48ead14bde84dac0207c1b9ceaf3abf1e637e 100644 +index b4c984e0dd22f148a426ce0ea04988798ed95aaa..5fd099b6396fc51d29fce2843531d5fc89642d35 100644 --- a/content/browser/service_worker/service_worker_context_wrapper.cc +++ b/content/browser/service_worker/service_worker_context_wrapper.cc -@@ -1971,6 +1971,26 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -1961,6 +1961,26 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( loader_factory_bundle_info = context()->loader_factory_bundle_for_update_check()->Clone(); @@ -38,7 +38,7 @@ index aa342545b9e629c4194b8da90380e612ede423d6..3ef48ead14bde84dac0207c1b9ceaf3a if (auto* config = content::WebUIConfigMap::GetInstance().GetConfig( browser_context(), scope)) { // If this is a Service Worker for a WebUI, the WebUI's URLDataSource -@@ -1990,9 +2010,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -1980,9 +2000,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( features::kEnableServiceWorkersForChromeScheme) && scope.scheme_piece() == kChromeUIScheme) { config->RegisterURLDataSource(browser_context()); @@ -49,7 +49,7 @@ index aa342545b9e629c4194b8da90380e612ede423d6..3ef48ead14bde84dac0207c1b9ceaf3a .emplace(kChromeUIScheme, CreateWebUIServiceWorkerLoaderFactory( browser_context(), kChromeUIScheme, base::flat_set())); -@@ -2000,9 +2018,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -1990,9 +2008,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( features::kEnableServiceWorkersForChromeUntrusted) && scope.scheme_piece() == kChromeUIUntrustedScheme) { config->RegisterURLDataSource(browser_context()); diff --git a/patches/chromium/disable_unload_metrics.patch b/patches/chromium/disable_unload_metrics.patch index 4e43463b8aecb..8d2c76ab543b2 100644 --- a/patches/chromium/disable_unload_metrics.patch +++ b/patches/chromium/disable_unload_metrics.patch @@ -24,10 +24,10 @@ This patch temporarily disables the metrics so we can have green CI, and we should continue seeking for a real fix. diff --git a/content/browser/renderer_host/navigator.cc b/content/browser/renderer_host/navigator.cc -index 9cc3ae76503699417e8b7a2bd18d0b899e20d790..cba63c2eacdb1c02391941854f94dd5e2ddc2776 100644 +index 54ce1ea5ac11c9831a9553fbb5c5584c05440071..be95785fa144a4f11a3c97fea562dd4635ffe7b0 100644 --- a/content/browser/renderer_host/navigator.cc +++ b/content/browser/renderer_host/navigator.cc -@@ -1470,6 +1470,7 @@ void Navigator::RecordNavigationMetrics( +@@ -1476,6 +1476,7 @@ void Navigator::RecordNavigationMetrics( .InMilliseconds()); } @@ -35,7 +35,7 @@ index 9cc3ae76503699417e8b7a2bd18d0b899e20d790..cba63c2eacdb1c02391941854f94dd5e // If this is a same-process navigation and we have timestamps for unload // durations, fill those metrics out as well. if (params.unload_start && params.unload_end && -@@ -1519,6 +1520,7 @@ void Navigator::RecordNavigationMetrics( +@@ -1525,6 +1526,7 @@ void Navigator::RecordNavigationMetrics( first_before_unload_start_time) .InMilliseconds()); } diff --git a/patches/chromium/feat_add_signals_when_embedder_cleanup_callbacks_run_for.patch b/patches/chromium/feat_add_signals_when_embedder_cleanup_callbacks_run_for.patch index 5da2f05929f3e..ed1ca148584f1 100644 --- a/patches/chromium/feat_add_signals_when_embedder_cleanup_callbacks_run_for.patch +++ b/patches/chromium/feat_add_signals_when_embedder_cleanup_callbacks_run_for.patch @@ -149,7 +149,7 @@ index 402355cb836cea14e9ee725a142a4bad44fd5bed..7e7f028dcfb87c7b80adebabac19ced8 void* FromV8Impl(v8::Isolate* isolate, v8::Local val, diff --git a/gin/wrappable.h b/gin/wrappable.h -index 4e7115685a5bf6997e78edcc1851e28bd00b1aa2..ca51fe33605e855438e88969e3d3cc734ef4523e 100644 +index 2ae2cf67157ce8b161ae917291a913d237b7d535..c8c8cbe84e946cebde97a71b42815c62ccaf7b96 100644 --- a/gin/wrappable.h +++ b/gin/wrappable.h @@ -80,6 +80,13 @@ class GIN_EXPORT WrappableBase { diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index d8be6ba8b293a..860a9947f1ba2 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -307,7 +307,7 @@ index 2c2f4f405074e5baa4a26f255283404f86b40e21..ebeb7d6988ee9e6a4e78cb82fc01fdad ContouredRect PixelSnappedContouredBorderInternal( diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn -index 6718aad4a16cd99c8dd7118ca62cebd29ffbfe97..39d426936b266d8f44ab8a614a48247462ceea2d 100644 +index b5a309cb7bad79f80fb43dcbcccbd8dc2fcdfef8..c90d8f2f283e9bd05184171d3971d0060731f67d 100644 --- a/third_party/blink/renderer/platform/BUILD.gn +++ b/third_party/blink/renderer/platform/BUILD.gn @@ -1658,6 +1658,8 @@ component("platform") { diff --git a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch index e503e5e8ab6b7..23a4d1bc337f5 100644 --- a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch +++ b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch @@ -90,7 +90,7 @@ index 8af69cac78b7488d28f1f05ccb174793fe5148cd..9f74e511c263d147b5fbe81fe100d217 private: const HWND hwnd_; diff --git a/components/viz/service/BUILD.gn b/components/viz/service/BUILD.gn -index d29bdc038fc6934c69b10b7a694d9cbf54839b02..6cc09172e0975387d614f67350215c80915c406d 100644 +index 3c43af49c5d6d5f604c71e9a9dc1f7afe9aaf0f7..857e422776e7ec33eaf4c9983d42d6433b7723cc 100644 --- a/components/viz/service/BUILD.gn +++ b/components/viz/service/BUILD.gn @@ -178,6 +178,8 @@ viz_component("service") { diff --git a/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch b/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch index 6a65f437bb790..e177a7bf83e1e 100644 --- a/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch +++ b/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch @@ -78,7 +78,7 @@ index 3d388a85aaf52acdcc2b7aaea56f5a24b2435bff..7a0d28cbf1651e76a4356f1193b502d2 } diff --git a/crypto/apple_keychain.h b/crypto/apple_keychain.h -index c2aeebc449c7cc2d2e2fcd30dde3e8b9732aa0b3..4acd945d31cb6cb5f3c74548ef9b9cc23ee80205 100644 +index bcff49c4bcee4a67b97172c3abc12dedda1eedda..43e0b9f8b421a1c0dc62cc2d66b6fdd0eae496ce 100644 --- a/crypto/apple_keychain.h +++ b/crypto/apple_keychain.h @@ -18,6 +18,12 @@ @@ -94,35 +94,65 @@ index c2aeebc449c7cc2d2e2fcd30dde3e8b9732aa0b3..4acd945d31cb6cb5f3c74548ef9b9cc2 // DEPRECATED: use `AppleKeychainV2` instead. // Wraps the KeychainServices API in a very thin layer, to allow it to be // mocked out for testing. -@@ -43,11 +49,16 @@ class CRYPTO_EXPORT AppleKeychain { +@@ -46,13 +52,18 @@ class CRYPTO_EXPORT AppleKeychain { // std::vector arm is populated instead. virtual base::expected, OSStatus> FindGenericPassword( std::string_view service_name, -- std::string_view account_name) const; +- std::string_view account_name) const = 0; + std::string_view account_name, -+ AppleSecKeychainItemRef* item = nullptr) const; ++ AppleSecKeychainItemRef* item = nullptr) const = 0; + + virtual OSStatus AddGenericPassword( + std::string_view service_name, + std::string_view account_name, + base::span password) const = 0; - virtual OSStatus AddGenericPassword(std::string_view service_name, - std::string_view account_name, - base::span password) const; -+ +#if BUILDFLAG(IS_MAC) + virtual OSStatus ItemDelete(AppleSecKeychainItemRef item) const; +#endif // !BUILDFLAG(IS_MAC) ++ + protected: + AppleKeychain(); }; +diff --git a/crypto/apple_keychain_secitem.h b/crypto/apple_keychain_secitem.h +index 1632c22c669607f9da8b4fe7783ee716c6467f6e..3f0e3e0af568627a0aae352a65be4cc7d5d40802 100644 +--- a/crypto/apple_keychain_secitem.h ++++ b/crypto/apple_keychain_secitem.h +@@ -17,7 +17,8 @@ class CRYPTO_EXPORT AppleKeychainSecItem : public AppleKeychain { + + base::expected, OSStatus> FindGenericPassword( + std::string_view service_name, +- std::string_view account_name) const override; ++ std::string_view account_name, ++ AppleSecKeychainItemRef* item) const override; - #if BUILDFLAG(IS_MAC) -diff --git a/crypto/apple_keychain_mac.cc b/crypto/apple_keychain_mac.cc -index 0613e22fc0ce35378dc3580d797badd5f2680ae6..3ec4a2ba2fa5679363fabfa007be6200a0660ce7 100644 ---- a/crypto/apple_keychain_mac.cc -+++ b/crypto/apple_keychain_mac.cc -@@ -58,14 +58,15 @@ AppleKeychain::~AppleKeychain() = default; + OSStatus AddGenericPassword( + std::string_view service_name, +diff --git a/crypto/apple_keychain_secitem.mm b/crypto/apple_keychain_secitem.mm +index 12b400a1f2d6c11bc4ac67d0a2c98984d0be24e0..1abb4623bfabacbca34068113fac2030fea2c065 100644 +--- a/crypto/apple_keychain_secitem.mm ++++ b/crypto/apple_keychain_secitem.mm +@@ -118,7 +118,8 @@ base::expected, OSStatus> - AppleKeychain::FindGenericPassword(std::string_view service_name, -- std::string_view account_name) const { -+ std::string_view account_name, -+ AppleSecKeychainItemRef* item) const { + AppleKeychainSecItem::FindGenericPassword(std::string_view service_name, +- std::string_view account_name) const { ++ std::string_view account_name, ++ AppleSecKeychainItemRef* item) const { + base::apple::ScopedCFTypeRef query = + MakeGenericPasswordQuery(service_name, account_name); + +diff --git a/crypto/apple_keychain_seckeychain.cc b/crypto/apple_keychain_seckeychain.cc +index 3fa4feac6de46a65bcb306329d0fc923525330ed..61a90e531c7cf8060425bf1cde571818d2da7979 100644 +--- a/crypto/apple_keychain_seckeychain.cc ++++ b/crypto/apple_keychain_seckeychain.cc +@@ -59,14 +59,15 @@ AppleKeychainSecKeychain::~AppleKeychainSecKeychain() = default; + base::expected, OSStatus> + AppleKeychainSecKeychain::FindGenericPassword( + std::string_view service_name, +- std::string_view account_name) const { ++ std::string_view account_name, ++ AppleSecKeychainItemRef* item) const { base::AutoLock lock(GetMacSecurityServicesLock()); uint32_t password_length = 0; void* password_data = nullptr; @@ -134,7 +164,7 @@ index 0613e22fc0ce35378dc3580d797badd5f2680ae6..3ec4a2ba2fa5679363fabfa007be6200 if (status != noErr) { return base::unexpected(status); } -@@ -91,6 +92,11 @@ OSStatus AppleKeychain::AddGenericPassword( +@@ -92,6 +93,11 @@ OSStatus AppleKeychainSecKeychain::AddGenericPassword( password.data(), nullptr); } @@ -146,11 +176,25 @@ index 0613e22fc0ce35378dc3580d797badd5f2680ae6..3ec4a2ba2fa5679363fabfa007be6200 ScopedKeychainUserInteractionAllowed::ScopedKeychainUserInteractionAllowed( Boolean allowed, OSStatus* status) { +diff --git a/crypto/apple_keychain_seckeychain.h b/crypto/apple_keychain_seckeychain.h +index ecf5e229c8f05a27574b635abc9c781d175c1773..6afb09c59011035337a287783bbef0c6b7d29d9a 100644 +--- a/crypto/apple_keychain_seckeychain.h ++++ b/crypto/apple_keychain_seckeychain.h +@@ -20,7 +20,8 @@ class CRYPTO_EXPORT AppleKeychainSecKeychain : public AppleKeychain { + + base::expected, OSStatus> FindGenericPassword( + std::string_view service_name, +- std::string_view account_name) const override; ++ std::string_view account_name, ++ AppleSecKeychainItemRef* item) const override; + + OSStatus AddGenericPassword( + std::string_view service_name, diff --git a/crypto/mock_apple_keychain.cc b/crypto/mock_apple_keychain.cc -index 9b48805aacd161ff8d5550edf993217d5c6acfad..3b9fa4dc7f020740edb55a5aa80c9b526e4f585b 100644 +index d766dc41299f32bc766e4efce5925c93f21b60c5..7f09d477ba152cbca798f3ef7a213786cc95a338 100644 --- a/crypto/mock_apple_keychain.cc +++ b/crypto/mock_apple_keychain.cc -@@ -30,7 +30,8 @@ MockAppleKeychain::~MockAppleKeychain() = default; +@@ -32,7 +32,8 @@ MockAppleKeychain::~MockAppleKeychain() = default; base::expected, OSStatus> MockAppleKeychain::FindGenericPassword(std::string_view service_name, diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index c1e844182bae8..22c7bf7fa71b8 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -28,10 +28,10 @@ The patch should be removed in favor of either: Upstream bug https://bugs.chromium.org/p/chromium/issues/detail?id=1081397. diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc -index 8a0e2b9520654002578a673bb22c9def4caa0d26..b2a28eb0276211d2949fb1b8b74cf098ae5aba41 100644 +index dccc2e00d6bc52d25d35dbee95898a03960da28f..c3baeec8bbec12e4cb4d85413b77830d344b622c 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc -@@ -11151,6 +11151,12 @@ NavigationRequest::GetOriginForURLLoaderFactoryUncheckedWithDebugInfo() { +@@ -11107,6 +11107,12 @@ NavigationRequest::GetOriginForURLLoaderFactoryUncheckedWithDebugInfo() { "blob"); } diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 94d0f1cb79268..2c5bb43acc5be 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index d0f80de98c2bd3cf686b05ef972c89a8c2276935..05859e343a6c1fa58f3fb847ad6e97982804f910 100644 +index c34bcb4f4a6ac03b4e3a6c87c3ac29e4450ffa71..da05a4f28cc03bc555a99bd4e10097cd175b479c 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -9997,7 +9997,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -9972,7 +9972,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch index 3469f2110bfd4..5479442ad430c 100644 --- a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch +++ b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch @@ -20,7 +20,7 @@ index fc9cb7e68bdad4c40fab63f70243e09ad005ab80..199fbceda530da31aab9126d78b4bd21 injector_->ExpectsResults(), injector_->ShouldWaitForPromise()); } diff --git a/third_party/blink/public/web/web_local_frame.h b/third_party/blink/public/web/web_local_frame.h -index 8db7be4dbc924c719783ceb667e4f5708ea0133e..d8622012721795c76831bf33c62ce393e81badbb 100644 +index 6ea4a0f04eab4e85ec4c9b67f50c5c4e5c6e01e1..5f055fe422904c95e05af5cb0e92241a5d9d53c1 100644 --- a/third_party/blink/public/web/web_local_frame.h +++ b/third_party/blink/public/web/web_local_frame.h @@ -461,6 +461,7 @@ class BLINK_EXPORT WebLocalFrame : public WebFrame { @@ -59,7 +59,7 @@ index cba373664bec3a32abad6fe0396bd67b53b7e67f..a54f1b3351efd2d8f324436f7f35cd43 #endif // THIRD_PARTY_BLINK_PUBLIC_WEB_WEB_SCRIPT_EXECUTION_CALLBACK_H_ diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index fbfd4d96e8082df8c5db5d354ac7c39bc329d4ee..c8be9f437cc19668f8349e8777135e66a67fb9cb 100644 +index dd148eb3cce762d20e9117b4f8030c881057b8bb..e626d63f295b2d0fa62b179c76c45df125bbaeeb 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc @@ -3113,6 +3113,7 @@ void LocalFrame::RequestExecuteScript( @@ -215,7 +215,7 @@ index 5e12b61ba14cd1afb07b71ff15e73e905da0addc..685a2ebb6694c173471d045014932125 mojom::blink::WantResultOption::kWantResult, wait_for_promise); } diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc -index dcab8b2d4adcf14b285b558d85f69c303dc0818a..c998cba53d57dda9c32e7f75a9de3dcf0b974f58 100644 +index dd0c441d45ebb30c5a32822365f2ebe273b8cd16..164daddaccb84a28cf4bd387f382afddfc2613d3 100644 --- a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc +++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc @@ -1111,14 +1111,15 @@ void WebLocalFrameImpl::RequestExecuteScript( @@ -237,7 +237,7 @@ index dcab8b2d4adcf14b285b558d85f69c303dc0818a..c998cba53d57dda9c32e7f75a9de3dcf bool WebLocalFrameImpl::IsInspectorConnected() { diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.h b/third_party/blink/renderer/core/frame/web_local_frame_impl.h -index 1d50260fb58eb439d68506de7de04b78c616b6ee..3699e331d5cb15ca12b6fa2d2ba058f7ca74df40 100644 +index 87d933b2e413f404a9b80480bdf676eb0c8a2bfa..17329fb46c0d19645ad5411bbfba33dadfea4529 100644 --- a/third_party/blink/renderer/core/frame/web_local_frame_impl.h +++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.h @@ -198,6 +198,7 @@ class CORE_EXPORT WebLocalFrameImpl final @@ -249,10 +249,10 @@ index 1d50260fb58eb439d68506de7de04b78c616b6ee..3699e331d5cb15ca12b6fa2d2ba058f7 mojom::blink::WantResultOption, mojom::blink::PromiseResultOption) override; diff --git a/third_party/blink/renderer/core/scheduler_integration_tests/virtual_time_test.cc b/third_party/blink/renderer/core/scheduler_integration_tests/virtual_time_test.cc -index 4eb146c0798514e9201f2d68dcfebfacc82b97ea..27398228f87982e5c53476d5dee13fde5a6fa64e 100644 +index 5e66719cf6d8170039c011ad03d56ea55ee8f2cb..5a71dd5172c88aed1498dea02f790a7f278ac174 100644 --- a/third_party/blink/renderer/core/scheduler_integration_tests/virtual_time_test.cc +++ b/third_party/blink/renderer/core/scheduler_integration_tests/virtual_time_test.cc -@@ -63,6 +63,7 @@ class VirtualTimeTest : public SimTest { +@@ -59,6 +59,7 @@ class VirtualTimeTest : public SimTest { mojom::blink::LoadEventBlockingOption::kDoNotBlock, WTF::BindOnce(&ScriptExecutionCallbackHelper::Completed, base::Unretained(&callback_helper)), diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index f66769ab5b3cb..089eb8077c218 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -6,10 +6,10 @@ Subject: frame_host_manager.patch Allows embedder to intercept site instances created by chromium. diff --git a/content/browser/renderer_host/render_frame_host_manager.cc b/content/browser/renderer_host/render_frame_host_manager.cc -index d26c850e28b7df6992bf07fda2abe260ed4da769..008c131e5b4f84daeaee5ffe6ab7ae8836725ea5 100644 +index b61dfcc8e3306a2c3eb8808c204254af4ad8c248..cec49ddafd46b0296cc548a17efd67527a48f157 100644 --- a/content/browser/renderer_host/render_frame_host_manager.cc +++ b/content/browser/renderer_host/render_frame_host_manager.cc -@@ -4782,6 +4782,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( +@@ -4684,6 +4684,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( request->ResetStateForSiteInstanceChange(); } diff --git a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch index b76ccfc88ca5b..f52c337c296b2 100644 --- a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch +++ b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch @@ -11,7 +11,7 @@ If removing this patch causes no sync failures, it's safe to delete :+1: Ref https://chromium-review.googlesource.com/c/chromium/src/+/2953903 diff --git a/tools/clang/scripts/update.py b/tools/clang/scripts/update.py -index 108d33c2e6380749b80631b57931af6beaf44404..ad7b3f3a4e0190983ee68b1503a38847d9f94014 100755 +index 420c106a5f6fbbcfc77f2409e6272689ec71cf87..dad329cec5786323a981e150129c97357122c617 100755 --- a/tools/clang/scripts/update.py +++ b/tools/clang/scripts/update.py @@ -307,6 +307,8 @@ def GetDefaultHostOs(): diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 3cfbbc9f20f8a..ca7b65cf54374 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,7 +35,7 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index a6cbbaa18ab6631aff7d76873077d2e15cbedeb6..db6fac3683f2737d05c5bc2dabfcc4b669a8a6d1 100644 +index 82219748cc05ee4781731da17879f50dc1cea05f..25f5e50259e093d814271e53236d3be0647cb12b 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn @@ -1045,6 +1045,7 @@ component("base") { @@ -477,7 +477,7 @@ index ff96d22a11051391423f4a49c7b1478b8176baf8..c7e640e968f8ef183d48a226d43cdac8 // Beware: This view was briefly removed (in favor of a bare CALayer) in // https://crrev.com/c/1236675. The ordering of unassociated layers relative diff --git a/components/viz/service/BUILD.gn b/components/viz/service/BUILD.gn -index e522423645bf313ad1504a7ec47ecf3619888e35..d29bdc038fc6934c69b10b7a694d9cbf54839b02 100644 +index 15297546aa2641af1a249ff99bcf51764b107dbd..3c43af49c5d6d5f604c71e9a9dc1f7afe9aaf0f7 100644 --- a/components/viz/service/BUILD.gn +++ b/components/viz/service/BUILD.gn @@ -385,6 +385,7 @@ viz_component("service") { @@ -582,7 +582,7 @@ index 371b7b3ba73ee7b88027fcc31cb0a346cae40eea..c4b0654a56f4f2b4ab57ef05a119e388 return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index bdc48f4549ce6f82c5558b3c9e70c5c5a92c4faa..d10a5afe9da445b6fb940a46252efa8e0c36bcb4 100644 +index cf87c4749846d98e56f130ac10c9004029f56464..27327923cfdd0c05ad0368b5f4678ff8ecf835fc 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn @@ -342,6 +342,7 @@ source_set("browser") { @@ -833,10 +833,10 @@ index 4c59b6c62ad3fed9717b0330c7b46b8dc83a51a1..1c88c8f449387258259bcd65c13709d7 if (enable_nocompile_tests) { diff --git a/content/web_test/BUILD.gn b/content/web_test/BUILD.gn -index c17535742efb9a229120953ecb00c73ad391c07d..8142161f2ed49d7ce4f3785b86d846bf0728a92f 100644 +index dacf6fe8bbb3008e548a757aafaebc0d0a5cd66e..1e06aed0d22e460e5b5ad3bf72d767295454ddcf 100644 --- a/content/web_test/BUILD.gn +++ b/content/web_test/BUILD.gn -@@ -229,6 +229,7 @@ static_library("web_test_browser") { +@@ -231,6 +231,7 @@ static_library("web_test_browser") { "//ui/gl", "//ui/shell_dialogs:shell_dialogs", "//url", @@ -1436,7 +1436,7 @@ index eb81a70e4d5d5cd3e6ae9b45f8cd1c795ea76c51..9921ccb10d3455600eddd85f77f10228 } // namespace sandbox diff --git a/third_party/blink/renderer/core/BUILD.gn b/third_party/blink/renderer/core/BUILD.gn -index 3ff395b3ff3b646a64c43503d2c172776bf68c84..e40030307e8d9df7e00a402e241e00664b236c7d 100644 +index f2b874b368c6857013f6fbb7522d5d590f0540b5..1593565d61d284902ea364bf7bbee065e95acb48 100644 --- a/third_party/blink/renderer/core/BUILD.gn +++ b/third_party/blink/renderer/core/BUILD.gn @@ -414,6 +414,7 @@ component("core") { @@ -1678,7 +1678,7 @@ index 6846060ef9622d8fc8d1d6c8da16e2f1b785e6bd..05c22db87e882b246bd7034e027cf149 // Accessible object if (AXElementWrapper::IsValidElement(value)) { diff --git a/ui/base/BUILD.gn b/ui/base/BUILD.gn -index dfca458adb5b38cb1e597c16e9e6b6cc1521dea2..2372ff1193d1d52b719b6ee311cc07ac472a2f8d 100644 +index d2bd63f57da9b3ff84ebe36053ec18978d86c9f3..a6261be96e00548af7eba8a5fc7461586b9dbf53 100644 --- a/ui/base/BUILD.gn +++ b/ui/base/BUILD.gn @@ -365,6 +365,13 @@ component("base") { @@ -1695,7 +1695,7 @@ index dfca458adb5b38cb1e597c16e9e6b6cc1521dea2..2372ff1193d1d52b719b6ee311cc07ac if (is_ios) { sources += [ "device_form_factor_ios.mm", -@@ -518,6 +525,12 @@ component("base") { +@@ -511,6 +518,12 @@ component("base") { "//url", ] diff --git a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch index 01b9cb3d386b9..2a90b7ecb9aa5 100644 --- a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch +++ b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch @@ -10,7 +10,7 @@ an about:blank check to this area. Ref: https://chromium-review.googlesource.com/c/chromium/src/+/5403876 diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 78b55aa09b6db29119a0f47e11ea157e8b0c6d3b..deb02736cf52536d1c65255146ee077650d18095 100644 +index eaf36446678a3d079149377a6954c04f01573c8d..b060a69fef72b11d3bc932064d29e39ce827fb32 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc @@ -807,8 +807,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index 3020f2fb1702e..e59344c859369 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -881,10 +881,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index d10a5afe9da445b6fb940a46252efa8e0c36bcb4..6cfd8d6e9a38da8adfa05075097cc491962bd8f7 100644 +index 27327923cfdd0c05ad0368b5f4678ff8ecf835fc..0bff462eff763b5f5b1ecca6ca723c2c52199350 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3157,8 +3157,9 @@ source_set("browser") { +@@ -3154,8 +3154,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 2575b051ad0a1..8de7f1a324267 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -44,7 +44,7 @@ index 8637d83c1d3a912bbc48effcc095b426640351ad..3419628c08b62a16c62778cc124c365a void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index fec569763d3ba8b171ca65a9ea523ada5f729f41..e236eb74db68a6c11892e1ea16cab05b8c47afbf 100644 +index a99621ef317ec59f1368e5c7959f73de8ed32c54..5df2433b30213ba5683a864dcf42a07a5deb56e7 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc @@ -5883,6 +5883,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { @@ -60,10 +60,10 @@ index fec569763d3ba8b171ca65a9ea523ada5f729f41..e236eb74db68a6c11892e1ea16cab05b RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index c0a0400ae804dca3679bf8e98dc06effcc96dfe0..2e305bca22ed140a8fe28077f611b845c5478a88 100644 +index ebbefa02e163c9f38fc7057a592684f869c880e2..6d66b554acd09a32684ef6343db795134d9d5c15 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h -@@ -1186,6 +1186,7 @@ class CONTENT_EXPORT WebContentsImpl +@@ -1183,6 +1183,7 @@ class CONTENT_EXPORT WebContentsImpl void SendScreenRects() override; void SendActiveState(bool active) override; TextInputManager* GetTextInputManager() override; diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index dbfa5f17c7b95..fc4713889a17f 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 5fef3e077072ee9dc3ff22110b7818503c8b4e4b..2d3fc900a04e6ddc291548a37aaf2322ccbc4846 100644 +index dd94f88d353eb9291e2a64f0281e3fc1d53b68da..60a21da52a9a0f301e3b5e320fe69e766951db4d 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10134,25 +10134,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10109,25 +10109,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index feafb0097d40a..df6f0eda01984 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,7 +9,7 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index b2d5733ff8c47f497af03171d9dfac68b2013e4d..52b782a40724ab6d8cd9abf2193aeb1a14a5d8e9 100644 +index 7500958c41904c61705d49f75b7a152005ce4890..95bffa1a93ce1b103c129503414f7832d87fd493 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc @@ -3952,6 +3952,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index b194903626de5..063f52d7498ea 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,7 +15,7 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index df50b84cca214a9b6a85afe2fd677a45e2529cdc..78b55aa09b6db29119a0f47e11ea157e8b0c6d3b 100644 +index 7578b4f9056b9be79645fa0eed9476ab9b80c509..eaf36446678a3d079149377a6954c04f01573c8d 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc @@ -8881,6 +8881,17 @@ void RenderFrameHostImpl::EnterFullscreen( @@ -37,7 +37,7 @@ index df50b84cca214a9b6a85afe2fd677a45e2529cdc..78b55aa09b6db29119a0f47e11ea157e if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 52b782a40724ab6d8cd9abf2193aeb1a14a5d8e9..d0f80de98c2bd3cf686b05ef972c89a8c2276935 100644 +index 95bffa1a93ce1b103c129503414f7832d87fd493..c34bcb4f4a6ac03b4e3a6c87c3ac29e4450ffa71 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc @@ -4227,21 +4227,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( diff --git a/shell/common/asar/archive.cc b/shell/common/asar/archive.cc index 34037ecd90480..7951632806215 100644 --- a/shell/common/asar/archive.cc +++ b/shell/common/asar/archive.cc @@ -16,6 +16,7 @@ #include "base/json/json_reader.h" #include "base/logging.h" #include "base/pickle.h" +#include "base/strings/string_number_conversions.h" #include "base/values.h" #include "electron/fuses.h" #include "shell/common/asar/asar_util.h" From 01994637e8320b83146beeb0aecf133171beded2 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 5 May 2025 20:59:34 +0900 Subject: [PATCH 011/186] fix: xdg portal version detection for file dialogs on linux (#46922) * chore: use dbus thread for portal version detection Co-authored-by: deepak1556 * Update shell/browser/ui/file_dialog_linux_portal.cc Co-authored-by: Robo Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: deepak1556 Co-authored-by: Charles Kerr --- filenames.gni | 1 + ...ing_dialog_features_to_shell_dialogs.patch | 115 ++++++----------- shell/browser/ui/file_dialog.h | 10 ++ shell/browser/ui/file_dialog_linux.cc | 9 +- shell/browser/ui/file_dialog_linux_portal.cc | 121 ++++++++++++++++++ 5 files changed, 171 insertions(+), 85 deletions(-) create mode 100644 shell/browser/ui/file_dialog_linux_portal.cc diff --git a/filenames.gni b/filenames.gni index 45fafbdb52eb5..50242a7e7a1c1 100644 --- a/filenames.gni +++ b/filenames.gni @@ -35,6 +35,7 @@ filenames = { "shell/browser/relauncher_linux.cc", "shell/browser/ui/electron_desktop_window_tree_host_linux.cc", "shell/browser/ui/file_dialog_linux.cc", + "shell/browser/ui/file_dialog_linux_portal.cc", "shell/browser/ui/gtk/menu_gtk.cc", "shell/browser/ui/gtk/menu_gtk.h", "shell/browser/ui/gtk/menu_util.cc", diff --git a/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch b/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch index 681f039b6343b..3b127aae5909b 100644 --- a/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch +++ b/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch @@ -10,6 +10,8 @@ This CL adds support for the following features to //shell_dialogs: It also: * Changes XDG Portal implementation behavior to set default path regardless of dialog type. +* XDG Portal implementation calls into //electron to perform version checks on the dbus thread + Refs https://github.com/electron/electron/issues/46652. This may be partially upstreamed to Chromium in the future. @@ -345,83 +347,52 @@ index 9d45ec49a4fb5e12407b65b83c1ba0c13cd0dfd8..400cce91b020ecd5e48566f125515d2c + } // namespace ui diff --git a/ui/shell_dialogs/select_file_dialog_linux_portal.cc b/ui/shell_dialogs/select_file_dialog_linux_portal.cc -index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..d29de35ac813cc68b1faa11e803ace9a78df74ba 100644 +index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db84e8dff6 100644 --- a/ui/shell_dialogs/select_file_dialog_linux_portal.cc +++ b/ui/shell_dialogs/select_file_dialog_linux_portal.cc -@@ -12,6 +12,7 @@ - #include - - #include "base/check.h" -+#include "base/command_line.h" - #include "base/files/file_util.h" - #include "base/functional/bind.h" - #include "base/logging.h" -@@ -45,6 +46,8 @@ namespace { - constexpr char kXdgPortalService[] = "org.freedesktop.portal.Desktop"; - constexpr char kXdgPortalObject[] = "/org/freedesktop/portal/desktop"; - -+// Version 4 includes support for current_folder option to the OpenFile method via -+// https://github.com/flatpak/xdg-desktop-portal/commit/71165a5. - constexpr int kXdgPortalRequiredVersion = 3; - - constexpr char kFileChooserInterfaceName[] = -@@ -66,6 +69,8 @@ constexpr uint32_t kFileChooserFilterKindGlob = 0; - - constexpr char kFileUriPrefix[] = "file://"; - -+const char kXdgPortalRequiredVersionFlag[] = "xdg-portal-required-version"; -+ - enum class ServiceAvailability { - kNotStarted, - kInProgress, -@@ -75,6 +80,9 @@ enum class ServiceAvailability { - - ServiceAvailability g_service_availability = ServiceAvailability::kNotStarted; - -+uint32_t g_available_portal_version = 0; -+uint32_t g_required_portal_version = kXdgPortalRequiredVersion; -+ - scoped_refptr& GetMainTaskRunner() { - static base::NoDestructor> - main_task_runner; -@@ -94,9 +102,10 @@ void OnGetPropertyReply(dbus::Response* response) { - return; - } - -- g_service_availability = version >= kXdgPortalRequiredVersion -+ g_service_availability = version >= g_required_portal_version - ? ServiceAvailability::kAvailable +@@ -28,6 +28,7 @@ + #include "dbus/message.h" + #include "dbus/object_path.h" + #include "dbus/object_proxy.h" ++#include "electron/shell/browser/ui/file_dialog.h" + #include "ui/aura/window_tree_host.h" + #include "ui/base/l10n/l10n_util.h" + #include "ui/gfx/native_widget_types.h" +@@ -99,7 +100,7 @@ void OnGetPropertyReply(dbus::Response* response) { : ServiceAvailability::kNotAvailable; -+ g_available_portal_version = version; } - void OnServiceStarted(std::optional service_started) { -@@ -164,6 +173,12 @@ void SelectFileDialogLinuxPortal::StartAvailabilityTestInBackground() { - } - g_service_availability = ServiceAvailability::kInProgress; +-void OnServiceStarted(std::optional service_started) { ++[[maybe_unused]] void OnServiceStarted(std::optional service_started) { + if (!service_started.value_or(false)) { + g_service_availability = ServiceAvailability::kNotAvailable; + return; +@@ -166,18 +167,24 @@ void SelectFileDialogLinuxPortal::StartAvailabilityTestInBackground() { -+ auto* cmd = base::CommandLine::ForCurrentProcess(); -+ if (!base::StringToUint(cmd->GetSwitchValueASCII(kXdgPortalRequiredVersionFlag), -+ &g_required_portal_version)) { -+ g_required_portal_version = kXdgPortalRequiredVersion; -+ } -+ GetMainTaskRunner() = base::SequencedTaskRunner::GetCurrentDefault(); ++#if 0 dbus_utils::CheckForServiceAndStart(dbus_thread_linux::GetSharedSessionBus(), -@@ -180,6 +195,11 @@ bool SelectFileDialogLinuxPortal::IsPortalAvailable() { + kXdgPortalService, + base::BindOnce(&OnServiceStarted)); ++#endif ++ file_dialog::StartPortalAvailabilityTestInBackground(); + } + + // static + bool SelectFileDialogLinuxPortal::IsPortalAvailable() { ++#if 0 + if (g_service_availability == ServiceAvailability::kInProgress) { + LOG(WARNING) << "Portal availability checked before test was complete"; + } + return g_service_availability == ServiceAvailability::kAvailable; ++#endif ++ return file_dialog::IsPortalAvailable(); } -+// static -+uint32_t SelectFileDialogLinuxPortal::GetPortalVersion() { -+ return g_available_portal_version; -+} -+ bool SelectFileDialogLinuxPortal::IsRunning( - gfx::NativeWindow parent_window) const { - return parent_window && host_ && host_.get() == parent_window->GetHost(); -@@ -382,11 +402,14 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( +@@ -382,11 +389,14 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( const PortalFilterSet& filter_set) { DbusDictionary dict; @@ -439,7 +410,7 @@ index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..d29de35ac813cc68b1faa11e803ace9a [[fallthrough]]; case SelectFileDialog::SELECT_FOLDER: case SelectFileDialog::Type::SELECT_EXISTING_FOLDER: -@@ -399,6 +422,10 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( +@@ -399,6 +409,10 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( break; } @@ -450,17 +421,3 @@ index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..d29de35ac813cc68b1faa11e803ace9a if (!default_path.empty()) { if (default_path_exists) { // If this is an existing directory, navigate to that directory, with no -diff --git a/ui/shell_dialogs/select_file_dialog_linux_portal.h b/ui/shell_dialogs/select_file_dialog_linux_portal.h -index 651684b1840eaff664f3d73d99bbea40e097c866..9a9d541f1e9586d9d545f8547d3f09ff33dce48d 100644 ---- a/ui/shell_dialogs/select_file_dialog_linux_portal.h -+++ b/ui/shell_dialogs/select_file_dialog_linux_portal.h -@@ -45,6 +45,9 @@ class SelectFileDialogLinuxPortal : public SelectFileDialogLinux { - // availability test has not yet completed. - static bool IsPortalAvailable(); - -+ // Get version of portal if available. -+ static uint32_t GetPortalVersion(); -+ - protected: - ~SelectFileDialogLinuxPortal() override; - diff --git a/shell/browser/ui/file_dialog.h b/shell/browser/ui/file_dialog.h index 5a6c4cadbbf22..b8858c06ecb3b 100644 --- a/shell/browser/ui/file_dialog.h +++ b/shell/browser/ui/file_dialog.h @@ -77,6 +77,16 @@ bool ShowSaveDialogSync(const DialogSettings& settings, base::FilePath* path); void ShowSaveDialog(const DialogSettings& settings, gin_helper::Promise promise); +#if BUILDFLAG(IS_LINUX) +// Rewrite of SelectFileDialogLinuxPortal equivalent functions with primary +// difference being that dbus_thread_linux::GetSharedSessionBus is not used +// so that version detection can be initiated and compeleted on the dbus thread +// Refs https://github.com/electron/electron/issues/46652 +void StartPortalAvailabilityTestInBackground(); +bool IsPortalAvailable(); +uint32_t GetPortalVersion(); +#endif + } // namespace file_dialog #endif // ELECTRON_SHELL_BROWSER_UI_FILE_DIALOG_H_ diff --git a/shell/browser/ui/file_dialog_linux.cc b/shell/browser/ui/file_dialog_linux.cc index 404aead64b5d9..732820aa193a9 100644 --- a/shell/browser/ui/file_dialog_linux.cc +++ b/shell/browser/ui/file_dialog_linux.cc @@ -18,7 +18,6 @@ #include "shell/common/gin_helper/dictionary.h" #include "shell/common/gin_helper/promise.h" #include "ui/shell_dialogs/select_file_dialog.h" -#include "ui/shell_dialogs/select_file_dialog_linux_portal.h" #include "ui/shell_dialogs/select_file_policy.h" #include "ui/shell_dialogs/selected_file_info.h" @@ -60,11 +59,9 @@ ui::SelectFileDialog::FileTypeInfo GetFilterInfo(const Filters& filters) { } void LogIfNeededAboutUnsupportedPortalFeature(const DialogSettings& settings) { - if (!settings.default_path.empty() && - ui::SelectFileDialogLinuxPortal::IsPortalAvailable() && - ui::SelectFileDialogLinuxPortal::GetPortalVersion() < 4) { - LOG(INFO) << "Available portal version " - << ui::SelectFileDialogLinuxPortal::GetPortalVersion() + if (!settings.default_path.empty() && IsPortalAvailable() && + GetPortalVersion() < 4) { + LOG(INFO) << "Available portal version " << GetPortalVersion() << " does not support defaultPath option, try the non-portal" << " file chooser dialogs by launching with" << " --xdg-portal-required-version"; diff --git a/shell/browser/ui/file_dialog_linux_portal.cc b/shell/browser/ui/file_dialog_linux_portal.cc new file mode 100644 index 0000000000000..298ee25caffb4 --- /dev/null +++ b/shell/browser/ui/file_dialog_linux_portal.cc @@ -0,0 +1,121 @@ +// Copyright (c) 2025 Microsoft, GmbH. +// Use of this source code is governed by the MIT license that can be +// found in the LICENSE file. + +#include "shell/browser/ui/file_dialog.h" + +#include + +#include "base/command_line.h" +#include "base/functional/bind.h" +#include "base/logging.h" +#include "base/memory/scoped_refptr.h" +#include "base/no_destructor.h" +#include "base/strings/string_number_conversions.h" +#include "base/synchronization/atomic_flag.h" +#include "components/dbus/thread_linux/dbus_thread_linux.h" +#include "components/dbus/utils/check_for_service_and_start.h" +#include "dbus/bus.h" +#include "dbus/object_path.h" +#include "dbus/object_proxy.h" +#include "dbus/property.h" + +namespace file_dialog { + +namespace { + +constexpr char kXdgPortalService[] = "org.freedesktop.portal.Desktop"; +constexpr char kXdgPortalObject[] = "/org/freedesktop/portal/desktop"; +constexpr char kFileChooserInterfaceName[] = + "org.freedesktop.portal.FileChooser"; + +// Version 4 includes support for current_folder option to the OpenFile method +// via https://github.com/flatpak/xdg-desktop-portal/commit/71165a5. +uint32_t g_required_portal_version = 3; +uint32_t g_available_portal_version = 0; +constexpr char kXdgPortalRequiredVersionFlag[] = "xdg-portal-required-version"; + +bool g_portal_available = false; + +struct FileChooserProperties : dbus::PropertySet { + dbus::Property version; + + explicit FileChooserProperties(dbus::ObjectProxy* object_proxy) + : dbus::PropertySet(object_proxy, kFileChooserInterfaceName, {}) { + RegisterProperty("version", &version); + } + + ~FileChooserProperties() override = default; +}; + +base::AtomicFlag* GetAvailabilityTestCompletionFlag() { + static base::NoDestructor flag; + return flag.get(); +} + +void CheckPortalAvailabilityOnBusThread() { + auto* flag = GetAvailabilityTestCompletionFlag(); + if (flag->IsSet()) + return; + + dbus::Bus::Options options; + options.bus_type = dbus::Bus::SESSION; + options.connection_type = dbus::Bus::PRIVATE; + options.dbus_task_runner = dbus_thread_linux::GetTaskRunner(); + scoped_refptr bus = base::MakeRefCounted(options); + dbus_utils::CheckForServiceAndStart( + bus, kXdgPortalService, + base::BindOnce( + [](scoped_refptr bus, base::AtomicFlag* flag, + std::optional name_has_owner) { + if (name_has_owner.value_or(false)) { + // + dbus::ObjectPath portal_path(kXdgPortalObject); + dbus::ObjectProxy* portal = + bus->GetObjectProxy(kXdgPortalService, portal_path); + FileChooserProperties properties(portal); + if (!properties.GetAndBlock(&properties.version)) { + LOG(ERROR) << "Failed to read portal version property"; + } else if (properties.version.value() >= + g_required_portal_version) { + g_portal_available = true; + g_available_portal_version = properties.version.value(); + } + } + VLOG(1) << "File chooser portal available: " + << (g_portal_available ? "yes" : "no"); + flag->Set(); + bus->ShutdownAndBlock(); + }, + std::move(bus), flag)); +} + +} // namespace + +void StartPortalAvailabilityTestInBackground() { + if (GetAvailabilityTestCompletionFlag()->IsSet()) + return; + + const auto* cmd = base::CommandLine::ForCurrentProcess(); + if (!base::StringToUint( + cmd->GetSwitchValueASCII(kXdgPortalRequiredVersionFlag), + &g_required_portal_version)) { + VLOG(1) << "Unable to parse --xdg-portal-required-version"; + } + + dbus_thread_linux::GetTaskRunner()->PostTask( + FROM_HERE, base::BindOnce(&CheckPortalAvailabilityOnBusThread)); +} + +bool IsPortalAvailable() { + if (!GetAvailabilityTestCompletionFlag()->IsSet()) + LOG(WARNING) << "Portal availability checked before test was complete"; + + return g_portal_available; +} + +uint32_t GetPortalVersion() { + return g_available_portal_version; +} + +} // namespace file_dialog From 258762929fefad3caf59796ad47865bd765d7d51 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 5 May 2025 13:02:47 -0400 Subject: [PATCH 012/186] refactor: add `NativeWindow::FromWidget()` helper (#46928) refactor: add NativeWindow::FromWidet() helper refactor: make kElectronNativeWindowKey a protected field Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_web_contents_view.cc | 13 ++++++------- shell/browser/native_window.cc | 7 +++++++ shell/browser/native_window.h | 8 +++++--- shell/browser/native_window_mac.mm | 2 +- shell/browser/native_window_views.cc | 2 +- 5 files changed, 20 insertions(+), 12 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents_view.cc b/shell/browser/api/electron_api_web_contents_view.cc index f76209fbdf5be..32ca981adcfe1 100644 --- a/shell/browser/api/electron_api_web_contents_view.cc +++ b/shell/browser/api/electron_api_web_contents_view.cc @@ -99,12 +99,11 @@ void WebContentsView::WebContentsDestroyed() { void WebContentsView::OnViewAddedToWidget(views::View* observed_view) { DCHECK_EQ(observed_view, view()); - views::Widget* widget = view()->GetWidget(); - auto* native_window = - static_cast(widget->GetNativeWindowProperty( - electron::kElectronNativeWindowKey.c_str())); + + NativeWindow* native_window = NativeWindow::FromWidget(view()->GetWidget()); if (!native_window) return; + // We don't need to call SetOwnerWindow(nullptr) in OnViewRemovedFromWidget // because that's handled in the WebContents dtor called prior. api_web_contents_->SetOwnerWindow(native_window); @@ -114,11 +113,11 @@ void WebContentsView::OnViewAddedToWidget(views::View* observed_view) { void WebContentsView::OnViewRemovedFromWidget(views::View* observed_view) { DCHECK_EQ(observed_view, view()); - views::Widget* widget = view()->GetWidget(); - auto* native_window = static_cast( - widget->GetNativeWindowProperty(kElectronNativeWindowKey.c_str())); + + NativeWindow* native_window = NativeWindow::FromWidget(view()->GetWidget()); if (!native_window) return; + native_window->RemoveDraggableRegionProvider(this); } diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index b6e7d9a9901c7..f54f329ce5152 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -284,6 +284,13 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { Show(); } +// static +NativeWindow* NativeWindow::FromWidget(const views::Widget* widget) { + DCHECK(widget); + return static_cast( + widget->GetNativeWindowProperty(kNativeWindowKey.c_str())); +} + void NativeWindow::SetSize(const gfx::Size& size, bool animate) { SetBounds(gfx::Rect(GetPosition(), size), animate); } diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index 176931bc2eb4f..8a28173da1acd 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -47,9 +47,6 @@ class PersistentDictionary; namespace electron { -inline constexpr base::cstring_view kElectronNativeWindowKey = - "__ELECTRON_NATIVE_WINDOW__"; - class ElectronMenuModel; class BackgroundThrottlingSource; @@ -78,6 +75,8 @@ class NativeWindow : public base::SupportsUserData, const gin_helper::Dictionary& options, NativeWindow* parent = nullptr); + [[nodiscard]] static NativeWindow* FromWidget(const views::Widget* widget); + void InitFromOptions(const gin_helper::Dictionary& options); virtual void SetContentView(views::View* view) = 0; @@ -450,6 +449,9 @@ class NativeWindow : public base::SupportsUserData, virtual void CloseImpl() = 0; virtual void CloseImmediatelyImpl() = 0; + static inline constexpr base::cstring_view kNativeWindowKey = + "__ELECTRON_NATIVE_WINDOW__"; + // The boolean parsing of the "titleBarOverlay" option bool titlebar_overlay_ = false; diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 2610ddeaf03ca..1386e5a826362 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -203,7 +203,7 @@ static bool FromV8(v8::Isolate* isolate, params.native_widget = new ElectronNativeWidgetMac(this, windowType, styleMask, widget()); widget()->Init(std::move(params)); - widget()->SetNativeWindowProperty(kElectronNativeWindowKey.c_str(), this); + widget()->SetNativeWindowProperty(kNativeWindowKey.c_str(), this); SetCanResize(resizable); window_ = static_cast( widget()->GetNativeWindow().GetNativeNSWindow()); diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 0c5e0fc58f2c5..e46aaff87007f 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -306,7 +306,7 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, #endif widget()->Init(std::move(params)); - widget()->SetNativeWindowProperty(kElectronNativeWindowKey.c_str(), this); + widget()->SetNativeWindowProperty(kNativeWindowKey.c_str(), this); SetCanResize(resizable_); bool fullscreen = false; From 3c8d971c531b638adabd34c893f7aab2d5c01f25 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 5 May 2025 13:26:41 -0400 Subject: [PATCH 013/186] refactor: simplify `NativeWindow::FullScreenTransitionState` (#46929) * refactor: make NativeWindow::fullscreen_transition_state_ private Co-authored-by: Charles Kerr * refactor: add NativeWindow::is_transitioning_fullscreen() helper Co-authored-by: Charles Kerr * refactor: remove unused NativeWindow::fullscreen_transition_state() Co-authored-by: Charles Kerr * refactor: replace NativeWindow::set_fullscreen_transition_state() with NativeWindow::set_is_transitioning_fullscreen() refactor: remove unused NativeWindow::FullScreenTransitionState Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_web_contents.cc | 3 +-- shell/browser/native_window.h | 15 +++++++-------- shell/browser/native_window_mac.mm | 13 +++++-------- .../ui/cocoa/electron_ns_window_delegate.mm | 12 +++++------- 4 files changed, 18 insertions(+), 25 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index 71b4733a34b61..2b8365d1aef72 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -3961,8 +3961,7 @@ bool WebContents::IsFullscreenForTabOrPending( if (!owner_window()) return is_html_fullscreen(); - bool in_transition = owner_window()->fullscreen_transition_state() != - NativeWindow::FullScreenTransitionState::kNone; + const bool in_transition = owner_window()->is_transitioning_fullscreen(); bool is_html_transition = owner_window()->fullscreen_transition_type() == NativeWindow::FullScreenTransitionType::kHTML; diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index 8a28173da1acd..baa9988e9ae54 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -354,13 +354,12 @@ class NativeWindow : public base::SupportsUserData, // Handle fullscreen transitions. void HandlePendingFullscreenTransitions(); - enum class FullScreenTransitionState { kEntering, kExiting, kNone }; - - void set_fullscreen_transition_state(FullScreenTransitionState state) { - fullscreen_transition_state_ = state; + constexpr void set_is_transitioning_fullscreen(const bool val) { + is_transitioning_fullscreen_ = val; } - FullScreenTransitionState fullscreen_transition_state() const { - return fullscreen_transition_state_; + + [[nodiscard]] constexpr bool is_transitioning_fullscreen() const { + return is_transitioning_fullscreen_; } enum class FullScreenTransitionType { kHTML, kNative, kNone }; @@ -470,8 +469,6 @@ class NativeWindow : public base::SupportsUserData, std::optional content_size_constraints_; std::queue pending_transitions_; - FullScreenTransitionState fullscreen_transition_state_ = - FullScreenTransitionState::kNone; FullScreenTransitionType fullscreen_transition_type_ = FullScreenTransitionType::kNone; @@ -519,6 +516,8 @@ class NativeWindow : public base::SupportsUserData, // Is this a modal window. bool is_modal_ = false; + bool is_transitioning_fullscreen_ = false; + std::list draggable_region_providers_; // Observers of this window. diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 1386e5a826362..c603590f54136 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -331,7 +331,7 @@ static bool FromV8(v8::Isolate* isolate, } void NativeWindowMac::CloseImpl() { - if (fullscreen_transition_state() != FullScreenTransitionState::kNone) { + if (is_transitioning_fullscreen()) { SetHasDeferredWindowClose(true); return; } @@ -623,7 +623,7 @@ static bool FromV8(v8::Isolate* isolate, // that it's possible to call it while a fullscreen transition is currently // in process. This can create weird behavior (incl. phantom windows), // so we want to schedule a transition for when the current one has completed. - if (fullscreen_transition_state() != FullScreenTransitionState::kNone) { + if (is_transitioning_fullscreen()) { if (!pending_transitions_.empty()) { bool last_pending = pending_transitions_.back(); // Only push new transitions if they're different than the last transition @@ -647,12 +647,10 @@ static bool FromV8(v8::Isolate* isolate, // SetFullScreen is called by a user before windowWillEnterFullScreen // or windowWillExitFullScreen are invoked, and so a potential transition // could be dropped. - fullscreen_transition_state_ = fullscreen - ? FullScreenTransitionState::kEntering - : FullScreenTransitionState::kExiting; + set_is_transitioning_fullscreen(true); if (![window_ toggleFullScreenMode:nil]) - fullscreen_transition_state_ = FullScreenTransitionState::kNone; + set_is_transitioning_fullscreen(false); } bool NativeWindowMac::IsFullscreen() const { @@ -780,8 +778,7 @@ static bool FromV8(v8::Isolate* isolate, } bool NativeWindowMac::IsResizable() const { - bool in_fs_transition = - fullscreen_transition_state() != FullScreenTransitionState::kNone; + const bool in_fs_transition = is_transitioning_fullscreen(); bool has_rs_mask = HasStyleMask(NSWindowStyleMaskResizable); return has_rs_mask && !IsFullscreen() && !in_fs_transition; } diff --git a/shell/browser/ui/cocoa/electron_ns_window_delegate.mm b/shell/browser/ui/cocoa/electron_ns_window_delegate.mm index 04fa6781dd1fe..d2a64514f12e3 100644 --- a/shell/browser/ui/cocoa/electron_ns_window_delegate.mm +++ b/shell/browser/ui/cocoa/electron_ns_window_delegate.mm @@ -18,8 +18,6 @@ #include "ui/views/widget/native_widget_mac.h" using TitleBarStyle = electron::NativeWindowMac::TitleBarStyle; -using FullScreenTransitionState = - electron::NativeWindow::FullScreenTransitionState; @implementation ElectronNSWindowDelegate @@ -302,7 +300,7 @@ - (void)windowWillEnterFullScreen:(NSNotification*)notification { // Store resizable mask so it can be restored after exiting fullscreen. is_resizable_ = shell_->HasStyleMask(NSWindowStyleMaskResizable); - shell_->set_fullscreen_transition_state(FullScreenTransitionState::kEntering); + shell_->set_is_transitioning_fullscreen(true); shell_->NotifyWindowWillEnterFullScreen(); @@ -311,7 +309,7 @@ - (void)windowWillEnterFullScreen:(NSNotification*)notification { } - (void)windowDidEnterFullScreen:(NSNotification*)notification { - shell_->set_fullscreen_transition_state(FullScreenTransitionState::kNone); + shell_->set_is_transitioning_fullscreen(false); shell_->NotifyWindowEnterFullScreen(); @@ -322,7 +320,7 @@ - (void)windowDidEnterFullScreen:(NSNotification*)notification { } - (void)windowDidFailToEnterFullScreen:(NSWindow*)window { - shell_->set_fullscreen_transition_state(FullScreenTransitionState::kNone); + shell_->set_is_transitioning_fullscreen(false); shell_->SetResizable(is_resizable_); shell_->NotifyWindowDidFailToEnterFullScreen(); @@ -334,13 +332,13 @@ - (void)windowDidFailToEnterFullScreen:(NSWindow*)window { } - (void)windowWillExitFullScreen:(NSNotification*)notification { - shell_->set_fullscreen_transition_state(FullScreenTransitionState::kExiting); + shell_->set_is_transitioning_fullscreen(true); shell_->NotifyWindowWillLeaveFullScreen(); } - (void)windowDidExitFullScreen:(NSNotification*)notification { - shell_->set_fullscreen_transition_state(FullScreenTransitionState::kNone); + shell_->set_is_transitioning_fullscreen(false); shell_->SetResizable(is_resizable_); shell_->NotifyWindowLeaveFullScreen(); From 018e2f6a3102ed9ba7021158123adeebe63b4fff Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 5 May 2025 20:39:50 +0200 Subject: [PATCH 014/186] refactor: devirtualize `NativeWindow` methods (#46931) * refactor: devirtualize NativeWindow::SetSize() refactor: devirtualize NativeWindow::GetSize() refactor: devirtualize NativeWindow::SetPosition() refactor: devirtualize NativeWindow::GetPosition() Co-authored-by: Charles Kerr * refactor: devirtualize NativeWinodw::SetMinimumSize() refactor: devirtualize NativeWinodw::GetMinimumSize() refactor: devirtualize NativeWinodw::SetMaximumSize() refactor: devirtualize NativeWinodw::GetMaximumSize() Co-authored-by: Charles Kerr * refactor: devirtualize NativeWindow::SetSheetOffset() refactor: devirtualize NativeWindow::GetSheetOffsetX() refactor: devirtualize NativeWindow::GetSheetOffsetY() Co-authored-by: Charles Kerr * refactor: devirtualize NativeWindow::GetContentMinimumSize() refactor: devirtualize NativeWindow::GetContentMaximumSize() Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window.h | 34 +++++++++++++++++++++------------- 1 file changed, 21 insertions(+), 13 deletions(-) diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index baa9988e9ae54..0188c31735243 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -103,10 +103,13 @@ class NativeWindow : public base::SupportsUserData, virtual bool IsFullscreen() const = 0; virtual void SetBounds(const gfx::Rect& bounds, bool animate = false) = 0; virtual gfx::Rect GetBounds() const = 0; - virtual void SetSize(const gfx::Size& size, bool animate = false); - virtual gfx::Size GetSize() const; - virtual void SetPosition(const gfx::Point& position, bool animate = false); - virtual gfx::Point GetPosition() const; + + void SetSize(const gfx::Size& size, bool animate = false); + [[nodiscard]] gfx::Size GetSize() const; + + void SetPosition(const gfx::Point& position, bool animate = false); + [[nodiscard]] gfx::Point GetPosition() const; + virtual void SetContentSize(const gfx::Size& size, bool animate = false); virtual gfx::Size GetContentSize() const; virtual void SetContentBounds(const gfx::Rect& bounds, bool animate = false); @@ -119,15 +122,20 @@ class NativeWindow : public base::SupportsUserData, virtual void SetContentSizeConstraints( const extensions::SizeConstraints& size_constraints); virtual extensions::SizeConstraints GetContentSizeConstraints() const; - virtual void SetMinimumSize(const gfx::Size& size); - virtual gfx::Size GetMinimumSize() const; - virtual void SetMaximumSize(const gfx::Size& size); - virtual gfx::Size GetMaximumSize() const; - virtual gfx::Size GetContentMinimumSize() const; - virtual gfx::Size GetContentMaximumSize() const; - virtual void SetSheetOffset(const double offsetX, const double offsetY); - virtual double GetSheetOffsetX() const; - virtual double GetSheetOffsetY() const; + + void SetMinimumSize(const gfx::Size& size); + [[nodiscard]] gfx::Size GetMinimumSize() const; + + void SetMaximumSize(const gfx::Size& size); + [[nodiscard]] gfx::Size GetMaximumSize() const; + + [[nodiscard]] gfx::Size GetContentMinimumSize() const; + [[nodiscard]] gfx::Size GetContentMaximumSize() const; + + void SetSheetOffset(const double offsetX, const double offsetY); + [[nodiscard]] double GetSheetOffsetX() const; + [[nodiscard]] double GetSheetOffsetY() const; + virtual void SetResizable(bool resizable) = 0; virtual bool MoveAbove(const std::string& sourceId) = 0; virtual void MoveTop() = 0; From 0c683552ec8e57ba85bd4244b26070a87ef1dc60 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 5 May 2025 16:05:40 -0500 Subject: [PATCH 015/186] chore: bump chromium to 138.0.7160.0 (37-x-y) (#46938) * chore: bump chromium in DEPS to 138.0.7158.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: bump chromium in DEPS to 138.0.7160.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6509206: Move Keychain UI suppression code into apple_keychain.cc https://chromium-review.googlesource.com/c/chromium/src/+/6509206 Co-authored-by: Shelley Vohr * 6489036: Fix DesktopDataControlsDialog for Glic https://chromium-review.googlesource.com/c/chromium/src/+/6489036 Co-authored-by: Shelley Vohr * chore: fixup patch indices Co-authored-by: Shelley Vohr * 6506662: Reland "NavigationThrottleRunner2: content::NavigationThrottleRegistry" https://chromium-review.googlesource.com/c/chromium/src/+/6506662 Co-authored-by: Shelley Vohr * 6499811: [video pip] Add live caption dialog https://chromium-review.googlesource.com/c/chromium/src/+/6499811 Co-authored-by: Shelley Vohr * 6487926: Add GetMaxImageDimension function to ScreenAI service API for OCR. https://chromium-review.googlesource.com/c/chromium/src/+/6487926 Co-authored-by: Shelley Vohr * 6494942: [json] Activate stringify fast-path by default https://chromium-review.googlesource.com/c/v8/v8/+/6494942 Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- DEPS | 2 +- .../build_add_electron_tracing_category.patch | 4 +- ..._depend_on_packed_resource_integrity.patch | 10 ++--- patches/chromium/can_create_window.patch | 24 ++++++------ ...ther_in_electron_views_and_delegates.patch | 12 +++--- .../chromium/chore_partial_revert_of.patch | 4 +- ...screationoverridden_with_full_params.patch | 4 +- patches/chromium/disable_hidden.patch | 4 +- ...t_allow_code_cache_in_custom_schemes.patch | 2 +- ...e_launch_options_for_service_process.patch | 6 +-- ...same_application_can_use_safestorage.patch | 14 +++---- ...ding_non-standard_schemes_in_iframes.patch | 4 +- ...ingshelper_behind_branding_buildflag.patch | 4 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ...original_resize_performance_on_macos.patch | 4 +- patches/chromium/frame_host_manager.patch | 4 +- .../chromium/gritsettings_resource_ids.patch | 2 +- patches/chromium/gtk_visibility.patch | 2 +- ...sync_with_host_os_mac_on_linux_in_ci.patch | 2 +- .../chromium/make_gtk_getlibgtk_public.patch | 6 +-- ..._avoid_private_macos_api_usage.patch.patch | 22 +++++------ .../chromium/notification_provenance.patch | 2 +- ...eated_to_allow_for_browser_initiated.patch | 4 +- patches/chromium/picture-in-picture.patch | 19 ++++++++-- patches/chromium/printing.patch | 4 +- ...r_changes_to_the_webcontentsobserver.patch | 10 ++--- ...efactor_unfilter_unresponsive_events.patch | 4 +- .../render_widget_host_view_mac.patch | 8 ++-- .../support_mixed_sandbox_with_zygote.patch | 2 +- patches/chromium/web_contents.patch | 6 +-- patches/chromium/webview_fullscreen.patch | 10 ++--- ...i_to_allow_electron_to_set_dock_side.patch | 4 +- patches/node/.patches | 1 + ...low_json_stringify_path_for_overflow.patch | 38 +++++++++++++++++++ shell/browser/electron_browser_client.cc | 5 ++- shell/browser/electron_browser_client.h | 4 +- shell/browser/feature_list.cc | 6 ++- 37 files changed, 164 insertions(+), 103 deletions(-) create mode 100644 patches/node/test_force_slow_json_stringify_path_for_overflow.patch diff --git a/DEPS b/DEPS index 127d47a33ff30..d5be3c35f88b8 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7156.0', + '138.0.7160.0', 'node_version': 'v22.14.0', 'nan_version': diff --git a/patches/chromium/build_add_electron_tracing_category.patch b/patches/chromium/build_add_electron_tracing_category.patch index b2495de6a8983..3799123b2b0a6 100644 --- a/patches/chromium/build_add_electron_tracing_category.patch +++ b/patches/chromium/build_add_electron_tracing_category.patch @@ -8,10 +8,10 @@ categories in use are known / declared. This patch is required for us to introduce a new Electron category for Electron-specific tracing. diff --git a/base/trace_event/builtin_categories.h b/base/trace_event/builtin_categories.h -index 5e0f05804e8142c735fa2f5afb27485caae895f9..48ac9a600b6a007e2e974b657c3d8048be97b3ce 100644 +index e9f891a025771899ffc888ea0095200342e48558..39d6f580c0cb5a0de41f32e9d7e103e05cefd0f0 100644 --- a/base/trace_event/builtin_categories.h +++ b/base/trace_event/builtin_categories.h -@@ -91,6 +91,7 @@ PERFETTO_DEFINE_CATEGORIES_IN_NAMESPACE_WITH_ATTRS( +@@ -102,6 +102,7 @@ PERFETTO_DEFINE_CATEGORIES_IN_NAMESPACE_WITH_ATTRS( perfetto::Category("drm"), perfetto::Category("drmcursor"), perfetto::Category("dwrite"), diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index a2f8cde7b70e7..72c3e0e47ec65 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -33,7 +33,7 @@ index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index 5c26efefaa030e5f5b7ba6089e989303795d771c..5df9bd353fe212491e473027a7080854cc5ea738 100644 +index ae32014a8a25f3b1de7f6087551a87400e1463b5..be77c4e02cc495194ed6b248e56bcb75abe4efce 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn @@ -4627,7 +4627,7 @@ static_library("browser") { @@ -46,10 +46,10 @@ index 5c26efefaa030e5f5b7ba6089e989303795d771c..5df9bd353fe212491e473027a7080854 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 897f91ed0f1fcd386f980fe2073c07915cfc6458..43c6c436a391362173cc3ae562d6cd0fb5191d1b 100644 +index e08035df314884fab39562cd9ee4960ec5af3cb5..28f0f4d671e16ffff770b43fa5a2e366491d4b30 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7181,9 +7181,12 @@ test("unit_tests") { +@@ -7185,9 +7185,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index 897f91ed0f1fcd386f980fe2073c07915cfc6458..43c6c436a391362173cc3ae562d6cd0f "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8149,6 +8152,10 @@ test("unit_tests") { +@@ -8153,6 +8156,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index 897f91ed0f1fcd386f980fe2073c07915cfc6458..43c6c436a391362173cc3ae562d6cd0f sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8204,7 +8211,6 @@ test("unit_tests") { +@@ -8208,7 +8215,6 @@ test("unit_tests") { # Non-android deps for "unit_tests" target. deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 07f617cab8e51..1d60f2508309c 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,10 +9,10 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 66c25476de83a9aabad58a042addc825e27ffd0c..7578b4f9056b9be79645fa0eed9476ab9b80c509 100644 +index 9d5452597f64906ac1d3223ca5290776df8809c5..46ddad111b2feb5cc1064a1eeb424800d2cba6c1 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -9775,6 +9775,7 @@ void RenderFrameHostImpl::CreateNewWindow( +@@ -9777,6 +9777,7 @@ void RenderFrameHostImpl::CreateNewWindow( last_committed_origin_, params->window_container_type, params->target_url, params->referrer.To(), params->frame_name, params->disposition, *params->features, @@ -21,10 +21,10 @@ index 66c25476de83a9aabad58a042addc825e27ffd0c..7578b4f9056b9be79645fa0eed9476ab &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index d2715008c411519ed6c2491bf093a92e81d8d874..a99621ef317ec59f1368e5c7959f73de8ed32c54 100644 +index 77954ceccdfb1e94598d5d7ad747721ab84aa1d7..aec96f969800e2a4d09e644df770d367e48b1b63 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5131,6 +5131,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5132,6 +5132,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( SetPartitionedPopinOpenerOnNewWindowIfNeeded(new_contents_impl, params, opener); @@ -37,7 +37,7 @@ index d2715008c411519ed6c2491bf093a92e81d8d874..a99621ef317ec59f1368e5c7959f73de // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5172,12 +5178,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5173,12 +5179,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -66,7 +66,7 @@ index 55bb4ae3bab4cdf20b3e1dde9450a5c0e4e62b37..fe444c7fa140166a1b65c7a8a2676e2d // Operation result when the renderer asks the browser to create a new window. diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc -index b3975f65bfbcff7bc9eb0815a0ac5e97d1ff3548..2b219ccfdbef82f9e4075243da48c4b1e53158c2 100644 +index 210e5ffc0da31cc0d214e8a3e65f7d8b045fd33e..237b279eeefe5b18402a7dea8d1c00072655ed22 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc @@ -823,6 +823,8 @@ bool ContentBrowserClient::CanCreateWindow( @@ -79,7 +79,7 @@ index b3975f65bfbcff7bc9eb0815a0ac5e97d1ff3548..2b219ccfdbef82f9e4075243da48c4b1 bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 77b3e5c0fe47e5ed0139d3e54394f7d96fc69d21..cabdb73fa092683cdd2dad38f7b62b6bac974d0d 100644 +index be551d7a09330edf4a204b181acb382c2c3d13f4..5ed4df05dd22cbf901ecbbcc9d892de806c93890 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -199,6 +199,7 @@ class NetworkService; @@ -90,7 +90,7 @@ index 77b3e5c0fe47e5ed0139d3e54394f7d96fc69d21..cabdb73fa092683cdd2dad38f7b62b6b } // namespace network namespace sandbox { -@@ -1378,6 +1379,8 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -1379,6 +1380,8 @@ class CONTENT_EXPORT ContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -163,10 +163,10 @@ index 7f33a5452de32f5f4f8a43d0314917f24308d77c..b0aa018f2f4e6865915516ab6b65fac2 // moved on send. bool is_background_tab = diff --git a/content/web_test/browser/web_test_content_browser_client.cc b/content/web_test/browser/web_test_content_browser_client.cc -index 9af07ab542531bd3354cf28135f36044e88c0dfb..5d763af59aec30cdfb763b8bd5fa1383c4cb5568 100644 +index e5f7596c1b3e525e1d64efbd6b7e0703b980dac9..0b4523200651c1edfd7678b177a24b7e64de6ddf 100644 --- a/content/web_test/browser/web_test_content_browser_client.cc +++ b/content/web_test/browser/web_test_content_browser_client.cc -@@ -535,6 +535,8 @@ bool WebTestContentBrowserClient::CanCreateWindow( +@@ -538,6 +538,8 @@ bool WebTestContentBrowserClient::CanCreateWindow( const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -176,10 +176,10 @@ index 9af07ab542531bd3354cf28135f36044e88c0dfb..5d763af59aec30cdfb763b8bd5fa1383 bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/web_test/browser/web_test_content_browser_client.h b/content/web_test/browser/web_test_content_browser_client.h -index a7f5f09f9f5147b565f5934c6b467c4a4c04b626..2d44bafc6a7c81f7189934c61d88a5bb3e921266 100644 +index e4eaba65b25262ce5ed27d78da13a260ec57f6db..ddd3be9aa7aac43140a1e664eefce7ac195ba119 100644 --- a/content/web_test/browser/web_test_content_browser_client.h +++ b/content/web_test/browser/web_test_content_browser_client.h -@@ -94,6 +94,8 @@ class WebTestContentBrowserClient : public ShellContentBrowserClient { +@@ -95,6 +95,8 @@ class WebTestContentBrowserClient : public ShellContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, diff --git a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch index ee30ed47b66ac..393e2d4ba08bc 100644 --- a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch +++ b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch @@ -49,11 +49,11 @@ index ae7eab37f12ba80ec423d229cf048021e9ba6765..507a75dc7947295db221b01356fa57ba // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop class. diff --git a/ui/views/widget/widget_delegate.h b/ui/views/widget/widget_delegate.h -index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..e79beefddbd815e1ba7d9be86256e49d3ee7c619 100644 +index 89de188e6a0139a236a824b189f1048613d6f457..c438376c34cac4ec7ac7a03d852685c18b10068e 100644 --- a/ui/views/widget/widget_delegate.h +++ b/ui/views/widget/widget_delegate.h -@@ -169,6 +169,12 @@ namespace data_controls { - class DesktopDataControlsDialog; +@@ -165,6 +165,12 @@ namespace crostini { + class AppRestartDialog; } +namespace electron { @@ -65,7 +65,7 @@ index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..e79beefddbd815e1ba7d9be86256e49d namespace enterprise_connectors { class ContentAnalysisDialog; class ContentAnalysisDialogBehaviorBrowserTest; -@@ -371,6 +377,7 @@ class VIEWS_EXPORT WidgetDelegate { +@@ -367,6 +373,7 @@ class VIEWS_EXPORT WidgetDelegate { class OwnedByWidgetPassKey { private: @@ -73,7 +73,7 @@ index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..e79beefddbd815e1ba7d9be86256e49d // DO NOT ADD TO THIS LIST! // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop `SetOwnedByWidget()`. -@@ -468,6 +475,7 @@ class VIEWS_EXPORT WidgetDelegate { +@@ -463,6 +470,7 @@ class VIEWS_EXPORT WidgetDelegate { }; class RegisterDeleteCallbackPassKey { private: @@ -81,7 +81,7 @@ index 7c2463cb91d00de2b0fa4f10221ea960be860d9a..e79beefddbd815e1ba7d9be86256e49d // DO NOT ADD TO THIS LIST! // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop `RegisterDeleteDelegateCallback()`. -@@ -918,6 +926,7 @@ class VIEWS_EXPORT WidgetDelegateView : public WidgetDelegate, public View { +@@ -913,6 +921,7 @@ class VIEWS_EXPORT WidgetDelegateView : public WidgetDelegate, public View { View* GetContentsView() override; private: diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 3ca00573ac9c0..23a9de3f7ce4b 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index da05a4f28cc03bc555a99bd4e10097cd175b479c..dd94f88d353eb9291e2a64f0281e3fc1d53b68da 100644 +index 459fc0eff0bfe2ec005d6f34cf7e91c2d601fd06..35de681eac3f65ce3e0435bd984159154ece2b7f 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5050,7 +5050,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5051,7 +5051,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index f3d22875f651e..fe4b7c4242915 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -218,10 +218,10 @@ index c6838c83ef971b88769b1f3fba8095025ae25464..2da6a4e08340e72ba7de5d03444c2f17 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 5df2433b30213ba5683a864dcf42a07a5deb56e7..7500958c41904c61705d49f75b7a152005ce4890 100644 +index c1c3db2992038cad0c01ce65c57676f8fe281830..2ad1479de622d956c701d8dc4adb75d0114f65b1 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5013,8 +5013,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5014,8 +5014,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( // TODO(crbug.com/40202416): Support a way for MPArch guests to support this. if (delegate_ && delegate_->IsWebContentsCreationOverridden( source_site_instance, params.window_container_type, diff --git a/patches/chromium/disable_hidden.patch b/patches/chromium/disable_hidden.patch index 73058d53f01c4..5216b4a2ede5e 100644 --- a/patches/chromium/disable_hidden.patch +++ b/patches/chromium/disable_hidden.patch @@ -6,10 +6,10 @@ Subject: disable_hidden.patch Electron uses this to disable background throttling for hidden windows. diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 7b11077760d2a79312bd1871582733a7b0af71a0..8637d83c1d3a912bbc48effcc095b426640351ad 100644 +index b722e19e8c660d13750ea7bf505e28a9c1d9d59f..bac913e30ce140d9b370186781cccf5817885076 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -830,6 +830,10 @@ void RenderWidgetHostImpl::WasHidden() { +@@ -831,6 +831,10 @@ void RenderWidgetHostImpl::WasHidden() { return; } diff --git a/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch b/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch index 0506b9f8512ff..a7845a1f9938d 100644 --- a/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch +++ b/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch @@ -9,7 +9,7 @@ embedders to make custom schemes allow V8 code cache. Chromium CL: https://chromium-review.googlesource.com/c/chromium/src/+/5019665 diff --git a/content/browser/code_cache/generated_code_cache.cc b/content/browser/code_cache/generated_code_cache.cc -index cad3cf44df0c65067d18490ee7694fd0f82153af..0f9b64a81e0c4114bd885b24ff65c458810ceb99 100644 +index d6ddb79521290790aeb8fbd997117cf3c6157c75..52a9536f4187418327f980fd3dd68211d8103374 100644 --- a/content/browser/code_cache/generated_code_cache.cc +++ b/content/browser/code_cache/generated_code_cache.cc @@ -8,6 +8,7 @@ diff --git a/patches/chromium/feat_configure_launch_options_for_service_process.patch b/patches/chromium/feat_configure_launch_options_for_service_process.patch index 41b88cc8254f9..68b50ef8a8023 100644 --- a/patches/chromium/feat_configure_launch_options_for_service_process.patch +++ b/patches/chromium/feat_configure_launch_options_for_service_process.patch @@ -347,10 +347,10 @@ index d13e6db4857242480591bff040709532d16f513d..1164da12ee71a8575c17bf1b84a505e8 // launch failed. enum class LaunchState { diff --git a/content/browser/service_host/utility_sandbox_delegate.cc b/content/browser/service_host/utility_sandbox_delegate.cc -index 824afc2cfd01a0321d1b01cd370243dafefa1d24..ab77c85595dd5bde9eb9fd21f4914e1f9dfd4433 100644 +index 5ff3c5dcb972eb635107557ea7c26eb1f3331d22..5b1939226dcb84a61b09eefe69ab24a5ad595e1b 100644 --- a/content/browser/service_host/utility_sandbox_delegate.cc +++ b/content/browser/service_host/utility_sandbox_delegate.cc -@@ -38,17 +38,19 @@ UtilitySandboxedProcessLauncherDelegate:: +@@ -39,17 +39,19 @@ UtilitySandboxedProcessLauncherDelegate:: UtilitySandboxedProcessLauncherDelegate( sandbox::mojom::Sandbox sandbox_type, const base::EnvironmentMap& env, @@ -374,7 +374,7 @@ index 824afc2cfd01a0321d1b01cd370243dafefa1d24..ab77c85595dd5bde9eb9fd21f4914e1f #if DCHECK_IS_ON() bool supported_sandbox_type = sandbox_type_ == sandbox::mojom::Sandbox::kNoSandbox || -@@ -114,11 +116,28 @@ UtilitySandboxedProcessLauncherDelegate::GetSandboxType() { +@@ -115,11 +117,28 @@ UtilitySandboxedProcessLauncherDelegate::GetSandboxType() { return sandbox_type_; } diff --git a/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch b/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch index e177a7bf83e1e..9a8fc18059786 100644 --- a/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch +++ b/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch @@ -78,7 +78,7 @@ index 3d388a85aaf52acdcc2b7aaea56f5a24b2435bff..7a0d28cbf1651e76a4356f1193b502d2 } diff --git a/crypto/apple_keychain.h b/crypto/apple_keychain.h -index bcff49c4bcee4a67b97172c3abc12dedda1eedda..43e0b9f8b421a1c0dc62cc2d66b6fdd0eae496ce 100644 +index 605a6db7fd8de4e9863d1b98c78bb628e9600987..dccc5f565733875b1c9e54cbff7383eafd5370e4 100644 --- a/crypto/apple_keychain.h +++ b/crypto/apple_keychain.h @@ -18,6 +18,12 @@ @@ -143,10 +143,10 @@ index 12b400a1f2d6c11bc4ac67d0a2c98984d0be24e0..1abb4623bfabacbca34068113fac2030 MakeGenericPasswordQuery(service_name, account_name); diff --git a/crypto/apple_keychain_seckeychain.cc b/crypto/apple_keychain_seckeychain.cc -index 3fa4feac6de46a65bcb306329d0fc923525330ed..61a90e531c7cf8060425bf1cde571818d2da7979 100644 +index c7f015a4108f93ef121c7bb56c3d67634a723146..6d905154de42cbc151b5dfd77af277e5a5b021a0 100644 --- a/crypto/apple_keychain_seckeychain.cc +++ b/crypto/apple_keychain_seckeychain.cc -@@ -59,14 +59,15 @@ AppleKeychainSecKeychain::~AppleKeychainSecKeychain() = default; +@@ -26,14 +26,15 @@ AppleKeychainSecKeychain::~AppleKeychainSecKeychain() = default; base::expected, OSStatus> AppleKeychainSecKeychain::FindGenericPassword( std::string_view service_name, @@ -164,7 +164,7 @@ index 3fa4feac6de46a65bcb306329d0fc923525330ed..61a90e531c7cf8060425bf1cde571818 if (status != noErr) { return base::unexpected(status); } -@@ -92,6 +93,11 @@ OSStatus AppleKeychainSecKeychain::AddGenericPassword( +@@ -59,6 +60,11 @@ OSStatus AppleKeychainSecKeychain::AddGenericPassword( password.data(), nullptr); } @@ -173,9 +173,9 @@ index 3fa4feac6de46a65bcb306329d0fc923525330ed..61a90e531c7cf8060425bf1cde571818 + return SecKeychainItemDelete(item); +} + - ScopedKeychainUserInteractionAllowed::ScopedKeychainUserInteractionAllowed( - Boolean allowed, - OSStatus* status) { + #pragma clang diagnostic pop + + } // namespace crypto diff --git a/crypto/apple_keychain_seckeychain.h b/crypto/apple_keychain_seckeychain.h index ecf5e229c8f05a27574b635abc9c781d175c1773..6afb09c59011035337a287783bbef0c6b7d29d9a 100644 --- a/crypto/apple_keychain_seckeychain.h diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index 22c7bf7fa71b8..b54a7fbf346c6 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -28,10 +28,10 @@ The patch should be removed in favor of either: Upstream bug https://bugs.chromium.org/p/chromium/issues/detail?id=1081397. diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc -index dccc2e00d6bc52d25d35dbee95898a03960da28f..c3baeec8bbec12e4cb4d85413b77830d344b622c 100644 +index 0dbbaddc1bef8b5a1b253297f47c33601dc6fe67..0c84f727b29c742ba4c2edd38dfa16d1f48df76f 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc -@@ -11107,6 +11107,12 @@ NavigationRequest::GetOriginForURLLoaderFactoryUncheckedWithDebugInfo() { +@@ -11110,6 +11110,12 @@ NavigationRequest::GetOriginForURLLoaderFactoryUncheckedWithDebugInfo() { "blob"); } diff --git a/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch b/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch index eaabe6b5754fd..4abaf36574521 100644 --- a/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch +++ b/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch @@ -75,10 +75,10 @@ index 659e8d79766a78d261e58adab08f9abccda8390b..bc4dc2e3a93877d2e20890560f61d3f2 PictureInPictureOcclusionTracker* diff --git a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc -index dde04e0070cfd0a294d88fad3c32eadacf4030e8..de6816ba24a300b936c5ddbc1b5f1dd0f4865a9c 100644 +index 106f2c27297ab437839b3e320a5e5c657947b1c3..f2d4bb25647e9075df68ace24ed910d62a90c89e 100644 --- a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc +++ b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc -@@ -431,11 +431,13 @@ std::unique_ptr VideoOverlayWindowViews::Create( +@@ -432,11 +432,13 @@ std::unique_ptr VideoOverlayWindowViews::Create( #endif // BUILDFLAG(IS_WIN) diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 2c5bb43acc5be..6c073e3ef8b1f 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index c34bcb4f4a6ac03b4e3a6c87c3ac29e4450ffa71..da05a4f28cc03bc555a99bd4e10097cd175b479c 100644 +index 05a102a33f4c05fe6d34fa721d37fcae05a3a577..459fc0eff0bfe2ec005d6f34cf7e91c2d601fd06 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -9972,7 +9972,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -9970,7 +9970,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch index eb41286a9cb71..c8da4b6dacf58 100644 --- a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch +++ b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch @@ -11,10 +11,10 @@ This patch should be upstreamed as a conditional revert of the logic in desktop vs mobile runtimes. i.e. restore the old logic only on desktop platforms diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 3419628c08b62a16c62778cc124c365aa19adec2..b1143074421e4ac37f1dc7041104bea3de1eaa4b 100644 +index 8c3ac60d029a76b004111cffd56e9b859594dd65..d398cb9f429f8304eeb6ed00c79e609a3b83bd3f 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2120,9 +2120,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { +@@ -2121,9 +2121,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { void RenderWidgetHostImpl::NotifyScreenInfoChanged() { // The resize message (which may not happen immediately) will carry with it // the screen info as well as the new size (if the screen has changed scale diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index 089eb8077c218..ec428f880a1fd 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -20,10 +20,10 @@ index b61dfcc8e3306a2c3eb8808c204254af4ad8c248..cec49ddafd46b0296cc548a17efd6752 } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index cabdb73fa092683cdd2dad38f7b62b6bac974d0d..6bd13985764981ccbc547faccdec78bce18600a0 100644 +index 5ed4df05dd22cbf901ecbbcc9d892de806c93890..d0623992ce30b29b088a1b92e503f9e29087f193 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h -@@ -340,6 +340,11 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -341,6 +341,11 @@ class CONTENT_EXPORT ContentBrowserClient { virtual ~ContentBrowserClient() = default; diff --git a/patches/chromium/gritsettings_resource_ids.patch b/patches/chromium/gritsettings_resource_ids.patch index 867f2aa4fdef0..0c71a0a667737 100644 --- a/patches/chromium/gritsettings_resource_ids.patch +++ b/patches/chromium/gritsettings_resource_ids.patch @@ -6,7 +6,7 @@ Subject: gritsettings_resource_ids.patch Add electron resources file to the list of resource ids generation. diff --git a/tools/gritsettings/resource_ids.spec b/tools/gritsettings/resource_ids.spec -index 342b54311138a3d156bc19e8428e79d6a1477b80..9bd726519ef854f577d5a84eaca489b021e9dba8 100644 +index e9d1729c376bc36ac2c5b0a2c03ae03eb7e3dbff..18f1797d64573ee676e7f3337256d3199f91f29f 100644 --- a/tools/gritsettings/resource_ids.spec +++ b/tools/gritsettings/resource_ids.spec @@ -1508,6 +1508,11 @@ diff --git a/patches/chromium/gtk_visibility.patch b/patches/chromium/gtk_visibility.patch index 060a840d896af..d638360f20449 100644 --- a/patches/chromium/gtk_visibility.patch +++ b/patches/chromium/gtk_visibility.patch @@ -6,7 +6,7 @@ Subject: gtk_visibility.patch Allow electron to depend on GTK in the GN build. diff --git a/build/config/linux/gtk/BUILD.gn b/build/config/linux/gtk/BUILD.gn -index 4498487579ba5f4c7d8292f65c1afed16e41bb03..4ea4f38a91f02700373cb97e39125dcb0469b70b 100644 +index fdc3442590bddda969681d49c451d32f086bd5d1..b6fd63c0c845e5d7648e8693f1639b1f0f39a779 100644 --- a/build/config/linux/gtk/BUILD.gn +++ b/build/config/linux/gtk/BUILD.gn @@ -27,6 +27,7 @@ pkg_config("gtk_internal_config") { diff --git a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch index f52c337c296b2..4523a105b4f90 100644 --- a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch +++ b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch @@ -11,7 +11,7 @@ If removing this patch causes no sync failures, it's safe to delete :+1: Ref https://chromium-review.googlesource.com/c/chromium/src/+/2953903 diff --git a/tools/clang/scripts/update.py b/tools/clang/scripts/update.py -index 420c106a5f6fbbcfc77f2409e6272689ec71cf87..dad329cec5786323a981e150129c97357122c617 100755 +index f274064efd55d7c4691e207c7274f2cee677f4d8..a69cc4107d94268190a0f19a6e53dae231e227ef 100755 --- a/tools/clang/scripts/update.py +++ b/tools/clang/scripts/update.py @@ -307,6 +307,8 @@ def GetDefaultHostOs(): diff --git a/patches/chromium/make_gtk_getlibgtk_public.patch b/patches/chromium/make_gtk_getlibgtk_public.patch index 9a0c214c6a368..061d60815ece8 100644 --- a/patches/chromium/make_gtk_getlibgtk_public.patch +++ b/patches/chromium/make_gtk_getlibgtk_public.patch @@ -7,10 +7,10 @@ Allows embedders to get a handle to the gdk_pixbuf library already loaded in the process. diff --git a/ui/gtk/gtk_compat.cc b/ui/gtk/gtk_compat.cc -index f28cf275db0205186fe6143b7e1550b6c30a4435..346992e202c507eeac454d657507e1bd336175fc 100644 +index 946eb3eef6b0c546ace65de0c7f14b4642208090..9c9a35d439602ea3612ed648931990ec224c8799 100644 --- a/ui/gtk/gtk_compat.cc +++ b/ui/gtk/gtk_compat.cc -@@ -69,11 +69,6 @@ void* GetLibGio() { +@@ -70,11 +70,6 @@ void* GetLibGio() { return libgio; } @@ -22,7 +22,7 @@ index f28cf275db0205186fe6143b7e1550b6c30a4435..346992e202c507eeac454d657507e1bd void* GetLibGdk3() { static void* libgdk3 = DlOpen("libgdk-3.so.0"); return libgdk3; -@@ -150,6 +145,11 @@ gfx::Insets InsetsFromGtkBorder(const GtkBorder& border) { +@@ -170,6 +165,11 @@ gfx::Insets InsetsFromGtkBorder(const GtkBorder& border) { } // namespace diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index ca7b65cf54374..877fbfa40302a 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,10 +35,10 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index 82219748cc05ee4781731da17879f50dc1cea05f..25f5e50259e093d814271e53236d3be0647cb12b 100644 +index 5267ae3844f58d17e795c17184c85592157fda6f..21cab5e75e92570260df2e5fe4d2e404d2cb020a 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn -@@ -1045,6 +1045,7 @@ component("base") { +@@ -1046,6 +1046,7 @@ component("base") { "//build:ios_buildflags", "//build/config/compiler:compiler_buildflags", "//third_party/modp_b64", @@ -548,7 +548,7 @@ index dbf334caa3a6d10017b69ad76802e389a011436b..da828823e8195cc9e497866363c9af93 void ForwardKeyboardEvent(const input::NativeWebKeyboardEvent& key_event, diff --git a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -index 371b7b3ba73ee7b88027fcc31cb0a346cae40eea..c4b0654a56f4f2b4ab57ef05a119e38862b5fd2d 100644 +index f97ab6bdafbc35216b1935cf979443d071dd889f..e72d2347099c6549b5f9f318f99a1140839939e7 100644 --- a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm +++ b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm @@ -36,6 +36,7 @@ @@ -559,7 +559,7 @@ index 371b7b3ba73ee7b88027fcc31cb0a346cae40eea..c4b0654a56f4f2b4ab57ef05a119e388 #include "skia/ext/skia_utils_mac.h" #include "third_party/blink/public/common/features.h" #include "third_party/blink/public/mojom/input/input_handler.mojom.h" -@@ -2138,15 +2139,21 @@ - (NSAccessibilityRole)accessibilityRole { +@@ -2144,15 +2145,21 @@ - (NSAccessibilityRole)accessibilityRole { // Since this implementation doesn't have to wait any IPC calls, this doesn't // make any key-typing jank. --hbono 7/23/09 // @@ -582,10 +582,10 @@ index 371b7b3ba73ee7b88027fcc31cb0a346cae40eea..c4b0654a56f4f2b4ab57ef05a119e388 return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index cf87c4749846d98e56f130ac10c9004029f56464..27327923cfdd0c05ad0368b5f4678ff8ecf835fc 100644 +index 86e30304014f4811578595013a20a76790b1e84d..7964ac6af0fc3821b8208e34be766a712ccd2026 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -342,6 +342,7 @@ source_set("browser") { +@@ -343,6 +343,7 @@ source_set("browser") { "//ui/webui/resources", "//v8", "//v8:v8_version", @@ -797,10 +797,10 @@ index a1068589ad844518038ee7bc15a3de9bc5cba525..1ff781c49f086ec8015c7d3c44567dbe } // namespace content diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn -index 4c59b6c62ad3fed9717b0330c7b46b8dc83a51a1..1c88c8f449387258259bcd65c13709d70f03117b 100644 +index d72fc747932acd8cca621cd4bbfd3cb244c17da9..58687ab05e82b6d6314c979c88d77323dd7047e4 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn -@@ -662,6 +662,7 @@ static_library("test_support") { +@@ -664,6 +664,7 @@ static_library("test_support") { "//url", "//url/mojom:url_mojom_gurl", "//v8", @@ -808,7 +808,7 @@ index 4c59b6c62ad3fed9717b0330c7b46b8dc83a51a1..1c88c8f449387258259bcd65c13709d7 ] data_deps = [ -@@ -1117,6 +1118,7 @@ static_library("browsertest_support") { +@@ -1120,6 +1121,7 @@ static_library("browsertest_support") { } configs += [ "//v8:external_startup_data" ] @@ -816,7 +816,7 @@ index 4c59b6c62ad3fed9717b0330c7b46b8dc83a51a1..1c88c8f449387258259bcd65c13709d7 } mojom("content_test_mojo_bindings") { -@@ -1959,6 +1961,7 @@ test("content_browsertests") { +@@ -1962,6 +1964,7 @@ test("content_browsertests") { "//ui/shell_dialogs", "//ui/snapshot", "//ui/webui:test_support", @@ -824,7 +824,7 @@ index 4c59b6c62ad3fed9717b0330c7b46b8dc83a51a1..1c88c8f449387258259bcd65c13709d7 ] if (!(is_chromeos && target_cpu == "arm64" && current_cpu == "arm")) { -@@ -3284,6 +3287,7 @@ test("content_unittests") { +@@ -3292,6 +3295,7 @@ test("content_unittests") { "//ui/shell_dialogs:shell_dialogs", "//ui/webui:test_support", "//url", diff --git a/patches/chromium/notification_provenance.patch b/patches/chromium/notification_provenance.patch index c660a1744294a..293237d00ddd8 100644 --- a/patches/chromium/notification_provenance.patch +++ b/patches/chromium/notification_provenance.patch @@ -133,7 +133,7 @@ index 5be62a3fb27e37f3c1db6b811172f6dfebe18f61..34349f9832fe4b9a3d48db613a789afb const GURL& document_url, const WeakDocumentPtr& weak_document_ptr, diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index 6606217ec587846d995c4312f9a6ecd0a82b9ba1..63c4c7d56dd8677f37c2eed64166647c17b26d1c 100644 +index 3b2c512edec286bcc283a1cff14d96d469d8b4db..6e435b12521d663086be770bb89106368b06d159 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc @@ -2217,7 +2217,7 @@ void RenderProcessHostImpl::CreateNotificationService( diff --git a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch index 2a90b7ecb9aa5..5c89c799112c6 100644 --- a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch +++ b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch @@ -10,10 +10,10 @@ an about:blank check to this area. Ref: https://chromium-review.googlesource.com/c/chromium/src/+/5403876 diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index eaf36446678a3d079149377a6954c04f01573c8d..b060a69fef72b11d3bc932064d29e39ce827fb32 100644 +index fea0bbb8a9604ffbc4d8c5f061baff81c4824cde..a9f6d2233ce9953d1e1d96aea3a2ee717adbdc3b 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -807,8 +807,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( +@@ -809,8 +809,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( // TODO(crbug.com/40092527): Consider adding a separate boolean that // tracks this instead of piggybacking `origin_calculation_debug_info`. if (renderer_side_origin.opaque() && diff --git a/patches/chromium/picture-in-picture.patch b/patches/chromium/picture-in-picture.patch index ca5e66fc16797..5fd000554592b 100644 --- a/patches/chromium/picture-in-picture.patch +++ b/patches/chromium/picture-in-picture.patch @@ -38,7 +38,7 @@ index 8168b4cfbafd42fa93a5aa9a3691c2552fabfb86..ba49212bd76d209f99c1cee649fc1466 ui::ImageModel::FromVectorIcon(*icon, kColorPipWindowForeground, kCloseButtonIconSize)); diff --git a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc -index 2878aa40f60e977ecd2f7eedd37d1ce199472cf4..dde04e0070cfd0a294d88fad3c32eadacf4030e8 100644 +index c80abff87a34a8dfb94eec4c856438b458ad7936..106f2c27297ab437839b3e320a5e5c657947b1c3 100644 --- a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc +++ b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc @@ -19,9 +19,11 @@ @@ -53,7 +53,7 @@ index 2878aa40f60e977ecd2f7eedd37d1ce199472cf4..dde04e0070cfd0a294d88fad3c32eada #include "chrome/browser/ui/color/chrome_color_id.h" #include "chrome/browser/ui/views/overlay/back_to_tab_button.h" #include "chrome/browser/ui/views/overlay/back_to_tab_label_button.h" -@@ -72,7 +74,7 @@ +@@ -73,7 +75,7 @@ #include "ui/aura/window.h" #endif @@ -62,7 +62,7 @@ index 2878aa40f60e977ecd2f7eedd37d1ce199472cf4..dde04e0070cfd0a294d88fad3c32eada #include "chrome/browser/shell_integration_win.h" #include "content/public/browser/render_widget_host_view.h" #include "ui/aura/window.h" -@@ -396,7 +398,7 @@ std::unique_ptr VideoOverlayWindowViews::Create( +@@ -397,7 +399,7 @@ std::unique_ptr VideoOverlayWindowViews::Create( overlay_window->Init(std::move(params)); overlay_window->OnRootViewReady(); @@ -71,3 +71,16 @@ index 2878aa40f60e977ecd2f7eedd37d1ce199472cf4..dde04e0070cfd0a294d88fad3c32eada std::wstring app_user_model_id; Browser* browser = chrome::FindBrowserWithTab(controller->GetWebContents()); if (browser) { +@@ -1099,10 +1101,12 @@ void VideoOverlayWindowViews::SetUpViews() { + l10n_util::GetStringUTF16( + IDS_PICTURE_IN_PICTURE_LIVE_CAPTION_CONTROL_TEXT)); + live_caption_button->SetSize(kActionButtonSize); ++#if 0 + live_caption_dialog = std::make_unique( + Profile::FromBrowserContext( + controller_->GetWebContents()->GetBrowserContext())); + live_caption_dialog->SetVisible(false); ++#endif + toggle_microphone_button = + std::make_unique(base::BindRepeating( + [](VideoOverlayWindowViews* overlay) { diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index e59344c859369..63903f039b82d 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -881,10 +881,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 27327923cfdd0c05ad0368b5f4678ff8ecf835fc..0bff462eff763b5f5b1ecca6ca723c2c52199350 100644 +index 7964ac6af0fc3821b8208e34be766a712ccd2026..5bb585cb7f0ec4e15038bba89179817d43256719 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3154,8 +3154,9 @@ source_set("browser") { +@@ -3158,8 +3158,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 8de7f1a324267..54d5ffd829a74 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -30,10 +30,10 @@ index a54a0dedf8ef1cfffa4e80a4707debed0e83d277..e66e71fdbabb40a5307b12cd8965e773 // RenderWidgetHost on the primary main frame, and false otherwise. virtual bool IsWidgetForPrimaryMainFrame(RenderWidgetHostImpl*); diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 8637d83c1d3a912bbc48effcc095b426640351ad..3419628c08b62a16c62778cc124c365aa19adec2 100644 +index bac913e30ce140d9b370186781cccf5817885076..8c3ac60d029a76b004111cffd56e9b859594dd65 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2054,6 +2054,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { +@@ -2055,6 +2055,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { if (view_) { view_->UpdateCursor(cursor); } @@ -44,10 +44,10 @@ index 8637d83c1d3a912bbc48effcc095b426640351ad..3419628c08b62a16c62778cc124c365a void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index a99621ef317ec59f1368e5c7959f73de8ed32c54..5df2433b30213ba5683a864dcf42a07a5deb56e7 100644 +index aec96f969800e2a4d09e644df770d367e48b1b63..c1c3db2992038cad0c01ce65c57676f8fe281830 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5883,6 +5883,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -5884,6 +5884,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,7 +60,7 @@ index a99621ef317ec59f1368e5c7959f73de8ed32c54..5df2433b30213ba5683a864dcf42a07a RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index ebbefa02e163c9f38fc7057a592684f869c880e2..6d66b554acd09a32684ef6343db795134d9d5c15 100644 +index 91f52c79054c184142d15cfad6b24330a365c167..51cc85f9c998cc9234700ec47065d69eaac8d474 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h @@ -1183,6 +1183,7 @@ class CONTENT_EXPORT WebContentsImpl diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index fc4713889a17f..ff700d4a1c034 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index dd94f88d353eb9291e2a64f0281e3fc1d53b68da..60a21da52a9a0f301e3b5e320fe69e766951db4d 100644 +index 35de681eac3f65ce3e0435bd984159154ece2b7f..f2d5a85376109b6127ca4a7b3c26dbbb61990e20 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10109,25 +10109,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10107,25 +10107,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/render_widget_host_view_mac.patch b/patches/chromium/render_widget_host_view_mac.patch index f79f8356bd8ad..e370a1a90b8a5 100644 --- a/patches/chromium/render_widget_host_view_mac.patch +++ b/patches/chromium/render_widget_host_view_mac.patch @@ -8,7 +8,7 @@ respond to the first mouse click in their window, which is desirable for some kinds of utility windows. Similarly for `disableAutoHideCursor`. diff --git a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -index 91e5beaa68fc0b8231fce4bf195efa924744a532..371b7b3ba73ee7b88027fcc31cb0a346cae40eea 100644 +index a606a4870bd3f504c4bd6316aa3ab833621ab205..f97ab6bdafbc35216b1935cf979443d071dd889f 100644 --- a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm +++ b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm @@ -171,6 +171,15 @@ void ExtractUnderlines(NSAttributedString* string, @@ -27,7 +27,7 @@ index 91e5beaa68fc0b8231fce4bf195efa924744a532..371b7b3ba73ee7b88027fcc31cb0a346 // RenderWidgetHostViewCocoa --------------------------------------------------- // Private methods: -@@ -776,6 +785,9 @@ - (AcceptMouseEventsOption)acceptsMouseEventsOption { +@@ -782,6 +791,9 @@ - (AcceptMouseEventsOption)acceptsMouseEventsOption { } - (BOOL)acceptsFirstMouse:(NSEvent*)theEvent { @@ -37,7 +37,7 @@ index 91e5beaa68fc0b8231fce4bf195efa924744a532..371b7b3ba73ee7b88027fcc31cb0a346 // Enable "click-through" if mouse clicks are accepted in inactive windows return [self acceptsMouseEventsOption] > kAcceptMouseEventsInActiveWindow; } -@@ -921,6 +933,10 @@ - (BOOL)shouldIgnoreMouseEvent:(NSEvent*)theEvent { +@@ -927,6 +939,10 @@ - (BOOL)shouldIgnoreMouseEvent:(NSEvent*)theEvent { // its parent view. BOOL hitSelf = NO; while (view) { @@ -48,7 +48,7 @@ index 91e5beaa68fc0b8231fce4bf195efa924744a532..371b7b3ba73ee7b88027fcc31cb0a346 if (view == self) hitSelf = YES; if ([view isKindOfClass:[self class]] && ![view isEqual:self] && -@@ -1255,6 +1271,10 @@ - (void)keyEvent:(NSEvent*)theEvent wasKeyEquivalent:(BOOL)equiv { +@@ -1261,6 +1277,10 @@ - (void)keyEvent:(NSEvent*)theEvent wasKeyEquivalent:(BOOL)equiv { eventType == NSEventTypeKeyDown && !(modifierFlags & NSEventModifierFlagCommand); diff --git a/patches/chromium/support_mixed_sandbox_with_zygote.patch b/patches/chromium/support_mixed_sandbox_with_zygote.patch index 3072d7397b569..04f040a0ab5cf 100644 --- a/patches/chromium/support_mixed_sandbox_with_zygote.patch +++ b/patches/chromium/support_mixed_sandbox_with_zygote.patch @@ -22,7 +22,7 @@ However, the patch would need to be reviewed by the security team, as it does touch a security-sensitive class. diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index 63c4c7d56dd8677f37c2eed64166647c17b26d1c..9df359cf6f5b71259d1df6d7e0fd8044bfa1ff73 100644 +index 6e435b12521d663086be770bb89106368b06d159..2c53f5575bdc96ba53bacf8a40e752e7a41576d9 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc @@ -1825,6 +1825,10 @@ bool RenderProcessHostImpl::Init() { diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index df6f0eda01984..9c4faf566d657 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 7500958c41904c61705d49f75b7a152005ce4890..95bffa1a93ce1b103c129503414f7832d87fd493 100644 +index 2ad1479de622d956c701d8dc4adb75d0114f65b1..3d4510df709ed60a1da7163d3226541ed8ff201c 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -3952,6 +3952,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3953,6 +3953,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index 7500958c41904c61705d49f75b7a152005ce4890..95bffa1a93ce1b103c129503414f7832 std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -3962,6 +3969,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3963,6 +3970,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index 063f52d7498ea..aa03f837cd0aa 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,10 +15,10 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 7578b4f9056b9be79645fa0eed9476ab9b80c509..eaf36446678a3d079149377a6954c04f01573c8d 100644 +index 46ddad111b2feb5cc1064a1eeb424800d2cba6c1..fea0bbb8a9604ffbc4d8c5f061baff81c4824cde 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -8881,6 +8881,17 @@ void RenderFrameHostImpl::EnterFullscreen( +@@ -8883,6 +8883,17 @@ void RenderFrameHostImpl::EnterFullscreen( } } @@ -37,10 +37,10 @@ index 7578b4f9056b9be79645fa0eed9476ab9b80c509..eaf36446678a3d079149377a6954c04f if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 95bffa1a93ce1b103c129503414f7832d87fd493..c34bcb4f4a6ac03b4e3a6c87c3ac29e4450ffa71 100644 +index 3d4510df709ed60a1da7163d3226541ed8ff201c..05a102a33f4c05fe6d34fa721d37fcae05a3a577 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4227,21 +4227,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4228,21 +4228,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index 95bffa1a93ce1b103c129503414f7832d87fd493..c34bcb4f4a6ac03b4e3a6c87c3ac29e4 } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4400,7 +4404,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4401,7 +4405,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch index 68185410f669e..c4d93ad468547 100644 --- a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch +++ b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch @@ -10,10 +10,10 @@ to handle this without patching, but this is fairly clean for now and no longer patching legacy devtools code. diff --git a/front_end/entrypoints/main/MainImpl.ts b/front_end/entrypoints/main/MainImpl.ts -index 20ffe01d89e65b3eb6dc97b75761166ae3c9acb9..0444f2d81e53a01a81861c158713336a8062434f 100644 +index 69673b4aa636c2b55065aa11ce65dbc4a45c39b8..bdf133c0cdd524a72d3ad78fa97102b44c336f51 100644 --- a/front_end/entrypoints/main/MainImpl.ts +++ b/front_end/entrypoints/main/MainImpl.ts -@@ -736,6 +736,8 @@ export class MainImpl { +@@ -730,6 +730,8 @@ export class MainImpl { globalThis.Main = globalThis.Main || {}; // @ts-expect-error Exported for Tests.js globalThis.Main.Main = MainImpl; diff --git a/patches/node/.patches b/patches/node/.patches index 7e230586f067e..477f65d8fcc55 100644 --- a/patches/node/.patches +++ b/patches/node/.patches @@ -53,3 +53,4 @@ fix_cppgc_initializing_twice.patch fix_task_starvation_in_inspector_context_test.patch zlib_fix_pointer_alignment.patch fix_expose_readfilesync_override_for_modules.patch +test_force_slow_json_stringify_path_for_overflow.patch diff --git a/patches/node/test_force_slow_json_stringify_path_for_overflow.patch b/patches/node/test_force_slow_json_stringify_path_for_overflow.patch new file mode 100644 index 0000000000000..7d57385f74f11 --- /dev/null +++ b/patches/node/test_force_slow_json_stringify_path_for_overflow.patch @@ -0,0 +1,38 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Shelley Vohr +Date: Mon, 5 May 2025 13:04:14 +0000 +Subject: test: force slow JSON.stringify path for overflow + +Refs https://chromium-review.googlesource.com/c/v8/v8/+/6011806 + +The V8 team just enabled the JSON.stringify fast path by default, +which is iterative and won't throw. Pre-emptively preserve test +functionality by forcing the slow path. See above linked PR for +approach this is borrowed from. + +Upstreamed in https://github.com/nodejs/node/pull/58181. + +diff --git a/test/fixtures/console/stack_overflow.js b/test/fixtures/console/stack_overflow.js +index 565692b6d6e4ba4c439a38250407004c5aa21df9..14bceef878b5cf27609b29c8cc7852cab4dd63ff 100644 +--- a/test/fixtures/console/stack_overflow.js ++++ b/test/fixtures/console/stack_overflow.js +@@ -26,11 +26,15 @@ Error.stackTraceLimit = 0; + + console.error('before'); + ++// Invalidate elements protector to force slow-path. ++// The fast-path of JSON.stringify is iterative and won't throw. ++Array.prototype[2] = 'foo'; ++ + // Trigger stack overflow by stringifying a deeply nested array. +-let array = []; +-for (let i = 0; i < 100000; i++) { +- array = [ array ]; +-} ++// eslint-disable-next-line no-sparse-arrays ++let array = [,]; ++for (let i = 0; i < 10000; i++) ++ array = [array]; + + JSON.stringify(array); + diff --git a/shell/browser/electron_browser_client.cc b/shell/browser/electron_browser_client.cc index b63e5f41e5d6c..0895213cb9c9a 100644 --- a/shell/browser/electron_browser_client.cc +++ b/shell/browser/electron_browser_client.cc @@ -36,6 +36,7 @@ #include "content/public/browser/browser_task_traits.h" #include "content/public/browser/client_certificate_delegate.h" #include "content/public/browser/login_delegate.h" +#include "content/public/browser/navigation_throttle_registry.h" #include "content/public/browser/overlay_window.h" #include "content/public/browser/render_frame_host.h" #include "content/public/browser/render_process_host.h" @@ -954,8 +955,10 @@ bool ElectronBrowserClient::HandleExternalProtocol( std::vector> ElectronBrowserClient::CreateThrottlesForNavigation( - content::NavigationHandle* handle) { + content::NavigationThrottleRegistry& registry) { std::vector> throttles; + + content::NavigationHandle* handle = ®istry.GetNavigationHandle(); throttles.push_back(std::make_unique(handle)); #if BUILDFLAG(ENABLE_ELECTRON_EXTENSIONS) diff --git a/shell/browser/electron_browser_client.h b/shell/browser/electron_browser_client.h index fa1792268a6ef..219a137d77222 100644 --- a/shell/browser/electron_browser_client.h +++ b/shell/browser/electron_browser_client.h @@ -31,6 +31,7 @@ class FilePath; namespace content { class ClientCertificateDelegate; class PlatformNotificationService; +class NavigationThrottleRegistry; class QuotaPermissionContext; } // namespace content @@ -76,7 +77,8 @@ class ElectronBrowserClient : public content::ContentBrowserClient, // content::NavigatorDelegate std::vector> - CreateThrottlesForNavigation(content::NavigationHandle* handle) override; + CreateThrottlesForNavigation( + content::NavigationThrottleRegistry& registry) override; // content::ContentBrowserClient: std::string GetApplicationLocale() override; diff --git a/shell/browser/feature_list.cc b/shell/browser/feature_list.cc index 44fef97b0132b..17ccdbaa91644 100644 --- a/shell/browser/feature_list.cc +++ b/shell/browser/feature_list.cc @@ -19,6 +19,7 @@ #include "printing/buildflags/buildflags.h" #include "services/network/public/cpp/features.h" #include "third_party/blink/public/common/features.h" +#include "ui/accessibility/ax_features.mojom-features.h" #if BUILDFLAG(IS_MAC) #include "device/base/features.h" // nogncheck @@ -49,7 +50,10 @@ void InitializeFeatureList() { // Can be reenabled when our site instance policy is aligned with chromium // when node integration is enabled. disable_features += - std::string(",") + features::kSpareRendererForSitePerProcess.name; + std::string(",") + features::kSpareRendererForSitePerProcess.name + + // See https://chromium-review.googlesource.com/c/chromium/src/+/6487926 + // this breaks PDFs locally as we don't have GLIC infra enabled. + std::string(",") + ax::mojom::features::kScreenAIOCREnabled.name; #if BUILDFLAG(IS_WIN) disable_features += From 8189b019875e8f6b8ff572b995e7f598785abdeb Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 5 May 2025 16:28:15 -0500 Subject: [PATCH 016/186] docs: use correct heading level for API function (#46941) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Erick Zhao --- docs/api/app.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/api/app.md b/docs/api/app.md index 7bc011cf3d54e..281f606f64ecf 100644 --- a/docs/api/app.md +++ b/docs/api/app.md @@ -1490,7 +1490,7 @@ and internal requests made by the runtime (ex: geolocation queries). This method can only be called after app is ready. -#### `app.resolveProxy(url)` +### `app.resolveProxy(url)` * `url` URL From 7dfa2b92fb523e2f8b344de83740c695b3558f44 Mon Sep 17 00:00:00 2001 From: Charles Kerr Date: Tue, 6 May 2025 02:51:08 -0500 Subject: [PATCH 017/186] refactor: remove some `NativeWindow` public API (37-x-y) (#46934) refactor: remove some `NativeWindow` public API (#46919) * refactor: make NativeWindow::titlebar_overlay_height_ private * refactor: make NativeWindow::set_has_frame() protected * refactor: remove NativeWindow::background_material() It's only used once, in NativeWindow, so use |background_material_| directly. * refactor: remove NativeWindow::vibrancy() It's only used once, in a NativeWindow method, so use |vibrancy_| directly. * refactor: unfriend api::BrowserView It was added in Oct 2022 by 23d4a25 for access to protected NativeWindow methods add_inspectable_view() and remove_inspectable_view(). That dependency was removed in Nov 2022 by 184ac2b, so BrowserView doesn't need access to NativeWindow's private fields & methods anymore. * refactor: make NativeWindow::ContentBoundsToWindowBounds() protected refactor: make NativeWindow::WindowBoundsToContentBounds() protected --- shell/browser/native_window.cc | 7 ++----- shell/browser/native_window.h | 27 +++++++++++---------------- 2 files changed, 13 insertions(+), 21 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index f54f329ce5152..15d7fbc2a7b6e 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -818,17 +818,14 @@ bool NativeWindow::IsTranslucent() const { #if BUILDFLAG(IS_MAC) // Windows with vibrancy set are translucent - if (!vibrancy().empty()) { + if (!vibrancy_.empty()) return true; - } #endif #if BUILDFLAG(IS_WIN) // Windows with certain background materials may be translucent - const std::string& bg_material = background_material(); - if (!bg_material.empty() && bg_material != "none") { + if (!background_material_.empty() && background_material_ != "none") return true; - } #endif return false; diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index 0188c31735243..46970600038d6 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -230,12 +230,8 @@ class NativeWindow : public base::SupportsUserData, virtual void SetAutoHideCursor(bool auto_hide) {} // Vibrancy API - const std::string& vibrancy() const { return vibrancy_; } virtual void SetVibrancy(const std::string& type, int duration); - const std::string& background_material() const { - return background_material_; - } virtual void SetBackgroundMaterial(const std::string& type); // Traffic Light API @@ -291,12 +287,6 @@ class NativeWindow : public base::SupportsUserData, virtual void SetGTKDarkThemeEnabled(bool use_dark_theme) {} - // Converts between content bounds and window bounds. - virtual gfx::Rect ContentBoundsToWindowBounds( - const gfx::Rect& bounds) const = 0; - virtual gfx::Rect WindowBoundsToContentBounds( - const gfx::Rect& bounds) const = 0; - base::WeakPtr GetWeakPtr() { return weak_factory_.GetWeakPtr(); } @@ -407,7 +397,6 @@ class NativeWindow : public base::SupportsUserData, } bool has_frame() const { return has_frame_; } - void set_has_frame(bool has_frame) { has_frame_ = has_frame; } bool has_client_frame() const { return has_client_frame_; } bool transparent() const { return transparent_; } @@ -440,12 +429,18 @@ class NativeWindow : public base::SupportsUserData, void UpdateBackgroundThrottlingState(); protected: - friend class api::BrowserView; + constexpr void set_has_frame(const bool val) { has_frame_ = val; } [[nodiscard]] constexpr bool is_closed() const { return is_closed_; } NativeWindow(const gin_helper::Dictionary& options, NativeWindow* parent); + // Converts between content bounds and window bounds. + virtual gfx::Rect ContentBoundsToWindowBounds( + const gfx::Rect& bounds) const = 0; + virtual gfx::Rect WindowBoundsToContentBounds( + const gfx::Rect& bounds) const = 0; + // views::WidgetDelegate: views::Widget* GetWidget() override; const views::Widget* GetWidget() const override; @@ -462,10 +457,6 @@ class NativeWindow : public base::SupportsUserData, // The boolean parsing of the "titleBarOverlay" option bool titlebar_overlay_ = false; - // The custom height parsed from the "height" option in a Object - // "titleBarOverlay" - int titlebar_overlay_height_ = 0; - // The "titleBarStyle" option. TitleBarStyle title_bar_style_ = TitleBarStyle::kNormal; @@ -491,6 +482,10 @@ class NativeWindow : public base::SupportsUserData, // The content view, weak ref. raw_ptr content_view_ = nullptr; + // The custom height parsed from the "height" option in a Object + // "titleBarOverlay" + int titlebar_overlay_height_ = 0; + // Whether window has standard frame. bool has_frame_ = true; From cd023b54f5b7dd9a2ac759b583074435d90f4385 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Tue, 6 May 2025 10:29:19 +0200 Subject: [PATCH 018/186] chore: bump node to v22.15.0 (37-x-y) (#46869) * chore: bump node in DEPS to v22.15.0 * inspector: fix GN build https://github.com/nodejs/node/pull/56798 * test: search cctest files https://github.com/nodejs/node/pull/56791 * crypto: fix missing OPENSSL_NO_ENGINE guard https://github.com/nodejs/node/pull/57012 * test,crypto: make tests work for BoringSSL https://github.com/nodejs/node/pull/57021 * module: use synchronous hooks for preparsing in import(cjs) https://github.com/nodejs/node/pull/55698 * deps: update simdjson to 3.12.0 https://github.com/nodejs/node/pull/56874 * build: remove explicit linker call to libm on macOS https://github.com/nodejs/node/pull/56901 * test: make eval snapshot comparison more flexible https://github.com/nodejs/node/pull/57020 * src: allow embedder customization of OOMErrorHandler https://github.com/nodejs/node/pull/57325 * src: do not pass nullptr to std::string ctor https://github.com/nodejs/node/pull/57354 * src: lock the isolate properly in IsolateData destructor https://github.com/nodejs/node/pull/57031 * chore: shrink --trace-atomics-wait patch * chore: fixup patch indices * build: fix GN build failure https://github.com/nodejs/node/pull/57013 * crypto: expose security levels https://github.com/nodejs/node/pull/56601 * zlib: add zstd support https://github.com/nodejs/node/pull/52100 * test: move crypto related common utilities in common/crypto https://github.com/nodejs/node/pull/56714 * cli: move --trace-atomics-wait to eol https://github.com/nodejs/node/pull/52747 * test: disable test-https-client-renegotiation-limit BoringSSL doesn't support caller-initiated renegotiation - see https://source.chromium.org/chromium/chromium/src/+/main:third_party/boringssl/src/ssl/ssl_lib.cc;l=1627-1631 --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- DEPS | 2 +- ...ld_allow_electron_to_use_exec_script.patch | 5 +- patches/node/.patches | 4 - patches/node/build_add_gn_build_files.patch | 119 +-- ...w_unbundling_of_node_js_dependencies.patch | 10 +- ...etraits_signatures_to_avoid_conflict.patch | 4 +- .../build_compile_with_c_20_support.patch | 6 +- patches/node/build_enable_perfetto.patch | 6 +- ...compilation_fails_if_not_using_a_new.patch | 14 +- ...f_original-fs_and_custom_embedder_js.patch | 2 +- ...o_use_custom_inspector_protocol_path.patch | 8 +- ...xplicit_linker_call_to_libm_on_macos.patch | 59 -- ...e_clang_as_default_compiler_on_macos.patch | 4 +- ...deprecation_ftbfs_in_simdjson_header.patch | 21 +- ...e_expose_importmoduledynamically_and.patch | 12 +- ...cli_move_--trace-atomics-wait_to_eol.patch | 754 +----------------- .../node/cli_remove_deprecated_v8_flag.patch | 12 +- .../expose_get_builtin_module_function.patch | 2 +- ...ror_callback_in_node_isolatesettings.patch | 42 - patches/node/fix_-wnonnull_warning.patch | 43 - ..._values_for_variables_in_common_gypi.patch | 4 +- ...g_fileexists_fn_to_legacymainresolve.patch | 10 +- ...ssert_module_in_the_renderer_process.patch | 4 +- .../node/fix_cppgc_initializing_twice.patch | 2 +- .../fix_crypto_tests_to_run_with_bssl.patch | 69 +- ..._do_not_resolve_electron_entrypoints.patch | 4 +- ...se_readfilesync_override_for_modules.patch | 4 +- ...n_electron_module_via_the_esm_loader.patch | 12 +- ...ingssl_and_openssl_incompatibilities.patch | 81 +- ...in_esm_loaders_to_apply_asar_patches.patch | 15 +- ...ix_remove_deprecated_errno_constants.patch | 2 +- .../fix_remove_fastapitypedarray_usage.patch | 20 +- ...rmony-import-assertions_from_node_cc.patch | 2 +- .../pass_all_globals_through_require.patch | 6 +- ...dder_overriding_of_internal_fs_calls.patch | 4 +- ...ch_cppgc_heap_on_v8_isolate_creation.patch | 23 +- ..._on_wrapper-descriptor-based_cppheap.patch | 18 +- ...ted_fields_of_fastapicallbackoptions.patch | 8 +- .../node/support_v8_sandboxed_pointers.patch | 20 +- ...st_formally_mark_some_tests_as_flaky.patch | 2 +- ...ke_eval_snapshot_tests_more_flexible.patch | 83 -- patches/node/zlib_fix_pointer_alignment.patch | 8 +- script/node-disabled-tests.json | 1 + 43 files changed, 256 insertions(+), 1275 deletions(-) delete mode 100644 patches/node/build_remove_explicit_linker_call_to_libm_on_macos.patch delete mode 100644 patches/node/feat_add_oom_error_callback_in_node_isolatesettings.patch delete mode 100644 patches/node/fix_-wnonnull_warning.patch delete mode 100644 patches/node/test_make_eval_snapshot_tests_more_flexible.patch diff --git a/DEPS b/DEPS index d5be3c35f88b8..8ea86b2458522 100644 --- a/DEPS +++ b/DEPS @@ -4,7 +4,7 @@ vars = { 'chromium_version': '138.0.7160.0', 'node_version': - 'v22.14.0', + 'v22.15.0', 'nan_version': 'e14bdcd1f72d62bca1d541b66da43130384ec213', 'squirrel.mac_version': diff --git a/patches/chromium/build_allow_electron_to_use_exec_script.patch b/patches/chromium/build_allow_electron_to_use_exec_script.patch index 28413b2100db5..ab53106869c05 100644 --- a/patches/chromium/build_allow_electron_to_use_exec_script.patch +++ b/patches/chromium/build_allow_electron_to_use_exec_script.patch @@ -6,10 +6,10 @@ Subject: build: allow electron to use exec_script This is similar to the //build usecase so we're OK adding ourselves here diff --git a/.gn b/.gn -index ae58a0b0a64ae1fdb3f9cd8587041d71a121c6b9..7a1373c1cb78133375071cf5479561b64376b4dc 100644 +index ae58a0b0a64ae1fdb3f9cd8587041d71a121c6b9..0ed56526002b12deb6d29f3dd23a0d74d8e7473c 100644 --- a/.gn +++ b/.gn -@@ -167,4 +167,26 @@ exec_script_allowlist = +@@ -167,4 +167,27 @@ exec_script_allowlist = "//tools/grit/grit_rule.gni", "//tools/gritsettings/BUILD.gn", @@ -34,5 +34,6 @@ index ae58a0b0a64ae1fdb3f9cd8587041d71a121c6b9..7a1373c1cb78133375071cf5479561b6 + "//third_party/electron_node/deps/sqlite/unofficial.gni", + "//third_party/electron_node/deps/uv/unofficial.gni", + "//third_party/electron_node/deps/uvwasi/unofficial.gni", ++ "//third_party/electron_node/deps/zstd/unofficial.gni", + "//third_party/electron_node/src/inspector/unofficial.gni", ] diff --git a/patches/node/.patches b/patches/node/.patches index 477f65d8fcc55..b9f8f3b2719a9 100644 --- a/patches/node/.patches +++ b/patches/node/.patches @@ -38,14 +38,10 @@ build_use_third_party_simdutf.patch fix_remove_fastapitypedarray_usage.patch test_handle_explicit_resource_management_globals.patch linux_try_preadv64_pwritev64_before_preadv_pwritev_4683.patch -build_remove_explicit_linker_call_to_libm_on_macos.patch build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch -test_make_eval_snapshot_tests_more_flexible.patch build_option_to_use_custom_inspector_protocol_path.patch fix_adjust_wpt_and_webidl_tests_for_enabled_float16array.patch chore_add_createexternalizabletwobytestring_to_globals.patch -feat_add_oom_error_callback_in_node_isolatesettings.patch -fix_-wnonnull_warning.patch refactor_attach_cppgc_heap_on_v8_isolate_creation.patch fix_ensure_traverseparent_bails_on_resource_path_exit.patch cli_move_--trace-atomics-wait_to_eol.patch diff --git a/patches/node/build_add_gn_build_files.patch b/patches/node/build_add_gn_build_files.patch index 7076c3671a84a..d1d2ec6d8a637 100644 --- a/patches/node/build_add_gn_build_files.patch +++ b/patches/node/build_add_gn_build_files.patch @@ -54,71 +54,11 @@ index a2123cc6c6d21c53fafc8934203b3720393e7b11..245a43920c7baf000ba63192a84a4c3f } assert(!node_enable_inspector || node_use_openssl, -diff --git a/src/inspector/unofficial.gni b/src/inspector/unofficial.gni -index 5d87f3c901ab509e534598ed1eb0796a96355b5e..3d7aa148678b2646b88fa7c32abec91791b02b82 100644 ---- a/src/inspector/unofficial.gni -+++ b/src/inspector/unofficial.gni -@@ -13,7 +13,7 @@ template("inspector_gn_build") { - } - - node_gen_dir = get_label_info("../..", "target_gen_dir") -- protocol_tool_path = "../../tools/inspector_protocol" -+ protocol_tool_path = "../../deps/inspector_protocol" - - gypi_values = exec_script( - "../../tools/gypi_to_gn.py", -@@ -35,6 +35,8 @@ template("inspector_gn_build") { - ] - - args = [ -+ "--inspector_protocol_dir", -+ rebase_path(protocol_tool_path, root_build_dir), - "--jinja_dir", - # jinja is in third_party. - rebase_path("//third_party/", root_build_dir), -@@ -72,4 +74,37 @@ template("inspector_gn_build") { - outputs = [ "$node_gen_dir/src/{{source_name_part}}.json" ] - args = [ "{{source}}" ] + rebase_path(outputs, root_build_dir) - } -+ -+ config("crdtp_config") { -+ include_dirs = [ protocol_tool_path ] -+ } -+ -+ static_library("crdtp") { -+ public_configs = [ ":crdtp_config" ] -+ sources = [ -+ "$protocol_tool_path/crdtp/cbor.cc", -+ "$protocol_tool_path/crdtp/cbor.h", -+ "$protocol_tool_path/crdtp/dispatch.cc", -+ "$protocol_tool_path/crdtp/dispatch.h", -+ "$protocol_tool_path/crdtp/error_support.cc", -+ "$protocol_tool_path/crdtp/error_support.h", -+ "$protocol_tool_path/crdtp/export.h", -+ "$protocol_tool_path/crdtp/find_by_first.h", -+ "$protocol_tool_path/crdtp/frontend_channel.h", -+ "$protocol_tool_path/crdtp/glue.h", -+ "$protocol_tool_path/crdtp/json.cc", -+ "$protocol_tool_path/crdtp/json.h", -+ "$protocol_tool_path/crdtp/parser_handler.h", -+ "$protocol_tool_path/crdtp/protocol_core.cc", -+ "$protocol_tool_path/crdtp/protocol_core.h", -+ "$protocol_tool_path/crdtp/serializable.cc", -+ "$protocol_tool_path/crdtp/serializable.h", -+ "$protocol_tool_path/crdtp/span.cc", -+ "$protocol_tool_path/crdtp/span.h", -+ "$protocol_tool_path/crdtp/status.cc", -+ "$protocol_tool_path/crdtp/status.h", -+ "$protocol_tool_path/crdtp/json_platform.cc", -+ "$protocol_tool_path/crdtp/json_platform.h", -+ ] -+ } - } diff --git a/src/node_builtins.cc b/src/node_builtins.cc -index 894fd515202cc3a1f933c2bbc618dd09869ad904..4f1ed661e9c432f3b50f2e7e348ad9794ff773d0 100644 +index e85860de93dd5753dd4542ecee9f0888af93898a..04eab49c368c8f86837ed2c1384bf3c63e4bde24 100644 --- a/src/node_builtins.cc +++ b/src/node_builtins.cc -@@ -781,6 +781,7 @@ void BuiltinLoader::RegisterExternalReferences( +@@ -783,6 +783,7 @@ void BuiltinLoader::RegisterExternalReferences( registry->Register(GetNatives); RegisterExternalReferencesForInternalizedBuiltinCode(registry); @@ -306,7 +246,7 @@ index 21992cbe894a880e3223c379326b62db22f2f12d..1296a5457422099035ba34f2b02624f2 } // namespace js2c } // namespace node diff --git a/tools/search_files.py b/tools/search_files.py -index 65d0e1be42f0a85418491ebb548278cf431aa6a0..d4a31342f1c6107b029394c6e1d00a1d1e877e03 100755 +index 856878c33681a73d41016729dabe48b0a6a80589..91a11852d206b65485fe90fd037a0bd17a16c20b 100755 --- a/tools/search_files.py +++ b/tools/search_files.py @@ -14,6 +14,7 @@ if __name__ == '__main__': @@ -314,14 +254,19 @@ index 65d0e1be42f0a85418491ebb548278cf431aa6a0..d4a31342f1c6107b029394c6e1d00a1d files = SearchFiles(*sys.argv[2:]) files = [ os.path.relpath(x, sys.argv[1]) for x in files ] + files = [os.path.normpath(x).replace(os.sep, '/') for x in files] - print('\n'.join(files)) - except Exception as e: - print(str(e)) + # Apply the same transform in SearchFiles after relpath + if sys.platform == 'win32': + files = [ x.replace('\\', '/') for x in files ] diff --git a/unofficial.gni b/unofficial.gni -index 9e496d99d7141bf42ef7374a3c676c7b333eeeab..a2f3a769ceaa08db6d7438223884dc5aeab1340d 100644 +index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50ae50a3d8 100644 --- a/unofficial.gni +++ b/unofficial.gni -@@ -145,6 +145,7 @@ template("node_gn_build") { +@@ -142,32 +142,39 @@ template("node_gn_build") { + public_configs = [ + ":node_external_config", + "deps/googletest:googletest_config", ++ ":zstd_include_config" + ] public_deps = [ "deps/ada", "deps/uv", @@ -329,7 +274,11 @@ index 9e496d99d7141bf42ef7374a3c676c7b333eeeab..a2f3a769ceaa08db6d7438223884dc5a "deps/simdjson", "$node_v8_path", ] -@@ -156,7 +157,6 @@ template("node_gn_build") { + deps = [ + ":run_node_js2c", +- "deps/brotli", + "deps/cares", + "deps/histogram", "deps/llhttp", "deps/nbytes", "deps/nghttp2", @@ -337,7 +286,13 @@ index 9e496d99d7141bf42ef7374a3c676c7b333eeeab..a2f3a769ceaa08db6d7438223884dc5a "deps/postject", "deps/sqlite", "deps/uvwasi", -@@ -165,7 +165,11 @@ template("node_gn_build") { +- "deps/zstd", + "//third_party/zlib", ++ "//third_party/brotli:dec", ++ "//third_party/brotli:enc", ++ "//third_party/zstd:decompress", ++ "//third_party/zstd:headers", + "$node_simdutf_path", "$node_v8_path:v8_libplatform", ] @@ -349,7 +304,7 @@ index 9e496d99d7141bf42ef7374a3c676c7b333eeeab..a2f3a769ceaa08db6d7438223884dc5a "$target_gen_dir/node_javascript.cc", ] + gypi_values.node_sources -@@ -185,11 +189,12 @@ template("node_gn_build") { +@@ -190,7 +197,7 @@ template("node_gn_build") { } if (node_use_openssl) { deps += [ "deps/ncrypto" ] @@ -358,12 +313,18 @@ index 9e496d99d7141bf42ef7374a3c676c7b333eeeab..a2f3a769ceaa08db6d7438223884dc5a sources += gypi_values.node_crypto_sources } if (node_enable_inspector) { - deps += [ -+ "src/inspector:crdtp", - "src/inspector:node_protocol_generated_sources", - "src/inspector:v8_inspector_compress_protocol_json", - ] -@@ -282,6 +287,7 @@ template("node_gn_build") { +@@ -214,6 +221,10 @@ template("node_gn_build") { + } + } + ++ config("zstd_include_config") { ++ include_dirs = [ "//third_party/zstd/src/lib" ] ++ } ++ + executable(target_name) { + forward_variables_from(invoker, "*") + +@@ -288,6 +299,7 @@ template("node_gn_build") { } executable("node_js2c") { @@ -371,7 +332,7 @@ index 9e496d99d7141bf42ef7374a3c676c7b333eeeab..a2f3a769ceaa08db6d7438223884dc5a deps = [ "deps/uv", "$node_simdutf_path", -@@ -292,26 +298,75 @@ template("node_gn_build") { +@@ -298,26 +310,75 @@ template("node_gn_build") { "src/embedded_data.cc", "src/embedded_data.h", ] @@ -457,7 +418,7 @@ index 9e496d99d7141bf42ef7374a3c676c7b333eeeab..a2f3a769ceaa08db6d7438223884dc5a outputs = [ "$target_gen_dir/node_javascript.cc" ] # Get the path to node_js2c executable of the host toolchain. -@@ -325,11 +380,11 @@ template("node_gn_build") { +@@ -331,11 +392,11 @@ template("node_gn_build") { get_label_info(":node_js2c($host_toolchain)", "name") + host_executable_suffix diff --git a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch index 952cc525820fc..a38d9cc5f0074 100644 --- a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch +++ b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch @@ -14,10 +14,10 @@ We don't need to do this for zlib, as the existing gn workflow uses the same Upstreamed at https://github.com/nodejs/node/pull/55903 diff --git a/unofficial.gni b/unofficial.gni -index 08603eaef2da51fd92f9bf977647b56409eff48c..cd0eae52ca9bf244e43643a2034fa9d26c4db206 100644 +index 672e97436d9220e8d5046b0c92025f50ae50a3d8..a8ce18acfe333350f91b3e5f235db5f756b2e34a 100644 --- a/unofficial.gni +++ b/unofficial.gni -@@ -153,7 +153,6 @@ template("node_gn_build") { +@@ -155,7 +155,6 @@ template("node_gn_build") { ":run_node_js2c", "deps/cares", "deps/histogram", @@ -25,7 +25,7 @@ index 08603eaef2da51fd92f9bf977647b56409eff48c..cd0eae52ca9bf244e43643a2034fa9d2 "deps/nbytes", "deps/nghttp2", "deps/postject", -@@ -184,7 +183,17 @@ template("node_gn_build") { +@@ -191,7 +190,17 @@ template("node_gn_build") { configs -= [ "//build/config/gcc:symbol_visibility_hidden" ] configs += [ "//build/config/gcc:symbol_visibility_default" ] } @@ -44,7 +44,7 @@ index 08603eaef2da51fd92f9bf977647b56409eff48c..cd0eae52ca9bf244e43643a2034fa9d2 if (v8_enable_i18n_support) { deps += [ "//third_party/icu" ] } -@@ -212,6 +221,19 @@ template("node_gn_build") { +@@ -219,6 +228,19 @@ template("node_gn_build") { sources += node_inspector.node_inspector_sources + node_inspector.node_inspector_generated_sources } @@ -63,4 +63,4 @@ index 08603eaef2da51fd92f9bf977647b56409eff48c..cd0eae52ca9bf244e43643a2034fa9d2 + } } - executable(target_name) { + config("zstd_include_config") { diff --git a/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch b/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch index 9f5b3c70a4ef8..68cbb15ef5eaa 100644 --- a/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch +++ b/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch @@ -14,7 +14,7 @@ error: duplicate symbol: crdtp::ProtocolTypeTraits -Date: Mon, 3 Feb 2025 21:44:36 +0900 -Subject: build: remove explicit linker call to libm on macOS - -/usr/lib/libm.tbd is available via libSystem.*.dylib and -reexports sanitizer symbols. When building for asan -this becomes an issue as the linker will resolve the symbols -from the system library rather from libclang_rt.* - -For V8 that rely on specific version of these symbols -that get bundled as part of clang, for ex: -https://source.chromium.org/chromium/chromium/src/+/main:v8/src/heap/cppgc/platform.cc;l=93-97 -accepting nullptr for shadow_offset in `asan_get_shadow_mapping`, -linking to system version that doesn't support this will lead to -a crash. - -Clang driver eventually links with `-lSystem` -https://github.com/llvm/llvm-project/blob/e82f93890daefeb38fe2a22ee3db87a89948ec57/clang/lib/Driver/ToolChains/Darwin.cpp#L1628-L1631, -this is done after linking the sanitizer libraries which -ensures right order of resolution for the symbols. - -PR-URL: https://github.com/nodejs/node/pull/56901 -Reviewed-By: Joyee Cheung -Reviewed-By: Chengzhong Wu -Reviewed-By: Luigi Pinca -Reviewed-By: Shelley Vohr - -diff --git a/deps/brotli/unofficial.gni b/deps/brotli/unofficial.gni -index 5e07e106672a04508a77584c109c97a67926c858..91001fa43ea4807d061f296eaeccb7512e34863e 100644 ---- a/deps/brotli/unofficial.gni -+++ b/deps/brotli/unofficial.gni -@@ -25,7 +25,7 @@ template("brotli_gn_build") { - } else if (target_os == "freebsd") { - defines = [ "OS_FREEBSD" ] - } -- if (!is_win) { -+ if (is_linux) { - libs = [ "m" ] - } - if (is_clang || !is_win) { -diff --git a/deps/uv/unofficial.gni b/deps/uv/unofficial.gni -index 348d2f0703e47ca7c5326a4b4c1d6ae31157eeb5..0944d6ddd241b113970ab6aa5804f9534fde882a 100644 ---- a/deps/uv/unofficial.gni -+++ b/deps/uv/unofficial.gni -@@ -87,11 +87,11 @@ template("uv_gn_build") { - ] - } - if (is_posix) { -- libs = [ "m" ] - ldflags = [ "-pthread" ] - } - if (is_linux) { -- libs += [ -+ libs = [ -+ "m", - "dl", - "rt", - ] diff --git a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch index be9e0aeffa012..7c7f11672aebd 100644 --- a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch +++ b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch @@ -11,10 +11,10 @@ node-gyp will use the result of `process.config` that reflects the environment in which the binary got built. diff --git a/common.gypi b/common.gypi -index a7a0ffde7209de51ffcbf0db0ed7efcf09ad606d..20fd68eeb878b51f361d72070d87338db3d9a8d4 100644 +index 99b147482b636706b1372b89298f35b60ca2bb31..5024e5fb0aee210f4986572638a523db6d26b4cc 100644 --- a/common.gypi +++ b/common.gypi -@@ -125,6 +125,7 @@ +@@ -127,6 +127,7 @@ 'v8_base': '<(PRODUCT_DIR)/obj.target/tools/v8_gypfiles/libv8_snapshot.a', }], ['OS=="mac"', { diff --git a/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch b/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch index b07d10c2715ec..a51aa2f27749d 100644 --- a/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch +++ b/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch @@ -11,10 +11,10 @@ Without this patch, building with simdjson fails with This patch can be removed once this is fixed upstream in simdjson. diff --git a/deps/simdjson/simdjson.h b/deps/simdjson/simdjson.h -index f21cd9381eef59ec43502c796fcaddb1b96525f5..e691fd24aa24d225f8c00fa5638be07265bfeeab 100644 +index c1535ee81300b9cb93eb9ee6e769246793f936c3..3350287401e181e1d4ee432b8bd16081d0d7a73e 100644 --- a/deps/simdjson/simdjson.h +++ b/deps/simdjson/simdjson.h -@@ -3654,12 +3654,17 @@ inline std::ostream& operator<<(std::ostream& out, simdjson_result padded_string::load(std::string_view filen +@@ -4242,6 +4247,9 @@ inline simdjson_result padded_string::load(std::string_view filen } // namespace simdjson +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdeprecated-literal-operator" + - inline simdjson::padded_string operator "" _padded(const char *str, size_t len) { + inline simdjson::padded_string operator ""_padded(const char *str, size_t len) { return simdjson::padded_string(str, len); } -@@ -4045,6 +4053,8 @@ inline simdjson::padded_string operator "" _padded(const char8_t *str, size_t le +@@ -4250,6 +4258,8 @@ inline simdjson::padded_string operator ""_padded(const char8_t *str, size_t len return simdjson::padded_string(reinterpret_cast(str), len); } #endif @@ -51,10 +51,3 @@ index f21cd9381eef59ec43502c796fcaddb1b96525f5..e691fd24aa24d225f8c00fa5638be072 #endif // SIMDJSON_PADDED_STRING_INL_H /* end file simdjson/padded_string-inl.h */ /* skipped duplicate #include "simdjson/padded_string_view.h" */ -@@ -118292,4 +118302,4 @@ namespace simdjson { - /* end file simdjson/ondemand.h */ - - #endif // SIMDJSON_H --/* end file simdjson.h */ -+/* end file simdjson.h */ -\ No newline at end of file diff --git a/patches/node/chore_expose_importmoduledynamically_and.patch b/patches/node/chore_expose_importmoduledynamically_and.patch index 2596e1482f10d..5e9f79e6ff54d 100644 --- a/patches/node/chore_expose_importmoduledynamically_and.patch +++ b/patches/node/chore_expose_importmoduledynamically_and.patch @@ -11,7 +11,7 @@ its own blended handler between Node and Blink. Not upstreamable. diff --git a/lib/internal/modules/esm/utils.js b/lib/internal/modules/esm/utils.js -index 99061e62976e7cb24be81e8632b0e21d1e9adf9a..bbc9311c059e8ab0328c5f92b21a6be57620717e 100644 +index fd17ce8695c55f8f38ed19d59960acc1a7692bc8..96754db3277b3a0445b69275368602166c6d5423 100644 --- a/lib/internal/modules/esm/utils.js +++ b/lib/internal/modules/esm/utils.js @@ -30,7 +30,7 @@ const { @@ -23,7 +23,7 @@ index 99061e62976e7cb24be81e8632b0e21d1e9adf9a..bbc9311c059e8ab0328c5f92b21a6be5 const { loadPreloadModules, initializeFrozenIntrinsics, -@@ -274,12 +274,13 @@ let _forceDefaultLoader = false; +@@ -280,12 +280,13 @@ let _forceDefaultLoader = false; * @param {boolean} [forceDefaultLoader=false] - A boolean indicating disabling custom loaders. */ function initializeESM(forceDefaultLoader = false) { @@ -40,10 +40,10 @@ index 99061e62976e7cb24be81e8632b0e21d1e9adf9a..bbc9311c059e8ab0328c5f92b21a6be5 /** diff --git a/src/module_wrap.cc b/src/module_wrap.cc -index 649ec428e2dd6fbf0082b3f1ba9fdfbfab892a94..168912fe6ede3b71ab3029c292ba430915fd79d8 100644 +index 912acc8da815405531d8b527383f19c3731be100..8d48f4693c3b5f0d1d94d3edadc48c4f36d1bf97 100644 --- a/src/module_wrap.cc +++ b/src/module_wrap.cc -@@ -832,7 +832,7 @@ MaybeLocal ModuleWrap::ResolveModuleCallback( +@@ -858,7 +858,7 @@ MaybeLocal ModuleWrap::ResolveModuleCallback( return module->module_.Get(isolate); } @@ -52,7 +52,7 @@ index 649ec428e2dd6fbf0082b3f1ba9fdfbfab892a94..168912fe6ede3b71ab3029c292ba4309 Local context, Local host_defined_options, Local resource_name, -@@ -897,12 +897,13 @@ void ModuleWrap::SetImportModuleDynamicallyCallback( +@@ -923,12 +923,13 @@ void ModuleWrap::SetImportModuleDynamicallyCallback( Realm* realm = Realm::GetCurrent(args); HandleScope handle_scope(isolate); @@ -68,7 +68,7 @@ index 649ec428e2dd6fbf0082b3f1ba9fdfbfab892a94..168912fe6ede3b71ab3029c292ba4309 } void ModuleWrap::HostInitializeImportMetaObjectCallback( -@@ -944,13 +945,14 @@ void ModuleWrap::SetInitializeImportMetaObjectCallback( +@@ -970,13 +971,14 @@ void ModuleWrap::SetInitializeImportMetaObjectCallback( Realm* realm = Realm::GetCurrent(args); Isolate* isolate = realm->isolate(); diff --git a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch index a9a2aa7f1d2cc..70ae224eebb1a 100644 --- a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch +++ b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch @@ -15,747 +15,17 @@ Reviewed-By: Benjamin Gruenbaum Reviewed-By: Yagiz Nizipli diff --git a/doc/api/cli.md b/doc/api/cli.md -index 431a6aa7a2cf4d537cb719f15c2749254e0433b3..1d1672a01c4fae6b339cb144d0d6e35b49209a14 100644 +index 114b7bbf6b1e105fc1696ed8a064065db73ff519..ad863e52761332c3249a86af0e3d239cd0f73b03 100644 --- a/doc/api/cli.md +++ b/doc/api/cli.md -@@ -32,11 +32,11 @@ is passed. If no corresponding file is found, an error is thrown. - If a file is found, its path will be passed to the - [ES module loader][Modules loaders] under any of the following conditions: - --* The program was started with a command-line flag that forces the entry -+- The program was started with a command-line flag that forces the entry - point to be loaded with ECMAScript module loader, such as `--import` or - [`--experimental-default-type=module`][]. --* The file has an `.mjs` extension. --* The file does not have a `.cjs` extension, and the nearest parent -+- The file has an `.mjs` extension. -+- The file does not have a `.cjs` extension, and the nearest parent - `package.json` file contains a top-level [`"type"`][] field with a value of - `"module"`. - -@@ -164,7 +164,10 @@ Example: - ```js - const childProcess = require('node:child_process'); - // Attempt to bypass the permission --childProcess.spawn('node', ['-e', 'require("fs").writeFileSync("/new-file", "example")']); -+childProcess.spawn('node', [ -+ '-e', -+ 'require("fs").writeFileSync("/new-file", "example")', -+]); - ``` - - ```console -@@ -206,8 +209,8 @@ the [Permission Model][]. - - The valid arguments for the `--allow-fs-read` flag are: - --* `*` - To allow all `FileSystemRead` operations. --* Multiple paths can be allowed using multiple `--allow-fs-read` flags. -+- `*` - To allow all `FileSystemRead` operations. -+- Multiple paths can be allowed using multiple `--allow-fs-read` flags. - Example `--allow-fs-read=/folder1/ --allow-fs-read=/folder1/` - - Examples can be found in the [File System Permissions][] documentation. -@@ -251,8 +254,8 @@ the [Permission Model][]. - - The valid arguments for the `--allow-fs-write` flag are: - --* `*` - To allow all `FileSystemWrite` operations. --* Multiple paths can be allowed using multiple `--allow-fs-write` flags. -+- `*` - To allow all `FileSystemWrite` operations. -+- Multiple paths can be allowed using multiple `--allow-fs-write` flags. - Example `--allow-fs-write=/folder1/ --allow-fs-write=/folder1/` - - Paths delimited by comma (`,`) are no longer allowed. -@@ -399,10 +402,10 @@ creation behavior. - - The following options are currently supported: - --* `builder` {string} Required. Provides the name to the script that is executed -+- `builder` {string} Required. Provides the name to the script that is executed - before building the snapshot, as if [`--build-snapshot`][] had been passed - with `builder` as the main script name. --* `withoutCodeCache` {boolean} Optional. Including the code cache reduces the -+- `withoutCodeCache` {boolean} Optional. Including the code cache reduces the - time spent on compiling functions included in the snapshot at the expense - of a bigger snapshot size and potentially breaking portability of the - snapshot. -@@ -550,9 +553,9 @@ Defaults to current working directory. - - Affects the default output directory of: - --* [`--cpu-prof-dir`][] --* [`--heap-prof-dir`][] --* [`--redirect-warnings`][] -+- [`--cpu-prof-dir`][] -+- [`--heap-prof-dir`][] -+- [`--redirect-warnings`][] - - ### `--disable-proto=mode` - -@@ -697,9 +700,9 @@ changes: - Set the default value of `order` in [`dns.lookup()`][] and - [`dnsPromises.lookup()`][]. The value could be: - --* `ipv4first`: sets default `order` to `ipv4first`. --* `ipv6first`: sets default `order` to `ipv6first`. --* `verbatim`: sets default `order` to `verbatim`. -+- `ipv4first`: sets default `order` to `ipv4first`. -+- `ipv6first`: sets default `order` to `ipv6first`. -+- `verbatim`: sets default `order` to `verbatim`. - - The default is `verbatim` and [`dns.setDefaultResultOrder()`][] have higher - priority than `--dns-result-order`. -@@ -890,7 +893,7 @@ added: v22.7.0 - > Stability: 1 - Experimental - - Enables the use of [`AsyncLocalStorage`][] backed by `AsyncContextFrame` rather --than the default implementation which relies on async\_hooks. This new model is -+than the default implementation which relies on async_hooks. This new model is - implemented very differently and so could have differences in how context data - flows within the application. As such, it is presently recommended to be sure - your application behaviour is unaffected by this change before using it in -@@ -909,12 +912,12 @@ added: - - Define which module system, `module` or `commonjs`, to use for the following: - --* String input provided via `--eval` or STDIN, if `--input-type` is unspecified. -+- String input provided via `--eval` or STDIN, if `--input-type` is unspecified. - --* Files ending in `.js` or with no extension, if there is no `package.json` file -+- Files ending in `.js` or with no extension, if there is no `package.json` file - present in the same folder or any parent folder. - --* Files ending in `.js` or with no extension, if the nearest parent -+- Files ending in `.js` or with no extension, if the nearest parent - `package.json` field lacks a `"type"` field; unless the `package.json` folder - or any parent folder is inside a `node_modules` folder. - -@@ -1450,15 +1453,15 @@ interoperability with non-conformant HTTP implementations. - - When enabled, the parser will accept the following: - --* Invalid HTTP headers values. --* Invalid HTTP versions. --* Allow message containing both `Transfer-Encoding` -+- Invalid HTTP headers values. -+- Invalid HTTP versions. -+- Allow message containing both `Transfer-Encoding` - and `Content-Length` headers. --* Allow extra data after message when `Connection: close` is present. --* Allow extra transfer encodings after `chunked` has been provided. --* Allow `\n` to be used as token separator instead of `\r\n`. --* Allow `\r\n` not to be provided after a chunk. --* Allow spaces to be present after a chunk size and before `\r\n`. -+- Allow extra data after message when `Connection: close` is present. -+- Allow extra transfer encodings after `chunked` has been provided. -+- Allow `\n` to be used as token separator instead of `\r\n`. -+- Allow `\r\n` not to be provided after a chunk. -+- Allow spaces to be present after a chunk size and before `\r\n`. - - All the above will expose your application to request smuggling - or poisoning attack. Avoid using this option. -@@ -1536,8 +1539,8 @@ a [remote code execution][] attack. - - If specifying a host, make sure that either: - --* The host is not accessible from public networks. --* A firewall disallows unwanted connections on the port. -+- The host is not accessible from public networks. -+- A firewall disallows unwanted connections on the port. - - **More specifically, `--inspect=0.0.0.0` is insecure if the port (`9229` by - default) is not firewall-protected.** -@@ -1799,7 +1802,7 @@ added: - --> - - Enable OpenSSL 3.0 legacy provider. For more information please see --[OSSL\_PROVIDER-legacy][OSSL_PROVIDER-legacy]. -+[OSSL_PROVIDER-legacy][OSSL_PROVIDER-legacy]. - - ### `--openssl-shared-config` - -@@ -1849,12 +1852,12 @@ changes: - Enable the Permission Model for current process. When enabled, the - following permissions are restricted: - --* File System - manageable through -+- File System - manageable through - [`--allow-fs-read`][], [`--allow-fs-write`][] flags --* Child Process - manageable through [`--allow-child-process`][] flag --* Worker Threads - manageable through [`--allow-worker`][] flag --* WASI - manageable through [`--allow-wasi`][] flag --* Addons - manageable through [`--allow-addons`][] flag -+- Child Process - manageable through [`--allow-child-process`][] flag -+- Worker Threads - manageable through [`--allow-worker`][] flag -+- WASI - manageable through [`--allow-wasi`][] flag -+- Addons - manageable through [`--allow-addons`][] flag - - ### `--preserve-symlinks` - -@@ -2194,16 +2197,16 @@ cases. - Some features of other `run` implementations that are intentionally excluded - are: - --* Running `pre` or `post` scripts in addition to the specified script. --* Defining package manager-specific environment variables. -+- Running `pre` or `post` scripts in addition to the specified script. -+- Defining package manager-specific environment variables. - - #### Environment variables - - The following environment variables are set when running a script with `--run`: - --* `NODE_RUN_SCRIPT_NAME`: The name of the script being run. For example, if -+- `NODE_RUN_SCRIPT_NAME`: The name of the script being run. For example, if - `--run` is used to run `test`, the value of this variable will be `test`. --* `NODE_RUN_PACKAGE_JSON_PATH`: The path to the `package.json` that is being -+- `NODE_RUN_PACKAGE_JSON_PATH`: The path to the `package.json` that is being - processed. - - ### `--secure-heap-min=n` -@@ -2601,39 +2604,6 @@ added: v12.0.0 - Set default [`tls.DEFAULT_MIN_VERSION`][] to 'TLSv1.3'. Use to disable support - for TLSv1.2, which is not as secure as TLSv1.3. - --### `--trace-atomics-wait` -- -- -- --> Stability: 0 - Deprecated -- --Print short summaries of calls to [`Atomics.wait()`][] to stderr. --The output could look like this: -- --```text --(node:15701) [Thread 0] Atomics.wait(<address> + 0, 1, inf) started --(node:15701) [Thread 0] Atomics.wait(<address> + 0, 1, inf) did not wait because the values mismatched --(node:15701) [Thread 0] Atomics.wait(<address> + 0, 0, 10) started --(node:15701) [Thread 0] Atomics.wait(<address> + 0, 0, 10) timed out --(node:15701) [Thread 0] Atomics.wait(<address> + 4, 0, inf) started --(node:15701) [Thread 1] Atomics.wait(<address> + 4, -1, inf) started --(node:15701) [Thread 0] Atomics.wait(<address> + 4, 0, inf) was woken up by another thread --(node:15701) [Thread 1] Atomics.wait(<address> + 4, -1, inf) was woken up by another thread --``` -- --The fields here correspond to: -- --* The thread id as given by [`worker_threads.threadId`][] --* The base address of the `SharedArrayBuffer` in question, as well as the -- byte offset corresponding to the index passed to `Atomics.wait()` --* The expected value that was passed to `Atomics.wait()` --* The timeout passed to `Atomics.wait` -- - ### `--trace-deprecation` - - - --* `--allow-addons` --* `--allow-child-process` --* `--allow-fs-read` --* `--allow-fs-write` --* `--allow-wasi` --* `--allow-worker` --* `--conditions`, `-C` --* `--diagnostic-dir` --* `--disable-proto` --* `--disable-sigusr1` --* `--disable-warning` --* `--disable-wasm-trap-handler` --* `--dns-result-order` --* `--enable-fips` --* `--enable-network-family-autoselection` --* `--enable-source-maps` --* `--entry-url` --* `--experimental-abortcontroller` --* `--experimental-async-context-frame` --* `--experimental-default-type` --* `--experimental-detect-module` --* `--experimental-eventsource` --* `--experimental-import-meta-resolve` --* `--experimental-json-modules` --* `--experimental-loader` --* `--experimental-modules` --* `--experimental-permission` --* `--experimental-print-required-tla` --* `--experimental-require-module` --* `--experimental-shadow-realm` --* `--experimental-specifier-resolution` --* `--experimental-strip-types` --* `--experimental-top-level-await` --* `--experimental-transform-types` --* `--experimental-vm-modules` --* `--experimental-wasi-unstable-preview1` --* `--experimental-wasm-modules` --* `--experimental-webstorage` --* `--force-context-aware` --* `--force-fips` --* `--force-node-api-uncaught-exceptions-policy` --* `--frozen-intrinsics` --* `--heap-prof-dir` --* `--heap-prof-interval` --* `--heap-prof-name` --* `--heap-prof` --* `--heapsnapshot-near-heap-limit` --* `--heapsnapshot-signal` --* `--http-parser` --* `--icu-data-dir` --* `--import` --* `--input-type` --* `--insecure-http-parser` --* `--inspect-brk` --* `--inspect-port`, `--debug-port` --* `--inspect-publish-uid` --* `--inspect-wait` --* `--inspect` --* `--localstorage-file` --* `--max-http-header-size` --* `--napi-modules` --* `--network-family-autoselection-attempt-timeout` --* `--no-addons` --* `--no-deprecation` --* `--no-experimental-fetch` --* `--no-experimental-global-customevent` --* `--no-experimental-global-navigator` --* `--no-experimental-global-webcrypto` --* `--no-experimental-repl-await` --* `--no-experimental-sqlite` --* `--no-experimental-websocket` --* `--no-extra-info-on-fatal-exception` --* `--no-force-async-hooks-checks` --* `--no-global-search-paths` --* `--no-network-family-autoselection` --* `--no-warnings` --* `--node-memory-debug` --* `--openssl-config` --* `--openssl-legacy-provider` --* `--openssl-shared-config` --* `--pending-deprecation` --* `--permission` --* `--preserve-symlinks-main` --* `--preserve-symlinks` --* `--prof-process` --* `--redirect-warnings` --* `--report-compact` --* `--report-dir`, `--report-directory` --* `--report-exclude-env` --* `--report-exclude-network` --* `--report-filename` --* `--report-on-fatalerror` --* `--report-on-signal` --* `--report-signal` --* `--report-uncaught-exception` --* `--require`, `-r` --* `--secure-heap-min` --* `--secure-heap` --* `--snapshot-blob` --* `--test-coverage-branches` --* `--test-coverage-exclude` --* `--test-coverage-functions` --* `--test-coverage-include` --* `--test-coverage-lines` --* `--test-name-pattern` --* `--test-only` --* `--test-reporter-destination` --* `--test-reporter` --* `--test-shard` --* `--test-skip-pattern` --* `--throw-deprecation` --* `--title` --* `--tls-cipher-list` --* `--tls-keylog` --* `--tls-max-v1.2` --* `--tls-max-v1.3` --* `--tls-min-v1.0` --* `--tls-min-v1.1` --* `--tls-min-v1.2` --* `--tls-min-v1.3` +@@ -3313,7 +3313,6 @@ one is included in the list below. + * `--tls-min-v1.1` + * `--tls-min-v1.2` + * `--tls-min-v1.3` -* `--trace-atomics-wait` --* `--trace-deprecation` --* `--trace-env-js-stack` --* `--trace-env-native-stack` --* `--trace-env` --* `--trace-event-categories` --* `--trace-event-file-pattern` --* `--trace-events-enabled` --* `--trace-exit` --* `--trace-require-module` --* `--trace-sigint` --* `--trace-sync-io` --* `--trace-tls` --* `--trace-uncaught` --* `--trace-warnings` --* `--track-heap-objects` --* `--unhandled-rejections` --* `--use-bundled-ca` --* `--use-largepages` --* `--use-openssl-ca` --* `--v8-pool-size` --* `--watch-path` --* `--watch-preserve-output` --* `--watch` --* `--zero-fill-buffers` -+- `--allow-addons` -+- `--allow-child-process` -+- `--allow-fs-read` -+- `--allow-fs-write` -+- `--allow-wasi` -+- `--allow-worker` -+- `--conditions`, `-C` -+- `--diagnostic-dir` -+- `--disable-proto` -+- `--disable-sigusr1` -+- `--disable-warning` -+- `--disable-wasm-trap-handler` -+- `--dns-result-order` -+- `--enable-fips` -+- `--enable-network-family-autoselection` -+- `--enable-source-maps` -+- `--entry-url` -+- `--experimental-abortcontroller` -+- `--experimental-async-context-frame` -+- `--experimental-default-type` -+- `--experimental-detect-module` -+- `--experimental-eventsource` -+- `--experimental-import-meta-resolve` -+- `--experimental-json-modules` -+- `--experimental-loader` -+- `--experimental-modules` -+- `--experimental-permission` -+- `--experimental-print-required-tla` -+- `--experimental-require-module` -+- `--experimental-shadow-realm` -+- `--experimental-specifier-resolution` -+- `--experimental-strip-types` -+- `--experimental-top-level-await` -+- `--experimental-transform-types` -+- `--experimental-vm-modules` -+- `--experimental-wasi-unstable-preview1` -+- `--experimental-wasm-modules` -+- `--experimental-webstorage` -+- `--force-context-aware` -+- `--force-fips` -+- `--force-node-api-uncaught-exceptions-policy` -+- `--frozen-intrinsics` -+- `--heap-prof-dir` -+- `--heap-prof-interval` -+- `--heap-prof-name` -+- `--heap-prof` -+- `--heapsnapshot-near-heap-limit` -+- `--heapsnapshot-signal` -+- `--http-parser` -+- `--icu-data-dir` -+- `--import` -+- `--input-type` -+- `--insecure-http-parser` -+- `--inspect-brk` -+- `--inspect-port`, `--debug-port` -+- `--inspect-publish-uid` -+- `--inspect-wait` -+- `--inspect` -+- `--localstorage-file` -+- `--max-http-header-size` -+- `--napi-modules` -+- `--network-family-autoselection-attempt-timeout` -+- `--no-addons` -+- `--no-deprecation` -+- `--no-experimental-fetch` -+- `--no-experimental-global-customevent` -+- `--no-experimental-global-navigator` -+- `--no-experimental-global-webcrypto` -+- `--no-experimental-repl-await` -+- `--no-experimental-sqlite` -+- `--no-experimental-websocket` -+- `--no-extra-info-on-fatal-exception` -+- `--no-force-async-hooks-checks` -+- `--no-global-search-paths` -+- `--no-network-family-autoselection` -+- `--no-warnings` -+- `--node-memory-debug` -+- `--openssl-config` -+- `--openssl-legacy-provider` -+- `--openssl-shared-config` -+- `--pending-deprecation` -+- `--permission` -+- `--preserve-symlinks-main` -+- `--preserve-symlinks` -+- `--prof-process` -+- `--redirect-warnings` -+- `--report-compact` -+- `--report-dir`, `--report-directory` -+- `--report-exclude-env` -+- `--report-exclude-network` -+- `--report-filename` -+- `--report-on-fatalerror` -+- `--report-on-signal` -+- `--report-signal` -+- `--report-uncaught-exception` -+- `--require`, `-r` -+- `--secure-heap-min` -+- `--secure-heap` -+- `--snapshot-blob` -+- `--test-coverage-branches` -+- `--test-coverage-exclude` -+- `--test-coverage-functions` -+- `--test-coverage-include` -+- `--test-coverage-lines` -+- `--test-name-pattern` -+- `--test-only` -+- `--test-reporter-destination` -+- `--test-reporter` -+- `--test-shard` -+- `--test-skip-pattern` -+- `--throw-deprecation` -+- `--title` -+- `--tls-cipher-list` -+- `--tls-keylog` -+- `--tls-max-v1.2` -+- `--tls-max-v1.3` -+- `--tls-min-v1.0` -+- `--tls-min-v1.1` -+- `--tls-min-v1.2` -+- `--tls-min-v1.3` -+- `--trace-deprecation` -+- `--trace-env-js-stack` -+- `--trace-env-native-stack` -+- `--trace-env` -+- `--trace-event-categories` -+- `--trace-event-file-pattern` -+- `--trace-events-enabled` -+- `--trace-exit` -+- `--trace-require-module` -+- `--trace-sigint` -+- `--trace-sync-io` -+- `--trace-tls` -+- `--trace-uncaught` -+- `--trace-warnings` -+- `--track-heap-objects` -+- `--unhandled-rejections` -+- `--use-bundled-ca` -+- `--use-largepages` -+- `--use-openssl-ca` -+- `--v8-pool-size` -+- `--watch-path` -+- `--watch-preserve-output` -+- `--watch` -+- `--zero-fill-buffers` - - - -@@ -3266,19 +3235,19 @@ V8 options that are allowed are: - - - --* `--abort-on-uncaught-exception` --* `--disallow-code-generation-from-strings` --* `--enable-etw-stack-walking` --* `--expose-gc` --* `--interpreted-frames-native-stack` --* `--jitless` --* `--max-old-space-size` --* `--max-semi-space-size` --* `--perf-basic-prof-only-functions` --* `--perf-basic-prof` --* `--perf-prof-unwinding-info` --* `--perf-prof` --* `--stack-trace-limit` -+- `--abort-on-uncaught-exception` -+- `--disallow-code-generation-from-strings` -+- `--enable-etw-stack-walking` -+- `--expose-gc` -+- `--interpreted-frames-native-stack` -+- `--jitless` -+- `--max-old-space-size` -+- `--max-semi-space-size` -+- `--perf-basic-prof-only-functions` -+- `--perf-basic-prof` -+- `--perf-prof-unwinding-info` -+- `--perf-prof` -+- `--stack-trace-limit` - - - -@@ -3446,23 +3415,12 @@ and the line lengths of the source file (in the key `lineLengths`). - "url": "./path-to-map.json", - "data": { - "version": 3, -- "sources": [ -- "file:///absolute/path/to/original.js" -- ], -- "names": [ -- "Foo", -- "console", -- "info" -- ], -+ "sources": ["file:///absolute/path/to/original.js"], -+ "names": ["Foo", "console", "info"], - "mappings": "MAAMA,IACJC,YAAaC", - "sourceRoot": "./" - }, -- "lineLengths": [ -- 13, -- 62, -- 38, -- 27 -- ] -+ "lineLengths": [13, 62, 38, 27] - } - } - } -@@ -3470,7 +3428,7 @@ and the line lengths of the source file (in the key `lineLengths`). - - ### `NO_COLOR=` - --[`NO_COLOR`][] is an alias for `NODE_DISABLE_COLORS`. The value of the -+[`NO_COLOR`][] is an alias for `NODE_DISABLE_COLORS`. The value of the - environment variable is arbitrary. - - ### `OPENSSL_CONF=file` -@@ -3552,12 +3510,12 @@ Asynchronous system APIs are used by Node.js whenever possible, but where they - do not exist, libuv's threadpool is used to create asynchronous node APIs based - on synchronous system APIs. Node.js APIs that use the threadpool are: - --* all `fs` APIs, other than the file watcher APIs and those that are explicitly -+- all `fs` APIs, other than the file watcher APIs and those that are explicitly - synchronous --* asynchronous crypto APIs such as `crypto.pbkdf2()`, `crypto.scrypt()`, -+- asynchronous crypto APIs such as `crypto.pbkdf2()`, `crypto.scrypt()`, - `crypto.randomBytes()`, `crypto.randomFill()`, `crypto.generateKeyPair()` --* `dns.lookup()` --* all `zlib` APIs, other than those that are explicitly synchronous -+- `dns.lookup()` -+- all `zlib` APIs, other than those that are explicitly synchronous - - Because libuv's threadpool has a fixed size, it means that if for whatever - reason any of these APIs takes a long time, other (seemingly unrelated) APIs -@@ -3723,7 +3681,6 @@ node --stack-trace-limit=12 -p -e "Error.stackTraceLimit" # prints 12 - [`--redirect-warnings`]: #--redirect-warningsfile - [`--require`]: #-r---require-module - [`AsyncLocalStorage`]: async_context.md#class-asynclocalstorage --[`Atomics.wait()`]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Atomics/wait - [`Buffer`]: buffer.md#class-buffer - [`CRYPTO_secure_malloc_init`]: https://www.openssl.org/docs/man3.0/man3/CRYPTO_secure_malloc_init.html - [`ERR_INVALID_TYPESCRIPT_SYNTAX`]: errors.md#err_invalid_typescript_syntax -@@ -3746,7 +3703,6 @@ node --stack-trace-limit=12 -p -e "Error.stackTraceLimit" # prints 12 - [`tls.DEFAULT_MIN_VERSION`]: tls.md#tlsdefault_min_version - [`unhandledRejection`]: process.md#event-unhandledrejection - [`v8.startupSnapshot` API]: v8.md#startup-snapshot-api --[`worker_threads.threadId`]: worker_threads.md#workerthreadid - [collecting code coverage from tests]: test.md#collecting-code-coverage - [conditional exports]: packages.md#conditional-exports - [context-aware]: addons.md#context-aware-addons -diff --git a/doc/api/deprecations.md b/doc/api/deprecations.md -index 0df7dce60058d518c9607094344461b60e540e60..f5f8ac77c848edf62b0a82f0644f61077a02aedd 100644 ---- a/doc/api/deprecations.md -+++ b/doc/api/deprecations.md -@@ -3313,6 +3313,9 @@ Values other than `undefined`, `null`, integer numbers, and integer strings - - - --Type: Runtime -+Type: End-of-Life - --The [`--trace-atomics-wait`][] flag is deprecated because -+The `--trace-atomics-wait` flag has been removed because - it uses the V8 hook `SetAtomicsWaitCallback`, - that will be removed in a future V8 release. - -@@ -3737,7 +3740,6 @@ deprecated, as their values are guaranteed to be identical to that of `process.f - [`--force-node-api-uncaught-exceptions-policy`]: cli.md#--force-node-api-uncaught-exceptions-policy - [`--pending-deprecation`]: cli.md#--pending-deprecation - [`--throw-deprecation`]: cli.md#--throw-deprecation --[`--trace-atomics-wait`]: cli.md#--trace-atomics-wait - [`--unhandled-rejections`]: cli.md#--unhandled-rejectionsmode - [`Buffer.allocUnsafeSlow(size)`]: buffer.md#static-method-bufferallocunsafeslowsize - [`Buffer.from(array)`]: buffer.md#static-method-bufferfromarray + * `--trace-deprecation` + * `--trace-env-js-stack` + * `--trace-env-native-stack` diff --git a/doc/node.1 b/doc/node.1 index 9f534746ef9d9c1c1ee2edd6c195573a2e228600..e01fc511a1034518c0fb9bc5fa925524aecad927 100644 --- a/doc/node.1 @@ -773,7 +43,7 @@ index 9f534746ef9d9c1c1ee2edd6c195573a2e228600..e01fc511a1034518c0fb9bc5fa925524 Print stack traces for deprecations. . diff --git a/src/node.cc b/src/node.cc -index 0ed78ab6b52906e980eebf1f625a1c7cbfc8097b..2ff08a9cb6124316049a91bda70cf6985045286a 100644 +index 2f58a6fa69069dabb99b5ddb8011991b07fa5f02..9f6fa646ba6673f67f5f625e157ed850633a26da 100644 --- a/src/node.cc +++ b/src/node.cc @@ -226,44 +226,6 @@ void Environment::WaitForInspectorFrontendByOptions() { @@ -840,10 +110,10 @@ index 0ed78ab6b52906e980eebf1f625a1c7cbfc8097b..2ff08a9cb6124316049a91bda70cf698 isolate_->SetPromiseHook(TracePromises); } diff --git a/src/node_options.cc b/src/node_options.cc -index 866f2a39a5e51a8bf434ccd54d76c685bcdd1502..2bedaa88582c369a4a420ff20a5204af96feb52e 100644 +index 54b253aa54f5cdebdb04315f9c6c2506977555c0..acf390bd456c7ddfa6987e440fb45940aec6b1ff 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -758,10 +758,6 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() { +@@ -762,10 +762,6 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() { "throw an exception on deprecations", &EnvironmentOptions::throw_deprecation, kAllowedInEnvvar); @@ -855,7 +125,7 @@ index 866f2a39a5e51a8bf434ccd54d76c685bcdd1502..2bedaa88582c369a4a420ff20a5204af "show stack traces on deprecations", &EnvironmentOptions::trace_deprecation, diff --git a/src/node_options.h b/src/node_options.h -index 41dd04f5e2b1cd54c32df70830389d44d7b39aa2..b10287d3eadc49b44e2e3fb8150a48be6866b0b4 100644 +index 065457acfde6ba4d04ed570cc72005cfd2798fd5..150f833bb21bd6d37f652f0785a4a98f3de5f67d 100644 --- a/src/node_options.h +++ b/src/node_options.h @@ -203,7 +203,6 @@ class EnvironmentOptions : public Options { diff --git a/patches/node/cli_remove_deprecated_v8_flag.patch b/patches/node/cli_remove_deprecated_v8_flag.patch index 5acad06fbdca2..caff01e09ec1d 100644 --- a/patches/node/cli_remove_deprecated_v8_flag.patch +++ b/patches/node/cli_remove_deprecated_v8_flag.patch @@ -18,10 +18,10 @@ Reviewed-By: MichaĆ«l Zasso Reviewed-By: Yagiz Nizipli diff --git a/doc/api/cli.md b/doc/api/cli.md -index 8105592764abca6036e8e029ca9b6a32402e7156..431a6aa7a2cf4d537cb719f15c2749254e0433b3 100644 +index 1b42c5a7f4715e56fa5bc39cd6f78a76473406f2..114b7bbf6b1e105fc1696ed8a064065db73ff519 100644 --- a/doc/api/cli.md +++ b/doc/api/cli.md -@@ -3270,7 +3270,6 @@ V8 options that are allowed are: +@@ -3350,7 +3350,6 @@ V8 options that are allowed are: * `--disallow-code-generation-from-strings` * `--enable-etw-stack-walking` * `--expose-gc` @@ -30,10 +30,10 @@ index 8105592764abca6036e8e029ca9b6a32402e7156..431a6aa7a2cf4d537cb719f15c274925 * `--jitless` * `--max-old-space-size` diff --git a/src/node_options.cc b/src/node_options.cc -index 620776c06d835eb1bfeed060751c570e8d435b29..866f2a39a5e51a8bf434ccd54d76c685bcdd1502 100644 +index b22fbb0a285f6f323779d6ebb2b027a3990b031e..54b253aa54f5cdebdb04315f9c6c2506977555c0 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -980,11 +980,6 @@ PerIsolateOptionsParser::PerIsolateOptionsParser( +@@ -984,11 +984,6 @@ PerIsolateOptionsParser::PerIsolateOptionsParser( "disallow eval and friends", V8Option{}, kAllowedInEnvvar); @@ -46,10 +46,10 @@ index 620776c06d835eb1bfeed060751c570e8d435b29..866f2a39a5e51a8bf434ccd54d76c685 "disable runtime allocation of executable memory", V8Option{}, diff --git a/test/parallel/test-cli-node-options.js b/test/parallel/test-cli-node-options.js -index b1d5c44ceeeebc674938d85736aace2a6ef570e2..9e89200e9f6dfd89340cd04afb76e271ffc82b54 100644 +index c5d74f40e7894980b45713c77cc36f836be73528..53bca572c3405c0357f868aae71fc2c82d973c04 100644 --- a/test/parallel/test-cli-node-options.js +++ b/test/parallel/test-cli-node-options.js -@@ -73,7 +73,6 @@ if (common.hasCrypto) { +@@ -76,7 +76,6 @@ if (common.hasCrypto) { expect('--abort_on-uncaught_exception', 'B\n'); expect('--disallow-code-generation-from-strings', 'B\n'); expect('--expose-gc', 'B\n'); diff --git a/patches/node/expose_get_builtin_module_function.patch b/patches/node/expose_get_builtin_module_function.patch index 39d3c031d4ef4..bee428c167591 100644 --- a/patches/node/expose_get_builtin_module_function.patch +++ b/patches/node/expose_get_builtin_module_function.patch @@ -9,7 +9,7 @@ modules to sandboxed renderers. TODO(codebytere): remove and replace with a public facing API. diff --git a/src/node_binding.cc b/src/node_binding.cc -index c2ef9b36d5b2967c798c123b6cbbd099b15c2791..b5c0a93d83ab4d4f6792d0eb648e7198de874bcf 100644 +index 6c337232149ccb8bdb1188e72d59a052b1cb79c1..44ad4a480a33a2c39494a7d961318270a25620d8 100644 --- a/src/node_binding.cc +++ b/src/node_binding.cc @@ -653,6 +653,10 @@ void GetInternalBinding(const FunctionCallbackInfo& args) { diff --git a/patches/node/feat_add_oom_error_callback_in_node_isolatesettings.patch b/patches/node/feat_add_oom_error_callback_in_node_isolatesettings.patch deleted file mode 100644 index 3eecb039f5d7e..0000000000000 --- a/patches/node/feat_add_oom_error_callback_in_node_isolatesettings.patch +++ /dev/null @@ -1,42 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Yang Liu -Date: Wed, 5 Mar 2025 17:22:39 +0800 -Subject: feat: add oom_error_callback in node::IsolateSettings - -Expose v8::OOMErrorCallback to allow setting OOM error handler outside Node.js - -As described in this issue https://github.com/electron/electron/issues/45894, -Electron fails to capture js heap oom because node::OOMErrorHandler just -terminates the process without raising an exception. - -To fix this issue, provide the interface oom_error_callback to enable a -custom oom error callback set from Electron. - -diff --git a/src/api/environment.cc b/src/api/environment.cc -index fc9b056d2f7e25109100fbde5f3ab0aebc8c619a..9b155213ce301df7e396a4a113992499fc7e9910 100644 ---- a/src/api/environment.cc -+++ b/src/api/environment.cc -@@ -241,7 +241,10 @@ void SetIsolateErrorHandlers(v8::Isolate* isolate, const IsolateSettings& s) { - auto* fatal_error_cb = s.fatal_error_callback ? - s.fatal_error_callback : OnFatalError; - isolate->SetFatalErrorHandler(fatal_error_cb); -- isolate->SetOOMErrorHandler(OOMErrorHandler); -+ -+ auto* oom_error_cb = s.oom_error_callback ? -+ s.oom_error_callback : OOMErrorHandler; -+ isolate->SetOOMErrorHandler(oom_error_cb); - - if ((s.flags & SHOULD_NOT_SET_PREPARE_STACK_TRACE_CALLBACK) == 0) { - auto* prepare_stack_trace_cb = s.prepare_stack_trace_callback ? -diff --git a/src/node.h b/src/node.h -index afb26ec5690ccd65a3c36f8b8a1b2de416b9d843..98ad0ea649eaef43d1f5231f7bc4044e100e08d7 100644 ---- a/src/node.h -+++ b/src/node.h -@@ -489,6 +489,7 @@ struct IsolateSettings { - v8::Isolate::AbortOnUncaughtExceptionCallback - should_abort_on_uncaught_exception_callback = nullptr; - v8::FatalErrorCallback fatal_error_callback = nullptr; -+ v8::OOMErrorCallback oom_error_callback = nullptr; - v8::PrepareStackTraceCallback prepare_stack_trace_callback = nullptr; - - // Miscellaneous callbacks diff --git a/patches/node/fix_-wnonnull_warning.patch b/patches/node/fix_-wnonnull_warning.patch deleted file mode 100644 index a75eaf4b373dd..0000000000000 --- a/patches/node/fix_-wnonnull_warning.patch +++ /dev/null @@ -1,43 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Charles Kerr -Date: Thu, 6 Mar 2025 19:31:29 -0600 -Subject: fix: -Wnonnull warning -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -Fixes this warning: - -> 2025-03-07T01:05:01.8637705Z ../../third_party/electron_node/src/debug_utils.cc(257,12): error: null passed to a callee that requires a non-null argument [-Werror,-Wnonnull] -> 2025-03-07T01:05:01.8638267Z 257 | return nullptr; -> 2025-03-07T01:05:01.8638481Z | ^~~~~~~ -> 2025-03-07T01:05:01.8638700Z 1 error generated. - -Not sure why this warning was never triggered before; `git blame` -indicates this code hasn't changed in ages: - -> c40a8273ef2 (MichaĆ«l Zasso 2024-05-10 09:50:20 +0200 255) #endif // DEBUG -> 8e2d33f1562 (Anna Henningsen 2018-06-07 16:54:29 +0200 256) } -> 247b5130595 (Refael Ackermann 2018-10-22 15:07:00 -0400 257) return nullptr; -> 247b5130595 (Refael Ackermann 2018-10-22 15:07:00 -0400 258) } - -Presumably this is failing in this Chromium roll due to a -clang version bump. - -We should remove this patch after upstreaming it. - -Upstream PR: https://github.com/nodejs/node/pull/57354 - -diff --git a/src/debug_utils.cc b/src/debug_utils.cc -index c8b3b11ee34d7ac98163aa563fd7f6f1fb0a3b79..8a85e066fd9e6f3d6131eca89d52495f904cd5a6 100644 ---- a/src/debug_utils.cc -+++ b/src/debug_utils.cc -@@ -254,7 +254,7 @@ class Win32SymbolDebuggingContext final : public NativeSymbolDebuggingContext { - USE(GetLastError()); - #endif // DEBUG - } -- return nullptr; -+ return {}; - } - - SymbolInfo LookupSymbol(void* address) override { diff --git a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch index e1722fdc64262..45edf948a98da 100644 --- a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch +++ b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch @@ -7,10 +7,10 @@ common.gypi is a file that's included in the node header bundle, despite the fact that we do not build node with gyp. diff --git a/common.gypi b/common.gypi -index 62f26bb07d27a02aedf18fdd1191b282f9340cac..5d74876ab28f8c10bb9543f7652478514414d8d2 100644 +index 372409f4b09cc3b3be9809f697816498e5c021fe..f2a45f0f0bbfce93e61d3696a18425af4d022a00 100644 --- a/common.gypi +++ b/common.gypi -@@ -88,6 +88,23 @@ +@@ -90,6 +90,23 @@ ##### end V8 defaults ##### diff --git a/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch b/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch index 79eff671572bd..72074233f7954 100644 --- a/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch +++ b/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch @@ -53,10 +53,10 @@ index 2879e5cf541fb4d226cfd7cc0fe367ca448fb926..03082f0ec4f91382933eec48e77331cd const maybeMain = resolvedOption <= legacyMainResolveExtensionsIndexes.kResolvedByMainIndexNode ? packageConfig.main || './' : ''; diff --git a/src/node_file.cc b/src/node_file.cc -index 1d22e19f16d5ad82466b0724971b2e4a685682f7..3d7e303741a73134e140152bed637fe5ae8bc1db 100644 +index a492b3aa113c4e1d50cc42721bd5eb58380a6264..c7915e2c8161a5d0fa05ccce368ce9c44345c05d 100644 --- a/src/node_file.cc +++ b/src/node_file.cc -@@ -3220,13 +3220,25 @@ static void CpSyncCheckPaths(const FunctionCallbackInfo& args) { +@@ -3237,13 +3237,25 @@ static void CpSyncCheckPaths(const FunctionCallbackInfo& args) { } BindingData::FilePathIsFileReturnType BindingData::FilePathIsFile( @@ -83,7 +83,7 @@ index 1d22e19f16d5ad82466b0724971b2e4a685682f7..3d7e303741a73134e140152bed637fe5 uv_fs_t req; int rc = uv_fs_stat(env->event_loop(), &req, file_path.c_str(), nullptr); -@@ -3284,6 +3296,11 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { +@@ -3301,6 +3313,11 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { std::optional initial_file_path; std::string file_path; @@ -95,7 +95,7 @@ index 1d22e19f16d5ad82466b0724971b2e4a685682f7..3d7e303741a73134e140152bed637fe5 if (args.Length() >= 2 && args[1]->IsString()) { auto package_config_main = Utf8Value(isolate, args[1]).ToString(); -@@ -3304,7 +3321,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { +@@ -3321,7 +3338,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { BufferValue buff_file_path(isolate, local_file_path); ToNamespacedPath(env, &buff_file_path); @@ -104,7 +104,7 @@ index 1d22e19f16d5ad82466b0724971b2e4a685682f7..3d7e303741a73134e140152bed637fe5 case BindingData::FilePathIsFileReturnType::kIsFile: return args.GetReturnValue().Set(i); case BindingData::FilePathIsFileReturnType::kIsNotFile: -@@ -3341,7 +3358,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { +@@ -3358,7 +3375,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { BufferValue buff_file_path(isolate, local_file_path); ToNamespacedPath(env, &buff_file_path); diff --git a/patches/node/fix_assert_module_in_the_renderer_process.patch b/patches/node/fix_assert_module_in_the_renderer_process.patch index 86cfb0a302ffe..e6ab076547afe 100644 --- a/patches/node/fix_assert_module_in_the_renderer_process.patch +++ b/patches/node/fix_assert_module_in_the_renderer_process.patch @@ -44,10 +44,10 @@ index 59b5a16f1309a5e4055bccfdb7a529045ad30402..bfdaf6211466a01b64b7942f7b16c480 let filename = call.getFileName(); const line = call.getLineNumber() - 1; diff --git a/src/node_options.cc b/src/node_options.cc -index 3608ab2b4aeb09e985ca98e23f2dff23567ade71..620776c06d835eb1bfeed060751c570e8d435b29 100644 +index 23cb558a22b4462f5ce4f74833d25c7f712f8139..b22fbb0a285f6f323779d6ebb2b027a3990b031e 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -1527,14 +1527,16 @@ void GetEmbedderOptions(const FunctionCallbackInfo& args) { +@@ -1535,14 +1535,16 @@ void GetEmbedderOptions(const FunctionCallbackInfo& args) { } Isolate* isolate = args.GetIsolate(); diff --git a/patches/node/fix_cppgc_initializing_twice.patch b/patches/node/fix_cppgc_initializing_twice.patch index f03ffed13d79f..6ecf3b9675de9 100644 --- a/patches/node/fix_cppgc_initializing_twice.patch +++ b/patches/node/fix_cppgc_initializing_twice.patch @@ -12,7 +12,7 @@ This can be removed/refactored once Node.js upgrades to a version of V8 containing the above CL. diff --git a/src/node.cc b/src/node.cc -index 2ff08a9cb6124316049a91bda70cf6985045286a..5de93329cbd40a2ca314d602b123092ed15741c5 100644 +index 9f6fa646ba6673f67f5f625e157ed850633a26da..63a462876c00588d22abdd6ed8ee41ecf6590d03 100644 --- a/src/node.cc +++ b/src/node.cc @@ -1173,7 +1173,7 @@ InitializeOncePerProcessInternal(const std::vector& args, diff --git a/patches/node/fix_crypto_tests_to_run_with_bssl.patch b/patches/node/fix_crypto_tests_to_run_with_bssl.patch index 31ecfb8700b29..ce3b8f49c39a5 100644 --- a/patches/node/fix_crypto_tests_to_run_with_bssl.patch +++ b/patches/node/fix_crypto_tests_to_run_with_bssl.patch @@ -11,7 +11,7 @@ before it's acceptable to upstream, as this patch comments out a couple of tests that upstream probably cares about. diff --git a/test/common/index.js b/test/common/index.js -index 92c7294e6f6298f511b5a289e1e0e3a4be68cc77..63a350c5ed912a785b042a238c064c98ed423af4 100644 +index 8f5af57a83dc6b426f1b11bd2e3a8c6c0f2d9a85..f6e00c9f3f3ac4b42662eed6c8d190586f92ab99 100644 --- a/test/common/index.js +++ b/test/common/index.js @@ -56,6 +56,8 @@ const hasCrypto = Boolean(process.versions.openssl) && @@ -23,7 +23,7 @@ index 92c7294e6f6298f511b5a289e1e0e3a4be68cc77..63a350c5ed912a785b042a238c064c98 function parseTestFlags(filename = process.argv[1]) { // The copyright notice is relatively big and the flags could come afterwards. const bytesToRead = 1500; -@@ -889,6 +891,7 @@ const common = { +@@ -901,6 +903,7 @@ const common = { mustNotMutateObjectDeep, mustSucceed, nodeProcessAborted, @@ -294,24 +294,6 @@ index 48cd1ed4df61aaddeee8785cb90f83bdd9628187..a18aeb2bdffcc7a7e9ef12328b849994 }); // No-pad encrypted string should return the same: -diff --git a/test/parallel/test-crypto-prime.js b/test/parallel/test-crypto-prime.js -index 5ffdc1394282be046150e3759f82f8787f5604f7..e1c7a7b4824a2df20a405355696022398216fa4f 100644 ---- a/test/parallel/test-crypto-prime.js -+++ b/test/parallel/test-crypto-prime.js -@@ -259,11 +259,11 @@ for (const checks of [-(2 ** 31), -1, 2 ** 31, 2 ** 32 - 1, 2 ** 32, 2 ** 50]) { - bytes[0] = 0x1; - assert.throws(() => checkPrime(bytes, common.mustNotCall()), { - code: 'ERR_OSSL_BN_BIGNUM_TOO_LONG', -- message: /bignum too long/ -+ message: /bignum[_ ]too[_ ]long/i - }); - assert.throws(() => checkPrimeSync(bytes), { - code: 'ERR_OSSL_BN_BIGNUM_TOO_LONG', -- message: /bignum too long/ -+ message: /bignum[_ ]too[_ ]long/i - }); - } - diff --git a/test/parallel/test-crypto-rsa-dsa.js b/test/parallel/test-crypto-rsa-dsa.js index dcd5045daaf58c60e27c1e2f7941033302241339..6ac75565792b92a97c622baba73f821d754b8d01 100644 --- a/test/parallel/test-crypto-rsa-dsa.js @@ -353,10 +335,10 @@ index dcd5045daaf58c60e27c1e2f7941033302241339..6ac75565792b92a97c622baba73f821d // DSA signatures vary across runs so there is no static string to verify diff --git a/test/parallel/test-crypto-scrypt.js b/test/parallel/test-crypto-scrypt.js -index 338a19b0e88ad6f08d2f6b6a5d38b9980996ce11..a4ee215575d072450ba66c558ddca88bfb23d85f 100644 +index 03a18c7522531c7317f12705550117dc389a0245..2f0f46f2c6ddc62de89877cfa0ca80949a0f4c5e 100644 --- a/test/parallel/test-crypto-scrypt.js +++ b/test/parallel/test-crypto-scrypt.js -@@ -178,7 +178,7 @@ for (const options of bad) { +@@ -176,7 +176,7 @@ for (const options of bad) { for (const options of toobig) { const expected = { @@ -599,6 +581,49 @@ index 6f88e81e9ff29defe73800fc038b0d96d1ebd846..c0b92e2bdf86d3d2638c973f8be3110d }; // Create TLS1.2 server +diff --git a/test/parallel/test-tls-alert-handling.js b/test/parallel/test-tls-alert-handling.js +index cba5bebaa29b6f8ac4fd0fcedaadb2f7bb3eb321..019d95df499892b14ab088f99013ee32c432779c 100644 +--- a/test/parallel/test-tls-alert-handling.js ++++ b/test/parallel/test-tls-alert-handling.js +@@ -35,7 +35,7 @@ let iter = 0; + + const errorHandler = common.mustCall((err) => { + let expectedErrorCode = 'ERR_SSL_WRONG_VERSION_NUMBER'; +- let expectedErrorReason = 'wrong version number'; ++ let expectedErrorReason = /wrong[\s_]version[\s_]number/i; + if (hasOpenSSL(3, 2)) { + expectedErrorCode = 'ERR_SSL_PACKET_LENGTH_TOO_LONG'; + expectedErrorReason = 'packet length too long'; +@@ -43,8 +43,8 @@ const errorHandler = common.mustCall((err) => { + + assert.strictEqual(err.code, expectedErrorCode); + assert.strictEqual(err.library, 'SSL routines'); +- if (!hasOpenSSL3) assert.strictEqual(err.function, 'ssl3_get_record'); +- assert.strictEqual(err.reason, expectedErrorReason); ++ if (!hasOpenSSL3 && !common.openSSLIsBoringSSL) assert.strictEqual(err.function, 'ssl3_get_record'); ++ assert.match(err.reason, expectedErrorReason); + errorReceived = true; + if (canCloseServer()) + server.close(); +@@ -98,15 +98,15 @@ function sendBADTLSRecord() { + })); + client.on('error', common.mustCall((err) => { + let expectedErrorCode = 'ERR_SSL_TLSV1_ALERT_PROTOCOL_VERSION'; +- let expectedErrorReason = 'tlsv1 alert protocol version'; ++ let expectedErrorReason = /tlsv1[\s_]alert[\s_]protocol[\s_]version/i; + if (hasOpenSSL(3, 2)) { + expectedErrorCode = 'ERR_SSL_TLSV1_ALERT_RECORD_OVERFLOW'; + expectedErrorReason = 'tlsv1 alert record overflow'; + } + assert.strictEqual(err.code, expectedErrorCode); + assert.strictEqual(err.library, 'SSL routines'); +- if (!hasOpenSSL3) ++ if (!hasOpenSSL3 && !common.openSSLIsBoringSSL) + assert.strictEqual(err.function, 'ssl3_read_bytes'); +- assert.strictEqual(err.reason, expectedErrorReason); ++ assert.match(err.reason, expectedErrorReason); + })); + } diff --git a/test/parallel/test-tls-getprotocol.js b/test/parallel/test-tls-getprotocol.js index b1eab88fd6517e3698934dea17752ef2bb8d8d54..3ad6db20316baa8490e3787dd55903b58a54ad06 100644 --- a/test/parallel/test-tls-getprotocol.js diff --git a/patches/node/fix_do_not_resolve_electron_entrypoints.patch b/patches/node/fix_do_not_resolve_electron_entrypoints.patch index 73608aa7e06e7..68ec69cf3ee8f 100644 --- a/patches/node/fix_do_not_resolve_electron_entrypoints.patch +++ b/patches/node/fix_do_not_resolve_electron_entrypoints.patch @@ -19,10 +19,10 @@ index c9d4a3536d0f60375ae623b48ca2fa7095c88d42..d818320fbbc430d06a0c2852e4723981 context = { __proto__: context, source }; } diff --git a/lib/internal/modules/esm/translators.js b/lib/internal/modules/esm/translators.js -index 0caba80bb213e0edfb1f834250f895ccc05d0d1c..6feab19d24a3524e36c5ed3bbac53cba0fa298c7 100644 +index 49aacb6262502ced54e817f99dd596db85b9659c..f9f065bb743275e9b2ce71375e6a9f06e00c0f36 100644 --- a/lib/internal/modules/esm/translators.js +++ b/lib/internal/modules/esm/translators.js -@@ -286,6 +286,9 @@ function cjsPreparseModuleExports(filename, source) { +@@ -291,6 +291,9 @@ function cjsPreparseModuleExports(filename, source, isMain, format) { if (module && module[kModuleExportNames] !== undefined) { return { module, exportNames: module[kModuleExportNames] }; } diff --git a/patches/node/fix_expose_readfilesync_override_for_modules.patch b/patches/node/fix_expose_readfilesync_override_for_modules.patch index d30767517d58a..c54548cd8b874 100644 --- a/patches/node/fix_expose_readfilesync_override_for_modules.patch +++ b/patches/node/fix_expose_readfilesync_override_for_modules.patch @@ -8,10 +8,10 @@ an API override to replace the native `ReadFileSync` in the `modules` binding. diff --git a/src/env_properties.h b/src/env_properties.h -index 9f89823170782242093bc5ee0df6a2a2ef5b919f..b9374ee1acceb3d0aab51c6c5ae6a79be1cc71a9 100644 +index ba8c80ff2842c63f16cae51cfa8084617bb35bf5..820aebd18d22bcef4992b09ffc8924e9b758fd3e 100644 --- a/src/env_properties.h +++ b/src/env_properties.h -@@ -478,6 +478,7 @@ +@@ -485,6 +485,7 @@ V(maybe_cache_generated_source_map, v8::Function) \ V(messaging_deserialize_create_object, v8::Function) \ V(message_port, v8::Object) \ diff --git a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch index f6652a3aeefaa..baa89612d412d 100644 --- a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch +++ b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch @@ -70,19 +70,19 @@ index bfd9bd3d127404de1cbb6f30c43ab0342590759d..9e7d8ef0adef3b68a3ec186e4b218f59 const packageConfig = packageJsonReader.read(packageJSONPath, { __proto__: null, specifier, base, isESM: true }); diff --git a/lib/internal/modules/esm/translators.js b/lib/internal/modules/esm/translators.js -index a587246e329b41f33a3fdfe5ef92910915911611..1b94d923b6d83cc7806d793497a4f9f978c5938c 100644 +index 7dcd7afe8ce3c25ceb314cdf15c330f3d66eb84f..4445bcc4c4c6c6f87ac45e693012a18a93739f9b 100644 --- a/lib/internal/modules/esm/translators.js +++ b/lib/internal/modules/esm/translators.js -@@ -182,7 +182,7 @@ function createCJSModuleWrap(url, source, isMain, loadCJS = loadCJSModule) { +@@ -186,7 +186,7 @@ function createCJSModuleWrap(url, source, isMain, format, loadCJS = loadCJSModul - const { exportNames, module } = cjsPreparseModuleExports(filename, source); + const { exportNames, module } = cjsPreparseModuleExports(filename, source, isMain, format); cjsCache.set(url, module); - const namesWithDefault = exportNames.has('default') ? + const namesWithDefault = filename === 'electron' ? ['default', ...Object.keys(module.exports)] : exportNames.has('default') ? [...exportNames] : ['default', ...exportNames]; if (isMain) { -@@ -204,8 +204,8 @@ function createCJSModuleWrap(url, source, isMain, loadCJS = loadCJSModule) { +@@ -208,8 +208,8 @@ function createCJSModuleWrap(url, source, isMain, format, loadCJS = loadCJSModul ({ exports } = module); } for (const exportName of exportNames) { @@ -93,8 +93,8 @@ index a587246e329b41f33a3fdfe5ef92910915911611..1b94d923b6d83cc7806d793497a4f9f9 continue; } // We might trigger a getter -> dont fail. -@@ -239,6 +239,10 @@ translators.set('require-commonjs', (url, source, isMain) => { - return createCJSModuleWrap(url, source); +@@ -243,6 +243,10 @@ translators.set('require-commonjs', (url, source, isMain) => { + return createCJSModuleWrap(url, source, isMain, 'commonjs'); }); +translators.set('electron', () => { diff --git a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch index cdd487fd9f6c2..3d8bea2f74f95 100644 --- a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch +++ b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch @@ -238,20 +238,10 @@ index d94f6e1c82c4a62547b3b395f375c86ce4deb5de..b81b9005365272217c77e2b9289bd9f8 X509View ca(sk_X509_value(peer_certs.get(), i)); if (!cert->view().isIssuedBy(ca)) continue; diff --git a/src/crypto/crypto_context.cc b/src/crypto/crypto_context.cc -index c89d591c6804ab7d41199d61452d10d12cdf7398..05740c7dc599954bca0779b8c8d6bd615183288a 100644 +index a054e4c1285208c9ba8b9679c284f459f1ace690..3de8ef4fafcdbdc2cb0ce31de162663d5272340f 100644 --- a/src/crypto/crypto_context.cc +++ b/src/crypto/crypto_context.cc -@@ -26,7 +26,9 @@ using ncrypto::BIOPointer; - using ncrypto::ClearErrorOnReturn; - using ncrypto::CryptoErrorList; - using ncrypto::DHPointer; -+#ifndef OPENSSL_NO_ENGINE - using ncrypto::EnginePointer; -+#endif // !OPENSSL_NO_ENGINE - using ncrypto::EVPKeyPointer; - using ncrypto::MarkPopErrorOnReturn; - using ncrypto::SSLPointer; -@@ -105,7 +107,7 @@ int SSL_CTX_use_certificate_chain(SSL_CTX* ctx, +@@ -123,7 +123,7 @@ int SSL_CTX_use_certificate_chain(SSL_CTX* ctx, // the CA certificates. SSL_CTX_clear_extra_chain_certs(ctx); @@ -260,7 +250,7 @@ index c89d591c6804ab7d41199d61452d10d12cdf7398..05740c7dc599954bca0779b8c8d6bd61 X509* ca = sk_X509_value(extra_certs, i); // NOTE: Increments reference count on `ca` -@@ -931,11 +933,12 @@ void SecureContext::SetDHParam(const FunctionCallbackInfo& args) { +@@ -1584,11 +1584,12 @@ void SecureContext::SetDHParam(const FunctionCallbackInfo& args) { // If the user specified "auto" for dhparams, the JavaScript layer will pass // true to this function instead of the original string. Any other string // value will be interpreted as custom DH parameters below. @@ -274,7 +264,7 @@ index c89d591c6804ab7d41199d61452d10d12cdf7398..05740c7dc599954bca0779b8c8d6bd61 DHPointer dh; { BIOPointer bio(LoadBIO(env, args[0])); -@@ -1161,7 +1164,7 @@ void SecureContext::LoadPKCS12(const FunctionCallbackInfo& args) { +@@ -1814,7 +1815,7 @@ void SecureContext::LoadPKCS12(const FunctionCallbackInfo& args) { } // Add CA certs too @@ -416,7 +406,7 @@ index 471fee77531139ce988292470dff443fdfb05b07..931f7c2ae3d7e12afce471545d610d22 return EVPKeyCtxPointer(); diff --git a/src/crypto/crypto_keys.cc b/src/crypto/crypto_keys.cc -index f66c57b1079af6cd040dc6d11e72f353507b75e5..abd2bccb9669e06dd8355f66220f8b06c8e863dc 100644 +index b38a9a377738fd5fe6cc89c3a27c403bf6a97715..0cd43c2005b431e180b7483cb89825a75e1fe03f 100644 --- a/src/crypto/crypto_keys.cc +++ b/src/crypto/crypto_keys.cc @@ -949,6 +949,7 @@ void KeyObjectHandle::GetAsymmetricKeyType( @@ -469,20 +459,20 @@ index 05a3882c7e17d78e27aabb29891aa250789a47c0..1f2fccce6ed8f14525557644e0bdd130 if (target diff --git a/src/crypto/crypto_util.cc b/src/crypto/crypto_util.cc -index e255288f6e013ce122f317c415d73d9c93d38580..25fa9af8153852f49d5289aa253f3c8f7268d89c 100644 +index 7c548d32b40365343f0e208c3aa856a1c847f4c3..6346f8f7199cf7b7d3736c59571606fff102fbb6 100644 --- a/src/crypto/crypto_util.cc +++ b/src/crypto/crypto_util.cc -@@ -29,7 +29,9 @@ namespace node { - using ncrypto::BignumPointer; - using ncrypto::BIOPointer; - using ncrypto::CryptoErrorList; -+#ifndef OPENSSL_NO_ENGINE - using ncrypto::EnginePointer; -+#endif // !OPENSSL_NO_ENGINE - using ncrypto::EVPKeyCtxPointer; - using v8::ArrayBuffer; - using v8::BackingStore; -@@ -502,24 +504,15 @@ Maybe Decorate(Environment* env, +@@ -207,7 +207,8 @@ void TestFipsCrypto(const v8::FunctionCallbackInfo& args) { + + void GetOpenSSLSecLevelCrypto(const FunctionCallbackInfo& args) { + // for BoringSSL assume the same as the default +- int sec_level = OPENSSL_TLS_SECURITY_LEVEL; ++ // value of OPENSSL_TLS_SECURITY_LEVEL. ++ int sec_level = 1; + #ifndef OPENSSL_IS_BORINGSSL + Environment* env = Environment::GetCurrent(args); + +@@ -527,24 +528,15 @@ Maybe Decorate(Environment* env, V(BIO) \ V(PKCS7) \ V(X509V3) \ @@ -508,7 +498,7 @@ index e255288f6e013ce122f317c415d73d9c93d38580..25fa9af8153852f49d5289aa253f3c8f V(USER) \ #define V(name) case ERR_LIB_##name: lib = #name "_"; break; -@@ -661,7 +654,7 @@ void SecureBuffer(const FunctionCallbackInfo& args) { +@@ -686,7 +678,7 @@ void SecureBuffer(const FunctionCallbackInfo& args) { CHECK(args[0]->IsUint32()); Environment* env = Environment::GetCurrent(args); uint32_t len = args[0].As()->Value(); @@ -517,7 +507,7 @@ index e255288f6e013ce122f317c415d73d9c93d38580..25fa9af8153852f49d5289aa253f3c8f if (data == nullptr) { // There's no memory available for the allocation. // Return nothing. -@@ -672,7 +665,7 @@ void SecureBuffer(const FunctionCallbackInfo& args) { +@@ -697,7 +689,7 @@ void SecureBuffer(const FunctionCallbackInfo& args) { data, len, [](void* data, size_t len, void* deleter_data) { @@ -526,7 +516,7 @@ index e255288f6e013ce122f317c415d73d9c93d38580..25fa9af8153852f49d5289aa253f3c8f }, data); Local buffer = ArrayBuffer::New(env->isolate(), store); -@@ -680,10 +673,12 @@ void SecureBuffer(const FunctionCallbackInfo& args) { +@@ -705,10 +697,12 @@ void SecureBuffer(const FunctionCallbackInfo& args) { } void SecureHeapUsed(const FunctionCallbackInfo& args) { @@ -540,7 +530,7 @@ index e255288f6e013ce122f317c415d73d9c93d38580..25fa9af8153852f49d5289aa253f3c8f } // namespace diff --git a/src/env.h b/src/env.h -index 1239cbdbf2d375a50ada37ee0ed5592c751d4c5c..aed066852d7c257076cc7ca8b173fd2a3a353a00 100644 +index b6bdff9b8580d2588a39f00b594c4c480157d78a..cfe917c797a6e4bb0f0284ec56be82637f840129 100644 --- a/src/env.h +++ b/src/env.h @@ -50,7 +50,7 @@ @@ -552,7 +542,7 @@ index 1239cbdbf2d375a50ada37ee0ed5592c751d4c5c..aed066852d7c257076cc7ca8b173fd2a #include #endif -@@ -1071,7 +1071,7 @@ class Environment final : public MemoryRetainer { +@@ -1073,7 +1073,7 @@ class Environment final : public MemoryRetainer { kExitInfoFieldCount }; @@ -562,7 +552,7 @@ index 1239cbdbf2d375a50ada37ee0ed5592c751d4c5c..aed066852d7c257076cc7ca8b173fd2a // We declare another alias here to avoid having to include crypto_util.h using EVPMDPointer = DeleteFnPtr; diff --git a/src/node_metadata.h b/src/node_metadata.h -index c59e65ad1fe3fac23f1fc25ca77e6133d1ccaccd..f2f07434e076e2977755ef7dac7d489aedb760b0 100644 +index 6f8cb433ff8059c63d5cf16c8783139ae92fbf61..603ac3dde7d1a1109afbc451b69c8d0935b81641 100644 --- a/src/node_metadata.h +++ b/src/node_metadata.h @@ -6,7 +6,7 @@ @@ -575,7 +565,7 @@ index c59e65ad1fe3fac23f1fc25ca77e6133d1ccaccd..f2f07434e076e2977755ef7dac7d489a #if NODE_OPENSSL_HAS_QUIC #include diff --git a/src/node_options.cc b/src/node_options.cc -index 1d81079a9b7d8a69ad2d87835090be88ae507bd8..3608ab2b4aeb09e985ca98e23f2dff23567ade71 100644 +index 1444acd59d42f64831cead5f153419f7c12a88bf..23cb558a22b4462f5ce4f74833d25c7f712f8139 100644 --- a/src/node_options.cc +++ b/src/node_options.cc @@ -6,7 +6,7 @@ @@ -588,7 +578,7 @@ index 1d81079a9b7d8a69ad2d87835090be88ae507bd8..3608ab2b4aeb09e985ca98e23f2dff23 #endif diff --git a/src/node_options.h b/src/node_options.h -index 621f5eca96b10685734a39e56cce7cee6c8a25bf..41dd04f5e2b1cd54c32df70830389d44d7b39aa2 100644 +index e68a41b60832c4b000e17dd15ce16c1bdaf4b54b..065457acfde6ba4d04ed570cc72005cfd2798fd5 100644 --- a/src/node_options.h +++ b/src/node_options.h @@ -11,7 +11,7 @@ @@ -600,24 +590,3 @@ index 621f5eca96b10685734a39e56cce7cee6c8a25bf..41dd04f5e2b1cd54c32df70830389d44 #include "openssl/opensslv.h" #endif -diff --git a/unofficial.gni b/unofficial.gni -index a2f3a769ceaa08db6d7438223884dc5aeab1340d..08603eaef2da51fd92f9bf977647b56409eff48c 100644 ---- a/unofficial.gni -+++ b/unofficial.gni -@@ -151,7 +151,6 @@ template("node_gn_build") { - ] - deps = [ - ":run_node_js2c", -- "deps/brotli", - "deps/cares", - "deps/histogram", - "deps/llhttp", -@@ -161,6 +160,8 @@ template("node_gn_build") { - "deps/sqlite", - "deps/uvwasi", - "//third_party/zlib", -+ "//third_party/brotli:dec", -+ "//third_party/brotli:enc", - "$node_simdutf_path", - "$node_v8_path:v8_libplatform", - ] diff --git a/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch b/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch index fa54a035afce3..8de78da28f2fe 100644 --- a/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch +++ b/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch @@ -60,7 +60,7 @@ index 9e7d8ef0adef3b68a3ec186e4b218f591aa69266..2879e5cf541fb4d226cfd7cc0fe367ca }); const { search, hash } = resolved; diff --git a/lib/internal/modules/esm/translators.js b/lib/internal/modules/esm/translators.js -index 1b94d923b6d83cc7806d793497a4f9f978c5938c..0caba80bb213e0edfb1f834250f895ccc05d0d1c 100644 +index 4445bcc4c4c6c6f87ac45e693012a18a93739f9b..49aacb6262502ced54e817f99dd596db85b9659c 100644 --- a/lib/internal/modules/esm/translators.js +++ b/lib/internal/modules/esm/translators.js @@ -24,7 +24,7 @@ const { @@ -69,10 +69,10 @@ index 1b94d923b6d83cc7806d793497a4f9f978c5938c..0caba80bb213e0edfb1f834250f895cc const assert = require('internal/assert'); -const { readFileSync } = require('fs'); +const fs = require('fs'); - const { dirname, extname, isAbsolute } = require('path'); + const { dirname, extname } = require('path'); const { assertBufferSource, -@@ -268,7 +268,7 @@ translators.set('commonjs', function commonjsStrategy(url, source, isMain) { +@@ -272,7 +272,7 @@ translators.set('commonjs', function commonjsStrategy(url, source, isMain) { try { // We still need to read the FS to detect the exports. @@ -81,12 +81,3 @@ index 1b94d923b6d83cc7806d793497a4f9f978c5938c..0caba80bb213e0edfb1f834250f895cc } catch { // Continue regardless of error. } -@@ -335,7 +335,7 @@ function cjsPreparseModuleExports(filename, source) { - isAbsolute(resolved)) { - // TODO: this should be calling the `load` hook chain to get the source - // (and fallback to reading the FS only if the source is nullish). -- const source = readFileSync(resolved, 'utf-8'); -+ const source = fs.readFileSync(resolved, 'utf-8'); - const { exportNames: reexportNames } = cjsPreparseModuleExports(resolved, source); - for (const name of reexportNames) { - exportNames.add(name); diff --git a/patches/node/fix_remove_deprecated_errno_constants.patch b/patches/node/fix_remove_deprecated_errno_constants.patch index ab580184a3177..0e9ce33bc3b42 100644 --- a/patches/node/fix_remove_deprecated_errno_constants.patch +++ b/patches/node/fix_remove_deprecated_errno_constants.patch @@ -86,7 +86,7 @@ index 13263149c111beede83b7063fa54f56655aea54c..99068098e1867af4846e18a5d039a256 NODE_DEFINE_CONSTANT(target, ETIMEDOUT); #endif diff --git a/src/node_errors.cc b/src/node_errors.cc -index 609601328f7f5ff5f121151e81c2df82e7ef4253..6b9b944c11af917fe4e296961e6ed7df7b89a123 100644 +index 5f51add4cdf68a9487edfc9382f586cc94539571..befb642f1effa3c4139e4cd99ff64d9c5175fd72 100644 --- a/src/node_errors.cc +++ b/src/node_errors.cc @@ -862,10 +862,6 @@ const char* errno_string(int errorno) { diff --git a/patches/node/fix_remove_fastapitypedarray_usage.patch b/patches/node/fix_remove_fastapitypedarray_usage.patch index b1dad662b7165..7ce2dea2c4fe0 100644 --- a/patches/node/fix_remove_fastapitypedarray_usage.patch +++ b/patches/node/fix_remove_fastapitypedarray_usage.patch @@ -48,7 +48,7 @@ index 867a1c4aca54b9d41490d23a5eb55088b7e941cc..09f4c65a18efea262b1f854f993c6f18 static v8::CFunction fast_equal(v8::CFunction::Make(FastTimingSafeEqual)); diff --git a/src/node_buffer.cc b/src/node_buffer.cc -index cd51d9acf9540d506ec35812b9d2c530fce24912..07068344262f7b73a83073d4da75bffe8b747a61 100644 +index 10659fbf57e4535736fc001c0dbdd9b93e8f60f1..c0bd975bae23d1c05ace42fd8c9846ee4d8ef8f0 100644 --- a/src/node_buffer.cc +++ b/src/node_buffer.cc @@ -44,6 +44,14 @@ @@ -74,7 +74,7 @@ index cd51d9acf9540d506ec35812b9d2c530fce24912..07068344262f7b73a83073d4da75bffe using v8::FunctionCallbackInfo; using v8::Global; using v8::HandleScope; -@@ -582,19 +589,24 @@ void SlowCopy(const FunctionCallbackInfo& args) { +@@ -586,19 +593,24 @@ void SlowCopy(const FunctionCallbackInfo& args) { // Assume caller has properly validated args. uint32_t FastCopy(Local receiver, @@ -107,7 +107,7 @@ index cd51d9acf9540d506ec35812b9d2c530fce24912..07068344262f7b73a83073d4da75bffe return to_copy; } -@@ -858,19 +870,17 @@ void Compare(const FunctionCallbackInfo &args) { +@@ -867,19 +879,17 @@ void Compare(const FunctionCallbackInfo &args) { } int32_t FastCompare(v8::Local, @@ -135,7 +135,7 @@ index cd51d9acf9540d506ec35812b9d2c530fce24912..07068344262f7b73a83073d4da75bffe } static v8::CFunction fast_compare(v8::CFunction::Make(FastCompare)); -@@ -1141,14 +1151,13 @@ void SlowIndexOfNumber(const FunctionCallbackInfo& args) { +@@ -1150,14 +1160,13 @@ void SlowIndexOfNumber(const FunctionCallbackInfo& args) { } int32_t FastIndexOfNumber(v8::Local, @@ -153,7 +153,7 @@ index cd51d9acf9540d506ec35812b9d2c530fce24912..07068344262f7b73a83073d4da75bffe } static v8::CFunction fast_index_of_number( -@@ -1501,21 +1510,31 @@ void SlowWriteString(const FunctionCallbackInfo& args) { +@@ -1511,21 +1520,31 @@ void SlowWriteString(const FunctionCallbackInfo& args) { template uint32_t FastWriteString(Local receiver, @@ -194,10 +194,10 @@ index cd51d9acf9540d506ec35812b9d2c530fce24912..07068344262f7b73a83073d4da75bffe static v8::CFunction fast_write_string_ascii( diff --git a/src/node_external_reference.h b/src/node_external_reference.h -index 8d49a119c218323674e29a522ecf71bd22cdaf1b..d39693f2f45f39e45960453112b0f6460a1b3a4d 100644 +index bb007dbdcce486659afeed07b78103e44b00307b..314a4ded6908a94107de1ae1e550b7d46afdce75 100644 --- a/src/node_external_reference.h +++ b/src/node_external_reference.h -@@ -40,16 +40,16 @@ using CFunctionCallbackWithStrings = +@@ -43,16 +43,16 @@ using CFunctionCallbackWithStrings = const v8::FastOneByteString& base); using CFunctionCallbackWithTwoUint8Arrays = int32_t (*)(v8::Local, @@ -219,7 +219,7 @@ index 8d49a119c218323674e29a522ecf71bd22cdaf1b..d39693f2f45f39e45960453112b0f646 uint32_t, int64_t, bool); -@@ -68,18 +68,20 @@ using CFunctionWithBool = void (*)(v8::Local, +@@ -71,18 +71,20 @@ using CFunctionWithBool = void (*)(v8::Local, using CFunctionWriteString = uint32_t (*)(v8::Local receiver, @@ -246,7 +246,7 @@ index 8d49a119c218323674e29a522ecf71bd22cdaf1b..d39693f2f45f39e45960453112b0f646 // This class manages the external references from the V8 heap // to the C++ addresses in Node.js. diff --git a/src/util.h b/src/util.h -index 0d4676ddade8d91d101b6aeb8763886a234f0bae..7af9ed01a919927ae3897d4989206ec23cfe50d3 100644 +index 48d3c7b8a304049cdb4d4ab2c027b300dc533dc0..f9d5a5b36701b3c65fda65ed8920521ff68e32cd 100644 --- a/src/util.h +++ b/src/util.h @@ -59,6 +59,7 @@ @@ -257,7 +257,7 @@ index 0d4676ddade8d91d101b6aeb8763886a234f0bae..7af9ed01a919927ae3897d4989206ec2 #ifdef _WIN32 /* MAX_PATH is in characters, not bytes. Make sure we have enough headroom. */ -@@ -579,6 +580,16 @@ class BufferValue : public MaybeStackBuffer { +@@ -584,6 +585,16 @@ class BufferValue : public MaybeStackBuffer { static_cast(name->Buffer()->Data()) + name##_offset; \ if (name##_length > 0) CHECK_NE(name##_data, nullptr); diff --git a/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch b/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch index 593eb1542b256..adb0fcc8506a3 100644 --- a/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch +++ b/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch @@ -11,7 +11,7 @@ This patch can be removed when we upgrade to a V8 version that contains the above CL. diff --git a/src/node.cc b/src/node.cc -index f4365c0eda7330bd02a921608951902f41004f77..b2b10ffb572f010992f221de752618fd56b5d50e 100644 +index a0f1deadfc58f18f23467889680219360386f9dd..8da5f5344051663f92d72848fbac9d041ac4fac3 100644 --- a/src/node.cc +++ b/src/node.cc @@ -808,7 +808,7 @@ static ExitCode ProcessGlobalArgsInternal(std::vector* args, diff --git a/patches/node/pass_all_globals_through_require.patch b/patches/node/pass_all_globals_through_require.patch index c6c29f00a2ea3..024cfdbfdddd5 100644 --- a/patches/node/pass_all_globals_through_require.patch +++ b/patches/node/pass_all_globals_through_require.patch @@ -6,10 +6,10 @@ Subject: Pass all globals through "require" (cherry picked from commit 7d015419cb7a0ecfe6728431a4ed2056cd411d62) diff --git a/lib/internal/modules/cjs/loader.js b/lib/internal/modules/cjs/loader.js -index 62c33730ed17cb98b6dd8d69b61360a419518ba5..9b5772fe9b8babbb892c7a5ec79258472da55a76 100644 +index 33385fa792b71ea3802904dd3c59ce845342c595..92b368394e17a9257578cd5b7422391689732d6d 100644 --- a/lib/internal/modules/cjs/loader.js +++ b/lib/internal/modules/cjs/loader.js -@@ -185,6 +185,13 @@ const { +@@ -200,6 +200,13 @@ const { CHAR_FORWARD_SLASH, } = require('internal/constants'); @@ -23,7 +23,7 @@ index 62c33730ed17cb98b6dd8d69b61360a419518ba5..9b5772fe9b8babbb892c7a5ec7925847 const { isProxy, } = require('internal/util/types'); -@@ -1549,10 +1556,12 @@ Module.prototype._compile = function(content, filename, format) { +@@ -1725,10 +1732,12 @@ Module.prototype._compile = function(content, filename, format) { if (this[kIsMainSymbol] && getOptionValue('--inspect-brk')) { const { callAndPauseOnStart } = internalBinding('inspector'); result = callAndPauseOnStart(compiledWrapper, thisValue, exports, diff --git a/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch b/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch index 091bdc3abcec9..e7344756b3855 100644 --- a/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch +++ b/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch @@ -7,10 +7,10 @@ We use this to allow node's 'fs' module to read from ASAR files as if they were a real filesystem. diff --git a/lib/internal/bootstrap/node.js b/lib/internal/bootstrap/node.js -index f5c0208864084a234a05898e793845681b6e80cc..48d809f61eaf09097acb3e996e956e39cf7b4ef3 100644 +index 4fd535f730e6382672b853bf2098b3fefc1f83b4..bd6724de52ee1f01fa42084c7652c71054f0a9c6 100644 --- a/lib/internal/bootstrap/node.js +++ b/lib/internal/bootstrap/node.js -@@ -134,6 +134,10 @@ process.domain = null; +@@ -132,6 +132,10 @@ process.domain = null; } process._exiting = false; diff --git a/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch b/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch index 7ed48324d3c39..7d775d9ef61ba 100644 --- a/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch +++ b/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch @@ -18,7 +18,7 @@ This can be removed when Node.js upgrades to a version of V8 containing CLs from the above issue. diff --git a/src/api/environment.cc b/src/api/environment.cc -index 9b155213ce301df7e396a4a113992499fc7e9910..8fe560014216f1fcea7f6e804816765999cebaa2 100644 +index 7f4f233b26425493a58ce71dfc0c3a92b7c0bef8..c3f422c6b212bf737a906d2a89df85b63c218617 100644 --- a/src/api/environment.cc +++ b/src/api/environment.cc @@ -312,6 +312,10 @@ Isolate* NewIsolate(Isolate::CreateParams* params, @@ -47,10 +47,10 @@ index 9b155213ce301df7e396a4a113992499fc7e9910..8fe560014216f1fcea7f6e8048167659 event_loop, platform, diff --git a/src/env.cc b/src/env.cc -index 1c1062a3996f2bb7de9e91f7f4385c8f8d20f490..b0156ee26c29ebe5b79c97834f3bfe8b56df50c6 100644 +index ddf82c8a18c29c355641e33974c1e5e67867379d..ae43803d8c2de90fb191a8e10605f6f3b18816ed 100644 --- a/src/env.cc +++ b/src/env.cc -@@ -575,14 +575,6 @@ IsolateData::IsolateData(Isolate* isolate, +@@ -577,14 +577,6 @@ IsolateData::IsolateData(Isolate* isolate, // We do not care about overflow since we just want this to be different // from the cppgc id. uint16_t non_cppgc_id = cppgc_id + 1; @@ -65,12 +65,13 @@ index 1c1062a3996f2bb7de9e91f7f4385c8f8d20f490..b0156ee26c29ebe5b79c97834f3bfe8b { // GC could still be run after the IsolateData is destroyed, so we store // the ids in a static map to ensure pointers to them are still valid -@@ -605,14 +597,6 @@ IsolateData::IsolateData(Isolate* isolate, +@@ -607,15 +599,6 @@ IsolateData::IsolateData(Isolate* isolate, } } -IsolateData::~IsolateData() { - if (cpp_heap_ != nullptr) { +- v8::Locker locker(isolate_); - // The CppHeap must be detached before being terminated. - isolate_->DetachCppHeap(); - cpp_heap_->Terminate(); @@ -81,7 +82,7 @@ index 1c1062a3996f2bb7de9e91f7f4385c8f8d20f490..b0156ee26c29ebe5b79c97834f3bfe8b void SetCppgcReference(Isolate* isolate, Local object, diff --git a/src/env.h b/src/env.h -index 1f8dc8f88d40ca95ba13d6517b2b5ed83184e1ce..ec3a813b3b864a0eda2e4aa0748b1447001fca9a 100644 +index 9f1c7ef45b6df10f811936a78ea6d9fcc13fef4f..c429eecd937d1df32a2ff90bc0a22a2e58df3a3d 100644 --- a/src/env.h +++ b/src/env.h @@ -155,7 +155,6 @@ class NODE_EXTERN_PRIVATE IsolateData : public MemoryRetainer { @@ -101,7 +102,7 @@ index 1f8dc8f88d40ca95ba13d6517b2b5ed83184e1ce..ec3a813b3b864a0eda2e4aa0748b1447 worker::Worker* worker_context_ = nullptr; PerIsolateWrapperData* wrapper_data_; diff --git a/src/node.cc b/src/node.cc -index b2b10ffb572f010992f221de752618fd56b5d50e..0ed78ab6b52906e980eebf1f625a1c7cbfc8097b 100644 +index 8da5f5344051663f92d72848fbac9d041ac4fac3..2f58a6fa69069dabb99b5ddb8011991b07fa5f02 100644 --- a/src/node.cc +++ b/src/node.cc @@ -1222,10 +1222,6 @@ InitializeOncePerProcessInternal(const std::vector& args, @@ -263,10 +264,10 @@ index edd413ae9b956b2e59e8166785adef6a8ff06d51..d1c1549efcb0320bc0f7d354db2101ac // Check that all the objects are created and destroyed properly. EXPECT_EQ(CppGCed::kConstructCount, 100); diff --git a/test/cctest/test_environment.cc b/test/cctest/test_environment.cc -index 14e82cc80ff73084fb43b2ef07febfd2667a0abc..b6a92f1685d1083c8f0c0b3ed110509f6d76b59f 100644 +index 008cda77b650dc2d904ae00e7629b5ad05d297ad..103931516cea9beb7f25c53526928e67b3c90d2d 100644 --- a/test/cctest/test_environment.cc +++ b/test/cctest/test_environment.cc -@@ -623,6 +623,9 @@ TEST_F(NodeZeroIsolateTestFixture, CtrlCWithOnlySafeTerminationTest) { +@@ -625,6 +625,9 @@ TEST_F(NodeZeroIsolateTestFixture, CtrlCWithOnlySafeTerminationTest) { // Allocate and initialize Isolate. v8::Isolate::CreateParams create_params; create_params.array_buffer_allocator = allocator.get(); @@ -276,7 +277,7 @@ index 14e82cc80ff73084fb43b2ef07febfd2667a0abc..b6a92f1685d1083c8f0c0b3ed110509f v8::Isolate* isolate = v8::Isolate::Allocate(); CHECK_NOT_NULL(isolate); platform->RegisterIsolate(isolate, ¤t_loop); -@@ -672,8 +675,8 @@ TEST_F(NodeZeroIsolateTestFixture, CtrlCWithOnlySafeTerminationTest) { +@@ -675,8 +678,8 @@ TEST_F(NodeZeroIsolateTestFixture, CtrlCWithOnlySafeTerminationTest) { } // Cleanup. @@ -287,10 +288,10 @@ index 14e82cc80ff73084fb43b2ef07febfd2667a0abc..b6a92f1685d1083c8f0c0b3ed110509f #endif // _WIN32 diff --git a/test/cctest/test_platform.cc b/test/cctest/test_platform.cc -index c2d7893813000601502d050f21ad5c740c6a3b8f..3042f63201bd0df3ad316e09f0f54e210cea8831 100644 +index 53644accf29749bf8fc18b641ae1eaef93cd6f98..7e5b143fb4b633e18a4b2d7440cba7e077c50950 100644 --- a/test/cctest/test_platform.cc +++ b/test/cctest/test_platform.cc -@@ -101,8 +101,8 @@ TEST_F(NodeZeroIsolateTestFixture, IsolatePlatformDelegateTest) { +@@ -102,8 +102,8 @@ TEST_F(NodeZeroIsolateTestFixture, IsolatePlatformDelegateTest) { // Graceful shutdown delegate->Shutdown(); diff --git a/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch b/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch index b99712eaf2547..eb31ed5e0e4a6 100644 --- a/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch +++ b/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch @@ -16,7 +16,7 @@ patch: (cherry picked from commit 30329d06235a9f9733b1d4da479b403462d1b326) diff --git a/src/env-inl.h b/src/env-inl.h -index 49c3513ee9b67b407a2bb6609ac89a5959a78cd1..9a8216354e646e86d692b25c2bed5134e267528c 100644 +index d4b211dfb2f77a65f311701d95365e66d92f8875..4c1a5f2b92d7fdddb8c2e7bbfd6788fdff3645b9 100644 --- a/src/env-inl.h +++ b/src/env-inl.h @@ -62,31 +62,6 @@ inline uv_loop_t* IsolateData::event_loop() const { @@ -52,7 +52,7 @@ index 49c3513ee9b67b407a2bb6609ac89a5959a78cd1..9a8216354e646e86d692b25c2bed5134 return &(wrapper_data_->cppgc_id); } diff --git a/src/env.cc b/src/env.cc -index b428c922ed218cbdf19cdba50d18b1f81a56b8ca..1c1062a3996f2bb7de9e91f7f4385c8f8d20f490 100644 +index f8c24e422756d5101a258175a2f28a96648bea47..ddf82c8a18c29c355641e33974c1e5e67867379d 100644 --- a/src/env.cc +++ b/src/env.cc @@ -23,6 +23,7 @@ @@ -63,7 +63,7 @@ index b428c922ed218cbdf19cdba50d18b1f81a56b8ca..1c1062a3996f2bb7de9e91f7f4385c8f #include #include -@@ -70,7 +71,6 @@ using v8::TryCatch; +@@ -72,7 +73,6 @@ using v8::TryCatch; using v8::Uint32; using v8::Undefined; using v8::Value; @@ -71,7 +71,7 @@ index b428c922ed218cbdf19cdba50d18b1f81a56b8ca..1c1062a3996f2bb7de9e91f7f4385c8f using worker::Worker; int const ContextEmbedderTag::kNodeContextTag = 0x6e6f64; -@@ -527,6 +527,14 @@ void IsolateData::CreateProperties() { +@@ -529,6 +529,14 @@ void IsolateData::CreateProperties() { CreateEnvProxyTemplate(this); } @@ -86,7 +86,7 @@ index b428c922ed218cbdf19cdba50d18b1f81a56b8ca..1c1062a3996f2bb7de9e91f7f4385c8f constexpr uint16_t kDefaultCppGCEmbedderID = 0x90de; Mutex IsolateData::isolate_data_mutex_; std::unordered_map> -@@ -564,36 +572,16 @@ IsolateData::IsolateData(Isolate* isolate, +@@ -566,36 +574,16 @@ IsolateData::IsolateData(Isolate* isolate, v8::CppHeap* cpp_heap = isolate->GetCppHeap(); uint16_t cppgc_id = kDefaultCppGCEmbedderID; @@ -130,7 +130,7 @@ index b428c922ed218cbdf19cdba50d18b1f81a56b8ca..1c1062a3996f2bb7de9e91f7f4385c8f { // GC could still be run after the IsolateData is destroyed, so we store -@@ -625,11 +613,12 @@ IsolateData::~IsolateData() { +@@ -628,11 +616,12 @@ IsolateData::~IsolateData() { } } @@ -146,7 +146,7 @@ index b428c922ed218cbdf19cdba50d18b1f81a56b8ca..1c1062a3996f2bb7de9e91f7f4385c8f void IsolateData::MemoryInfo(MemoryTracker* tracker) const { diff --git a/src/env.h b/src/env.h -index aed066852d7c257076cc7ca8b173fd2a3a353a00..1f8dc8f88d40ca95ba13d6517b2b5ed83184e1ce 100644 +index cfe917c797a6e4bb0f0284ec56be82637f840129..9f1c7ef45b6df10f811936a78ea6d9fcc13fef4f 100644 --- a/src/env.h +++ b/src/env.h @@ -175,10 +175,6 @@ class NODE_EXTERN_PRIVATE IsolateData : public MemoryRetainer { @@ -161,10 +161,10 @@ index aed066852d7c257076cc7ca8b173fd2a3a353a00..1f8dc8f88d40ca95ba13d6517b2b5ed8 inline MultiIsolatePlatform* platform() const; inline const SnapshotData* snapshot_data() const; diff --git a/src/node.h b/src/node.h -index 120e3a1042e29590cbbf4be258a1cd2d3d4f0043..afb26ec5690ccd65a3c36f8b8a1b2de416b9d843 100644 +index bdc77f8eb7abffa9e6c98cd254daedad3e44b981..98ad0ea649eaef43d1f5231f7bc4044e100e08d7 100644 --- a/src/node.h +++ b/src/node.h -@@ -1552,24 +1552,14 @@ void RegisterSignalHandler(int signal, +@@ -1553,24 +1553,14 @@ void RegisterSignalHandler(int signal, bool reset_handler = false); #endif // _WIN32 diff --git a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch index 8c61c3b3d788c..1e68d7e6b68f3 100644 --- a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch +++ b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch @@ -40,10 +40,10 @@ index 0f0cde7be431dcb80c5314b1a9da49886c436d1c..f6d2bd439cad8b9f91c9d9a6cdb302e6 } HistogramBase* histogram; diff --git a/src/node_file.cc b/src/node_file.cc -index 3d7e303741a73134e140152bed637fe5ae8bc1db..5e744bc34b9dc364e8f20adfd37ee41d76451170 100644 +index c7915e2c8161a5d0fa05ccce368ce9c44345c05d..23347379328794467a497c86cbae0b428b7ba791 100644 --- a/src/node_file.cc +++ b/src/node_file.cc -@@ -1061,13 +1061,8 @@ static int32_t FastInternalModuleStat( +@@ -1071,13 +1071,8 @@ static int32_t FastInternalModuleStat( // NOLINTNEXTLINE(runtime/references) This is V8 api. FastApiCallbackOptions& options) { // This needs a HandleScope which needs an isolate. @@ -60,10 +60,10 @@ index 3d7e303741a73134e140152bed637fe5ae8bc1db..5e744bc34b9dc364e8f20adfd37ee41d auto path = std::filesystem::path(input.data, input.data + input.length); diff --git a/src/node_wasi.cc b/src/node_wasi.cc -index 468c2e59903fefe58d9c178d3afac3ef5b09f611..23a376e52e08a8af49dd47c47488552e01287426 100644 +index 090866960beb8f1759c99e95536924b8b61fb723..3f91b651b83a20e70d5b368e012f5ee4b9d16092 100644 --- a/src/node_wasi.cc +++ b/src/node_wasi.cc -@@ -251,17 +251,19 @@ R WASI::WasiFunction::FastCallback( +@@ -275,17 +275,19 @@ R WASI::WasiFunction::FastCallback( return EinvalError(); } diff --git a/patches/node/support_v8_sandboxed_pointers.patch b/patches/node/support_v8_sandboxed_pointers.patch index 100326397f400..f909667671ec9 100644 --- a/patches/node/support_v8_sandboxed_pointers.patch +++ b/patches/node/support_v8_sandboxed_pointers.patch @@ -7,7 +7,7 @@ This refactors several allocators to allocate within the V8 memory cage, allowing them to be compatible with the V8_SANDBOXED_POINTERS feature. diff --git a/src/api/environment.cc b/src/api/environment.cc -index ad323fc800a33c010b0504a4aa55c107498dee26..fc9b056d2f7e25109100fbde5f3ab0aebc8c619a 100644 +index 88c2c932a6b045317c83c911b1cd8267b60d9334..7f4f233b26425493a58ce71dfc0c3a92b7c0bef8 100644 --- a/src/api/environment.cc +++ b/src/api/environment.cc @@ -102,6 +102,14 @@ MaybeLocal PrepareStackTraceCallback(Local context, @@ -64,10 +64,10 @@ index 5387d9625a28bb7d11f7f0f05a5f07d1fee2c216..1b3b8c7b70073926f8dbf02759c2e1af return Buffer::New(env, ab, 0, ab->ByteLength()).FromMaybe(Local()); } diff --git a/src/crypto/crypto_util.cc b/src/crypto/crypto_util.cc -index 25fa9af8153852f49d5289aa253f3c8f7268d89c..a67268f78b18cf71b90b9e31ad733eb0c8d93af3 100644 +index 6346f8f7199cf7b7d3736c59571606fff102fbb6..7eea2eaefcad5780663a6b87985925ae5d70a5f9 100644 --- a/src/crypto/crypto_util.cc +++ b/src/crypto/crypto_util.cc -@@ -335,10 +335,35 @@ ByteSource& ByteSource::operator=(ByteSource&& other) noexcept { +@@ -359,10 +359,35 @@ ByteSource& ByteSource::operator=(ByteSource&& other) noexcept { return *this; } @@ -104,7 +104,7 @@ index 25fa9af8153852f49d5289aa253f3c8f7268d89c..a67268f78b18cf71b90b9e31ad733eb0 std::unique_ptr ptr = ArrayBuffer::NewBackingStore( allocated_data_, size(), -@@ -350,10 +375,11 @@ std::unique_ptr ByteSource::ReleaseToBackingStore() { +@@ -374,10 +399,11 @@ std::unique_ptr ByteSource::ReleaseToBackingStore() { data_ = nullptr; size_ = 0; return ptr; @@ -117,7 +117,7 @@ index 25fa9af8153852f49d5289aa253f3c8f7268d89c..a67268f78b18cf71b90b9e31ad733eb0 return ArrayBuffer::New(env->isolate(), std::move(store)); } -@@ -650,6 +676,16 @@ namespace { +@@ -674,6 +700,16 @@ namespace { // in which case this has the same semantics as // using OPENSSL_malloc. However, if the secure heap is // initialized, SecureBuffer will automatically use it. @@ -134,7 +134,7 @@ index 25fa9af8153852f49d5289aa253f3c8f7268d89c..a67268f78b18cf71b90b9e31ad733eb0 void SecureBuffer(const FunctionCallbackInfo& args) { CHECK(args[0]->IsUint32()); Environment* env = Environment::GetCurrent(args); -@@ -671,6 +707,7 @@ void SecureBuffer(const FunctionCallbackInfo& args) { +@@ -695,6 +731,7 @@ void SecureBuffer(const FunctionCallbackInfo& args) { Local buffer = ArrayBuffer::New(env->isolate(), store); args.GetReturnValue().Set(Uint8Array::New(buffer, 0, len)); } @@ -143,10 +143,10 @@ index 25fa9af8153852f49d5289aa253f3c8f7268d89c..a67268f78b18cf71b90b9e31ad733eb0 void SecureHeapUsed(const FunctionCallbackInfo& args) { #ifndef OPENSSL_IS_BORINGSSL diff --git a/src/crypto/crypto_util.h b/src/crypto/crypto_util.h -index a5967c7d24b8365eb64ab63ec0b3ef8dc23c727e..2acebc3ac2ed9f631fc572f42f19f2e3dccfeb12 100644 +index b85c8daeb464097c2e93bdc7ffdfcfe16b76234b..470a0c4adadcd092dd0105c384e87917ac6fe69a 100644 --- a/src/crypto/crypto_util.h +++ b/src/crypto/crypto_util.h -@@ -241,7 +241,7 @@ class ByteSource { +@@ -242,7 +242,7 @@ class ByteSource { // Creates a v8::BackingStore that takes over responsibility for // any allocated data. The ByteSource will be reset with size = 0 // after being called. @@ -189,7 +189,7 @@ index 3465454e4de4a78912b81e7eca0de395fbe89911..c8ae863460107c69dd77d67c76c11843 Local ret; if (!Buffer::New(env, ab, 0, ab->ByteLength()).ToLocal(&ret)) return {}; diff --git a/src/node_i18n.cc b/src/node_i18n.cc -index 0bcf10a0b35accb8d6d5fe9891d4f52b27d40346..606c2021242e6967ea4195af3e2493a7d5745dae 100644 +index ea7810e41e2667713a896250dc1b904b0a7cf198..865b3128c1edfe7074769f25a0b87878ca094f31 100644 --- a/src/node_i18n.cc +++ b/src/node_i18n.cc @@ -104,7 +104,7 @@ namespace { @@ -253,7 +253,7 @@ index 382df89a2312f76b5293412a8d51969ae5d9fa9c..1c90da9bbcb9547ab36de4d01088c03f // Delegate to V8's allocator for compatibility with the V8 memory cage. diff --git a/src/node_serdes.cc b/src/node_serdes.cc -index 7a70997bc024efa4f3ff4cabe30d5e88dcc7bc78..6552af3ed0acede41c1b16ef77eb359dc54f088a 100644 +index c55a2e28066147ae5ca5def10ec76ccc03c634b4..c54183c72944989219b6437c9e571a3f7f3f8dd5 100644 --- a/src/node_serdes.cc +++ b/src/node_serdes.cc @@ -29,6 +29,26 @@ using v8::ValueSerializer; diff --git a/patches/node/test_formally_mark_some_tests_as_flaky.patch b/patches/node/test_formally_mark_some_tests_as_flaky.patch index 974c8eeeb6c27..5dd4584847450 100644 --- a/patches/node/test_formally_mark_some_tests_as_flaky.patch +++ b/patches/node/test_formally_mark_some_tests_as_flaky.patch @@ -7,7 +7,7 @@ Instead of disabling the tests, flag them as flaky so they still run but don't cause CI failures on flakes. diff --git a/test/parallel/parallel.status b/test/parallel/parallel.status -index fd42444c7b216a4a1fa026efc1bbc1b5df8c7394..26f78764842aaaa781a9409dda2a7d3265351178 100644 +index cc99efd7a743d683d5210ad83e258560c28cbd16..b2f0f7fb49665f0dc924cdd3e344c2579d617fbf 100644 --- a/test/parallel/parallel.status +++ b/test/parallel/parallel.status @@ -5,6 +5,16 @@ prefix parallel diff --git a/patches/node/test_make_eval_snapshot_tests_more_flexible.patch b/patches/node/test_make_eval_snapshot_tests_more_flexible.patch deleted file mode 100644 index 8d930ce9360d2..0000000000000 --- a/patches/node/test_make_eval_snapshot_tests_more_flexible.patch +++ /dev/null @@ -1,83 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Shelley Vohr -Date: Wed, 12 Feb 2025 21:01:13 +0100 -Subject: test: make eval snapshot tests more flexible - -Upstreamed in X - -diff --git a/test/fixtures/eval/eval_messages.snapshot b/test/fixtures/eval/eval_messages.snapshot -index f6fc803e0e3ec3f6a0c7cd056f42ac860012c907..998a06584b3bf3648e6703774aeb31c07bdb5d0e 100644 ---- a/test/fixtures/eval/eval_messages.snapshot -+++ b/test/fixtures/eval/eval_messages.snapshot -@@ -35,7 +35,7 @@ Node.js * - var ______________________________________________; throw 10 - ^ - 10 --(Use `node --trace-uncaught ...` to show where the exception was thrown) -+(Use `* --trace-uncaught ...` to show where the exception was thrown) - - Node.js * - -@@ -43,7 +43,7 @@ Node.js * - var ______________________________________________; throw 10 - ^ - 10 --(Use `node --trace-uncaught ...` to show where the exception was thrown) -+(Use `* --trace-uncaught ...` to show where the exception was thrown) - - Node.js * - done -diff --git a/test/fixtures/eval/stdin_messages.snapshot b/test/fixtures/eval/stdin_messages.snapshot -index 66bd506f758ca93906f850a9c773b617745eb834..0382a6ae3ccd792523cc19847bbdeef4d53e1579 100644 ---- a/test/fixtures/eval/stdin_messages.snapshot -+++ b/test/fixtures/eval/stdin_messages.snapshot -@@ -40,7 +40,7 @@ Node.js * - let ______________________________________________; throw 10 - ^ - 10 --(Use `node --trace-uncaught ...` to show where the exception was thrown) -+(Use `* --trace-uncaught ...` to show where the exception was thrown) - - Node.js * - -@@ -48,7 +48,7 @@ Node.js * - let ______________________________________________; throw 10 - ^ - 10 --(Use `node --trace-uncaught ...` to show where the exception was thrown) -+(Use `* --trace-uncaught ...` to show where the exception was thrown) - - Node.js * - done -diff --git a/test/parallel/test-node-output-eval.mjs b/test/parallel/test-node-output-eval.mjs -index d8c52176b1c3c3a0664d7f6b6750da03aa960587..8a3cc59574206769e4c80a04f05b03586f511ac2 100644 ---- a/test/parallel/test-node-output-eval.mjs -+++ b/test/parallel/test-node-output-eval.mjs -@@ -1,6 +1,7 @@ - import '../common/index.mjs'; - import * as fixtures from '../common/fixtures.mjs'; - import * as snapshot from '../common/assertSnapshot.js'; -+import { basename } from 'node:path'; - import { describe, it } from 'node:test'; - - describe('eval output', { concurrency: true }, () => { -@@ -16,6 +17,7 @@ describe('eval output', { concurrency: true }, () => { - snapshot.replaceNodeVersion, - removeStackTraces, - filterEmptyLines, -+ generalizeProcessName, - ); - - function removeStackTraces(output) { -@@ -26,6 +28,11 @@ describe('eval output', { concurrency: true }, () => { - return output.replaceAll(/^\s*$/gm, ''); - } - -+ function generalizeProcessName(output) { -+ const baseName = basename(process.argv0 || 'node', '.exe'); -+ return output.replaceAll(`${baseName} --`, '* --'); -+ } -+ - const tests = [ - { name: 'eval/eval_messages.js' }, - { name: 'eval/stdin_messages.js' }, diff --git a/patches/node/zlib_fix_pointer_alignment.patch b/patches/node/zlib_fix_pointer_alignment.patch index 47c51a49e62ab..418e74d53ccdd 100644 --- a/patches/node/zlib_fix_pointer_alignment.patch +++ b/patches/node/zlib_fix_pointer_alignment.patch @@ -16,10 +16,10 @@ a bus error killing node. see https://github.com/google/brotli/issues/1159 diff --git a/src/node_zlib.cc b/src/node_zlib.cc -index 90307cd4984ae5aa55386f2980ad9cd540322dfd..6f12b5034d1a98da50c064cf2cfdf12fc88137eb 100644 +index 0b7c47b326c7c5480086228b3d40d54c260ef16a..7e6b38ecd1aa360012c0d73e94412530a48cb8c3 100644 --- a/src/node_zlib.cc +++ b/src/node_zlib.cc -@@ -493,7 +493,8 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { +@@ -608,7 +608,8 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { } static void* AllocForBrotli(void* data, size_t size) { @@ -29,7 +29,7 @@ index 90307cd4984ae5aa55386f2980ad9cd540322dfd..6f12b5034d1a98da50c064cf2cfdf12f CompressionStream* ctx = static_cast(data); char* memory = UncheckedMalloc(size); if (memory == nullptr) [[unlikely]] { -@@ -502,7 +503,7 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { +@@ -617,7 +618,7 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { *reinterpret_cast(memory) = size; ctx->unreported_allocations_.fetch_add(size, std::memory_order_relaxed); @@ -38,7 +38,7 @@ index 90307cd4984ae5aa55386f2980ad9cd540322dfd..6f12b5034d1a98da50c064cf2cfdf12f } static void FreeForZlib(void* data, void* pointer) { -@@ -510,7 +511,8 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { +@@ -625,7 +626,8 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { return; } CompressionStream* ctx = static_cast(data); diff --git a/script/node-disabled-tests.json b/script/node-disabled-tests.json index 09c1eda68c3a9..469f9cf2ff649 100644 --- a/script/node-disabled-tests.json +++ b/script/node-disabled-tests.json @@ -30,6 +30,7 @@ "parallel/test-http2-https-fallback", "parallel/test-http2-server-unknown-protocol", "parallel/test-https-agent-session-reuse", + "parallel/test-https-client-renegotiation-limit", "parallel/test-https-options-boolean-check", "parallel/test-icu-env", "parallel/test-icu-minimum-version", From 6bd6180703c6b744769e3e3997f11f3ec40a2055 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 6 May 2025 16:10:25 +0200 Subject: [PATCH 019/186] fix: allowed dialog file types with one filter (#46946) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/ui/file_dialog_mac.mm | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/shell/browser/ui/file_dialog_mac.mm b/shell/browser/ui/file_dialog_mac.mm index 99c46738256cc..881054f0445d6 100644 --- a/shell/browser/ui/file_dialog_mac.mm +++ b/shell/browser/ui/file_dialog_mac.mm @@ -131,10 +131,6 @@ void SetAllowedFileTypes(NSSavePanel* dialog, const Filters& filters) { [file_types_list addObject:content_types_set]; } - // Don't add file format picker. - if ([file_types_list count] <= 1) - return; - NSArray* content_types = [file_types_list objectAtIndex:0]; __block BOOL allowAllFiles = NO; @@ -148,6 +144,10 @@ void SetAllowedFileTypes(NSSavePanel* dialog, const Filters& filters) { [dialog setAllowedContentTypes:allowAllFiles ? @[] : content_types]; + // Don't add file format picker. + if ([file_types_list count] <= 1) + return; + // Add file format picker. ElectronAccessoryView* accessoryView = [[ElectronAccessoryView alloc] initWithFrame:NSMakeRect(0.0, 0.0, 200, 32.0)]; From 3029cdb4dd77f4ed6549a1c5dc082fb311bc610f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 6 May 2025 17:29:14 +0200 Subject: [PATCH 020/186] fix: crash on macOS dialog after `window-all-closed` (#46952) fix: crash on dialog after window-all-closed Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/ui/cocoa/electron_ns_window.mm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/shell/browser/ui/cocoa/electron_ns_window.mm b/shell/browser/ui/cocoa/electron_ns_window.mm index f1435d0fc7f5e..cf9d479b93fc5 100644 --- a/shell/browser/ui/cocoa/electron_ns_window.mm +++ b/shell/browser/ui/cocoa/electron_ns_window.mm @@ -218,7 +218,7 @@ - (void)rotateWithEvent:(NSEvent*)event { } - (NSRect)contentRectForFrameRect:(NSRect)frameRect { - if (shell_->has_frame()) + if (shell_ && shell_->has_frame()) return [super contentRectForFrameRect:frameRect]; else return frameRect; From 2cf774b2b8a3fe92264522d1070642caf4f4e70f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 6 May 2025 15:56:36 -0500 Subject: [PATCH 021/186] test: test menu rendering accelerators (#46965) * test: test menu rendering accelerators Co-authored-by: Shelley Vohr * Update spec/api-menu-spec.ts Co-authored-by: John Kleinschmidt Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- spec/api-global-shortcut-spec.ts | 38 +---------------------------- spec/api-menu-spec.ts | 30 +++++++++++++---------- spec/lib/accelerator-helpers.ts | 41 ++++++++++++++++++++++++++++++++ 3 files changed, 59 insertions(+), 50 deletions(-) create mode 100644 spec/lib/accelerator-helpers.ts diff --git a/spec/api-global-shortcut-spec.ts b/spec/api-global-shortcut-spec.ts index a88d08647347b..cf6f9fc7d752b 100644 --- a/spec/api-global-shortcut-spec.ts +++ b/spec/api-global-shortcut-spec.ts @@ -2,51 +2,15 @@ import { globalShortcut } from 'electron/main'; import { expect } from 'chai'; +import { singleModifierCombinations, doubleModifierCombinations } from './lib/accelerator-helpers'; import { ifdescribe } from './lib/spec-helpers'; -const modifiers = [ - 'CmdOrCtrl', - 'Alt', - process.platform === 'darwin' ? 'Option' : null, - 'AltGr', - 'Shift', - 'Super', - 'Meta' -].filter(Boolean); - -const keyCodes = [ - ...Array.from({ length: 10 }, (_, i) => `${i}`), // 0 to 9 - ...Array.from({ length: 26 }, (_, i) => String.fromCharCode(65 + i)), // A to Z - ...Array.from({ length: 24 }, (_, i) => `F${i + 1}`), // F1 to F24 - ')', '!', '@', '#', '$', '%', '^', '&', '*', '(', ':', ';', ':', '+', '=', - '<', ',', '_', '-', '>', '.', '?', '/', '~', '`', '{', ']', '[', '|', '\\', - '}', '"', 'Plus', 'Space', 'Tab', 'Capslock', 'Numlock', 'Scrolllock', - 'Backspace', 'Delete', 'Insert', 'Return', 'Enter', 'Up', 'Down', 'Left', - 'Right', 'Home', 'End', 'PageUp', 'PageDown', 'Escape', 'Esc', 'PrintScreen', - 'num0', 'num1', 'num2', 'num3', 'num4', 'num5', 'num6', 'num7', 'num8', 'num9', - 'numdec', 'numadd', 'numsub', 'nummult', 'numdiv' -]; - ifdescribe(process.platform !== 'win32')('globalShortcut module', () => { beforeEach(() => { globalShortcut.unregisterAll(); }); it('can register and unregister single accelerators', () => { - const singleModifierCombinations = modifiers.flatMap( - mod => keyCodes.map(key => { - return key === '+' ? `${mod}+Plus` : `${mod}+${key}`; - }) - ); - - const doubleModifierCombinations = modifiers.flatMap( - (mod1, i) => modifiers.slice(i + 1).flatMap( - mod2 => keyCodes.map(key => { - return key === '+' ? `${mod1}+${mod2}+Plus` : `${mod1}+${mod2}+${key}`; - }) - ) - ); - const combinations = [...singleModifierCombinations, ...doubleModifierCombinations]; combinations.forEach((accelerator) => { diff --git a/spec/api-menu-spec.ts b/spec/api-menu-spec.ts index e3343e8cf1077..9e8143e94ac82 100644 --- a/spec/api-menu-spec.ts +++ b/spec/api-menu-spec.ts @@ -7,6 +7,7 @@ import { once } from 'node:events'; import * as path from 'node:path'; import { setTimeout } from 'node:timers/promises'; +import { singleModifierCombinations } from './lib/accelerator-helpers'; import { ifit } from './lib/spec-helpers'; import { closeWindow } from './lib/window-helpers'; import { sortMenuItems } from '../lib/browser/api/menu-utils'; @@ -927,19 +928,22 @@ describe('Menu module', function () { w.show(); }); - it('does not crash when rendering menu item with Super or meta accelerator', async () => { - const menu = Menu.buildFromTemplate([{ - label: 'Test Super', - accelerator: 'Super+Ctrl+T' - }, { - label: 'Test Meta', - accelerator: 'Meta+Ctrl+T' - }]); - const menuWillClose = once(menu, 'menu-will-close'); - menu.popup({ window: w }); - menu.closePopup(); - await menuWillClose; - }); + const chunkSize = 10; + let chunkCount = 0; + const totalChunks = Math.ceil(singleModifierCombinations.length / chunkSize); + for (let i = 0; i < singleModifierCombinations.length; i += chunkSize) { + const chunk = singleModifierCombinations.slice(i, i + chunkSize); + it(`does not crash when rendering menu item with single accelerator combinations ${++chunkCount}/${totalChunks}`, async () => { + const menu = Menu.buildFromTemplate([ + ...chunk.map(combination => ({ + label: `Test ${combination}`, + accelerator: combination + })) + ]); + menu.popup({ window: w }); + menu.closePopup(); + }); + } }); describe('Menu.setApplicationMenu', () => { diff --git a/spec/lib/accelerator-helpers.ts b/spec/lib/accelerator-helpers.ts new file mode 100644 index 0000000000000..0ed3dd807b853 --- /dev/null +++ b/spec/lib/accelerator-helpers.ts @@ -0,0 +1,41 @@ +/** + * @fileoverview A set of helper functions to make it easier to work + * with accelerators across tests. + */ + +const modifiers = [ + 'CmdOrCtrl', + 'Alt', + process.platform === 'darwin' ? 'Option' : null, + 'AltGr', + 'Shift', + 'Super', + 'Meta' +].filter(Boolean); + +const keyCodes = [ + ...Array.from({ length: 10 }, (_, i) => `${i}`), // 0 to 9 + ...Array.from({ length: 26 }, (_, i) => String.fromCharCode(65 + i)), // A to Z + ...Array.from({ length: 24 }, (_, i) => `F${i + 1}`), // F1 to F24 + ')', '!', '@', '#', '$', '%', '^', '&', '*', '(', ':', ';', ':', '+', '=', + '<', ',', '_', '-', '>', '.', '?', '/', '~', '`', '{', ']', '[', '|', '\\', + '}', '"', 'Plus', 'Space', 'Tab', 'Capslock', 'Numlock', 'Scrolllock', + 'Backspace', 'Delete', 'Insert', 'Return', 'Enter', 'Up', 'Down', 'Left', + 'Right', 'Home', 'End', 'PageUp', 'PageDown', 'Escape', 'Esc', 'PrintScreen', + 'num0', 'num1', 'num2', 'num3', 'num4', 'num5', 'num6', 'num7', 'num8', 'num9', + 'numdec', 'numadd', 'numsub', 'nummult', 'numdiv' +]; + +export const singleModifierCombinations = modifiers.flatMap( + mod => keyCodes.map(key => { + return key === '+' ? `${mod}+Plus` : `${mod}+${key}`; + }) +); + +export const doubleModifierCombinations = modifiers.flatMap( + (mod1, i) => modifiers.slice(i + 1).flatMap( + mod2 => keyCodes.map(key => { + return key === '+' ? `${mod1}+${mod2}+Plus` : `${mod1}+${mod2}+${key}`; + }) + ) +); From 4597f4ba9e7dd088f3ebc3bbadd32e59495b0332 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 6 May 2025 16:08:57 -0500 Subject: [PATCH 022/186] refactor: pass `gfx::ResizeEdge` by value (#46960) refactor: pass gfx::ResizeEdge by value It is an enum class, so no reason to pass by reference Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_base_window.cc | 2 +- shell/browser/api/electron_api_base_window.h | 2 +- shell/browser/native_window.cc | 2 +- shell/browser/native_window.h | 2 +- shell/browser/native_window_observer.h | 2 +- shell/common/gin_converters/gfx_converter.cc | 2 +- shell/common/gin_converters/gfx_converter.h | 2 +- 7 files changed, 7 insertions(+), 7 deletions(-) diff --git a/shell/browser/api/electron_api_base_window.cc b/shell/browser/api/electron_api_base_window.cc index 27d9da1ba7dbd..d9f0a9987ccda 100644 --- a/shell/browser/api/electron_api_base_window.cc +++ b/shell/browser/api/electron_api_base_window.cc @@ -254,7 +254,7 @@ void BaseWindow::OnWindowRestore() { } void BaseWindow::OnWindowWillResize(const gfx::Rect& new_bounds, - const gfx::ResizeEdge& edge, + const gfx::ResizeEdge edge, bool* prevent_default) { v8::Isolate* isolate = JavascriptEnvironment::GetIsolate(); v8::HandleScope handle_scope(isolate); diff --git a/shell/browser/api/electron_api_base_window.h b/shell/browser/api/electron_api_base_window.h index 68619364a8fbf..0a44c592781eb 100644 --- a/shell/browser/api/electron_api_base_window.h +++ b/shell/browser/api/electron_api_base_window.h @@ -71,7 +71,7 @@ class BaseWindow : public gin_helper::TrackableObject, void OnWindowMinimize() override; void OnWindowRestore() override; void OnWindowWillResize(const gfx::Rect& new_bounds, - const gfx::ResizeEdge& edge, + gfx::ResizeEdge edge, bool* prevent_default) override; void OnWindowResize() override; void OnWindowResized() override; diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 15d7fbc2a7b6e..ffd9c4a36930f 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -602,7 +602,7 @@ void NativeWindow::NotifyWindowRestore() { } void NativeWindow::NotifyWindowWillResize(const gfx::Rect& new_bounds, - const gfx::ResizeEdge& edge, + const gfx::ResizeEdge edge, bool* prevent_default) { observers_.Notify(&NativeWindowObserver::OnWindowWillResize, new_bounds, edge, prevent_default); diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index 46970600038d6..b729b068fc878 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -318,7 +318,7 @@ class NativeWindow : public base::SupportsUserData, void NotifyWindowRestore(); void NotifyWindowMove(); void NotifyWindowWillResize(const gfx::Rect& new_bounds, - const gfx::ResizeEdge& edge, + gfx::ResizeEdge edge, bool* prevent_default); void NotifyWindowResize(); void NotifyWindowResized(); diff --git a/shell/browser/native_window_observer.h b/shell/browser/native_window_observer.h index 22efa174aedd4..1adf24d474043 100644 --- a/shell/browser/native_window_observer.h +++ b/shell/browser/native_window_observer.h @@ -78,7 +78,7 @@ class NativeWindowObserver : public base::CheckedObserver { virtual void OnWindowMinimize() {} virtual void OnWindowRestore() {} virtual void OnWindowWillResize(const gfx::Rect& new_bounds, - const gfx::ResizeEdge& edge, + gfx::ResizeEdge edge, bool* prevent_default) {} virtual void OnWindowResize() {} virtual void OnWindowResized() {} diff --git a/shell/common/gin_converters/gfx_converter.cc b/shell/common/gin_converters/gfx_converter.cc index c6c75da3f1379..c54ec7062eabd 100644 --- a/shell/common/gin_converters/gfx_converter.cc +++ b/shell/common/gin_converters/gfx_converter.cc @@ -197,7 +197,7 @@ v8::Local Converter::ToV8( v8::Local Converter::ToV8( v8::Isolate* isolate, - const gfx::ResizeEdge& val) { + const gfx::ResizeEdge val) { switch (val) { case gfx::ResizeEdge::kRight: return StringToV8(isolate, "right"); diff --git a/shell/common/gin_converters/gfx_converter.h b/shell/common/gin_converters/gfx_converter.h index 43903b464ed21..700ce8134c3f7 100644 --- a/shell/common/gin_converters/gfx_converter.h +++ b/shell/common/gin_converters/gfx_converter.h @@ -77,7 +77,7 @@ struct Converter { template <> struct Converter { static v8::Local ToV8(v8::Isolate* isolate, - const gfx::ResizeEdge& val); + const gfx::ResizeEdge val); }; template <> From c9d1615b19f6e9e199c7c884f3ebd2f227a33ccb Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 6 May 2025 19:11:30 -0500 Subject: [PATCH 023/186] refactor: add `gin_helper::Dictionary::ValueOrDefault()` (#46969) * feat: add gin_helper::Dictionary::ValueOrDefault() A convenience function for using a default value if the specified key isn't present in the dictionary. Co-authored-by: Charles Kerr * refactor: use ValueOrDefault() in native_window.cc Co-authored-by: Charles Kerr * refactor: use ValueOrDefault() in native_window_mac.mm Co-authored-by: Charles Kerr * refactor: use ValueOrDefault() in native_window_views.cc Co-authored-by: Charles Kerr * refactor: use ValueOrDefault() in electron_api_native_image.cc Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window.cc | 16 +++--- shell/browser/native_window_mac.mm | 49 +++++++++---------- shell/browser/native_window_views.cc | 16 +++--- shell/common/api/electron_api_native_image.cc | 12 ++--- shell/common/gin_helper/dictionary.h | 9 ++++ 5 files changed, 48 insertions(+), 54 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index ffd9c4a36930f..442503fd8ba3a 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -168,17 +168,17 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { Center(); } - bool use_content_size = false; - options.Get(options::kUseContentSize, &use_content_size); + const bool use_content_size = + options.ValueOrDefault(options::kUseContentSize, false); // On Linux and Window we may already have maximum size defined. extensions::SizeConstraints size_constraints( use_content_size ? GetContentSizeConstraints() : GetSizeConstraints()); - int min_width = size_constraints.GetMinimumSize().width(); - int min_height = size_constraints.GetMinimumSize().height(); - options.Get(options::kMinWidth, &min_width); - options.Get(options::kMinHeight, &min_height); + const int min_width = options.ValueOrDefault( + options::kMinWidth, size_constraints.GetMinimumSize().width()); + const int min_height = options.ValueOrDefault( + options::kMinHeight, size_constraints.GetMinimumSize().height()); size_constraints.set_minimum_size(gfx::Size(min_width, min_height)); gfx::Size max_size = size_constraints.GetMaximumSize(); @@ -278,9 +278,7 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { SetTitle(title); // Then show it. - bool show = true; - options.Get(options::kShow, &show); - if (show) + if (options.ValueOrDefault(options::kShow, true)) Show(); } diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index c603590f54136..4c6bda59bd328 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -119,42 +119,37 @@ static bool FromV8(v8::Isolate* isolate, ui::NativeTheme::GetInstanceForNativeUi()->AddObserver(this); display::Screen::GetScreen()->AddObserver(this); - int width = 800, height = 600; - options.Get(options::kWidth, &width); - options.Get(options::kHeight, &height); + const int width = options.ValueOrDefault(options::kWidth, 800); + const int height = options.ValueOrDefault(options::kHeight, 600); NSRect main_screen_rect = [[[NSScreen screens] firstObject] frame]; gfx::Rect bounds(round((NSWidth(main_screen_rect) - width) / 2), round((NSHeight(main_screen_rect) - height) / 2), width, height); - bool resizable = true; - options.Get(options::kResizable, &resizable); + const bool resizable = options.ValueOrDefault(options::kResizable, true); options.Get(options::kZoomToPageWidth, &zoom_to_page_width_); options.Get(options::kSimpleFullscreen, &always_simple_fullscreen_); options.GetOptional(options::kTrafficLightPosition, &traffic_light_position_); options.Get(options::kVisualEffectState, &visual_effect_state_); - bool minimizable = true; - options.Get(options::kMinimizable, &minimizable); + const bool minimizable = options.ValueOrDefault(options::kMinimizable, true); - bool maximizable = true; - options.Get(options::kMaximizable, &maximizable); + const bool maximizable = options.ValueOrDefault(options::kMaximizable, true); - bool closable = true; - options.Get(options::kClosable, &closable); + const bool closable = options.ValueOrDefault(options::kClosable, true); - std::string tabbingIdentifier; - options.Get(options::kTabbingIdentifier, &tabbingIdentifier); + const std::string tabbingIdentifier = + options.ValueOrDefault(options::kTabbingIdentifier, std::string{}); - std::string windowType; - options.Get(options::kType, &windowType); + const std::string windowType = + options.ValueOrDefault(options::kType, std::string{}); - bool hiddenInMissionControl = false; - options.Get(options::kHiddenInMissionControl, &hiddenInMissionControl); + const bool hiddenInMissionControl = + options.ValueOrDefault(options::kHiddenInMissionControl, false); - bool paint_when_initially_hidden = true; - options.Get(options::kPaintWhenInitiallyHidden, &paint_when_initially_hidden); + const bool paint_when_initially_hidden = + options.ValueOrDefault(options::kPaintWhenInitiallyHidden, true); // The window without titlebar is treated the same with frameless window. if (title_bar_style_ != TitleBarStyle::kNormal) @@ -164,8 +159,8 @@ static bool FromV8(v8::Isolate* isolate, // The NSWindowStyleMaskFullSizeContentView style removes rounded corners // for frameless window. - bool rounded_corner = true; - options.Get(options::kRoundedCorners, &rounded_corner); + const bool rounded_corner = + options.ValueOrDefault(options::kRoundedCorners, true); if (!rounded_corner && !has_frame()) styleMask = NSWindowStyleMaskBorderless; @@ -288,19 +283,19 @@ static bool FromV8(v8::Isolate* isolate, } // Resize to content bounds. - bool use_content_size = false; - options.Get(options::kUseContentSize, &use_content_size); + const bool use_content_size = + options.ValueOrDefault(options::kUseContentSize, false); if (!has_frame() || use_content_size) SetContentSize(gfx::Size(width, height)); // Enable the NSView to accept first mouse event. - bool acceptsFirstMouse = false; - options.Get(options::kAcceptFirstMouse, &acceptsFirstMouse); + const bool acceptsFirstMouse = + options.ValueOrDefault(options::kAcceptFirstMouse, false); [window_ setAcceptsFirstMouse:acceptsFirstMouse]; // Disable auto-hiding cursor. - bool disableAutoHideCursor = false; - options.Get(options::kDisableAutoHideCursor, &disableAutoHideCursor); + const bool disableAutoHideCursor = + options.ValueOrDefault(options::kDisableAutoHideCursor, false); [window_ setDisableAutoHideCursor:disableAutoHideCursor]; SetHiddenInMissionControl(hiddenInMissionControl); diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index e46aaff87007f..d7b6d0ac54c02 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -256,10 +256,9 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, SetContentSizeConstraints(extensions::SizeConstraints( gfx::Size(), gfx::Size(INT_MAX / 10, INT_MAX / 10))); - int width = 800, height = 600; - options.Get(options::kWidth, &width); - options.Get(options::kHeight, &height); - gfx::Rect bounds(0, 0, width, height); + const int width = options.ValueOrDefault(options::kWidth, 800); + const int height = options.ValueOrDefault(options::kHeight, 600); + const gfx::Rect bounds{0, 0, width, height}; widget_size_ = bounds.size(); widget()->AddObserver(this); @@ -309,18 +308,15 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, widget()->SetNativeWindowProperty(kNativeWindowKey.c_str(), this); SetCanResize(resizable_); - bool fullscreen = false; - options.Get(options::kFullscreen, &fullscreen); + const bool fullscreen = options.ValueOrDefault(options::kFullscreen, false); std::string window_type; options.Get(options::kType, &window_type); #if BUILDFLAG(IS_LINUX) // Set _GTK_THEME_VARIANT to dark if we have "dark-theme" option set. - bool use_dark_theme = false; - if (options.Get(options::kDarkTheme, &use_dark_theme) && use_dark_theme) { - SetGTKDarkThemeEnabled(use_dark_theme); - } + if (options.ValueOrDefault(options::kDarkTheme, false)) + SetGTKDarkThemeEnabled(true); if (parent) SetParentWindow(parent); diff --git a/shell/common/api/electron_api_native_image.cc b/shell/common/api/electron_api_native_image.cc index ffe3267b2999a..67970d8faea24 100644 --- a/shell/common/api/electron_api_native_image.cc +++ b/shell/common/api/electron_api_native_image.cc @@ -382,12 +382,9 @@ gin::Handle NativeImage::Crop(v8::Isolate* isolate, } void NativeImage::AddRepresentation(const gin_helper::Dictionary& options) { - int width = 0; - int height = 0; - float scale_factor = 1.0f; - options.Get("width", &width); - options.Get("height", &height); - options.Get("scaleFactor", &scale_factor); + const int width = options.ValueOrDefault("width", 0); + const int height = options.ValueOrDefault("height", 0); + const float scale_factor = options.ValueOrDefault("scaleFactor", 1.0F); bool skia_rep_added = false; gfx::ImageSkia image_skia = image_.AsImageSkia(); @@ -515,8 +512,7 @@ gin::Handle NativeImage::CreateFromBitmap( bitmap.allocN32Pixels(width, height, false); bitmap.writePixels({info, buffer_data.data(), bitmap.rowBytes()}); - float scale_factor = 1.0F; - options.Get("scaleFactor", &scale_factor); + const float scale_factor = options.ValueOrDefault("scaleFactor", 1.0F); gfx::ImageSkia image_skia = gfx::ImageSkia::CreateFromBitmap(bitmap, scale_factor); diff --git a/shell/common/gin_helper/dictionary.h b/shell/common/gin_helper/dictionary.h index 589c24d1f7346..85d7c7786dc5a 100644 --- a/shell/common/gin_helper/dictionary.h +++ b/shell/common/gin_helper/dictionary.h @@ -67,6 +67,15 @@ class Dictionary : public gin::Dictionary { return result.FromMaybe(false); } + // Convenience function for using a default value if the + // specified key isn't present in the dictionary. + template + T ValueOrDefault(const std::string_view key, T default_value) const { + if (auto value = T{}; Get(key, &value)) + return value; + return default_value; + } + // Like normal Get but put result in an std::optional. template bool GetOptional(const std::string_view key, std::optional* out) const { From 839590eb9024d2b854c886943e545a59aea82ec6 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 7 May 2025 09:35:56 +0200 Subject: [PATCH 024/186] chore: bump chromium to 138.0.7164.0 (37-x-y) (#46964) * chore: bump chromium in DEPS to 138.0.7164.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6508870: Add missing PermissionType mapping and remove default case. https://chromium-review.googlesource.com/c/chromium/src/+/6508870 Co-authored-by: Shelley Vohr * chore: fixup patch indices Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- DEPS | 2 +- ..._scheduler_throttling_per_renderview.patch | 4 +-- ..._depend_on_packed_resource_integrity.patch | 16 ++++++------ patches/chromium/can_create_window.patch | 10 +++---- ...e_reference_to_chrome_browser_themes.patch | 2 +- ...xpose_setuseragent_on_networkcontext.patch | 8 +++--- .../extend_apply_webpreferences.patch | 2 +- ...sharingpicker_on_supported_platforms.patch | 6 ++--- ...moothing_css_rule_and_blink_painting.patch | 8 +++--- ..._raw_response_headers_from_urlloader.patch | 12 ++++----- ...allback_for_sync_and_async_clipboard.patch | 4 +-- ...king_and_message_bubbling_on_windows.patch | 6 ++--- patches/chromium/frame_host_manager.patch | 2 +- ...tform_electron_can_call_x11_property.patch | 4 +-- ..._avoid_private_macos_api_usage.patch.patch | 8 +++--- ...emote_certificate_verification_logic.patch | 16 ++++++------ ...eated_to_allow_for_browser_initiated.patch | 2 +- ..._electron_permissiontypes_into_blink.patch | 26 +++++-------------- .../render_widget_host_view_base.patch | 10 +++---- .../render_widget_host_view_mac.patch | 8 +++--- patches/chromium/resource_file_conflict.patch | 6 ++--- patches/chromium/webview_fullscreen.patch | 2 +- 22 files changed, 76 insertions(+), 88 deletions(-) diff --git a/DEPS b/DEPS index 8ea86b2458522..98aa16e443445 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7160.0', + '138.0.7164.0', 'node_version': 'v22.15.0', 'nan_version': diff --git a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch index a36161acbffe9..3ed6d3c7d73e3 100644 --- a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch +++ b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch @@ -116,7 +116,7 @@ index b1689844282d6917b9750fbc6a875848ddf84b70..f1cc159b7c3448a33a6d9e213f8fbd3b // Visibility ----------------------------------------------------------- diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index 1af1fa035b3da8967526d704e362ddbc5c3194ac..f470ada1bf84938427fb89f4508e5f56aaeebc1f 100644 +index e167db6d5f208f2f3e923ec7dec7c4da4155dd90..cd31f34df12a94748e4fc9066c6f344610ce73f0 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -2466,6 +2466,10 @@ void WebViewImpl::SetPageLifecycleStateInternal( @@ -130,7 +130,7 @@ index 1af1fa035b3da8967526d704e362ddbc5c3194ac..f470ada1bf84938427fb89f4508e5f56 bool storing_in_bfcache = new_state->is_in_back_forward_cache && !old_state->is_in_back_forward_cache; bool restoring_from_bfcache = !new_state->is_in_back_forward_cache && -@@ -3989,10 +3993,23 @@ PageScheduler* WebViewImpl::Scheduler() const { +@@ -3987,10 +3991,23 @@ PageScheduler* WebViewImpl::Scheduler() const { return GetPage()->GetPageScheduler(); } diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index 72c3e0e47ec65..b7c7daad9cc48 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -11,10 +11,10 @@ if we ever align our .pak file generation with Chrome we can remove this patch. diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b47749874 100644 +index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff62717ba00 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn -@@ -200,11 +200,16 @@ if (!is_android && !is_mac) { +@@ -197,11 +197,16 @@ if (!is_android && !is_mac) { "common/crash_keys.h", ] @@ -33,10 +33,10 @@ index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index ae32014a8a25f3b1de7f6087551a87400e1463b5..be77c4e02cc495194ed6b248e56bcb75abe4efce 100644 +index ed639e1fd384ce325f56df99d5fcf72f00aaf2b1..ea7919d5a9dd2699822facb47ae974a7a4e87172 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4627,7 +4627,7 @@ static_library("browser") { +@@ -4633,7 +4633,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,10 +46,10 @@ index ae32014a8a25f3b1de7f6087551a87400e1463b5..be77c4e02cc495194ed6b248e56bcb75 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index e08035df314884fab39562cd9ee4960ec5af3cb5..28f0f4d671e16ffff770b43fa5a2e366491d4b30 100644 +index dd82cb96686234350a078536bce94a47aeb96ef8..2cb71c9c12ad89aa6a16c538f97979b3094b9cda 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7185,9 +7185,12 @@ test("unit_tests") { +@@ -7210,9 +7210,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index e08035df314884fab39562cd9ee4960ec5af3cb5..28f0f4d671e16ffff770b43fa5a2e366 "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8153,6 +8156,10 @@ test("unit_tests") { +@@ -8170,6 +8173,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index e08035df314884fab39562cd9ee4960ec5af3cb5..28f0f4d671e16ffff770b43fa5a2e366 sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8208,7 +8215,6 @@ test("unit_tests") { +@@ -8225,7 +8232,6 @@ test("unit_tests") { # Non-android deps for "unit_tests" target. deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 1d60f2508309c..0e62932fe95c0 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,7 +9,7 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 9d5452597f64906ac1d3223ca5290776df8809c5..46ddad111b2feb5cc1064a1eeb424800d2cba6c1 100644 +index 184fb0e5ce15f624300a35f47ef7e34759e2e9eb..73f56d65160a114bea9dcefa6ba03a417b7a273b 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc @@ -9777,6 +9777,7 @@ void RenderFrameHostImpl::CreateNewWindow( @@ -66,10 +66,10 @@ index 55bb4ae3bab4cdf20b3e1dde9450a5c0e4e62b37..fe444c7fa140166a1b65c7a8a2676e2d // Operation result when the renderer asks the browser to create a new window. diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc -index 210e5ffc0da31cc0d214e8a3e65f7d8b045fd33e..237b279eeefe5b18402a7dea8d1c00072655ed22 100644 +index 1f5468c6f81db64929fbfc6715a586c69a29afc9..4c37155c240c3ef2c54523cfe12e0c0054a6e603 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc -@@ -823,6 +823,8 @@ bool ContentBrowserClient::CanCreateWindow( +@@ -828,6 +828,8 @@ bool ContentBrowserClient::CanCreateWindow( const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -79,7 +79,7 @@ index 210e5ffc0da31cc0d214e8a3e65f7d8b045fd33e..237b279eeefe5b18402a7dea8d1c0007 bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index be551d7a09330edf4a204b181acb382c2c3d13f4..5ed4df05dd22cbf901ecbbcc9d892de806c93890 100644 +index a0f6c7e63a32d4cfc8a8e25cdbd90f23dbce8f24..4a995e6c35abba567bb8be826effb06ba7e2119a 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -199,6 +199,7 @@ class NetworkService; @@ -90,7 +90,7 @@ index be551d7a09330edf4a204b181acb382c2c3d13f4..5ed4df05dd22cbf901ecbbcc9d892de8 } // namespace network namespace sandbox { -@@ -1379,6 +1380,8 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -1385,6 +1386,8 @@ class CONTENT_EXPORT ContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, diff --git a/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch b/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch index 2ebb63b2ae6ec..0ffd60d534c9a 100644 --- a/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch +++ b/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch @@ -11,7 +11,7 @@ not need this dependency. refs https://chromium-review.googlesource.com/c/chromium/src/+/5573603 diff --git a/chrome/browser/ui/color/BUILD.gn b/chrome/browser/ui/color/BUILD.gn -index 77c7485b0fa885ddff38f336d1c7a52f2e969c73..045c0751a0c43f3360e334dd227b6cff7ddfd681 100644 +index 29c3dafa96df631e36aa1ced6798990c768adeaa..0281a50f04fecfc4ded3805a8f9637e184288581 100644 --- a/chrome/browser/ui/color/BUILD.gn +++ b/chrome/browser/ui/color/BUILD.gn @@ -84,9 +84,6 @@ source_set("mixers") { diff --git a/patches/chromium/expose_setuseragent_on_networkcontext.patch b/patches/chromium/expose_setuseragent_on_networkcontext.patch index a5e91db0421a8..53dc349f59ad2 100644 --- a/patches/chromium/expose_setuseragent_on_networkcontext.patch +++ b/patches/chromium/expose_setuseragent_on_networkcontext.patch @@ -33,10 +33,10 @@ index 0ab8187b0db8ae6db46d81738f653a2bc4c566f6..de3d55e85c22317f7f9375eb94d0d5d4 } // namespace net diff --git a/services/network/network_context.cc b/services/network/network_context.cc -index 06fcdf2daf2ae50b8eb1a9b73b34b64926a3106e..029c8fd0102c0a4418151e0ccda7ef25be12cbd4 100644 +index 7d65c373ac4f1f538085a44ca0b11ddce89b1e62..8d3a7ca4c955a0e5004e3e2a8435591cfbfe2f16 100644 --- a/services/network/network_context.cc +++ b/services/network/network_context.cc -@@ -1830,6 +1830,13 @@ void NetworkContext::SetNetworkConditions( +@@ -1838,6 +1838,13 @@ void NetworkContext::SetNetworkConditions( std::move(network_conditions)); } @@ -51,10 +51,10 @@ index 06fcdf2daf2ae50b8eb1a9b73b34b64926a3106e..029c8fd0102c0a4418151e0ccda7ef25 // This may only be called on NetworkContexts created with the constructor // that calls MakeURLRequestContext(). diff --git a/services/network/network_context.h b/services/network/network_context.h -index ca064589d9f2f6e00697f3b896ad522a5cf9bb6c..7ebbef514a99497fcb024a4a57adca6facf039fe 100644 +index 5b5d8eccb9c84965e996cd8d2a8c7d962df7852a..66da9008486d58ad4835b3ba58a6b0aefb53ab2f 100644 --- a/services/network/network_context.h +++ b/services/network/network_context.h -@@ -325,6 +325,7 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext +@@ -326,6 +326,7 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext void CloseIdleConnections(CloseIdleConnectionsCallback callback) override; void SetNetworkConditions(const base::UnguessableToken& throttling_profile_id, mojom::NetworkConditionsPtr conditions) override; diff --git a/patches/chromium/extend_apply_webpreferences.patch b/patches/chromium/extend_apply_webpreferences.patch index 42e76b532e058..b1d09069d7789 100644 --- a/patches/chromium/extend_apply_webpreferences.patch +++ b/patches/chromium/extend_apply_webpreferences.patch @@ -12,7 +12,7 @@ Ideally we could add an embedder observer pattern here but that can be done in future work. diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index f470ada1bf84938427fb89f4508e5f56aaeebc1f..524928729e34cc6b2ae427181e2ac4f8c1128688 100644 +index cd31f34df12a94748e4fc9066c6f344610ce73f0..f9298f9ff6f5fc0f16d9366fb6fd569de83b55ce 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -171,6 +171,7 @@ diff --git a/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch b/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch index af85984794495..972a59652bdc6 100644 --- a/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch +++ b/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch @@ -317,10 +317,10 @@ index 7e17594c30ac3cf8cb484b53563b03fc75bd2e0b..0e4a68f2fd8179640f877cb258b40496 // Although ScreenCaptureKit is available in 12.3 there were some bugs that diff --git a/content/browser/renderer_host/media/in_process_video_capture_device_launcher.cc b/content/browser/renderer_host/media/in_process_video_capture_device_launcher.cc -index 0ab684dc8e792359abb90b91917eddae42e6123d..f0f08a834f06c7669da6030640434308a5cbd056 100644 +index 23b19cc8405293aa44c4f2c20f715f8443fcd151..21c0c84dc6e3128b641fac682e3069a0acb97c0b 100644 --- a/content/browser/renderer_host/media/in_process_video_capture_device_launcher.cc +++ b/content/browser/renderer_host/media/in_process_video_capture_device_launcher.cc -@@ -316,8 +316,16 @@ void InProcessVideoCaptureDeviceLauncher::LaunchDeviceAsync( +@@ -322,8 +322,16 @@ void InProcessVideoCaptureDeviceLauncher::LaunchDeviceAsync( break; } @@ -338,7 +338,7 @@ index 0ab684dc8e792359abb90b91917eddae42e6123d..f0f08a834f06c7669da6030640434308 // For the other capturers, when a bug reports the type of capture it's // easy enough to determine which capturer was used, but it's a little // fuzzier with window capture. -@@ -333,13 +341,15 @@ void InProcessVideoCaptureDeviceLauncher::LaunchDeviceAsync( +@@ -339,13 +347,15 @@ void InProcessVideoCaptureDeviceLauncher::LaunchDeviceAsync( } #endif // defined(USE_AURA) || BUILDFLAG(IS_MAC) diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index 860a9947f1ba2..6effb0187d542 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -154,10 +154,10 @@ index ff1cc33c1787df522300a220000ad3d3123cd7bd..6b9e72f60db9af5ceeac7cc663ac666b return a.EmptyCells() == b.EmptyCells(); case CSSPropertyID::kFill: diff --git a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -index 206a0158a688ce807d656872179f4e50a7a1a237..967f547e9e3907f58a8f082311aba86f415f291d 100644 +index 4bc9534e12a7f71f9837ea8de4c85572d2e4af11..0d9368c96b175b767c8ed912daf434a334093123 100644 --- a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -@@ -12048,5 +12048,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( +@@ -12050,5 +12050,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( CSSValueID::kNone>(stream); } @@ -239,10 +239,10 @@ index 5e8d2bfbccd0625c2598544a9cba3d71373eded2..e68a97ee75754fc7196f11cf5c731550 bool RenderVSyncNotificationEnabled() const { return render_v_sync_notification_enabled_; diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index 524928729e34cc6b2ae427181e2ac4f8c1128688..9ce184f279b11a90c7d6f9b9ab7b20da09122a40 100644 +index f9298f9ff6f5fc0f16d9366fb6fd569de83b55ce..ef16711d93643a0612c8b34db8b3773a70aa210f 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc -@@ -3576,6 +3576,9 @@ void WebViewImpl::UpdateRendererPreferences( +@@ -3574,6 +3574,9 @@ void WebViewImpl::UpdateRendererPreferences( CanvasNoiseToken::Set(renderer_preferences_.canvas_noise_token); MaybePreloadSystemFonts(GetPage()); diff --git a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch index f5bf6d35ca68f..7b937ea8c4ff9 100644 --- a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch +++ b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch @@ -112,10 +112,10 @@ index 99bf736ebe303d46ab1ced924ba929a0cd258909..e10c8782d2704ff9cff8062d201a4339 string mime_type; diff --git a/services/network/url_loader.cc b/services/network/url_loader.cc -index 35d3acb1a088a7b4cba7b062a62e8033c31dfe52..9770306449b39f26c047ed0c15cba9feae55c5d3 100644 +index 7d04e7f5f7f4261909fe06d6894849db34d7552b..6af6e0a32e59523ff7b3ba3a5d32e711ba422f87 100644 --- a/services/network/url_loader.cc +++ b/services/network/url_loader.cc -@@ -386,6 +386,9 @@ URLLoader::URLLoader( +@@ -388,6 +388,9 @@ URLLoader::URLLoader( mojo::SimpleWatcher::ArmingPolicy::MANUAL, base::SequencedTaskRunner::GetCurrentDefault()), per_factory_orb_state_(context.GetMutableOrbState()), @@ -125,7 +125,7 @@ index 35d3acb1a088a7b4cba7b062a62e8033c31dfe52..9770306449b39f26c047ed0c15cba9fe devtools_request_id_(request.devtools_request_id), options_(PopulateOptions(options, factory_params_->is_orb_enabled, -@@ -521,7 +524,7 @@ void URLLoader::SetUpUrlRequestCallbacks( +@@ -524,7 +527,7 @@ void URLLoader::SetUpUrlRequestCallbacks( &URLLoader::IsSharedDictionaryReadAllowed, base::Unretained(this))); } @@ -134,7 +134,7 @@ index 35d3acb1a088a7b4cba7b062a62e8033c31dfe52..9770306449b39f26c047ed0c15cba9fe url_request_->SetResponseHeadersCallback(base::BindRepeating( &URLLoader::SetRawResponseHeaders, base::Unretained(this))); } -@@ -1126,6 +1129,19 @@ void URLLoader::OnResponseStarted(net::URLRequest* url_request, int net_error) { +@@ -1129,6 +1132,19 @@ void URLLoader::OnResponseStarted(net::URLRequest* url_request, int net_error) { } response_ = BuildResponseHead(); @@ -155,10 +155,10 @@ index 35d3acb1a088a7b4cba7b062a62e8033c31dfe52..9770306449b39f26c047ed0c15cba9fe ad_auction_event_record_request_helper_.HandleResponse( diff --git a/services/network/url_loader.h b/services/network/url_loader.h -index f4d16508d4a34f9991b1b2f4e519e6cb2a7f5a73..099e146bc04bb4eb768c79099c5646ad7a029382 100644 +index b0f14e050dea10385e244085dcf1d40542220404..89ed2779e5fff251b6d0d52e91c6a321673b33e6 100644 --- a/services/network/url_loader.h +++ b/services/network/url_loader.h -@@ -599,6 +599,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) URLLoader +@@ -601,6 +601,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) URLLoader std::unique_ptr resource_scheduler_request_handle_; diff --git a/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch b/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch index fe27ef5e7f68f..d929dd7d0054b 100644 --- a/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch +++ b/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch @@ -20,7 +20,7 @@ This patch will be removed when the deprecated sync api support is removed. diff --git a/components/permissions/permission_util.cc b/components/permissions/permission_util.cc -index 0aae1d3b2777d5f6db711d1ade99b4bde24e76bf..e350f6789c710826e0885ccdc19e66e2213820df 100644 +index f134056b6b255935250721d6fbd417b1d658c87c..f69c10c32011c9da5c235a5199abce44e64982da 100644 --- a/components/permissions/permission_util.cc +++ b/components/permissions/permission_util.cc @@ -502,6 +502,7 @@ ContentSettingsType PermissionUtil::PermissionTypeToContentSettingsTypeSafe( @@ -58,7 +58,7 @@ index 6c36ada80f6f225b84a8f3832405128f8ba83224..714d582d1060873765b24770b18eddcb NOTREACHED(); } diff --git a/third_party/blink/common/permissions/permission_utils.cc b/third_party/blink/common/permissions/permission_utils.cc -index b19b5781f426bdfd4a8b6dfbead0f854545ca90a..9833c25f97e55ab7e7095243c307a90fbf4b53d8 100644 +index 6886f5764a87dd8b41746969745e80c82b69430b..cb39508717b9ebdd30470f6d7fd7e8626cc65948 100644 --- a/third_party/blink/common/permissions/permission_utils.cc +++ b/third_party/blink/common/permissions/permission_utils.cc @@ -101,6 +101,8 @@ std::string GetPermissionString(PermissionType permission) { diff --git a/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch b/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch index d33a5c4458fee..522af70a18e98 100644 --- a/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch +++ b/patches/chromium/fix_non-client_mouse_tracking_and_message_bubbling_on_windows.patch @@ -13,10 +13,10 @@ messages in the legacy window handle layer. These conditions are regularly hit with WCO-enabled windows on Windows. diff --git a/content/browser/renderer_host/legacy_render_widget_host_win.cc b/content/browser/renderer_host/legacy_render_widget_host_win.cc -index 1c03162fbcda8ab75dcd53722f92e10403fbae08..a21c58d3f13fadf3a7888f4fe16c0e6cf6c215b0 100644 +index 48b91785925ba2d3712560a209fe07799df0face..99b06250fa5cf939bd66155f595796baf8cf9755 100644 --- a/content/browser/renderer_host/legacy_render_widget_host_win.cc +++ b/content/browser/renderer_host/legacy_render_widget_host_win.cc -@@ -328,12 +328,12 @@ LRESULT LegacyRenderWidgetHostHWND::OnMouseRange(UINT message, +@@ -325,12 +325,12 @@ LRESULT LegacyRenderWidgetHostHWND::OnMouseRange(UINT message, WPARAM w_param, LPARAM l_param, BOOL& handled) { @@ -31,7 +31,7 @@ index 1c03162fbcda8ab75dcd53722f92e10403fbae08..a21c58d3f13fadf3a7888f4fe16c0e6c tme.hwndTrack = hwnd(); tme.dwHoverTime = 0; TrackMouseEvent(&tme); -@@ -366,7 +366,10 @@ LRESULT LegacyRenderWidgetHostHWND::OnMouseRange(UINT message, +@@ -363,7 +363,10 @@ LRESULT LegacyRenderWidgetHostHWND::OnMouseRange(UINT message, // the picture. if (!handled && (message >= WM_NCMOUSEMOVE && message <= WM_NCXBUTTONDBLCLK)) { diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index ec428f880a1fd..f9cef5ce656bd 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -20,7 +20,7 @@ index b61dfcc8e3306a2c3eb8808c204254af4ad8c248..cec49ddafd46b0296cc548a17efd6752 } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 5ed4df05dd22cbf901ecbbcc9d892de806c93890..d0623992ce30b29b088a1b92e503f9e29087f193 100644 +index 4a995e6c35abba567bb8be826effb06ba7e2119a..c9636db4a29ae4af408a84eb58d863ae07caf2a2 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -341,6 +341,11 @@ class CONTENT_EXPORT ContentBrowserClient { diff --git a/patches/chromium/introduce_ozoneplatform_electron_can_call_x11_property.patch b/patches/chromium/introduce_ozoneplatform_electron_can_call_x11_property.patch index 6f34e821fb844..3b780f397dbac 100644 --- a/patches/chromium/introduce_ozoneplatform_electron_can_call_x11_property.patch +++ b/patches/chromium/introduce_ozoneplatform_electron_can_call_x11_property.patch @@ -9,10 +9,10 @@ at rutime. It would be best if eventually all usages of this property were replaced with clean ozone native implementations. diff --git a/ui/ozone/platform/x11/ozone_platform_x11.cc b/ui/ozone/platform/x11/ozone_platform_x11.cc -index 14a38b11d595c63cd827f542479df04473bdbe42..c6e1398fcce871ba50017d6e528d6018226f9649 100644 +index 4f00f630665a10a0fb85fe7c2ddc0fa67add1603..e9e8da125b518387546275bf84e0b09c3d49e254 100644 --- a/ui/ozone/platform/x11/ozone_platform_x11.cc +++ b/ui/ozone/platform/x11/ozone_platform_x11.cc -@@ -193,6 +193,7 @@ class OzonePlatformX11 : public OzonePlatform, +@@ -194,6 +194,7 @@ class OzonePlatformX11 : public OzonePlatform, base::MessagePumpType::UI; properties->supports_vulkan_swap_chain = true; properties->skia_can_fall_back_to_x11 = true; diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 877fbfa40302a..523898fb50fd8 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -548,7 +548,7 @@ index dbf334caa3a6d10017b69ad76802e389a011436b..da828823e8195cc9e497866363c9af93 void ForwardKeyboardEvent(const input::NativeWebKeyboardEvent& key_event, diff --git a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -index f97ab6bdafbc35216b1935cf979443d071dd889f..e72d2347099c6549b5f9f318f99a1140839939e7 100644 +index d83f420d25e2c108ad400ebecae02b1ac327c058..77852c5c315ac09dddb7227adf3b840ee9d93928 100644 --- a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm +++ b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm @@ -36,6 +36,7 @@ @@ -559,7 +559,7 @@ index f97ab6bdafbc35216b1935cf979443d071dd889f..e72d2347099c6549b5f9f318f99a1140 #include "skia/ext/skia_utils_mac.h" #include "third_party/blink/public/common/features.h" #include "third_party/blink/public/mojom/input/input_handler.mojom.h" -@@ -2144,15 +2145,21 @@ - (NSAccessibilityRole)accessibilityRole { +@@ -2147,15 +2148,21 @@ - (NSAccessibilityRole)accessibilityRole { // Since this implementation doesn't have to wait any IPC calls, this doesn't // make any key-typing jank. --hbono 7/23/09 // @@ -797,7 +797,7 @@ index a1068589ad844518038ee7bc15a3de9bc5cba525..1ff781c49f086ec8015c7d3c44567dbe } // namespace content diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn -index d72fc747932acd8cca621cd4bbfd3cb244c17da9..58687ab05e82b6d6314c979c88d77323dd7047e4 100644 +index 2c8e8e9b4260366b5312be7f2a3bbf9d332fe916..fb9e07491c93593904db7fd55c24e67820de982c 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn @@ -664,6 +664,7 @@ static_library("test_support") { @@ -1436,7 +1436,7 @@ index eb81a70e4d5d5cd3e6ae9b45f8cd1c795ea76c51..9921ccb10d3455600eddd85f77f10228 } // namespace sandbox diff --git a/third_party/blink/renderer/core/BUILD.gn b/third_party/blink/renderer/core/BUILD.gn -index f2b874b368c6857013f6fbb7522d5d590f0540b5..1593565d61d284902ea364bf7bbee065e95acb48 100644 +index 1b5e616ebd3c610739a9dcf3fd6694f1e442d783..8449d7eb65687fa82db0f23c7627807ef26e34f3 100644 --- a/third_party/blink/renderer/core/BUILD.gn +++ b/third_party/blink/renderer/core/BUILD.gn @@ -414,6 +414,7 @@ component("core") { diff --git a/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch b/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch index 94a0f05f9340b..44c72ea13f4a3 100644 --- a/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch +++ b/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch @@ -7,10 +7,10 @@ This adds a callback from the network service that's used to implement session.setCertificateVerifyCallback. diff --git a/services/network/network_context.cc b/services/network/network_context.cc -index 616f639ce1cadb8117b703294cee66b7ef73b958..06fcdf2daf2ae50b8eb1a9b73b34b64926a3106e 100644 +index 3c261f50a966bd9d472671c9d9c74cfa843355a6..7d65c373ac4f1f538085a44ca0b11ddce89b1e62 100644 --- a/services/network/network_context.cc +++ b/services/network/network_context.cc -@@ -164,6 +164,11 @@ +@@ -165,6 +165,11 @@ #include "services/network/web_transport.h" #include "url/gurl.h" @@ -22,7 +22,7 @@ index 616f639ce1cadb8117b703294cee66b7ef73b958..06fcdf2daf2ae50b8eb1a9b73b34b649 #if BUILDFLAG(IS_CT_SUPPORTED) // gn check does not account for BUILDFLAG(). So, for iOS builds, it will // complain about a missing dependency on the target exposing this header. Add a -@@ -603,6 +608,99 @@ void RecordHSTSPreconnectUpgradeReason(HSTSRedirectUpgradeReason reason) { +@@ -604,6 +609,99 @@ void RecordHSTSPreconnectUpgradeReason(HSTSRedirectUpgradeReason reason) { } // namespace @@ -122,7 +122,7 @@ index 616f639ce1cadb8117b703294cee66b7ef73b958..06fcdf2daf2ae50b8eb1a9b73b34b649 constexpr uint32_t NetworkContext::kMaxOutstandingRequestsPerProcess; NetworkContext::NetworkContextHttpAuthPreferences:: -@@ -999,6 +1097,13 @@ void NetworkContext::SetClient( +@@ -1007,6 +1105,13 @@ void NetworkContext::SetClient( client_.Bind(std::move(client)); } @@ -136,7 +136,7 @@ index 616f639ce1cadb8117b703294cee66b7ef73b958..06fcdf2daf2ae50b8eb1a9b73b34b649 void NetworkContext::CreateURLLoaderFactory( mojo::PendingReceiver receiver, mojom::URLLoaderFactoryParamsPtr params) { -@@ -2604,6 +2709,10 @@ URLRequestContextOwner NetworkContext::MakeURLRequestContext( +@@ -2612,6 +2717,10 @@ URLRequestContextOwner NetworkContext::MakeURLRequestContext( cert_verifier = std::make_unique( std::make_unique( std::move(cert_verifier))); @@ -148,7 +148,7 @@ index 616f639ce1cadb8117b703294cee66b7ef73b958..06fcdf2daf2ae50b8eb1a9b73b34b649 builder.SetCertVerifier(IgnoreErrorsCertVerifier::MaybeWrapCertVerifier( diff --git a/services/network/network_context.h b/services/network/network_context.h -index 775788f8cee653f31fa995d1e3414305d039483d..ca064589d9f2f6e00697f3b896ad522a5cf9bb6c 100644 +index 867d3002dc9dada51319c5ed15f5746f58f19fd1..5b5d8eccb9c84965e996cd8d2a8c7d962df7852a 100644 --- a/services/network/network_context.h +++ b/services/network/network_context.h @@ -115,6 +115,7 @@ class URLMatcher; @@ -159,7 +159,7 @@ index 775788f8cee653f31fa995d1e3414305d039483d..ca064589d9f2f6e00697f3b896ad522a class CookieManager; class HostResolver; class MdnsResponderManager; -@@ -251,6 +252,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext +@@ -252,6 +253,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext void CreateURLLoaderFactory( mojo::PendingReceiver receiver, mojom::URLLoaderFactoryParamsPtr params) override; @@ -168,7 +168,7 @@ index 775788f8cee653f31fa995d1e3414305d039483d..ca064589d9f2f6e00697f3b896ad522a void ResetURLLoaderFactories() override; void GetViaObliviousHttp( mojom::ObliviousHttpRequestPtr request, -@@ -956,6 +959,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext +@@ -961,6 +964,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext std::vector dismount_closures_; #endif // BUILDFLAG(IS_DIRECTORY_TRANSFER_REQUIRED) diff --git a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch index 5c89c799112c6..c130481a552b8 100644 --- a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch +++ b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch @@ -10,7 +10,7 @@ an about:blank check to this area. Ref: https://chromium-review.googlesource.com/c/chromium/src/+/5403876 diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index fea0bbb8a9604ffbc4d8c5f061baff81c4824cde..a9f6d2233ce9953d1e1d96aea3a2ee717adbdc3b 100644 +index cd3ef19b973bcd0f9268684ae087b9197756715a..18a9ac180526faa053060f6d21abb2a90ebfc1cc 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc @@ -809,8 +809,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( diff --git a/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch b/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch index 6f67a6ed9ce64..d776be1c11dd6 100644 --- a/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch +++ b/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch @@ -6,7 +6,7 @@ Subject: refactor: patch electron PermissionTypes into blink 6387077: [PermissionOptions] Generalize PermissionRequestDescription | https://chromium-review.googlesource.com/c/chromium/src/+/6387077 diff --git a/components/permissions/permission_util.cc b/components/permissions/permission_util.cc -index e350f6789c710826e0885ccdc19e66e2213820df..b8ba008470f39f6f3559d29b9eff0a23863da364 100644 +index f69c10c32011c9da5c235a5199abce44e64982da..3b166dd8f571538102772a9bcd5bbe55015742f3 100644 --- a/components/permissions/permission_util.cc +++ b/components/permissions/permission_util.cc @@ -502,7 +502,17 @@ ContentSettingsType PermissionUtil::PermissionTypeToContentSettingsTypeSafe( @@ -80,15 +80,11 @@ index 714d582d1060873765b24770b18eddcbbdcf5506..3746bafd72223a65c4183a59726601e8 NOTREACHED(); } diff --git a/third_party/blink/common/permissions/permission_utils.cc b/third_party/blink/common/permissions/permission_utils.cc -index 9833c25f97e55ab7e7095243c307a90fbf4b53d8..6489d1c932fc8e92e13af55227088fa1c169dcd6 100644 +index cb39508717b9ebdd30470f6d7fd7e8626cc65948..10af1f297739d29cc96d6fd5752fca1532e6fba4 100644 --- a/third_party/blink/common/permissions/permission_utils.cc +++ b/third_party/blink/common/permissions/permission_utils.cc -@@ -101,8 +101,23 @@ std::string GetPermissionString(PermissionType permission) { - return "WebAppInstallation"; - case PermissionType::LOCAL_NETWORK_ACCESS: +@@ -103,6 +103,18 @@ std::string GetPermissionString(PermissionType permission) { return "LocalNetworkAccess"; -+ -+ // Permissions added by Electron case PermissionType::DEPRECATED_SYNC_CLIPBOARD_READ: return "DeprecatedSyncClipboardRead"; + case PermissionType::FILE_SYSTEM: @@ -103,11 +99,10 @@ index 9833c25f97e55ab7e7095243c307a90fbf4b53d8..6489d1c932fc8e92e13af55227088fa1 + return "Serial"; + case PermissionType::USB: + return "USB"; -+ case PermissionType::NUM: NOTREACHED(); } -@@ -177,7 +192,15 @@ PermissionTypeToPermissionsPolicyFeature(PermissionType permission) { +@@ -177,7 +189,15 @@ PermissionTypeToPermissionsPolicyFeature(PermissionType permission) { case PermissionType::NOTIFICATIONS: case PermissionType::KEYBOARD_LOCK: case PermissionType::POINTER_LOCK: @@ -123,15 +118,10 @@ index 9833c25f97e55ab7e7095243c307a90fbf4b53d8..6489d1c932fc8e92e13af55227088fa1 return std::nullopt; case PermissionType::NUM: -@@ -345,9 +368,26 @@ std::optional PermissionDescriptorInfoToPermissionType( - return PermissionType::HAND_TRACKING; - case PermissionName::WEB_PRINTING: +@@ -347,6 +367,21 @@ std::optional PermissionDescriptorInfoToPermissionType( return PermissionType::WEB_PRINTING; -- default: -- NOTREACHED(); -+ case PermissionName::SMART_CARD: -+ return PermissionType::SMART_CARD; -+ + case PermissionName::SMART_CARD: + return PermissionType::SMART_CARD; + // Permissions added by Electron + case PermissionName::DEPRECATED_SYNC_CLIPBOARD_READ: + return PermissionType::DEPRECATED_SYNC_CLIPBOARD_READ; @@ -148,10 +138,8 @@ index 9833c25f97e55ab7e7095243c307a90fbf4b53d8..6489d1c932fc8e92e13af55227088fa1 + case PermissionName::USB: + return PermissionType::USB; } -+ NOTREACHED(); } - } // namespace blink diff --git a/third_party/blink/public/common/permissions/permission_utils.h b/third_party/blink/public/common/permissions/permission_utils.h index c286d87043ec4cb2e51ec9d82d08e4c84f5a270c..164a2a446947dae687922363d324a6d35b7ae0b8 100644 --- a/third_party/blink/public/common/permissions/permission_utils.h diff --git a/patches/chromium/render_widget_host_view_base.patch b/patches/chromium/render_widget_host_view_base.patch index 8fc2c81a2b312..62838493d731a 100644 --- a/patches/chromium/render_widget_host_view_base.patch +++ b/patches/chromium/render_widget_host_view_base.patch @@ -6,10 +6,10 @@ Subject: render_widget_host_view_base.patch ... something to do with OSR? and maybe as well? terrifying. diff --git a/content/browser/renderer_host/render_widget_host_view_base.cc b/content/browser/renderer_host/render_widget_host_view_base.cc -index 30ec1b5e2688b94bfe6a9c6cf55a839580e81e68..e9ee463b37ebc61d01fe1ceccbb6a280e33fd268 100644 +index bb7475f1f8be4038c77d2dc68b09a7ac2338b160..c35ef5290ef1f812c5e7ff31d71ae0661b26d124 100644 --- a/content/browser/renderer_host/render_widget_host_view_base.cc +++ b/content/browser/renderer_host/render_widget_host_view_base.cc -@@ -654,6 +654,13 @@ void RenderWidgetHostViewBase::OnFrameTokenChangedForView( +@@ -655,6 +655,13 @@ void RenderWidgetHostViewBase::OnFrameTokenChangedForView( host()->DidProcessFrame(frame_token, activation_time); } @@ -24,7 +24,7 @@ index 30ec1b5e2688b94bfe6a9c6cf55a839580e81e68..e9ee463b37ebc61d01fe1ceccbb6a280 const blink::WebMouseEvent& event, const ui::LatencyInfo& latency) { diff --git a/content/browser/renderer_host/render_widget_host_view_base.h b/content/browser/renderer_host/render_widget_host_view_base.h -index c93e93d13f1013641709f5808bc1c66ea772d082..db5234cd13819d14b737aec3315e77e420e01603 100644 +index faed571e3232545cdba8fc113c039d3432441448..e349711282d623c975501de5fc1a5c9c7309001f 100644 --- a/content/browser/renderer_host/render_widget_host_view_base.h +++ b/content/browser/renderer_host/render_widget_host_view_base.h @@ -30,6 +30,8 @@ @@ -50,7 +50,7 @@ index c93e93d13f1013641709f5808bc1c66ea772d082..db5234cd13819d14b737aec3315e77e4 class DelegatedFrameHost; class SyntheticGestureTarget; -@@ -151,6 +155,10 @@ class CONTENT_EXPORT RenderWidgetHostViewBase +@@ -149,6 +153,10 @@ class CONTENT_EXPORT RenderWidgetHostViewBase void ProcessGestureEvent(const blink::WebGestureEvent& event, const ui::LatencyInfo& latency) override; RenderWidgetHostViewBase* GetRootView() override; @@ -61,7 +61,7 @@ index c93e93d13f1013641709f5808bc1c66ea772d082..db5234cd13819d14b737aec3315e77e4 void OnAutoscrollStart() override; const viz::DisplayHitTestQueryMap& GetDisplayHitTestQuery() const override; -@@ -199,6 +207,9 @@ class CONTENT_EXPORT RenderWidgetHostViewBase +@@ -197,6 +205,9 @@ class CONTENT_EXPORT RenderWidgetHostViewBase void NotifyContextMenuInsetsObservers(const gfx::Rect&) override {} bool IsHTMLFormPopup() const override; diff --git a/patches/chromium/render_widget_host_view_mac.patch b/patches/chromium/render_widget_host_view_mac.patch index e370a1a90b8a5..40e26d6628396 100644 --- a/patches/chromium/render_widget_host_view_mac.patch +++ b/patches/chromium/render_widget_host_view_mac.patch @@ -8,7 +8,7 @@ respond to the first mouse click in their window, which is desirable for some kinds of utility windows. Similarly for `disableAutoHideCursor`. diff --git a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm -index a606a4870bd3f504c4bd6316aa3ab833621ab205..f97ab6bdafbc35216b1935cf979443d071dd889f 100644 +index e2b524c968d67405161738f4e21ef8d5958c9a63..d83f420d25e2c108ad400ebecae02b1ac327c058 100644 --- a/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm +++ b/content/app_shim_remote_cocoa/render_widget_host_view_cocoa.mm @@ -171,6 +171,15 @@ void ExtractUnderlines(NSAttributedString* string, @@ -27,7 +27,7 @@ index a606a4870bd3f504c4bd6316aa3ab833621ab205..f97ab6bdafbc35216b1935cf979443d0 // RenderWidgetHostViewCocoa --------------------------------------------------- // Private methods: -@@ -782,6 +791,9 @@ - (AcceptMouseEventsOption)acceptsMouseEventsOption { +@@ -785,6 +794,9 @@ - (AcceptMouseEventsOption)acceptsMouseEventsOption { } - (BOOL)acceptsFirstMouse:(NSEvent*)theEvent { @@ -37,7 +37,7 @@ index a606a4870bd3f504c4bd6316aa3ab833621ab205..f97ab6bdafbc35216b1935cf979443d0 // Enable "click-through" if mouse clicks are accepted in inactive windows return [self acceptsMouseEventsOption] > kAcceptMouseEventsInActiveWindow; } -@@ -927,6 +939,10 @@ - (BOOL)shouldIgnoreMouseEvent:(NSEvent*)theEvent { +@@ -930,6 +942,10 @@ - (BOOL)shouldIgnoreMouseEvent:(NSEvent*)theEvent { // its parent view. BOOL hitSelf = NO; while (view) { @@ -48,7 +48,7 @@ index a606a4870bd3f504c4bd6316aa3ab833621ab205..f97ab6bdafbc35216b1935cf979443d0 if (view == self) hitSelf = YES; if ([view isKindOfClass:[self class]] && ![view isEqual:self] && -@@ -1261,6 +1277,10 @@ - (void)keyEvent:(NSEvent*)theEvent wasKeyEquivalent:(BOOL)equiv { +@@ -1264,6 +1280,10 @@ - (void)keyEvent:(NSEvent*)theEvent wasKeyEquivalent:(BOOL)equiv { eventType == NSEventTypeKeyDown && !(modifierFlags & NSEventModifierFlagCommand); diff --git a/patches/chromium/resource_file_conflict.patch b/patches/chromium/resource_file_conflict.patch index 2f21e75bd6457..19e08c4342b0d 100644 --- a/patches/chromium/resource_file_conflict.patch +++ b/patches/chromium/resource_file_conflict.patch @@ -52,10 +52,10 @@ Some alternatives to this patch: None of these options seems like a substantial maintainability win over this patch to me (@nornagon). diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index 97f843f8133c49d684b415f61ef4b4084c4d345c..4b3f01018a9dea91b46b5917e099f272582991b2 100644 +index f47270687b9a12fb74be2e90cc1e9f25e2e2d34e..84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn -@@ -1554,7 +1554,7 @@ if (is_chrome_branded && !is_android) { +@@ -1551,7 +1551,7 @@ if (is_chrome_branded && !is_android) { } } @@ -64,7 +64,7 @@ index 97f843f8133c49d684b415f61ef4b4084c4d345c..4b3f01018a9dea91b46b5917e099f272 chrome_paks("packed_resources") { if (is_mac) { output_dir = "$root_gen_dir/repack" -@@ -1600,6 +1600,12 @@ repack("browser_tests_pak") { +@@ -1597,6 +1597,12 @@ repack("browser_tests_pak") { deps = [ "//chrome/test/data/webui:resources" ] } diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index aa03f837cd0aa..259ab91f6616d 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,7 +15,7 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 46ddad111b2feb5cc1064a1eeb424800d2cba6c1..fea0bbb8a9604ffbc4d8c5f061baff81c4824cde 100644 +index 73f56d65160a114bea9dcefa6ba03a417b7a273b..cd3ef19b973bcd0f9268684ae087b9197756715a 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc @@ -8883,6 +8883,17 @@ void RenderFrameHostImpl::EnterFullscreen( From 5602efb2b684022748039f36dd3e6600ff2de37e Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 7 May 2025 09:36:17 +0200 Subject: [PATCH 025/186] fix: printing when no `mediaSize` specified (#46971) fix: printing when no mediaSize specified Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/api/electron_api_web_contents.cc | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index 2b8365d1aef72..d10d8926a31aa 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -3133,11 +3133,21 @@ void WebContents::Print(gin::Arguments* args) { options.Get("duplexMode", &duplex_mode); settings.Set(printing::kSettingDuplexMode, static_cast(duplex_mode)); - // We've already done necessary parameter sanitization at the - // JS level, so we can simply pass this through. - base::Value media_size(base::Value::Type::DICT); - if (options.Get("mediaSize", &media_size)) + base::Value::Dict media_size; + if (options.Get("mediaSize", &media_size)) { settings.Set(printing::kSettingMediaSize, std::move(media_size)); + } else { + // Default to A4 paper size (210mm x 297mm) + settings.Set(printing::kSettingMediaSize, + base::Value::Dict() + .Set(printing::kSettingMediaSizeHeightMicrons, 297000) + .Set(printing::kSettingMediaSizeWidthMicrons, 210000) + .Set(printing::kSettingsImageableAreaLeftMicrons, 0) + .Set(printing::kSettingsImageableAreaTopMicrons, 297000) + .Set(printing::kSettingsImageableAreaRightMicrons, 210000) + .Set(printing::kSettingsImageableAreaBottomMicrons, 0) + .Set(printing::kSettingMediaSizeIsDefault, true)); + } // Set custom dots per inch (dpi) gin_helper::Dictionary dpi_settings; From 069c9a9e1f5eba1b5e2883c156fefe4e36c5114d Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 7 May 2025 20:01:39 -0500 Subject: [PATCH 026/186] chore: bump chromium to 138.0.7165.0 (37-x-y) (#46985) * chore: bump chromium in DEPS to 138.0.7165.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6492127: Add new less invasive context menu mode for mobile interesttarget https://chromium-review.googlesource.com/c/chromium/src/+/6492127 Co-authored-by: Shelley Vohr * chore: fixup patch indices Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- DEPS | 2 +- .../add_didinstallconditionalfeatures.patch | 2 +- ..._scheduler_throttling_per_renderview.patch | 26 +++++++++---------- patches/chromium/blink_local_frame.patch | 6 ++--- ..._depend_on_packed_resource_integrity.patch | 8 +++--- patches/chromium/can_create_window.patch | 16 ++++++------ ..._introduce_blocking_api_for_electron.patch | 6 ++--- .../chromium/chore_partial_revert_of.patch | 4 +-- ...screationoverridden_with_full_params.patch | 4 +-- ...e_reference_to_chrome_browser_themes.patch | 2 +- patches/chromium/disable_hidden.patch | 8 +++--- patches/chromium/disable_unload_metrics.patch | 2 +- .../extend_apply_webpreferences.patch | 2 +- ...moothing_css_rule_and_blink_painting.patch | 2 +- ...etdefersloading_on_webdocumentloader.patch | 2 +- ...ding_non-standard_schemes_in_iframes.patch | 6 ++--- ...board_hides_on_input_blur_in_webview.patch | 4 +-- ...original_resize_performance_on_macos.patch | 4 +-- ...from_localframe_requestexecutescript.patch | 14 +++++----- ..._avoid_private_macos_api_usage.patch.patch | 2 +- ...eated_to_allow_for_browser_initiated.patch | 4 +-- patches/chromium/printing.patch | 18 ++++++------- ...r_changes_to_the_webcontentsobserver.patch | 10 +++---- ...efactor_unfilter_unresponsive_events.patch | 4 +-- .../render_widget_host_view_base.patch | 6 ++--- patches/chromium/resource_file_conflict.patch | 6 ++--- patches/chromium/web_contents.patch | 6 ++--- patches/chromium/webview_fullscreen.patch | 10 +++---- 28 files changed, 93 insertions(+), 93 deletions(-) diff --git a/DEPS b/DEPS index 98aa16e443445..194612f5d50af 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7164.0', + '138.0.7165.0', 'node_version': 'v22.15.0', 'nan_version': diff --git a/patches/chromium/add_didinstallconditionalfeatures.patch b/patches/chromium/add_didinstallconditionalfeatures.patch index 7f134c862747b..dd021e0e177e4 100644 --- a/patches/chromium/add_didinstallconditionalfeatures.patch +++ b/patches/chromium/add_didinstallconditionalfeatures.patch @@ -23,7 +23,7 @@ index db655a7b52eacb74f2a8637db36abd87f6b86792..8014cb08e2090a12ea8b9e92cb8f93c9 int32_t world_id) {} virtual void DidClearWindowObject() {} diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index b0aa018f2f4e6865915516ab6b65fac20d9e6f20..c04a544eb8991bfa718322e6e3a090ef4733a50b 100644 +index 6c569b4a0f4ddea5d071753bb4a72002ba174171..d1085ca830b5a98f1550e6c01728cd760df6141a 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc @@ -4807,6 +4807,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, diff --git a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch index 3ed6d3c7d73e3..b63183201c679 100644 --- a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch +++ b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch @@ -6,10 +6,10 @@ Subject: allow disabling blink scheduler throttling per RenderView This allows us to disable throttling for hidden windows. diff --git a/content/browser/renderer_host/navigation_controller_impl_unittest.cc b/content/browser/renderer_host/navigation_controller_impl_unittest.cc -index f9b27264f7e3e1f8de6f088ccb78e4a4693c5e93..85aebec5028fd6b324a1f1d9416fbf99c150e09a 100644 +index 495daa75895a4545287da53f305e6cd348db7183..fd749047a7d505d02c4e8e4631da823275c27822 100644 --- a/content/browser/renderer_host/navigation_controller_impl_unittest.cc +++ b/content/browser/renderer_host/navigation_controller_impl_unittest.cc -@@ -168,6 +168,12 @@ class MockPageBroadcast : public blink::mojom::PageBroadcast { +@@ -166,6 +166,12 @@ class MockPageBroadcast : public blink::mojom::PageBroadcast { (network::mojom::AttributionSupport support), (override)); @@ -23,10 +23,10 @@ index f9b27264f7e3e1f8de6f088ccb78e4a4693c5e93..85aebec5028fd6b324a1f1d9416fbf99 return receiver_.BindNewEndpointAndPassDedicatedRemote(); } diff --git a/content/browser/renderer_host/render_view_host_impl.cc b/content/browser/renderer_host/render_view_host_impl.cc -index 9d430ebff1067323f229c3b81b18300e8cb7e8a9..090125bc5a4c485c83d9eaa6b82ed5cf3402cbbd 100644 +index 4a70fd017915c1d631a47096c735d9c4b6e2c2af..0b2eb574f86e4c192d7cd986abea72e85163a7bd 100644 --- a/content/browser/renderer_host/render_view_host_impl.cc +++ b/content/browser/renderer_host/render_view_host_impl.cc -@@ -768,6 +768,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { +@@ -759,6 +759,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { GetWidget()->GetAssociatedFrameWidget()->SetBackgroundOpaque(opaque); } @@ -80,7 +80,7 @@ index 20ca763ff7f55e8176b77349b41917b11e051ae6..a50c122064b5f0092f57e3d508fb1938 // This interface should only be implemented inside content. friend class RenderViewHostImpl; diff --git a/content/test/test_page_broadcast.h b/content/test/test_page_broadcast.h -index 913e465918750df6852c3ede34a75ecebab8b1fa..c81d6ad098cf977cbd8933721e539c52056c258b 100644 +index 58895f0ed0e18703c45eee37210003150c24550a..6a138d4cd852f6f2b9fd2294062c9b6ab4f08855 100644 --- a/content/test/test_page_broadcast.h +++ b/content/test/test_page_broadcast.h @@ -50,6 +50,7 @@ class TestPageBroadcast : public blink::mojom::PageBroadcast { @@ -92,10 +92,10 @@ index 913e465918750df6852c3ede34a75ecebab8b1fa..c81d6ad098cf977cbd8933721e539c52 mojo::AssociatedReceiver receiver_; }; diff --git a/third_party/blink/public/mojom/page/page.mojom b/third_party/blink/public/mojom/page/page.mojom -index f868a3cc56b49b7fdac9fa1415386bd3a59a3dd7..ac7e92740bf7a61f3d8dcf8feff0fee978ffbfee 100644 +index 4614f84c3d8f709fb2a12d662e5a13dc12c59e8a..76444fcbf68b91ad64c46debc565ffc35a3e2c68 100644 --- a/third_party/blink/public/mojom/page/page.mojom +++ b/third_party/blink/public/mojom/page/page.mojom -@@ -173,4 +173,7 @@ interface PageBroadcast { +@@ -172,4 +172,7 @@ interface PageBroadcast { // 2. The ColorProvider associated with the WebContents changes as a result // of theme changes. UpdateColorProviders(ColorProviderColorMaps color_provider_colors); @@ -104,10 +104,10 @@ index f868a3cc56b49b7fdac9fa1415386bd3a59a3dd7..ac7e92740bf7a61f3d8dcf8feff0fee9 + SetSchedulerThrottling(bool allowed); }; diff --git a/third_party/blink/public/web/web_view.h b/third_party/blink/public/web/web_view.h -index b1689844282d6917b9750fbc6a875848ddf84b70..f1cc159b7c3448a33a6d9e213f8fbd3b47141fb7 100644 +index 7c1eb9baabfb9e0f3645421b5cbe467862252638..00d2cd41d795cb550e16fb80944b238252e4e53c 100644 --- a/third_party/blink/public/web/web_view.h +++ b/third_party/blink/public/web/web_view.h -@@ -371,6 +371,7 @@ class BLINK_EXPORT WebView { +@@ -370,6 +370,7 @@ class BLINK_EXPORT WebView { // Scheduling ----------------------------------------------------------- virtual PageScheduler* Scheduler() const = 0; @@ -116,7 +116,7 @@ index b1689844282d6917b9750fbc6a875848ddf84b70..f1cc159b7c3448a33a6d9e213f8fbd3b // Visibility ----------------------------------------------------------- diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index e167db6d5f208f2f3e923ec7dec7c4da4155dd90..cd31f34df12a94748e4fc9066c6f344610ce73f0 100644 +index 6b056decc43e9ba9e7970a7d8fefaed6a86d9a2d..0b2956425d2feb84f1d0db7be4f3d4b0875b1d10 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -2466,6 +2466,10 @@ void WebViewImpl::SetPageLifecycleStateInternal( @@ -155,10 +155,10 @@ index e167db6d5f208f2f3e923ec7dec7c4da4155dd90..cd31f34df12a94748e4fc9066c6f3446 // Do not throttle if the page should be painting. bool is_visible = diff --git a/third_party/blink/renderer/core/exported/web_view_impl.h b/third_party/blink/renderer/core/exported/web_view_impl.h -index 06f7cf79b4526ca3ec7670c234a6bb8faec32f04..b8fe2a9b7b6b4de2a689f3857c7ce44909e6f2dc 100644 +index aff99e7e1feb7addcdf631b7e3ac4209da6b502d..b759aca8d1e61c19904db146840e6f0c57a3d86a 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.h +++ b/third_party/blink/renderer/core/exported/web_view_impl.h -@@ -448,6 +448,7 @@ class CORE_EXPORT WebViewImpl final : public WebView, +@@ -447,6 +447,7 @@ class CORE_EXPORT WebViewImpl final : public WebView, LocalDOMWindow* PagePopupWindow() const; PageScheduler* Scheduler() const override; @@ -166,7 +166,7 @@ index 06f7cf79b4526ca3ec7670c234a6bb8faec32f04..b8fe2a9b7b6b4de2a689f3857c7ce449 void SetVisibilityState(mojom::blink::PageVisibilityState visibility_state, bool is_initial_state) override; mojom::blink::PageVisibilityState GetVisibilityState() override; -@@ -936,6 +937,8 @@ class CORE_EXPORT WebViewImpl final : public WebView, +@@ -935,6 +936,8 @@ class CORE_EXPORT WebViewImpl final : public WebView, // If true, we send IPC messages when |preferred_size_| changes. bool send_preferred_size_changes_ = false; diff --git a/patches/chromium/blink_local_frame.patch b/patches/chromium/blink_local_frame.patch index 6dcc64570f651..a34ca819e2716 100644 --- a/patches/chromium/blink_local_frame.patch +++ b/patches/chromium/blink_local_frame.patch @@ -49,10 +49,10 @@ index 2072f6b14289b1f3a76dbccc98f29aa178c1c35c..d7017437a7e7e6ac130677e52731d048 // its owning reference back to our owning LocalFrame. client_->Detached(type); diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index a309befcbcb1e7fe667bc1d794141fb90fea1035..dd148eb3cce762d20e9117b4f8030c881057b8bb 100644 +index f075d02c0695ca5fe06152295179b6ec76e3597a..e5d629937aaa175d11731bc1048a1b459927e93a 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc -@@ -753,10 +753,6 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { +@@ -727,10 +727,6 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { } DCHECK(!view_ || !view_->IsAttached()); @@ -63,7 +63,7 @@ index a309befcbcb1e7fe667bc1d794141fb90fea1035..dd148eb3cce762d20e9117b4f8030c88 if (!Client()) return false; -@@ -810,6 +806,11 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { +@@ -784,6 +780,11 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { DCHECK(!view_->IsAttached()); Client()->WillBeDetached(); diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index b7c7daad9cc48..9964154875dab 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -11,10 +11,10 @@ if we ever align our .pak file generation with Chrome we can remove this patch. diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff62717ba00 100644 +index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b47749874 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn -@@ -197,11 +197,16 @@ if (!is_android && !is_mac) { +@@ -200,11 +200,16 @@ if (!is_android && !is_mac) { "common/crash_keys.h", ] @@ -33,7 +33,7 @@ index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff6 "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index ed639e1fd384ce325f56df99d5fcf72f00aaf2b1..ea7919d5a9dd2699822facb47ae974a7a4e87172 100644 +index 73f7fc927f1c14c038e0ca91066dbb4e9bd8be62..d7d46198d11b7454d07188641f46617c924d63b1 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn @@ -4633,7 +4633,7 @@ static_library("browser") { @@ -46,7 +46,7 @@ index ed639e1fd384ce325f56df99d5fcf72f00aaf2b1..ea7919d5a9dd2699822facb47ae974a7 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index dd82cb96686234350a078536bce94a47aeb96ef8..2cb71c9c12ad89aa6a16c538f97979b3094b9cda 100644 +index 4866689b354bc9d963638edabf1eb02d16ba984c..c5b383f2c78592a57f0d138538733937b8e76ecd 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn @@ -7210,9 +7210,12 @@ test("unit_tests") { diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 0e62932fe95c0..6e968d7e6d069 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,10 +9,10 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 184fb0e5ce15f624300a35f47ef7e34759e2e9eb..73f56d65160a114bea9dcefa6ba03a417b7a273b 100644 +index ddfefbacebd5d89e112a15f29328c9674f7df3ae..ef8a80d2148c0ec0d8a3493ae58a4e723a9601e1 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -9777,6 +9777,7 @@ void RenderFrameHostImpl::CreateNewWindow( +@@ -9776,6 +9776,7 @@ void RenderFrameHostImpl::CreateNewWindow( last_committed_origin_, params->window_container_type, params->target_url, params->referrer.To(), params->frame_name, params->disposition, *params->features, @@ -21,10 +21,10 @@ index 184fb0e5ce15f624300a35f47ef7e34759e2e9eb..73f56d65160a114bea9dcefa6ba03a41 &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 77954ceccdfb1e94598d5d7ad747721ab84aa1d7..aec96f969800e2a4d09e644df770d367e48b1b63 100644 +index cb039c0ac747feefd5e8a13ed03715508ae874d0..b6fc96993cdea489450978495ca4c1f3c58166af 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5132,6 +5132,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5139,6 +5139,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( SetPartitionedPopinOpenerOnNewWindowIfNeeded(new_contents_impl, params, opener); @@ -37,7 +37,7 @@ index 77954ceccdfb1e94598d5d7ad747721ab84aa1d7..aec96f969800e2a4d09e644df770d367 // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5173,12 +5179,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5180,12 +5186,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -51,10 +51,10 @@ index 77954ceccdfb1e94598d5d7ad747721ab84aa1d7..aec96f969800e2a4d09e644df770d367 new_contents_impl, opener, params.target_url, params.referrer.To(), params.disposition, diff --git a/content/common/frame.mojom b/content/common/frame.mojom -index 55bb4ae3bab4cdf20b3e1dde9450a5c0e4e62b37..fe444c7fa140166a1b65c7a8a2676e2de7c4e0fc 100644 +index d1e8581724adeca8b6776ded7e7c7e921f68905c..6c4abeaf847328f73b4e53a552a038b29421d9aa 100644 --- a/content/common/frame.mojom +++ b/content/common/frame.mojom -@@ -646,6 +646,10 @@ struct CreateNewWindowParams { +@@ -645,6 +645,10 @@ struct CreateNewWindowParams { pending_associated_remote widget; pending_associated_receiver frame_widget_host; pending_associated_remote frame_widget; @@ -148,7 +148,7 @@ index da319cb20733150366d85bee95609f0f2d9def7f..8a18958035cc1dd26be558349f64f772 // typically happens when popups are created. virtual void WebContentsCreated(WebContents* source_contents, diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index 7f33a5452de32f5f4f8a43d0314917f24308d77c..b0aa018f2f4e6865915516ab6b65fac20d9e6f20 100644 +index 4d40964aa6bb93759dd73f63e48a36c66b50a61d..6c569b4a0f4ddea5d071753bb4a72002ba174171 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc @@ -6938,6 +6938,10 @@ WebView* RenderFrameImpl::CreateNewWindow( diff --git a/patches/chromium/chore_introduce_blocking_api_for_electron.patch b/patches/chromium/chore_introduce_blocking_api_for_electron.patch index b4b1d1ef83bbe..0fbdb80214b08 100644 --- a/patches/chromium/chore_introduce_blocking_api_for_electron.patch +++ b/patches/chromium/chore_introduce_blocking_api_for_electron.patch @@ -7,7 +7,7 @@ This patch comes after Chromium removed the ScopedAllowIO API in favor of explicitly adding ScopedAllowBlocking calls as friends. diff --git a/base/threading/thread_restrictions.h b/base/threading/thread_restrictions.h -index 59d6e6e4d899f10d1adeb4f23c32f0dd565cf963..674954816b6c241c1923668f8da7ad5c79a04256 100644 +index b1abcfaab58df4555d3a26481915d64ef5458e17..f2f43454c1c124da9983998564837ebf3589aefd 100644 --- a/base/threading/thread_restrictions.h +++ b/base/threading/thread_restrictions.h @@ -132,6 +132,7 @@ class KeyStorageLinux; @@ -28,7 +28,7 @@ index 59d6e6e4d899f10d1adeb4f23c32f0dd565cf963..674954816b6c241c1923668f8da7ad5c namespace enterprise_connectors { class LinuxKeyRotationCommand; } // namespace enterprise_connectors -@@ -572,6 +576,7 @@ class BASE_EXPORT ScopedAllowBlocking { +@@ -577,6 +581,7 @@ class BASE_EXPORT ScopedAllowBlocking { friend class ::DesktopNotificationBalloon; friend class ::FirefoxProfileLock; friend class ::GaiaConfig; @@ -36,7 +36,7 @@ index 59d6e6e4d899f10d1adeb4f23c32f0dd565cf963..674954816b6c241c1923668f8da7ad5c friend class ::ProfileImpl; friend class ::ScopedAllowBlockingForProfile; friend class ::StartupTabProviderImpl; -@@ -610,6 +615,7 @@ class BASE_EXPORT ScopedAllowBlocking { +@@ -615,6 +620,7 @@ class BASE_EXPORT ScopedAllowBlocking { friend class cronet::CronetPrefsManager; friend class crypto::ScopedAllowBlockingForNSS; // http://crbug.com/59847 friend class drive::FakeDriveService; diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 23a9de3f7ce4b..5cc2ada8cb2d0 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 459fc0eff0bfe2ec005d6f34cf7e91c2d601fd06..35de681eac3f65ce3e0435bd984159154ece2b7f 100644 +index e3085847de7875afa655b3cfa4aa39892be626eb..46fc6d6683c50fb8a340680de2eda340f5be4cca 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5051,7 +5051,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5058,7 +5058,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index fe4b7c4242915..fa1e1b29d0c8f 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -218,10 +218,10 @@ index c6838c83ef971b88769b1f3fba8095025ae25464..2da6a4e08340e72ba7de5d03444c2f17 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index c1c3db2992038cad0c01ce65c57676f8fe281830..2ad1479de622d956c701d8dc4adb75d0114f65b1 100644 +index 94b4429fffb474304c1d43d1cf1337fde90d9e45..2a683ac9a810d7bc7286e56ce50dd51adfc4f25f 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5014,8 +5014,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5021,8 +5021,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( // TODO(crbug.com/40202416): Support a way for MPArch guests to support this. if (delegate_ && delegate_->IsWebContentsCreationOverridden( source_site_instance, params.window_container_type, diff --git a/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch b/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch index 0ffd60d534c9a..2ebb63b2ae6ec 100644 --- a/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch +++ b/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch @@ -11,7 +11,7 @@ not need this dependency. refs https://chromium-review.googlesource.com/c/chromium/src/+/5573603 diff --git a/chrome/browser/ui/color/BUILD.gn b/chrome/browser/ui/color/BUILD.gn -index 29c3dafa96df631e36aa1ced6798990c768adeaa..0281a50f04fecfc4ded3805a8f9637e184288581 100644 +index 77c7485b0fa885ddff38f336d1c7a52f2e969c73..045c0751a0c43f3360e334dd227b6cff7ddfd681 100644 --- a/chrome/browser/ui/color/BUILD.gn +++ b/chrome/browser/ui/color/BUILD.gn @@ -84,9 +84,6 @@ source_set("mixers") { diff --git a/patches/chromium/disable_hidden.patch b/patches/chromium/disable_hidden.patch index 5216b4a2ede5e..e212dd9060bee 100644 --- a/patches/chromium/disable_hidden.patch +++ b/patches/chromium/disable_hidden.patch @@ -6,10 +6,10 @@ Subject: disable_hidden.patch Electron uses this to disable background throttling for hidden windows. diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index b722e19e8c660d13750ea7bf505e28a9c1d9d59f..bac913e30ce140d9b370186781cccf5817885076 100644 +index 00583269d16f4b8eacb4875b12a3e69155839d12..23d5baa267333e18551d449317f3e3a6520f34a6 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -831,6 +831,10 @@ void RenderWidgetHostImpl::WasHidden() { +@@ -834,6 +834,10 @@ void RenderWidgetHostImpl::WasHidden() { return; } @@ -21,10 +21,10 @@ index b722e19e8c660d13750ea7bf505e28a9c1d9d59f..bac913e30ce140d9b370186781cccf58 // Prompts should remain open and functional across tab switches. if (!delegate_ || !delegate_->IsWaitingForPointerLockPrompt(this)) { diff --git a/content/browser/renderer_host/render_widget_host_impl.h b/content/browser/renderer_host/render_widget_host_impl.h -index c11b7183397d28c6db61969390d1d078261e4c47..5d92247f088942250fbb6bd1ff83ab1c2c7140f7 100644 +index 86a80795fb931f569b21c3138697b90d8b38d750..6268d7e3a64bac17b94f0bfb8e24c44a61cf7d3f 100644 --- a/content/browser/renderer_host/render_widget_host_impl.h +++ b/content/browser/renderer_host/render_widget_host_impl.h -@@ -1013,6 +1013,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl +@@ -1012,6 +1012,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl // Requests a commit and forced redraw in the renderer compositor. void ForceRedrawForTesting(); diff --git a/patches/chromium/disable_unload_metrics.patch b/patches/chromium/disable_unload_metrics.patch index 8d2c76ab543b2..7e147685b0355 100644 --- a/patches/chromium/disable_unload_metrics.patch +++ b/patches/chromium/disable_unload_metrics.patch @@ -24,7 +24,7 @@ This patch temporarily disables the metrics so we can have green CI, and we should continue seeking for a real fix. diff --git a/content/browser/renderer_host/navigator.cc b/content/browser/renderer_host/navigator.cc -index 54ce1ea5ac11c9831a9553fbb5c5584c05440071..be95785fa144a4f11a3c97fea562dd4635ffe7b0 100644 +index d976c082529a62bcef7352531ced808e5970027e..31e95005359f6e8e4e18ebd75324940f4fdd11eb 100644 --- a/content/browser/renderer_host/navigator.cc +++ b/content/browser/renderer_host/navigator.cc @@ -1476,6 +1476,7 @@ void Navigator::RecordNavigationMetrics( diff --git a/patches/chromium/extend_apply_webpreferences.patch b/patches/chromium/extend_apply_webpreferences.patch index b1d09069d7789..26bcd05582b59 100644 --- a/patches/chromium/extend_apply_webpreferences.patch +++ b/patches/chromium/extend_apply_webpreferences.patch @@ -12,7 +12,7 @@ Ideally we could add an embedder observer pattern here but that can be done in future work. diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index cd31f34df12a94748e4fc9066c6f344610ce73f0..f9298f9ff6f5fc0f16d9366fb6fd569de83b55ce 100644 +index 0b2956425d2feb84f1d0db7be4f3d4b0875b1d10..f2e37be51049caab4fd6385b5b55f1151708bd82 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -171,6 +171,7 @@ diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index 6effb0187d542..b5576097e870b 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -239,7 +239,7 @@ index 5e8d2bfbccd0625c2598544a9cba3d71373eded2..e68a97ee75754fc7196f11cf5c731550 bool RenderVSyncNotificationEnabled() const { return render_v_sync_notification_enabled_; diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index f9298f9ff6f5fc0f16d9366fb6fd569de83b55ce..ef16711d93643a0612c8b34db8b3773a70aa210f 100644 +index f2e37be51049caab4fd6385b5b55f1151708bd82..c0078bff37cfd1a4e5da111f6ec1aa817987a7ab 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -3574,6 +3574,9 @@ void WebViewImpl::UpdateRendererPreferences( diff --git a/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch b/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch index d5a070ab577e1..342d76d0d85da 100644 --- a/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch +++ b/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch @@ -28,7 +28,7 @@ index 0527831e1f8d7923ba0f687a5c0da8573189d867..f72af0e6cfcf06d47bd917def993f081 // Returns the http referrer of original request which initited this load. diff --git a/third_party/blink/renderer/core/loader/document_loader.h b/third_party/blink/renderer/core/loader/document_loader.h -index e86efe8c9fc2d27fefc5e47afe401b8a6b1419ba..9d1ef55e4e122f30564f35406c8b51335e3d6996 100644 +index 10682e129daf40104a71d0067aa126cc13a1e8b7..fb8696d850fc3fbbcd66087c8cafc53acee462aa 100644 --- a/third_party/blink/renderer/core/loader/document_loader.h +++ b/third_party/blink/renderer/core/loader/document_loader.h @@ -328,7 +328,7 @@ class CORE_EXPORT DocumentLoader : public GarbageCollected, diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index b54a7fbf346c6..a8d7aceba2887 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -45,10 +45,10 @@ index 0dbbaddc1bef8b5a1b253297f47c33601dc6fe67..0c84f727b29c742ba4c2edd38dfa16d1 // origin of |common_params.url| and/or |common_params.initiator_origin|. url::Origin resolved_origin = url::Origin::Resolve( diff --git a/third_party/blink/renderer/core/loader/document_loader.cc b/third_party/blink/renderer/core/loader/document_loader.cc -index b2329dcaf3ef464fc4b7db477e2431017711d501..635029fa9680eeb6d01223c5cf683c7854763f40 100644 +index abcc4436479e7c9bc0dbf77c70c628e48d6ea1b8..510c088fd06d5989e710ba6674e1798bd5d63954 100644 --- a/third_party/blink/renderer/core/loader/document_loader.cc +++ b/third_party/blink/renderer/core/loader/document_loader.cc -@@ -2334,6 +2334,10 @@ Frame* DocumentLoader::CalculateOwnerFrame() { +@@ -2333,6 +2333,10 @@ Frame* DocumentLoader::CalculateOwnerFrame() { scoped_refptr DocumentLoader::CalculateOrigin( Document* owner_document) { scoped_refptr origin; @@ -59,7 +59,7 @@ index b2329dcaf3ef464fc4b7db477e2431017711d501..635029fa9680eeb6d01223c5cf683c78 StringBuilder debug_info_builder; // Whether the origin is newly created within this call, instead of copied // from an existing document's origin or from `origin_to_commit_`. If this is -@@ -2387,6 +2391,10 @@ scoped_refptr DocumentLoader::CalculateOrigin( +@@ -2386,6 +2390,10 @@ scoped_refptr DocumentLoader::CalculateOrigin( // the end of this function. origin = origin_to_commit_; debug_info_builder.Append("use_origin_to_commit"); diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 6c073e3ef8b1f..4a2a682c365f2 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 05a102a33f4c05fe6d34fa721d37fcae05a3a577..459fc0eff0bfe2ec005d6f34cf7e91c2d601fd06 100644 +index e96a656473e0d18a8053dab92dbeb1afb174d27f..e3085847de7875afa655b3cfa4aa39892be626eb 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -9970,7 +9970,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -9997,7 +9997,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch index c8da4b6dacf58..cf566bffed5c1 100644 --- a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch +++ b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch @@ -11,10 +11,10 @@ This patch should be upstreamed as a conditional revert of the logic in desktop vs mobile runtimes. i.e. restore the old logic only on desktop platforms diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 8c3ac60d029a76b004111cffd56e9b859594dd65..d398cb9f429f8304eeb6ed00c79e609a3b83bd3f 100644 +index 2551b4a2b9dfca9767c39e2e9bd79ed19c439db4..81844d36b86d5590b59d3b87f3f2d5bef3a7b24d 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2121,9 +2121,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { +@@ -2135,9 +2135,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { void RenderWidgetHostImpl::NotifyScreenInfoChanged() { // The resize message (which may not happen immediately) will carry with it // the screen info as well as the new size (if the screen has changed scale diff --git a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch index 5479442ad430c..fe1bffc491c77 100644 --- a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch +++ b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch @@ -59,10 +59,10 @@ index cba373664bec3a32abad6fe0396bd67b53b7e67f..a54f1b3351efd2d8f324436f7f35cd43 #endif // THIRD_PARTY_BLINK_PUBLIC_WEB_WEB_SCRIPT_EXECUTION_CALLBACK_H_ diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index dd148eb3cce762d20e9117b4f8030c881057b8bb..e626d63f295b2d0fa62b179c76c45df125bbaeeb 100644 +index e5d629937aaa175d11731bc1048a1b459927e93a..5fa2f36b65a876edc8f2e5905b695b9e5d88afbd 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc -@@ -3113,6 +3113,7 @@ void LocalFrame::RequestExecuteScript( +@@ -3081,6 +3081,7 @@ void LocalFrame::RequestExecuteScript( mojom::blink::EvaluationTiming evaluation_timing, mojom::blink::LoadEventBlockingOption blocking_option, WebScriptExecutionCallback callback, @@ -70,7 +70,7 @@ index dd148eb3cce762d20e9117b4f8030c881057b8bb..e626d63f295b2d0fa62b179c76c45df1 BackForwardCacheAware back_forward_cache_aware, mojom::blink::WantResultOption want_result_option, mojom::blink::PromiseResultOption promise_behavior) { -@@ -3145,7 +3146,7 @@ void LocalFrame::RequestExecuteScript( +@@ -3113,7 +3114,7 @@ void LocalFrame::RequestExecuteScript( PausableScriptExecutor::CreateAndRun( script_state, std::move(script_sources), execute_script_policy, user_gesture, evaluation_timing, blocking_option, want_result_option, @@ -80,10 +80,10 @@ index dd148eb3cce762d20e9117b4f8030c881057b8bb..e626d63f295b2d0fa62b179c76c45df1 void LocalFrame::SetEvictCachedSessionStorageOnFreezeOrUnload() { diff --git a/third_party/blink/renderer/core/frame/local_frame.h b/third_party/blink/renderer/core/frame/local_frame.h -index 80c37508a9382a0aeb221c37d2a96f13c526e550..0d12cf49599f0a249ab97f371e5c27cfe654f463 100644 +index 80c57253678d1aa6e655c84f4ccd9c0899eb5a5b..4d6b860409d35da509b7ef8c5d52fa9f92f1b542 100644 --- a/third_party/blink/renderer/core/frame/local_frame.h +++ b/third_party/blink/renderer/core/frame/local_frame.h -@@ -826,6 +826,7 @@ class CORE_EXPORT LocalFrame final +@@ -830,6 +830,7 @@ class CORE_EXPORT LocalFrame final mojom::blink::EvaluationTiming, mojom::blink::LoadEventBlockingOption, WebScriptExecutionCallback, @@ -92,10 +92,10 @@ index 80c37508a9382a0aeb221c37d2a96f13c526e550..0d12cf49599f0a249ab97f371e5c27cf mojom::blink::WantResultOption, mojom::blink::PromiseResultOption); diff --git a/third_party/blink/renderer/core/frame/local_frame_mojo_handler.cc b/third_party/blink/renderer/core/frame/local_frame_mojo_handler.cc -index 58b8f5b22c01d41cca3ec0088341d036917d5838..930d9fa36a616fe27d7b5b5a39436cbe375140bc 100644 +index 48c2ef6fe7bb92dda5199849266228e2008b605b..f49577958bba8eb69e5be44efb0bb696934ba1f3 100644 --- a/third_party/blink/renderer/core/frame/local_frame_mojo_handler.cc +++ b/third_party/blink/renderer/core/frame/local_frame_mojo_handler.cc -@@ -969,6 +969,7 @@ void LocalFrameMojoHandler::JavaScriptExecuteRequestInIsolatedWorld( +@@ -973,6 +973,7 @@ void LocalFrameMojoHandler::JavaScriptExecuteRequestInIsolatedWorld( std::move(callback).Run(value ? std::move(*value) : base::Value()); }, std::move(callback)), diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 523898fb50fd8..665e92fc25d62 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,7 +35,7 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index 5267ae3844f58d17e795c17184c85592157fda6f..21cab5e75e92570260df2e5fe4d2e404d2cb020a 100644 +index 02ac517502a51603a689c74d8073b2e5862f1e45..f0d167bb6c3a53950c431170eaa45a69408f93d9 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn @@ -1046,6 +1046,7 @@ component("base") { diff --git a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch index c130481a552b8..b158e8a185200 100644 --- a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch +++ b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch @@ -10,10 +10,10 @@ an about:blank check to this area. Ref: https://chromium-review.googlesource.com/c/chromium/src/+/5403876 diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index cd3ef19b973bcd0f9268684ae087b9197756715a..18a9ac180526faa053060f6d21abb2a90ebfc1cc 100644 +index 71174dc9f0e15622c67a2d33dc119594de68fc69..d73dced1fa1ad073a75df83657380a78659a8a1e 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -809,8 +809,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( +@@ -808,8 +808,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( // TODO(crbug.com/40092527): Consider adding a separate boolean that // tracks this instead of piggybacking `origin_calculation_debug_info`. if (renderer_side_origin.opaque() && diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index 63903f039b82d..ceff97c56ad66 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -666,7 +666,7 @@ index 6809c4576c71bc1e1a6ad4e0a37707272a9a10f4..3aad10424a6a31dab2ca393d00149ec6 PrintingFailed(int32 cookie, PrintFailureReason reason); diff --git a/components/printing/renderer/print_render_frame_helper.cc b/components/printing/renderer/print_render_frame_helper.cc -index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049514788e9 100644 +index 774392650ad07ee56cb931db7d1a46eaedb1eaa1..d42afb1a744113af660aadc832c71244b8918090 100644 --- a/components/printing/renderer/print_render_frame_helper.cc +++ b/components/printing/renderer/print_render_frame_helper.cc @@ -52,6 +52,7 @@ @@ -677,7 +677,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 #include "printing/units.h" #include "services/metrics/public/cpp/ukm_source_id.h" #include "third_party/blink/public/common/associated_interfaces/associated_interface_provider.h" -@@ -1236,14 +1237,14 @@ void PrintRenderFrameHelper::ScriptedPrint(bool user_initiated) { +@@ -1235,14 +1236,14 @@ void PrintRenderFrameHelper::ScriptedPrint(bool user_initiated) { } print_in_progress_ = true; @@ -694,7 +694,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 if (!weak_this) { return; } -@@ -1274,12 +1275,14 @@ void PrintRenderFrameHelper::BindPrintRenderFrameReceiver( +@@ -1273,12 +1274,14 @@ void PrintRenderFrameHelper::BindPrintRenderFrameReceiver( receivers_.Add(this, std::move(receiver)); } @@ -712,7 +712,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 ScopedIPC scoped_ipc(weak_ptr_factory_.GetWeakPtr()); if (ipc_nesting_level_ > kAllowedIpcDepthForPrint) { return; -@@ -1296,9 +1299,10 @@ void PrintRenderFrameHelper::PrintRequestedPagesInternal( +@@ -1295,9 +1298,10 @@ void PrintRenderFrameHelper::PrintRequestedPagesInternal( is_loading_ = frame->WillPrintSoon(); if (is_loading_) { @@ -726,7 +726,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 SetupOnStopLoadingTimeout(); return; } -@@ -1308,7 +1312,7 @@ void PrintRenderFrameHelper::PrintRequestedPagesInternal( +@@ -1307,7 +1311,7 @@ void PrintRenderFrameHelper::PrintRequestedPagesInternal( // plugin node and print that instead. auto plugin = delegate_->GetPdfElement(frame); @@ -735,7 +735,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 if (render_frame_gone_) { return; -@@ -1464,6 +1468,8 @@ void PrintRenderFrameHelper::PrintPreview(base::Value::Dict settings) { +@@ -1463,6 +1467,8 @@ void PrintRenderFrameHelper::PrintPreview(base::Value::Dict settings) { if (ipc_nesting_level_ > kAllowedIpcDepthForPrint) return; @@ -744,7 +744,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 print_preview_context_.OnPrintPreview(); #if BUILDFLAG(IS_CHROMEOS) -@@ -2076,17 +2082,19 @@ void PrintRenderFrameHelper::PrintNode(const blink::WebNode& node) { +@@ -2075,17 +2081,19 @@ void PrintRenderFrameHelper::PrintNode(const blink::WebNode& node) { void PrintRenderFrameHelper::Print(blink::WebLocalFrame* frame, const blink::WebNode& node, @@ -767,7 +767,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 DidFinishPrinting(PrintingResult::kFailPrintInit); return; } -@@ -2107,8 +2115,15 @@ void PrintRenderFrameHelper::Print(blink::WebLocalFrame* frame, +@@ -2106,8 +2114,15 @@ void PrintRenderFrameHelper::Print(blink::WebLocalFrame* frame, print_pages_params_->params->print_scaling_option; auto self = weak_ptr_factory_.GetWeakPtr(); @@ -784,7 +784,7 @@ index 09eec30627132cf715380518643cf245b10b4bf8..a1b0bd1e46c8608ad0e3a0be8b882049 // Check if `this` is still valid. if (!self) return; -@@ -2376,29 +2391,43 @@ void PrintRenderFrameHelper::IPCProcessed() { +@@ -2375,29 +2390,43 @@ void PrintRenderFrameHelper::IPCProcessed() { } bool PrintRenderFrameHelper::InitPrintSettings(blink::WebLocalFrame* frame, diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 54d5ffd829a74..4bf2d50bdaddb 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -30,10 +30,10 @@ index a54a0dedf8ef1cfffa4e80a4707debed0e83d277..e66e71fdbabb40a5307b12cd8965e773 // RenderWidgetHost on the primary main frame, and false otherwise. virtual bool IsWidgetForPrimaryMainFrame(RenderWidgetHostImpl*); diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index bac913e30ce140d9b370186781cccf5817885076..8c3ac60d029a76b004111cffd56e9b859594dd65 100644 +index 23d5baa267333e18551d449317f3e3a6520f34a6..2551b4a2b9dfca9767c39e2e9bd79ed19c439db4 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2055,6 +2055,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { +@@ -2069,6 +2069,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { if (view_) { view_->UpdateCursor(cursor); } @@ -44,10 +44,10 @@ index bac913e30ce140d9b370186781cccf5817885076..8c3ac60d029a76b004111cffd56e9b85 void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index aec96f969800e2a4d09e644df770d367e48b1b63..c1c3db2992038cad0c01ce65c57676f8fe281830 100644 +index b6fc96993cdea489450978495ca4c1f3c58166af..94b4429fffb474304c1d43d1cf1337fde90d9e45 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5884,6 +5884,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -5891,6 +5891,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,7 +60,7 @@ index aec96f969800e2a4d09e644df770d367e48b1b63..c1c3db2992038cad0c01ce65c57676f8 RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index 91f52c79054c184142d15cfad6b24330a365c167..51cc85f9c998cc9234700ec47065d69eaac8d474 100644 +index 54e9de12419c5e70775116b404d8ea4d370197bb..e1535116bbffeda9b6a881849c0a7d9de001c248 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h @@ -1183,6 +1183,7 @@ class CONTENT_EXPORT WebContentsImpl diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index ff700d4a1c034..552175e6ca3ce 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 35de681eac3f65ce3e0435bd984159154ece2b7f..f2d5a85376109b6127ca4a7b3c26dbbb61990e20 100644 +index 46fc6d6683c50fb8a340680de2eda340f5be4cca..2be25d84a831b0fa2baefeb95d413a5503d64b1b 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10107,25 +10107,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10134,25 +10134,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/render_widget_host_view_base.patch b/patches/chromium/render_widget_host_view_base.patch index 62838493d731a..429955c98fb21 100644 --- a/patches/chromium/render_widget_host_view_base.patch +++ b/patches/chromium/render_widget_host_view_base.patch @@ -24,7 +24,7 @@ index bb7475f1f8be4038c77d2dc68b09a7ac2338b160..c35ef5290ef1f812c5e7ff31d71ae066 const blink::WebMouseEvent& event, const ui::LatencyInfo& latency) { diff --git a/content/browser/renderer_host/render_widget_host_view_base.h b/content/browser/renderer_host/render_widget_host_view_base.h -index faed571e3232545cdba8fc113c039d3432441448..e349711282d623c975501de5fc1a5c9c7309001f 100644 +index 5627ee381a99c49760bbaa6e5e3476d8b4bc8cb1..230e059ee11ed64a1694232dad791fbb5644b578 100644 --- a/content/browser/renderer_host/render_widget_host_view_base.h +++ b/content/browser/renderer_host/render_widget_host_view_base.h @@ -30,6 +30,8 @@ @@ -61,8 +61,8 @@ index faed571e3232545cdba8fc113c039d3432441448..e349711282d623c975501de5fc1a5c9c void OnAutoscrollStart() override; const viz::DisplayHitTestQueryMap& GetDisplayHitTestQuery() const override; -@@ -197,6 +205,9 @@ class CONTENT_EXPORT RenderWidgetHostViewBase - void NotifyContextMenuInsetsObservers(const gfx::Rect&) override {} +@@ -198,6 +206,9 @@ class CONTENT_EXPORT RenderWidgetHostViewBase + void ShowInterestInElement(int) override {} bool IsHTMLFormPopup() const override; + virtual void InitAsGuest(RenderWidgetHostView* parent_host_view, diff --git a/patches/chromium/resource_file_conflict.patch b/patches/chromium/resource_file_conflict.patch index 19e08c4342b0d..2f21e75bd6457 100644 --- a/patches/chromium/resource_file_conflict.patch +++ b/patches/chromium/resource_file_conflict.patch @@ -52,10 +52,10 @@ Some alternatives to this patch: None of these options seems like a substantial maintainability win over this patch to me (@nornagon). diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index f47270687b9a12fb74be2e90cc1e9f25e2e2d34e..84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2 100644 +index 97f843f8133c49d684b415f61ef4b4084c4d345c..4b3f01018a9dea91b46b5917e099f272582991b2 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn -@@ -1551,7 +1551,7 @@ if (is_chrome_branded && !is_android) { +@@ -1554,7 +1554,7 @@ if (is_chrome_branded && !is_android) { } } @@ -64,7 +64,7 @@ index f47270687b9a12fb74be2e90cc1e9f25e2e2d34e..84fab7fcdb1a7ded880c0ff4867e09c7 chrome_paks("packed_resources") { if (is_mac) { output_dir = "$root_gen_dir/repack" -@@ -1597,6 +1597,12 @@ repack("browser_tests_pak") { +@@ -1600,6 +1600,12 @@ repack("browser_tests_pak") { deps = [ "//chrome/test/data/webui:resources" ] } diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index 9c4faf566d657..700deb20f1961 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 2ad1479de622d956c701d8dc4adb75d0114f65b1..3d4510df709ed60a1da7163d3226541ed8ff201c 100644 +index 2a683ac9a810d7bc7286e56ce50dd51adfc4f25f..8bf17cff8a1bea7cc73a91cec52887671f2c8aa4 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -3953,6 +3953,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3960,6 +3960,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index 2ad1479de622d956c701d8dc4adb75d0114f65b1..3d4510df709ed60a1da7163d3226541e std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -3963,6 +3970,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3970,6 +3977,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index 259ab91f6616d..08d3636f2fac8 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,10 +15,10 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 73f56d65160a114bea9dcefa6ba03a417b7a273b..cd3ef19b973bcd0f9268684ae087b9197756715a 100644 +index ef8a80d2148c0ec0d8a3493ae58a4e723a9601e1..71174dc9f0e15622c67a2d33dc119594de68fc69 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -8883,6 +8883,17 @@ void RenderFrameHostImpl::EnterFullscreen( +@@ -8882,6 +8882,17 @@ void RenderFrameHostImpl::EnterFullscreen( } } @@ -37,10 +37,10 @@ index 73f56d65160a114bea9dcefa6ba03a417b7a273b..cd3ef19b973bcd0f9268684ae087b919 if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 3d4510df709ed60a1da7163d3226541ed8ff201c..05a102a33f4c05fe6d34fa721d37fcae05a3a577 100644 +index 8bf17cff8a1bea7cc73a91cec52887671f2c8aa4..e96a656473e0d18a8053dab92dbeb1afb174d27f 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4228,21 +4228,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4235,21 +4235,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index 3d4510df709ed60a1da7163d3226541ed8ff201c..05a102a33f4c05fe6d34fa721d37fcae } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4401,7 +4405,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4408,7 +4412,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); From b59a7ef2c34436363f0802d515901003a401d176 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 8 May 2025 01:06:31 -0500 Subject: [PATCH 027/186] refactor: Node.js temporary "explicit" microtask policy scope pattern (#46991) refactor: Node.js explicit microtask scope pattern Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: clavin --- shell/common/node_bindings.cc | 30 +++++++++------------- shell/common/node_util.cc | 10 ++++++++ shell/common/node_util.h | 23 +++++++++++++++++ shell/renderer/electron_renderer_client.cc | 20 +++++---------- shell/renderer/web_worker_observer.cc | 21 ++++++--------- 5 files changed, 60 insertions(+), 44 deletions(-) diff --git a/shell/common/node_bindings.cc b/shell/common/node_bindings.cc index f88ff0303da93..3d837b31985ca 100644 --- a/shell/common/node_bindings.cc +++ b/shell/common/node_bindings.cc @@ -909,28 +909,22 @@ void NodeBindings::UvRunOnce() { // Enter node context while dealing with uv events. v8::Context::Scope context_scope(env->context()); - // Node.js expects `kExplicit` microtasks policy and will run microtasks - // checkpoints after every call into JavaScript. Since we use a different - // policy in the renderer - switch to `kExplicit` and then drop back to the - // previous policy value. - v8::MicrotaskQueue* microtask_queue = env->context()->GetMicrotaskQueue(); - auto old_policy = microtask_queue->microtasks_policy(); - DCHECK_EQ(microtask_queue->GetMicrotasksScopeDepth(), 0); - microtask_queue->set_microtasks_policy(v8::MicrotasksPolicy::kExplicit); + { + util::ExplicitMicrotasksScope microtasks_scope( + env->context()->GetMicrotaskQueue()); - if (browser_env_ != BrowserEnvironment::kBrowser) - TRACE_EVENT_BEGIN0("devtools.timeline", "FunctionCall"); - - // Deal with uv events. - int r = uv_run(uv_loop_, UV_RUN_NOWAIT); + if (browser_env_ != BrowserEnvironment::kBrowser) + TRACE_EVENT_BEGIN0("devtools.timeline", "FunctionCall"); - if (browser_env_ != BrowserEnvironment::kBrowser) - TRACE_EVENT_END0("devtools.timeline", "FunctionCall"); + // Deal with uv events. + int r = uv_run(uv_loop_, UV_RUN_NOWAIT); - microtask_queue->set_microtasks_policy(old_policy); + if (browser_env_ != BrowserEnvironment::kBrowser) + TRACE_EVENT_END0("devtools.timeline", "FunctionCall"); - if (r == 0) - base::RunLoop().QuitWhenIdle(); // Quit from uv. + if (r == 0) + base::RunLoop().QuitWhenIdle(); // Quit from uv. + } // Tell the worker thread to continue polling. uv_sem_post(&embed_sem_); diff --git a/shell/common/node_util.cc b/shell/common/node_util.cc index 89eaf88942194..f777796339a14 100644 --- a/shell/common/node_util.cc +++ b/shell/common/node_util.cc @@ -130,6 +130,16 @@ node::Environment* CreateEnvironment(v8::Isolate* isolate, return env; } +ExplicitMicrotasksScope::ExplicitMicrotasksScope(v8::MicrotaskQueue* queue) + : microtask_queue_(queue), original_policy_(queue->microtasks_policy()) { + DCHECK_EQ(microtask_queue_->GetMicrotasksScopeDepth(), 0); + microtask_queue_->set_microtasks_policy(v8::MicrotasksPolicy::kExplicit); +} + +ExplicitMicrotasksScope::~ExplicitMicrotasksScope() { + microtask_queue_->set_microtasks_policy(original_policy_); +} + } // namespace electron::util namespace electron::Buffer { diff --git a/shell/common/node_util.h b/shell/common/node_util.h index fdc92c0f6b9e5..b159fcf657768 100644 --- a/shell/common/node_util.h +++ b/shell/common/node_util.h @@ -10,6 +10,8 @@ #include #include "base/containers/span.h" +#include "base/memory/raw_ptr.h" +#include "v8-microtask-queue.h" #include "v8/include/v8-forward.h" namespace node { @@ -63,6 +65,27 @@ node::Environment* CreateEnvironment(v8::Isolate* isolate, node::EnvironmentFlags::Flags env_flags, std::string_view process_type = ""); +// A scope that temporarily changes the microtask policy to explicit. Use this +// anywhere that can trigger Node.js or uv_run(). +// +// Node.js expects `kExplicit` microtasks policy and will run microtasks +// checkpoints after every call into JavaScript. Since we use a different +// policy in the renderer, this scope temporarily changes the policy to +// `kExplicit` while the scope is active, then restores the original policy +// when it's destroyed. +class ExplicitMicrotasksScope { + public: + explicit ExplicitMicrotasksScope(v8::MicrotaskQueue* queue); + ~ExplicitMicrotasksScope(); + + ExplicitMicrotasksScope(const ExplicitMicrotasksScope&) = delete; + ExplicitMicrotasksScope& operator=(const ExplicitMicrotasksScope&) = delete; + + private: + base::raw_ptr microtask_queue_; + v8::MicrotasksPolicy original_policy_; +}; + } // namespace electron::util namespace electron::Buffer { diff --git a/shell/renderer/electron_renderer_client.cc b/shell/renderer/electron_renderer_client.cc index c18b81d49ddee..5757c2c76cad5 100644 --- a/shell/renderer/electron_renderer_client.cc +++ b/shell/renderer/electron_renderer_client.cc @@ -16,6 +16,7 @@ #include "shell/common/gin_helper/event_emitter_caller.h" #include "shell/common/node_bindings.h" #include "shell/common/node_includes.h" +#include "shell/common/node_util.h" #include "shell/common/options_switches.h" #include "shell/renderer/electron_render_frame_observer.h" #include "shell/renderer/web_worker_observer.h" @@ -178,19 +179,12 @@ void ElectronRendererClient::WillReleaseScriptContext( if (env == node_bindings_->uv_env()) node_bindings_->set_uv_env(nullptr); - // Destroying the node environment will also run the uv loop, - // Node.js expects `kExplicit` microtasks policy and will run microtasks - // checkpoints after every call into JavaScript. Since we use a different - // policy in the renderer - switch to `kExplicit` and then drop back to the - // previous policy value. - v8::MicrotaskQueue* microtask_queue = context->GetMicrotaskQueue(); - auto old_policy = microtask_queue->microtasks_policy(); - DCHECK_EQ(microtask_queue->GetMicrotasksScopeDepth(), 0); - microtask_queue->set_microtasks_policy(v8::MicrotasksPolicy::kExplicit); - - environments_.erase(iter); - - microtask_queue->set_microtasks_policy(old_policy); + // Destroying the node environment will also run the uv loop. + { + util::ExplicitMicrotasksScope microtasks_scope( + context->GetMicrotaskQueue()); + environments_.erase(iter); + } // ElectronBindings is tracking node environments. electron_bindings_->EnvironmentDestroyed(env); diff --git a/shell/renderer/web_worker_observer.cc b/shell/renderer/web_worker_observer.cc index d1953998cb72e..ccdaf7911a315 100644 --- a/shell/renderer/web_worker_observer.cc +++ b/shell/renderer/web_worker_observer.cc @@ -14,6 +14,7 @@ #include "shell/common/gin_helper/event_emitter_caller.h" #include "shell/common/node_bindings.h" #include "shell/common/node_includes.h" +#include "shell/common/node_util.h" namespace electron { @@ -112,19 +113,13 @@ void WebWorkerObserver::ContextWillDestroy(v8::Local context) { gin_helper::EmitEvent(env->isolate(), env->process_object(), "exit"); } - // Destroying the node environment will also run the uv loop, - // Node.js expects `kExplicit` microtasks policy and will run microtasks - // checkpoints after every call into JavaScript. Since we use a different - // policy in the renderer - switch to `kExplicit` - v8::MicrotaskQueue* microtask_queue = context->GetMicrotaskQueue(); - auto old_policy = microtask_queue->microtasks_policy(); - DCHECK_EQ(microtask_queue->GetMicrotasksScopeDepth(), 0); - microtask_queue->set_microtasks_policy(v8::MicrotasksPolicy::kExplicit); - - base::EraseIf(environments_, - [env](auto const& item) { return item.get() == env; }); - - microtask_queue->set_microtasks_policy(old_policy); + // Destroying the node environment will also run the uv loop. + { + util::ExplicitMicrotasksScope microtasks_scope( + context->GetMicrotaskQueue()); + base::EraseIf(environments_, + [env](auto const& item) { return item.get() == env; }); + } // ElectronBindings is tracking node environments. electron_bindings_->EnvironmentDestroyed(env); From 057437f7398c3434a556d562986af0638b8fe9e4 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 8 May 2025 09:37:26 -0500 Subject: [PATCH 028/186] test: enable `hasShadow` tests on Linux (#47001) refactor: enable hasShadow tests on Linux Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- spec/api-browser-window-spec.ts | 102 ++++++++++++++++---------------- 1 file changed, 51 insertions(+), 51 deletions(-) diff --git a/spec/api-browser-window-spec.ts b/spec/api-browser-window-spec.ts index f8aebc55d93b6..2afadcfcdf80c 100755 --- a/spec/api-browser-window-spec.ts +++ b/spec/api-browser-window-spec.ts @@ -5428,6 +5428,57 @@ describe('BrowserWindow module', () => { }); }); }); + + describe('hasShadow state', () => { + describe('with properties', () => { + it('returns a boolean on all platforms', () => { + const w = new BrowserWindow({ show: false }); + expect(w.shadow).to.be.a('boolean'); + }); + + // On Windows there's no shadow by default & it can't be changed dynamically. + it('can be changed with hasShadow option', () => { + const hasShadow = process.platform !== 'darwin'; + const w = new BrowserWindow({ show: false, hasShadow }); + expect(w.shadow).to.equal(hasShadow); + }); + + it('can be changed with setHasShadow method', () => { + const w = new BrowserWindow({ show: false }); + w.shadow = false; + expect(w.shadow).to.be.false('hasShadow'); + w.shadow = true; + expect(w.shadow).to.be.true('hasShadow'); + w.shadow = false; + expect(w.shadow).to.be.false('hasShadow'); + }); + }); + + describe('with functions', () => { + it('returns a boolean on all platforms', () => { + const w = new BrowserWindow({ show: false }); + const hasShadow = w.hasShadow(); + expect(hasShadow).to.be.a('boolean'); + }); + + // On Windows there's no shadow by default & it can't be changed dynamically. + it('can be changed with hasShadow option', () => { + const hasShadow = process.platform !== 'darwin'; + const w = new BrowserWindow({ show: false, hasShadow }); + expect(w.hasShadow()).to.equal(hasShadow); + }); + + it('can be changed with setHasShadow method', () => { + const w = new BrowserWindow({ show: false }); + w.setHasShadow(false); + expect(w.hasShadow()).to.be.false('hasShadow'); + w.setHasShadow(true); + expect(w.hasShadow()).to.be.true('hasShadow'); + w.setHasShadow(false); + expect(w.hasShadow()).to.be.false('hasShadow'); + }); + }); + }); }); ifdescribe(process.platform !== 'linux')('window states (excluding Linux)', () => { @@ -6207,57 +6258,6 @@ describe('BrowserWindow module', () => { }); }); }); - - describe('hasShadow state', () => { - describe('with properties', () => { - it('returns a boolean on all platforms', () => { - const w = new BrowserWindow({ show: false }); - expect(w.shadow).to.be.a('boolean'); - }); - - // On Windows there's no shadow by default & it can't be changed dynamically. - it('can be changed with hasShadow option', () => { - const hasShadow = process.platform !== 'darwin'; - const w = new BrowserWindow({ show: false, hasShadow }); - expect(w.shadow).to.equal(hasShadow); - }); - - it('can be changed with setHasShadow method', () => { - const w = new BrowserWindow({ show: false }); - w.shadow = false; - expect(w.shadow).to.be.false('hasShadow'); - w.shadow = true; - expect(w.shadow).to.be.true('hasShadow'); - w.shadow = false; - expect(w.shadow).to.be.false('hasShadow'); - }); - }); - - describe('with functions', () => { - it('returns a boolean on all platforms', () => { - const w = new BrowserWindow({ show: false }); - const hasShadow = w.hasShadow(); - expect(hasShadow).to.be.a('boolean'); - }); - - // On Windows there's no shadow by default & it can't be changed dynamically. - it('can be changed with hasShadow option', () => { - const hasShadow = process.platform !== 'darwin'; - const w = new BrowserWindow({ show: false, hasShadow }); - expect(w.hasShadow()).to.equal(hasShadow); - }); - - it('can be changed with setHasShadow method', () => { - const w = new BrowserWindow({ show: false }); - w.setHasShadow(false); - expect(w.hasShadow()).to.be.false('hasShadow'); - w.setHasShadow(true); - expect(w.hasShadow()).to.be.true('hasShadow'); - w.setHasShadow(false); - expect(w.hasShadow()).to.be.false('hasShadow'); - }); - }); - }); }); describe('window.getMediaSourceId()', () => { From 2c6f713d72ea73ebad39413a14c23a82747fc2ed Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 8 May 2025 15:33:43 -0500 Subject: [PATCH 029/186] refactor: reduce use of `NativeWidgetPrivate` (#47006) * refactor: do not use native_widget_private() in NativeWindowViews::SetContentProtection() refactor: do not use native_widget_private() in NativeWindowViews::IsContentProtected() Co-authored-by: Charles Kerr * refactor: do not use native_widget_private() in NativeWindowViews::Show() Co-authored-by: Charles Kerr * chore: remove native_widget_private #include from native_window_views_win Not needed since Feb 2025: 9199d5c6 Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window_views.cc | 9 ++++----- shell/browser/native_window_views_win.cc | 1 - 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index d7b6d0ac54c02..39c066aed2929 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -487,8 +487,7 @@ bool NativeWindowViews::IsFocused() const { } void NativeWindowViews::Show() { - if (is_modal() && NativeWindow::parent() && - !widget()->native_widget_private()->IsVisible()) + if (is_modal() && NativeWindow::parent() && !widget()->IsVisible()) static_cast(parent())->IncrementChildModals(); widget()->native_widget_private()->Show(GetRestoredState(), gfx::Rect()); @@ -1295,15 +1294,15 @@ void NativeWindowViews::SetIgnoreMouseEvents(bool ignore, bool forward) { #endif } -void NativeWindowViews::SetContentProtection(bool enable) { +void NativeWindowViews::SetContentProtection(const bool enable) { #if BUILDFLAG(IS_WIN) - widget()->native_widget_private()->SetAllowScreenshots(!enable); + widget()->SetAllowScreenshots(!enable); #endif } bool NativeWindowViews::IsContentProtected() const { #if BUILDFLAG(IS_WIN) - return !widget()->native_widget_private()->AreScreenshotsAllowed(); + return !widget()->AreScreenshotsAllowed(); #else // Not implemented on Linux return false; #endif diff --git a/shell/browser/native_window_views_win.cc b/shell/browser/native_window_views_win.cc index 858418af4f8d5..7202464f608d9 100644 --- a/shell/browser/native_window_views_win.cc +++ b/shell/browser/native_window_views_win.cc @@ -19,7 +19,6 @@ #include "ui/display/display.h" #include "ui/display/screen.h" #include "ui/gfx/geometry/resize_utils.h" -#include "ui/views/widget/native_widget_private.h" // Must be included after other Windows headers. #include From 4eea6e49746ffd86c773b4cd0b1ab4fcd98560ae Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 8 May 2025 15:34:41 -0500 Subject: [PATCH 030/186] build: remove deps_add_v8_object_setinternalfieldfornodecore.patch (#46998) chore: remove deps_add_v8_object_setinternalfieldfornodecore.patch This was a Node 20-specific workaround that's no longer needed in Node 22. Xref: https://github.com/nodejs/node/pull/49874. Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- patches/v8/.patches | 1 - ...8_object_setinternalfieldfornodecore.patch | 87 ------------------- 2 files changed, 88 deletions(-) delete mode 100644 patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch diff --git a/patches/v8/.patches b/patches/v8/.patches index 280a34b936037..dc98544242e85 100644 --- a/patches/v8/.patches +++ b/patches/v8/.patches @@ -1,2 +1 @@ chore_allow_customizing_microtask_policy_per_context.patch -deps_add_v8_object_setinternalfieldfornodecore.patch diff --git a/patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch b/patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch deleted file mode 100644 index b682b49f0e1ea..0000000000000 --- a/patches/v8/deps_add_v8_object_setinternalfieldfornodecore.patch +++ /dev/null @@ -1,87 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Shelley Vohr -Date: Tue, 14 Nov 2023 17:48:11 +0100 -Subject: deps: add v8::Object::SetInternalFieldForNodeCore() - -This is a non-ABI breaking solution added by Node.js in v20.x for: - -* https://chromium-review.googlesource.com/c/v8/v8/+/4827307 -* https://chromium-review.googlesource.com/c/v8/v8/+/4707972 - -which are necessary for backporting the vm-related memory fixes in https://github.com/nodejs/node/pull/48510. - -diff --git a/include/v8-object.h b/include/v8-object.h -index 3e57ae8efe33f326ef0e5d609c311d4be5b8afd6..dc521d39c2280dfc3217e97c1e413b2be9b4f7ff 100644 ---- a/include/v8-object.h -+++ b/include/v8-object.h -@@ -22,6 +22,8 @@ class Function; - class FunctionTemplate; - template - class PropertyCallbackInfo; -+class Module; -+class UnboundScript; - - /** - * A private symbol -@@ -532,6 +534,21 @@ class V8_EXPORT Object : public Value { - index); - } - -+ /** -+ * Warning: These are Node.js-specific extentions used to avoid breaking -+ * changes in Node.js v20.x. They do not exist in V8 upstream and will -+ * not exist in Node.js v21.x. Node.js embedders and addon authors should -+ * not use them from v20.x. -+ */ -+#ifndef NODE_WANT_INTERNALS -+ V8_DEPRECATED("This extention should only be used by Node.js core") -+#endif -+ void SetInternalFieldForNodeCore(int index, Local value); -+#ifndef NODE_WANT_INTERNALS -+ V8_DEPRECATED("This extention should only be used by Node.js core") -+#endif -+ void SetInternalFieldForNodeCore(int index, Local value); -+ - /** Same as above, but works for TracedReference. */ - V8_INLINE static void* GetAlignedPointerFromInternalField( - const BasicTracedReference& object, int index) { -diff --git a/src/api/api.cc b/src/api/api.cc -index 62a71b9cb7594e5fcc86f32d7af160c32b8e8944..0b2d5bfa9480ea90eb0adb89132505b8cabafc08 100644 ---- a/src/api/api.cc -+++ b/src/api/api.cc -@@ -6313,14 +6313,33 @@ Local v8::Object::SlowGetInternalField(int index) { - i::Cast(*obj)->GetEmbedderField(index), isolate)); - } - --void v8::Object::SetInternalField(int index, v8::Local value) { -- auto obj = Utils::OpenDirectHandle(this); -+template -+void SetInternalFieldImpl(v8::Object* receiver, int index, v8::Local value) { -+ auto obj = Utils::OpenDirectHandle(receiver); - const char* location = "v8::Object::SetInternalField()"; - if (!InternalFieldOK(obj, index, location)) return; - auto val = Utils::OpenDirectHandle(*value); - i::Cast(obj)->SetEmbedderField(index, *val); - } - -+void v8::Object::SetInternalField(int index, v8::Local value) { -+ SetInternalFieldImpl(this, index, value); -+} -+ -+/** -+ * These are Node.js-specific extentions used to avoid breaking changes in -+ * Node.js v20.x. -+ */ -+void v8::Object::SetInternalFieldForNodeCore(int index, -+ v8::Local value) { -+ SetInternalFieldImpl(this, index, value); -+} -+ -+void v8::Object::SetInternalFieldForNodeCore(int index, -+ v8::Local value) { -+ SetInternalFieldImpl(this, index, value); -+} -+ - void* v8::Object::SlowGetAlignedPointerFromInternalField(v8::Isolate* isolate, - int index) { - auto obj = Utils::OpenDirectHandle(this); From 440cdec0613c3958823da9e8a839cc2b41954560 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 9 May 2025 09:36:35 +0200 Subject: [PATCH 031/186] build: update hasher return value (#47011) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Keeley Hammond --- script/release/get-url-hash.ts | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/script/release/get-url-hash.ts b/script/release/get-url-hash.ts index b4fc10b053b07..f144c2fa33df9 100644 --- a/script/release/get-url-hash.ts +++ b/script/release/get-url-hash.ts @@ -28,7 +28,9 @@ export async function getUrlHash (targetUrl: string, algorithm = 'sha256', attem } if (!resp.body) throw new Error('Successful lambda call but failed to get valid hash'); - return resp.body.trim(); + // response shape should be { hash: 'xyz', invocationId: "abc"} + const { hash } = JSON.parse(resp.body.trim()); + return hash; } catch (err) { if (attempts > 1) { const { response } = err as any; From 3d836267edc0409ddffba1a9f334296763576e93 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 9 May 2025 09:36:47 +0200 Subject: [PATCH 032/186] refactor: use `gin_helper::Dictionary::ValueOrDefault()` (#47014) refactor: use `gin_helper::Dictionary::ValueOrDefault()` (#46982) * refactor: use ValueOrDefault() in electron_api_web_contents.cc * refactor: use ValueOrDefault() in electron_api_url_loader.cc * refactor: use ValueOrDefault() in electron_download_manager_delegate.cc * refactor: use ValueOrDefault() in electron_touch_bar.mm * refactor: use ValueOrDefault() in electron_url_loader_factory.cc * refactor: use ValueOrDefault() in electron_browser_context.cc * refactor: use ValueOrDefault() in electron_touch_bar.mm * refactor: use ValueOrDefault() in blink_converter.cc * feat: add ValueOrDefault() to PersistentDictionary * empty commit * refactor: use ValueOrDefault() in blink_converter.cc * refactor: inline the rectangle base::Value::Dict * refactor: remove has_scroll temporary --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- .../browser/api/electron_api_web_contents.cc | 101 +++++++----------- shell/browser/electron_browser_context.cc | 6 +- .../electron_download_manager_delegate.cc | 3 +- .../net/electron_url_loader_factory.cc | 4 +- shell/browser/ui/cocoa/electron_touch_bar.mm | 34 ++---- shell/common/api/electron_api_url_loader.cc | 13 +-- .../common/gin_converters/blink_converter.cc | 20 ++-- .../common/gin_helper/persistent_dictionary.h | 9 ++ 8 files changed, 76 insertions(+), 114 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index d10d8926a31aa..bf7a1bb38b155 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -822,8 +822,7 @@ WebContents::WebContents(v8::Isolate* isolate, // Whether to enable DevTools. options.Get("devTools", &enable_devtools_); - bool initially_shown = true; - options.Get(options::kShow, &initially_shown); + const bool initially_shown = options.ValueOrDefault(options::kShow, true); // Obtain the session. std::string partition; @@ -2332,9 +2331,7 @@ void WebContents::LoadURL(const GURL& url, params.load_type = content::NavigationController::LOAD_TYPE_DATA; } - bool reload_ignoring_cache = false; - if (options.Get("reloadIgnoringCache", &reload_ignoring_cache) && - reload_ignoring_cache) { + if (options.ValueOrDefault("reloadIgnoringCache", false)) { params.reload_type = content::ReloadType::BYPASSING_CACHE; } @@ -3011,13 +3008,10 @@ void WebContents::Print(gin::Arguments* args) { } // Set optional silent printing. - bool silent = false; - options.Get("silent", &silent); - settings.Set("silent", silent); + settings.Set("silent", options.ValueOrDefault("silent", false)); - bool print_background = false; - options.Get("printBackground", &print_background); - settings.Set(printing::kSettingShouldPrintBackgrounds, print_background); + settings.Set(printing::kSettingShouldPrintBackgrounds, + options.ValueOrDefault("printBackground", false)); // Set custom margin settings auto margins = gin_helper::Dictionary::CreateEmpty(args->isolate()); @@ -3028,20 +3022,16 @@ void WebContents::Print(gin::Arguments* args) { settings.Set(printing::kSettingMarginsType, static_cast(margin_type)); if (margin_type == printing::mojom::MarginType::kCustomMargins) { - base::Value::Dict custom_margins; - int top = 0; - margins.Get("top", &top); - custom_margins.Set(printing::kSettingMarginTop, top); - int bottom = 0; - margins.Get("bottom", &bottom); - custom_margins.Set(printing::kSettingMarginBottom, bottom); - int left = 0; - margins.Get("left", &left); - custom_margins.Set(printing::kSettingMarginLeft, left); - int right = 0; - margins.Get("right", &right); - custom_margins.Set(printing::kSettingMarginRight, right); - settings.Set(printing::kSettingMarginsCustom, std::move(custom_margins)); + settings.Set(printing::kSettingMarginsCustom, + base::Value::Dict{} + .Set(printing::kSettingMarginTop, + margins.ValueOrDefault("top", 0)) + .Set(printing::kSettingMarginBottom, + margins.ValueOrDefault("bottom", 0)) + .Set(printing::kSettingMarginLeft, + margins.ValueOrDefault("left", 0)) + .Set(printing::kSettingMarginRight, + margins.ValueOrDefault("right", 0))); } } else { settings.Set( @@ -3050,46 +3040,37 @@ void WebContents::Print(gin::Arguments* args) { } // Set whether to print color or greyscale - bool print_color = true; - options.Get("color", &print_color); - auto const color_model = print_color ? printing::mojom::ColorModel::kColor - : printing::mojom::ColorModel::kGray; - settings.Set(printing::kSettingColor, static_cast(color_model)); + settings.Set(printing::kSettingColor, + static_cast(options.ValueOrDefault("color", true) + ? printing::mojom::ColorModel::kColor + : printing::mojom::ColorModel::kGray)); // Is the orientation landscape or portrait. - bool landscape = false; - options.Get("landscape", &landscape); - settings.Set(printing::kSettingLandscape, landscape); + settings.Set(printing::kSettingLandscape, + options.ValueOrDefault("landscape", false)); // We set the default to the system's default printer and only update // if at the Chromium level if the user overrides. // Printer device name as opened by the OS. - std::u16string device_name; - options.Get("deviceName", &device_name); + const auto device_name = + options.ValueOrDefault("deviceName", std::u16string{}); - int scale_factor = 100; - options.Get("scaleFactor", &scale_factor); - settings.Set(printing::kSettingScaleFactor, scale_factor); + settings.Set(printing::kSettingScaleFactor, + options.ValueOrDefault("scaleFactor", 100)); - int pages_per_sheet = 1; - options.Get("pagesPerSheet", &pages_per_sheet); - settings.Set(printing::kSettingPagesPerSheet, pages_per_sheet); + settings.Set(printing::kSettingPagesPerSheet, + options.ValueOrDefault("pagesPerSheet", 1)); // True if the user wants to print with collate. - bool collate = true; - options.Get("collate", &collate); - settings.Set(printing::kSettingCollate, collate); + settings.Set(printing::kSettingCollate, + options.ValueOrDefault("collate", true)); // The number of individual copies to print - int copies = 1; - options.Get("copies", &copies); - settings.Set(printing::kSettingCopies, copies); + settings.Set(printing::kSettingCopies, options.ValueOrDefault("copies", 1)); // Strings to be printed as headers and footers if requested by the user. - std::string header; - options.Get("header", &header); - std::string footer; - options.Get("footer", &footer); + const auto header = options.ValueOrDefault("header", std::string{}); + const auto footer = options.ValueOrDefault("footer", std::string{}); if (!(header.empty() && footer.empty())) { settings.Set(printing::kSettingHeaderFooterEnabled, true); @@ -3128,9 +3109,8 @@ void WebContents::Print(gin::Arguments* args) { } // Duplex type user wants to use. - printing::mojom::DuplexMode duplex_mode = - printing::mojom::DuplexMode::kSimplex; - options.Get("duplexMode", &duplex_mode); + const auto duplex_mode = options.ValueOrDefault( + "duplexMode", printing::mojom::DuplexMode::kSimplex); settings.Set(printing::kSettingDuplexMode, static_cast(duplex_mode)); base::Value::Dict media_size; @@ -3150,14 +3130,11 @@ void WebContents::Print(gin::Arguments* args) { } // Set custom dots per inch (dpi) - gin_helper::Dictionary dpi_settings; - if (options.Get("dpi", &dpi_settings)) { - int horizontal = 72; - dpi_settings.Get("horizontal", &horizontal); - settings.Set(printing::kSettingDpiHorizontal, horizontal); - int vertical = 72; - dpi_settings.Get("vertical", &vertical); - settings.Set(printing::kSettingDpiVertical, vertical); + if (gin_helper::Dictionary dpi; options.Get("dpi", &dpi)) { + settings.Set(printing::kSettingDpiHorizontal, + dpi.ValueOrDefault("horizontal", 72)); + settings.Set(printing::kSettingDpiVertical, + dpi.ValueOrDefault("vertical", 72)); } print_task_runner_->PostTaskAndReplyWithResult( diff --git a/shell/browser/electron_browser_context.cc b/shell/browser/electron_browser_context.cc index 044b42175db44..9f4d6d5bee795 100644 --- a/shell/browser/electron_browser_context.cc +++ b/shell/browser/electron_browser_context.cc @@ -758,9 +758,9 @@ void ElectronBrowserContext::DisplayMediaDeviceChosen( GetAudioDesktopMediaId(request.requested_audio_device_ids)); devices.audio_device = audio_device; } else if (result_dict.Get("audio", &rfh)) { - bool enable_local_echo = false; - result_dict.Get("enableLocalEcho", &enable_local_echo); - bool disable_local_echo = !enable_local_echo; + const bool enable_local_echo = + result_dict.ValueOrDefault("enableLocalEcho", false); + const bool disable_local_echo = !enable_local_echo; auto* web_contents = content::WebContents::FromRenderFrameHost(rfh); blink::MediaStreamDevice audio_device( request.audio_type, diff --git a/shell/browser/electron_download_manager_delegate.cc b/shell/browser/electron_download_manager_delegate.cc index 560bf867790a3..320941208d626 100644 --- a/shell/browser/electron_download_manager_delegate.cc +++ b/shell/browser/electron_download_manager_delegate.cc @@ -294,8 +294,7 @@ void ElectronDownloadManagerDelegate::OnDownloadSaveDialogDone( if (!item) return; - bool canceled = true; - result.Get("canceled", &canceled); + const bool canceled = result.ValueOrDefault("canceled", true); base::FilePath path; diff --git a/shell/browser/net/electron_url_loader_factory.cc b/shell/browser/net/electron_url_loader_factory.cc index 847c858c990c0..fa7c4aa501c0d 100644 --- a/shell/browser/net/electron_url_loader_factory.cc +++ b/shell/browser/net/electron_url_loader_factory.cc @@ -124,8 +124,8 @@ network::mojom::URLResponseHeadPtr ToResponseHead( return head; } - int status_code = net::HTTP_OK; - dict.Get("statusCode", &status_code); + const int status_code = + dict.ValueOrDefault("statusCode", static_cast(net::HTTP_OK)); head->headers = base::MakeRefCounted( absl::StrFormat("HTTP/1.1 %d %s", status_code, net::GetHttpReasonPhrase( diff --git a/shell/browser/ui/cocoa/electron_touch_bar.mm b/shell/browser/ui/cocoa/electron_touch_bar.mm index 39f8a53cb8aa3..ee198098f3baf 100644 --- a/shell/browser/ui/cocoa/electron_touch_bar.mm +++ b/shell/browser/ui/cocoa/electron_touch_bar.mm @@ -398,8 +398,7 @@ - (void)updateButton:(NSCustomTouchBarItem*)item } } - bool enabled = true; - settings.Get("enabled", &enabled); + const bool enabled = settings.ValueOrDefault("enabled", true); [button setEnabled:enabled]; } @@ -501,16 +500,9 @@ - (void)updateSlider:(NSSliderTouchBarItem*)item settings.Get("label", &label); item.label = base::SysUTF8ToNSString(label); - int maxValue = 100; - int minValue = 0; - int value = 50; - settings.Get("minValue", &minValue); - settings.Get("maxValue", &maxValue); - settings.Get("value", &value); - - item.slider.minValue = minValue; - item.slider.maxValue = maxValue; - item.slider.doubleValue = value; + item.slider.minValue = settings.ValueOrDefault("minValue", 0); + item.slider.maxValue = settings.ValueOrDefault("maxValue", 100); + item.slider.doubleValue = settings.ValueOrDefault("value", 50); } - (NSTouchBarItem*)makePopoverForID:(NSString*)id @@ -540,9 +532,7 @@ - (void)updatePopover:(NSPopoverTouchBarItem*)item item.collapsedRepresentationImage = image.AsNSImage(); } - bool showCloseButton = true; - settings.Get("showCloseButton", &showCloseButton); - item.showsCloseButton = showCloseButton; + item.showsCloseButton = settings.ValueOrDefault("showCloseButton", true); v8::Isolate* isolate = electron::JavascriptEnvironment::GetIsolate(); v8::HandleScope handle_scope(isolate); @@ -670,8 +660,7 @@ - (void)updateSegmentedControl:(NSCustomTouchBarItem*)item for (size_t i = 0; i < segments.size(); ++i) { std::string label; gfx::Image image; - bool enabled = true; - segments[i].Get("enabled", &enabled); + const bool enabled = segments[i].ValueOrDefault("enabled", true); if (segments[i].Get("label", &label)) { [control setLabel:base::SysUTF8ToNSString(label) forSegment:i]; } else { @@ -686,8 +675,7 @@ - (void)updateSegmentedControl:(NSCustomTouchBarItem*)item [control setEnabled:enabled forSegment:i]; } - int selectedIndex = 0; - settings.Get("selectedIndex", &selectedIndex); + const int selectedIndex = settings.ValueOrDefault("selectedIndex", 0); if (selectedIndex >= 0 && selectedIndex < control.segmentCount) control.selectedSegment = selectedIndex; } @@ -726,8 +714,8 @@ - (void)updateScrubber:(NSCustomTouchBarItem*)item withSettings:(const gin_helper::PersistentDictionary&)settings { NSScrubber* scrubber = item.view; - bool showsArrowButtons = false; - settings.Get("showArrowButtons", &showsArrowButtons); + const bool showsArrowButtons = + settings.ValueOrDefault("showArrowButtons", false); // The scrubber will crash if the user tries to scroll // and there are no items. if ([self numberOfItemsForScrubber:scrubber] > 0) @@ -766,9 +754,7 @@ - (void)updateScrubber:(NSCustomTouchBarItem*)item scrubber.mode = NSScrubberModeFree; } - bool continuous = true; - settings.Get("continuous", &continuous); - scrubber.continuous = continuous; + scrubber.continuous = settings.ValueOrDefault("continuous", true); [scrubber reloadData]; } diff --git a/shell/common/api/electron_api_url_loader.cc b/shell/common/api/electron_api_url_loader.cc index 8ec31ae1a56f2..dcf539060c18b 100644 --- a/shell/common/api/electron_api_url_loader.cc +++ b/shell/common/api/electron_api_url_loader.cc @@ -609,9 +609,8 @@ gin::Handle SimpleURLLoaderWrapper::Create( } } - blink::mojom::FetchCacheMode cache_mode = - blink::mojom::FetchCacheMode::kDefault; - opts.Get("cache", &cache_mode); + const auto cache_mode = + opts.ValueOrDefault("cache", blink::mojom::FetchCacheMode::kDefault); switch (cache_mode) { case blink::mojom::FetchCacheMode::kNoStore: request->load_flags |= net::LOAD_DISABLE_CACHE; @@ -639,8 +638,8 @@ gin::Handle SimpleURLLoaderWrapper::Create( break; } - bool use_session_cookies = false; - opts.Get("useSessionCookies", &use_session_cookies); + const bool use_session_cookies = + opts.ValueOrDefault("useSessionCookies", false); int options = network::mojom::kURLLoadOptionSniffMimeType; if (!credentials_specified && !use_session_cookies) { // This is the default case, as well as the case when credentials is not @@ -650,9 +649,7 @@ gin::Handle SimpleURLLoaderWrapper::Create( options |= network::mojom::kURLLoadOptionBlockAllCookies; } - bool bypass_custom_protocol_handlers = false; - opts.Get("bypassCustomProtocolHandlers", &bypass_custom_protocol_handlers); - if (bypass_custom_protocol_handlers) + if (opts.ValueOrDefault("bypassCustomProtocolHandlers", false)) options |= kBypassCustomProtocolHandlers; v8::Local body; diff --git a/shell/common/gin_converters/blink_converter.cc b/shell/common/gin_converters/blink_converter.cc index f4f012d07fd24..f172c74cfd2e1 100644 --- a/shell/common/gin_converters/blink_converter.cc +++ b/shell/common/gin_converters/blink_converter.cc @@ -369,10 +369,8 @@ bool Converter::FromV8(v8::Isolate* isolate, if (!dict.Get("button", &out->button)) out->button = blink::WebMouseEvent::Button::kLeft; - float global_x = 0.f; - float global_y = 0.f; - dict.Get("globalX", &global_x); - dict.Get("globalY", &global_y); + const float global_x = dict.ValueOrDefault("globalX", 0.F); + const float global_y = dict.ValueOrDefault("globalY", 0.F); out->SetPositionInScreen(global_x, global_y); dict.Get("movementX", &out->movement_x); @@ -397,23 +395,19 @@ bool Converter::FromV8( dict.Get("accelerationRatioX", &out->acceleration_ratio_x); dict.Get("accelerationRatioY", &out->acceleration_ratio_y); - bool has_precise_scrolling_deltas = false; - dict.Get("hasPreciseScrollingDeltas", &has_precise_scrolling_deltas); - if (has_precise_scrolling_deltas) { - out->delta_units = ui::ScrollGranularity::kScrollByPrecisePixel; - } else { - out->delta_units = ui::ScrollGranularity::kScrollByPixel; - } + const bool precise = dict.ValueOrDefault("hasPreciseScrollingDeltas", false); + out->delta_units = precise ? ui::ScrollGranularity::kScrollByPrecisePixel + : ui::ScrollGranularity::kScrollByPixel; #if defined(USE_AURA) // Matches the behavior of ui/events/blink/web_input_event_traits.cc: - bool can_scroll = true; - if (dict.Get("canScroll", &can_scroll) && !can_scroll) { + if (!dict.ValueOrDefault("canScroll", true)) { out->delta_units = ui::ScrollGranularity::kScrollByPage; out->SetModifiers(out->GetModifiers() & ~blink::WebInputEvent::Modifiers::kControlKey); } #endif + return true; } diff --git a/shell/common/gin_helper/persistent_dictionary.h b/shell/common/gin_helper/persistent_dictionary.h index 7bb41835fd7b1..4020606d09dfd 100644 --- a/shell/common/gin_helper/persistent_dictionary.h +++ b/shell/common/gin_helper/persistent_dictionary.h @@ -41,6 +41,15 @@ class PersistentDictionary { gin::ConvertFromV8(isolate_, value, out); } + // Convenience function for using a default value if the + // specified key isn't present in the dictionary. + template + T ValueOrDefault(const std::string_view key, T default_value) const { + if (auto value = T{}; Get(key, &value)) + return value; + return default_value; + } + private: raw_ptr isolate_ = nullptr; v8::Global handle_; From 8f37d4224119749482c53fb9ac4d2a8a492b99ac Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 9 May 2025 09:38:19 +0200 Subject: [PATCH 033/186] build: move release script to new hasher function (#46993) build: move to new hasher function Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Keeley Hammond --- script/release/get-url-hash.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/script/release/get-url-hash.ts b/script/release/get-url-hash.ts index f144c2fa33df9..dc4bb77672a2a 100644 --- a/script/release/get-url-hash.ts +++ b/script/release/get-url-hash.ts @@ -2,12 +2,12 @@ import got from 'got'; import * as url from 'node:url'; -const HASHER_FUNCTION_HOST = 'electron-artifact-hasher.azurewebsites.net'; -const HASHER_FUNCTION_ROUTE = '/api/HashArtifact'; +const HASHER_FUNCTION_HOST = 'electron-hasher.azurewebsites.net'; +const HASHER_FUNCTION_ROUTE = '/api/hashRemoteAsset'; export async function getUrlHash (targetUrl: string, algorithm = 'sha256', attempts = 3) { const options = { - code: process.env.ELECTRON_ARTIFACT_HASHER_FUNCTION_KEY!, + code: process.env.ELECTRON_HASHER_FUNCTION_KEY!, targetUrl, algorithm }; From 0e9c0d8c04465b3d2b584c793a75b11f57378d53 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 9 May 2025 09:39:17 -0500 Subject: [PATCH 034/186] fix: use-after-move of bus connection in xdg portal detection (#47023) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: deepak1556 --- shell/browser/ui/file_dialog_linux_portal.cc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/shell/browser/ui/file_dialog_linux_portal.cc b/shell/browser/ui/file_dialog_linux_portal.cc index 298ee25caffb4..7dd520d92bdfa 100644 --- a/shell/browser/ui/file_dialog_linux_portal.cc +++ b/shell/browser/ui/file_dialog_linux_portal.cc @@ -86,8 +86,9 @@ void CheckPortalAvailabilityOnBusThread() { << (g_portal_available ? "yes" : "no"); flag->Set(); bus->ShutdownAndBlock(); + bus.reset(); }, - std::move(bus), flag)); + bus, flag)); } } // namespace From ace7ef4316ccbcb3d3499cfb9631c6897f411b9d Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 9 May 2025 13:10:44 -0400 Subject: [PATCH 035/186] fix: restore previous Windows screenshotting (#47033) Fixes https://github.com/electron/electron/issues/45990 We previously made a change in https://github.com/electron/electron/pull/45868 to fix content protection being lost on hide and re-show. However, this cause a breaking change where protected windows were made opaque black instead of being hidden as before. This overrides relevant methods in ElectronDesktopWindowTreeHostWin to restore the previous behavior. without regressing the original issue. Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .../ui/win/electron_desktop_window_tree_host_win.cc | 10 ++++++++++ .../ui/win/electron_desktop_window_tree_host_win.h | 2 ++ 2 files changed, 12 insertions(+) diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc index ee6509b9b79ce..3618bb840cb6d 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc @@ -126,6 +126,16 @@ bool ElectronDesktopWindowTreeHostWin::HandleMouseEvent(ui::MouseEvent* event) { return views::DesktopWindowTreeHostWin::HandleMouseEvent(event); } +void ElectronDesktopWindowTreeHostWin::HandleVisibilityChanged(bool visible) { + if (native_window_view_->widget()) + native_window_view_->widget()->OnNativeWidgetVisibilityChanged(visible); +} + +void ElectronDesktopWindowTreeHostWin::SetAllowScreenshots(bool allow) { + ::SetWindowDisplayAffinity(GetAcceleratedWidget(), + allow ? WDA_NONE : WDA_EXCLUDEFROMCAPTURE); +} + void ElectronDesktopWindowTreeHostWin::OnNativeThemeUpdated( ui::NativeTheme* observed_theme) { HWND hWnd = GetAcceleratedWidget(); diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.h b/shell/browser/ui/win/electron_desktop_window_tree_host_win.h index 940328fbd221e..acfbfda8be348 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.h +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.h @@ -41,6 +41,8 @@ class ElectronDesktopWindowTreeHostWin : public views::DesktopWindowTreeHostWin, int frame_thickness) const override; bool HandleMouseEventForCaption(UINT message) const override; bool HandleMouseEvent(ui::MouseEvent* event) override; + void HandleVisibilityChanged(bool visible) override; + void SetAllowScreenshots(bool allow) override; // ui::NativeThemeObserver: void OnNativeThemeUpdated(ui::NativeTheme* observed_theme) override; From 434f77e6c132fe27a24164dccec0447102487436 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 9 May 2025 17:46:11 -0500 Subject: [PATCH 036/186] docs: unify [!NOTE] structure (#47048) * docs: unify [!NOTE] structure Co-authored-by: Erick Zhao * Update docs/api/command-line.md Co-authored-by: Niklas Wenzel Co-authored-by: Erick Zhao * Update docs/api/browser-window.md Co-authored-by: Niklas Wenzel Co-authored-by: Erick Zhao * Update docs/api/download-item.md Co-authored-by: Niklas Wenzel Co-authored-by: Erick Zhao * Update docs/api/global-shortcut.md Co-authored-by: Niklas Wenzel Co-authored-by: Erick Zhao * revert line break Co-authored-by: Erick Zhao --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Erick Zhao Co-authored-by: Erick Zhao --- docs/api/app.md | 165 +++++++++++------- docs/api/auto-updater.md | 22 ++- docs/api/base-window.md | 69 +++++--- docs/api/browser-view.md | 7 +- docs/api/browser-window.md | 82 +++++---- docs/api/clipboard.md | 10 +- docs/api/command-line-switches.md | 6 +- docs/api/command-line.md | 18 +- docs/api/content-tracing.md | 5 +- docs/api/crash-reporter.md | 48 +++-- docs/api/desktop-capturer.md | 10 +- docs/api/dialog.md | 41 +++-- docs/api/dock.md | 3 +- docs/api/download-item.md | 15 +- docs/api/extensions-api.md | 25 +-- docs/api/extensions.md | 9 +- docs/api/global-shortcut.md | 14 +- docs/api/ipc-renderer.md | 7 +- docs/api/menu-item.md | 9 +- docs/api/menu.md | 17 +- docs/api/native-image.md | 3 +- docs/api/net-log.md | 5 +- docs/api/net.md | 5 +- docs/api/power-save-blocker.md | 9 +- docs/api/process.md | 3 +- docs/api/protocol.md | 10 +- docs/api/screen.md | 8 +- docs/api/session.md | 54 +++--- docs/api/shell.md | 3 +- docs/api/structures/jump-list-category.md | 16 +- docs/api/structures/point.md | 7 +- docs/api/touch-bar-other-items-proxy.md | 5 +- docs/api/touch-bar.md | 14 +- docs/api/tray.md | 3 +- docs/api/utility-process.md | 6 +- docs/api/view.md | 6 +- docs/api/web-contents.md | 22 ++- docs/api/web-frame.md | 13 +- docs/api/webview-tag.md | 12 +- docs/development/build-instructions-gn.md | 3 +- .../development/build-instructions-windows.md | 5 +- docs/development/creating-api.md | 3 +- docs/development/patches.md | 3 +- docs/tutorial/keyboard-shortcuts.md | 7 +- docs/tutorial/multithreading.md | 3 +- docs/tutorial/online-offline-events.md | 3 +- docs/tutorial/process-model.md | 3 +- docs/tutorial/repl.md | 5 +- docs/tutorial/web-embeds.md | 12 +- 49 files changed, 509 insertions(+), 324 deletions(-) diff --git a/docs/api/app.md b/docs/api/app.md index 281f606f64ecf..119c867abef9b 100644 --- a/docs/api/app.md +++ b/docs/api/app.md @@ -41,9 +41,10 @@ that was used to open the application, if it was launched from Notification Cent You can also call `app.isReady()` to check if this event has already fired and `app.whenReady()` to get a Promise that is fulfilled when Electron is initialized. -**Note**: The `ready` event is only fired after the main process has finished running the first -tick of the event loop. If an Electron API needs to be called before the `ready` event, ensure -that it is called synchronously in the top-level context of the main process. +> [!NOTE] +> The `ready` event is only fired after the main process has finished running the first +> tick of the event loop. If an Electron API needs to be called before the `ready` event, ensure +> that it is called synchronously in the top-level context of the main process. ### Event: 'window-all-closed' @@ -66,12 +67,14 @@ Emitted before the application starts closing its windows. Calling `event.preventDefault()` will prevent the default behavior, which is terminating the application. -**Note:** If application quit was initiated by `autoUpdater.quitAndInstall()`, -then `before-quit` is emitted _after_ emitting `close` event on all windows and -closing them. +> [!NOTE] +> If application quit was initiated by `autoUpdater.quitAndInstall()`, +> then `before-quit` is emitted _after_ emitting `close` event on all windows and +> closing them. -**Note:** On Windows, this event will not be emitted if the app is closed due -to a shutdown/restart of the system or a user logout. +> [!NOTE] +> On Windows, this event will not be emitted if the app is closed due +> to a shutdown/restart of the system or a user logout. ### Event: 'will-quit' @@ -86,8 +89,9 @@ terminating the application. See the description of the `window-all-closed` event for the differences between the `will-quit` and `window-all-closed` events. -**Note:** On Windows, this event will not be emitted if the app is closed due -to a shutdown/restart of the system or a user logout. +> [!NOTE] +> On Windows, this event will not be emitted if the app is closed due +> to a shutdown/restart of the system or a user logout. ### Event: 'quit' @@ -98,8 +102,9 @@ Returns: Emitted when the application is quitting. -**Note:** On Windows, this event will not be emitted if the app is closed due -to a shutdown/restart of the system or a user logout. +> [!NOTE] +> On Windows, this event will not be emitted if the app is closed due +> to a shutdown/restart of the system or a user logout. ### Event: 'open-file' _macOS_ @@ -470,24 +475,28 @@ and `workingDirectory` is its current working directory. Usually applications respond to this by making their primary window focused and non-minimized. -**Note:** `argv` will not be exactly the same list of arguments as those passed -to the second instance. The order might change and additional arguments might be appended. -If you need to maintain the exact same arguments, it's advised to use `additionalData` instead. +> [!NOTE] +> `argv` will not be exactly the same list of arguments as those passed +> to the second instance. The order might change and additional arguments might be appended. +> If you need to maintain the exact same arguments, it's advised to use `additionalData` instead. -**Note:** If the second instance is started by a different user than the first, the `argv` array will not include the arguments. +> [!NOTE] +> If the second instance is started by a different user than the first, the `argv` array will not include the arguments. This event is guaranteed to be emitted after the `ready` event of `app` gets emitted. -**Note:** Extra command line arguments might be added by Chromium, -such as `--original-process-start-time`. +> [!NOTE] +> Extra command line arguments might be added by Chromium, +> such as `--original-process-start-time`. ## Methods The `app` object has the following methods: -**Note:** Some methods are only available on specific operating systems and are -labeled as such. +> [!NOTE] +> Some methods are only available on specific operating systems and are +> labeled as such. ### `app.quit()` @@ -679,7 +688,8 @@ preferred over `name` by Electron. Overrides the current application's name. -**Note:** This function overrides the name used internally by Electron; it does not affect the name that the OS uses. +> [!NOTE] +> This function overrides the name used internally by Electron; it does not affect the name that the OS uses. ### `app.getLocale()` @@ -688,18 +698,22 @@ Possible return values are documented [here](https://source.chromium.org/chromiu To set the locale, you'll want to use a command line switch at app startup, which may be found [here](command-line-switches.md). -**Note:** When distributing your packaged app, you have to also ship the -`locales` folder. +> [!NOTE] +> When distributing your packaged app, you have to also ship the +> `locales` folder. -**Note:** This API must be called after the `ready` event is emitted. +> [!NOTE] +> This API must be called after the `ready` event is emitted. -**Note:** To see example return values of this API compared to other locale and language APIs, see [`app.getPreferredSystemLanguages()`](#appgetpreferredsystemlanguages). +> [!NOTE] +> To see example return values of this API compared to other locale and language APIs, see [`app.getPreferredSystemLanguages()`](#appgetpreferredsystemlanguages). ### `app.getLocaleCountryCode()` Returns `string` - User operating system's locale two-letter [ISO 3166](https://www.iso.org/iso-3166-country-codes.html) country code. The value is taken from native OS APIs. -**Note:** When unable to detect locale country code, it returns empty string. +> [!NOTE] +> When unable to detect locale country code, it returns empty string. ### `app.getSystemLocale()` @@ -712,9 +726,11 @@ Different operating systems also use the regional data differently: Therefore, this API can be used for purposes such as choosing a format for rendering dates and times in a calendar app, especially when the developer wants the format to be consistent with the OS. -**Note:** This API must be called after the `ready` event is emitted. +> [!NOTE] +> This API must be called after the `ready` event is emitted. -**Note:** To see example return values of this API compared to other locale and language APIs, see [`app.getPreferredSystemLanguages()`](#appgetpreferredsystemlanguages). +> [!NOTE] +> To see example return values of this API compared to other locale and language APIs, see [`app.getPreferredSystemLanguages()`](#appgetpreferredsystemlanguages). ### `app.getPreferredSystemLanguages()` @@ -777,16 +793,18 @@ Once registered, all links with `your-protocol://` will be opened with the current executable. The whole link, including protocol, will be passed to your application as a parameter. -**Note:** On macOS, you can only register protocols that have been added to -your app's `info.plist`, which cannot be modified at runtime. However, you can -change the file during build time via [Electron Forge][electron-forge], -[Electron Packager][electron-packager], or by editing `info.plist` with a text -editor. Please refer to [Apple's documentation][CFBundleURLTypes] for details. +> [!NOTE] +> On macOS, you can only register protocols that have been added to +> your app's `info.plist`, which cannot be modified at runtime. However, you can +> change the file during build time via [Electron Forge][electron-forge], +> [Electron Packager][electron-packager], or by editing `info.plist` with a text +> editor. Please refer to [Apple's documentation][CFBundleURLTypes] for details. -**Note:** In a Windows Store environment (when packaged as an `appx`) this API -will return `true` for all calls but the registry key it sets won't be accessible -by other applications. In order to register your Windows Store application -as a default protocol handler you must [declare the protocol in your manifest](https://learn.microsoft.com/en-us/uwp/schemas/appxpackage/uapmanifestschema/element-uap-protocol). +> [!NOTE] +> In a Windows Store environment (when packaged as an `appx`) this API +> will return `true` for all calls but the registry key it sets won't be accessible +> by other applications. In order to register your Windows Store application +> as a default protocol handler you must [declare the protocol in your manifest](https://learn.microsoft.com/en-us/uwp/schemas/appxpackage/uapmanifestschema/element-uap-protocol). The API uses the Windows Registry and `LSSetDefaultHandlerForURLScheme` internally. @@ -810,11 +828,12 @@ protocol (aka URI scheme). If so, it will remove the app as the default handler. Returns `boolean` - Whether the current executable is the default handler for a protocol (aka URI scheme). -**Note:** On macOS, you can use this method to check if the app has been -registered as the default protocol handler for a protocol. You can also verify -this by checking `~/Library/Preferences/com.apple.LaunchServices.plist` on the -macOS machine. Please refer to -[Apple's documentation][LSCopyDefaultHandlerForURLScheme] for details. +> [!NOTE] +> On macOS, you can use this method to check if the app has been +> registered as the default protocol handler for a protocol. You can also verify +> this by checking `~/Library/Preferences/com.apple.LaunchServices.plist` on the +> macOS machine. Please refer to +> [Apple's documentation][LSCopyDefaultHandlerForURLScheme] for details. The API uses the Windows Registry and `LSCopyDefaultHandlerForURLScheme` internally. @@ -858,8 +877,9 @@ Adds `tasks` to the [Tasks][tasks] category of the Jump List on Windows. Returns `boolean` - Whether the call succeeded. -**Note:** If you'd like to customize the Jump List even more use -`app.setJumpList(categories)` instead. +> [!NOTE] +> If you'd like to customize the Jump List even more use +> `app.setJumpList(categories)` instead. ### `app.getJumpListSettings()` _Windows_ @@ -897,21 +917,24 @@ following strings: If `categories` is `null` the previously set custom Jump List (if any) will be replaced by the standard Jump List for the app (managed by Windows). -**Note:** If a `JumpListCategory` object has neither the `type` nor the `name` -property set then its `type` is assumed to be `tasks`. If the `name` property +> [!NOTE] +> If a `JumpListCategory` object has neither the `type` nor the `name` +> property set then its `type` is assumed to be `tasks`. If the `name` property is set but the `type` property is omitted then the `type` is assumed to be `custom`. -**Note:** Users can remove items from custom categories, and Windows will not -allow a removed item to be added back into a custom category until **after** -the next successful call to `app.setJumpList(categories)`. Any attempt to -re-add a removed item to a custom category earlier than that will result in the -entire custom category being omitted from the Jump List. The list of removed -items can be obtained using `app.getJumpListSettings()`. +> [!NOTE] +> Users can remove items from custom categories, and Windows will not +> allow a removed item to be added back into a custom category until **after** +> the next successful call to `app.setJumpList(categories)`. Any attempt to +> re-add a removed item to a custom category earlier than that will result in the +> entire custom category being omitted from the Jump List. The list of removed +> items can be obtained using `app.getJumpListSettings()`. -**Note:** The maximum length of a Jump List item's `description` property is -260 characters. Beyond this limit, the item will not be added to the Jump -List, nor will it be displayed. +> [!NOTE] +> The maximum length of a Jump List item's `description` property is +> 260 characters. Beyond this limit, the item will not be added to the Jump +> List, nor will it be displayed. Here's a very simple example of creating a custom Jump List: @@ -1188,7 +1211,8 @@ Returns [`ProcessMetric[]`](structures/process-metric.md): Array of `ProcessMetr Returns [`GPUFeatureStatus`](structures/gpu-feature-status.md) - The Graphics Feature Status from `chrome://gpu/`. -**Note:** This information is only usable after the `gpu-info-update` event is emitted. +> [!NOTE] +> This information is only usable after the `gpu-info-update` event is emitted. ### `app.getGPUInfo(infoType)` @@ -1242,11 +1266,13 @@ badge. On macOS, it shows on the dock icon. On Linux, it only works for Unity launcher. -**Note:** Unity launcher requires a `.desktop` file to work. For more information, -please read the [Unity integration documentation][unity-requirement]. +> [!NOTE] +> Unity launcher requires a `.desktop` file to work. For more information, +> please read the [Unity integration documentation][unity-requirement]. -**Note:** On macOS, you need to ensure that your application has the permission -to display notifications for this method to work. +> [!NOTE] +> On macOS, you need to ensure that your application has the permission +> to display notifications for this method to work. ### `app.getBadgeCount()` _Linux_ _macOS_ @@ -1348,7 +1374,8 @@ details. Disabled by default. This API must be called after the `ready` event is emitted. -**Note:** Rendering accessibility tree can significantly affect the performance of your app. It should not be enabled by default. +> [!NOTE] +> Rendering accessibility tree can significantly affect the performance of your app. It should not be enabled by default. ### `app.showAboutPanel()` @@ -1476,7 +1503,8 @@ By using this API, important information such as password and other sensitive in See [Apple's documentation](https://developer.apple.com/library/archive/technotes/tn2150/_index.html) for more details. -**Note:** Enable `Secure Keyboard Entry` only when it is needed and disable it when it is no longer needed. +> [!NOTE] +> Enable `Secure Keyboard Entry` only when it is needed and disable it when it is no longer needed. ### `app.setProxy(config)` @@ -1538,7 +1566,8 @@ See [Chromium's accessibility docs](https://www.chromium.org/developers/design-d This API must be called after the `ready` event is emitted. -**Note:** Rendering accessibility tree can significantly affect the performance of your app. It should not be enabled by default. +> [!NOTE] +> Rendering accessibility tree can significantly affect the performance of your app. It should not be enabled by default. ### `app.applicationMenu` @@ -1551,11 +1580,13 @@ An `Integer` property that returns the badge count for current app. Setting the On macOS, setting this with any nonzero integer shows on the dock icon. On Linux, this property only works for Unity launcher. -**Note:** Unity launcher requires a `.desktop` file to work. For more information, -please read the [Unity integration documentation][unity-requirement]. +> [!NOTE] +> Unity launcher requires a `.desktop` file to work. For more information, +> please read the [Unity integration documentation][unity-requirement]. -**Note:** On macOS, you need to ensure that your application has the permission -to display notifications for this property to take effect. +> [!NOTE] +> On macOS, you need to ensure that your application has the permission +> to display notifications for this property to take effect. ### `app.commandLine` _Readonly_ diff --git a/docs/api/auto-updater.md b/docs/api/auto-updater.md index bf419f33ad70a..f2e4a37945037 100644 --- a/docs/api/auto-updater.md +++ b/docs/api/auto-updater.md @@ -26,8 +26,9 @@ requirements, you can read [Server Support][server-support]. Note that update process. Apps that need to disable ATS can add the `NSAllowsArbitraryLoads` key to their app's plist. -**Note:** Your application must be signed for automatic updates on macOS. -This is a requirement of `Squirrel.Mac`. +> [!IMPORTANT] +> Your application must be signed for automatic updates on macOS. +> This is a requirement of `Squirrel.Mac`. ### Windows @@ -93,8 +94,9 @@ Emitted when an update has been downloaded. On Windows only `releaseName` is available. -**Note:** It is not strictly necessary to handle this event. A successfully -downloaded update will still be applied the next time the application starts. +> [!NOTE] +> It is not strictly necessary to handle this event. A successfully +> downloaded update will still be applied the next time the application starts. ### Event: 'before-quit-for-update' @@ -125,8 +127,9 @@ Returns `string` - The current update feed URL. Asks the server whether there is an update. You must call `setFeedURL` before using this API. -**Note:** If an update is available it will be downloaded automatically. -Calling `autoUpdater.checkForUpdates()` twice will download the update two times. +> [!NOTE] +> If an update is available it will be downloaded automatically. +> Calling `autoUpdater.checkForUpdates()` twice will download the update two times. ### `autoUpdater.quitAndInstall()` @@ -137,9 +140,10 @@ Under the hood calling `autoUpdater.quitAndInstall()` will close all application windows first, and automatically call `app.quit()` after all windows have been closed. -**Note:** It is not strictly necessary to call this function to apply an update, -as a successfully downloaded update will always be applied the next time the -application starts. +> [!NOTE] +> It is not strictly necessary to call this function to apply an update, +> as a successfully downloaded update will always be applied the next time the +> application starts. [squirrel-mac]: https://github.com/Squirrel/Squirrel.Mac [server-support]: https://github.com/Squirrel/Squirrel.Mac#server-support diff --git a/docs/api/base-window.md b/docs/api/base-window.md index c988ddb4b426d..52e6deb288f8c 100644 --- a/docs/api/base-window.md +++ b/docs/api/base-window.md @@ -4,7 +4,7 @@ Process: [Main](../glossary.md#main-process) -> **Note** +> [!NOTE] > `BaseWindow` provides a flexible way to compose multiple web views in a > single window. For windows with only a single, full-size web view, the > [`BrowserWindow`](browser-window.md) class may be a simpler option. @@ -107,8 +107,9 @@ It creates a new `BaseWindow` with native properties as set by the `options`. Objects created with `new BaseWindow` emit the following events: -**Note:** Some events are only available on specific operating systems and are -labeled as such. +> [!NOTE] +> Some events are only available on specific operating systems and are +> labeled as such. #### Event: 'close' @@ -137,7 +138,11 @@ window.onbeforeunload = (e) => { } ``` -_**Note**: There is a subtle difference between the behaviors of `window.onbeforeunload = handler` and `window.addEventListener('beforeunload', handler)`. It is recommended to always set the `event.returnValue` explicitly, instead of only returning a value, as the former works more consistently within Electron._ +> [!NOTE] +> There is a subtle difference between the behaviors of `window.onbeforeunload = handler` and +> `window.addEventListener('beforeunload', handler)`. It is recommended to always set the +> `event.returnValue` explicitly, instead of only returning a value, as the former works more +> consistently within Electron. #### Event: 'closed' @@ -252,7 +257,8 @@ Emitted when the window is being moved to a new position. Emitted once when the window is moved to a new position. -**Note**: On macOS this event is an alias of `move`. +> [!NOTE] +> On macOS, this event is an alias of `move`. #### Event: 'enter-full-screen' @@ -421,7 +427,8 @@ A `boolean` property that determines whether the window is focusable. A `boolean` property that determines whether the window is visible on all workspaces. -**Note:** Always returns false on Windows. +> [!NOTE] +> Always returns false on Windows. #### `win.shadow` @@ -431,7 +438,8 @@ A `boolean` property that determines whether the window has a shadow. A `boolean` property that determines whether the menu bar should be visible. -**Note:** If the menu bar is auto-hide, users can still bring up the menu bar by pressing the single `Alt` key. +> [!NOTE] +> If the menu bar is auto-hide, users can still bring up the menu bar by pressing the single `Alt` key. #### `win.kiosk` @@ -452,7 +460,8 @@ and the icon of the file will show in window's title bar. A `string` property that determines the title of the native window. -**Note:** The title of the web page can be different from the title of the native window. +> [!NOTE] +> The title of the web page can be different from the title of the native window. #### `win.minimizable` _macOS_ _Windows_ @@ -521,8 +530,9 @@ A `boolean` property that indicates whether the window is arranged via [Snap.](h Objects created with `new BaseWindow` have the following instance methods: -**Note:** Some methods are only available on specific operating systems and are -labeled as such. +> [!NOTE] +> Some methods are only available on specific operating systems and are +> labeled as such. #### `win.setContentView(view)` @@ -614,7 +624,8 @@ Returns `boolean` - Whether the window is minimized. Sets whether the window should be in fullscreen mode. -**Note:** On macOS, fullscreen transitions take place asynchronously. If further actions depend on the fullscreen state, use the ['enter-full-screen'](base-window.md#event-enter-full-screen) or ['leave-full-screen'](base-window.md#event-leave-full-screen) events. +> [!NOTE] +> On macOS, fullscreen transitions take place asynchronously. If further actions depend on the fullscreen state, use the ['enter-full-screen'](base-window.md#event-enter-full-screen) or > ['leave-full-screen'](base-window.md#event-leave-full-screen) events. #### `win.isFullScreen()` @@ -728,13 +739,15 @@ win.setBounds({ width: 100 }) console.log(win.getBounds()) ``` -**Note:** On macOS, the y-coordinate value cannot be smaller than the [Tray](tray.md) height. The tray height has changed over time and depends on the operating system, but is between 20-40px. Passing a value lower than the tray height will result in a window that is flush to the tray. +> [!NOTE] +> On macOS, the y-coordinate value cannot be smaller than the [Tray](tray.md) height. The tray height has changed over time and depends on the operating system, but is between 20-40px. Passing a value lower than the tray height will result in a window that is flush to the tray. #### `win.getBounds()` Returns [`Rectangle`](structures/rectangle.md) - The `bounds` of the window as `Object`. -**Note:** On macOS, the y-coordinate value returned will be at minimum the [Tray](tray.md) height. For example, calling `win.setBounds({ x: 25, y: 20, width: 800, height: 600 })` with a tray height of 38 means that `win.getBounds()` will return `{ x: 25, y: 38, width: 800, height: 600 }`. +> [!NOTE] +> On macOS, the y-coordinate value returned will be at minimum the [Tray](tray.md) height. For example, calling `win.setBounds({ x: 25, y: 20, width: 800, height: 600 })` with a tray height of 38 means that `win.getBounds()` will return `{ x: 25, y: 38, width: 800, height: 600 }`. #### `win.getBackgroundColor()` @@ -742,7 +755,8 @@ Returns `string` - Gets the background color of the window in Hex (`#RRGGBB`) fo See [Setting `backgroundColor`](browser-window.md#setting-the-backgroundcolor-property). -**Note:** The alpha value is _not_ returned alongside the red, green, and blue values. +> [!NOTE] +> The alpha value is _not_ returned alongside the red, green, and blue values. #### `win.setContentBounds(bounds[, animate])` @@ -760,7 +774,8 @@ Returns [`Rectangle`](structures/rectangle.md) - The `bounds` of the window's cl Returns [`Rectangle`](structures/rectangle.md) - Contains the window bounds of the normal state -**Note:** whatever the current state of the window : maximized, minimized or in fullscreen, this function always returns the position and size of the window in normal state. In normal state, getBounds and getNormalBounds returns the same [`Rectangle`](structures/rectangle.md). +> [!NOTE] +> Whatever the current state of the window : maximized, minimized or in fullscreen, this function always returns the position and size of the window in normal state. In normal state, getBounds and getNormalBounds returns the same [`Rectangle`](structures/rectangle.md). #### `win.setEnabled(enable)` @@ -957,8 +972,9 @@ Changes the title of native window to `title`. Returns `string` - The title of the native window. -**Note:** The title of the web page can be different from the title of the native -window. +> [!NOTE] +> The title of the web page can be different from the title of the native +> window. #### `win.setSheetOffset(offsetY[, offsetX])` _macOS_ @@ -1232,8 +1248,9 @@ in the taskbar. Sets the properties for the window's taskbar button. -**Note:** `relaunchCommand` and `relaunchDisplayName` must always be set -together. If one of those properties is not set, then neither will be used. +> [!NOTE] +> `relaunchCommand` and `relaunchDisplayName` must always be set +> together. If one of those properties is not set, then neither will be used. #### `win.setIcon(icon)` _Windows_ _Linux_ @@ -1293,13 +1310,15 @@ maximize button, or by dragging it to the edges of the screen. Sets whether the window should be visible on all workspaces. -**Note:** This API does nothing on Windows. +> [!NOTE] +> This API does nothing on Windows. #### `win.isVisibleOnAllWorkspaces()` _macOS_ _Linux_ Returns `boolean` - Whether the window is visible on all workspaces. -**Note:** This API always returns false on Windows. +> [!NOTE] +> This API always returns false on Windows. #### `win.setIgnoreMouseEvents(ignore[, options])` @@ -1416,7 +1435,8 @@ This method sets the browser window's system-drawn background material, includin See the [Windows documentation](https://learn.microsoft.com/en-us/windows/win32/api/dwmapi/ne-dwmapi-dwm_systembackdrop_type) for more details. -**Note:** This method is only supported on Windows 11 22H2 and up. +> [!NOTE] +> This method is only supported on Windows 11 22H2 and up. #### `win.setWindowButtonPosition(position)` _macOS_ @@ -1438,8 +1458,9 @@ Sets the touchBar layout for the current window. Specifying `null` or `undefined` clears the touch bar. This method only has an effect if the machine has a touch bar. -**Note:** The TouchBar API is currently experimental and may change or be -removed in future Electron releases. +> [!NOTE] +> The TouchBar API is currently experimental and may change or be +> removed in future Electron releases. #### `win.setTitleBarOverlay(options)` _Windows_ _Linux_ diff --git a/docs/api/browser-view.md b/docs/api/browser-view.md index f3873c538a69b..693363ec4b2eb 100644 --- a/docs/api/browser-view.md +++ b/docs/api/browser-view.md @@ -8,7 +8,7 @@ deprecated: ``` --> -> **Note** +> [!NOTE] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -29,7 +29,7 @@ deprecated: > Create and control views. -> **Note** +> [!NOTE] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -176,4 +176,5 @@ Examples of valid `color` values: * Similar to CSS Color Module Level 3 keywords, but case-sensitive. * e.g. `blueviolet` or `red` -**Note:** Hex format with alpha takes `AARRGGBB` or `ARGB`, _not_ `RRGGBBAA` or `RGB`. +> [!NOTE] +> Hex format with alpha takes `AARRGGBB` or `ARGB`, _not_ `RRGGBBAA` or `RGB`. diff --git a/docs/api/browser-window.md b/docs/api/browser-window.md index aba24068dadf5..e61faa458fe26 100644 --- a/docs/api/browser-window.md +++ b/docs/api/browser-window.md @@ -158,7 +158,8 @@ It creates a new `BrowserWindow` with native properties as set by the `options`. Objects created with `new BrowserWindow` emit the following events: -**Note:** Some events are only available on specific operating systems and are +> [!NOTE] +> Some events are only available on specific operating systems and are labeled as such. #### Event: 'page-title-updated' @@ -200,7 +201,11 @@ window.onbeforeunload = (e) => { } ``` -_**Note**: There is a subtle difference between the behaviors of `window.onbeforeunload = handler` and `window.addEventListener('beforeunload', handler)`. It is recommended to always set the `event.returnValue` explicitly, instead of only returning a value, as the former works more consistently within Electron._ +> [!NOTE] +> There is a subtle difference between the behaviors of `window.onbeforeunload = handler` and +> `window.addEventListener('beforeunload', handler)`. It is recommended to always set the +> `event.returnValue` explicitly, instead of only returning a value, as the former works more +> consistently within Electron. #### Event: 'closed' @@ -323,7 +328,8 @@ Emitted when the window is being moved to a new position. Emitted once when the window is moved to a new position. -**Note**: On macOS this event is an alias of `move`. +> [!NOTE] +> On macOS, this event is an alias of `move`. #### Event: 'enter-full-screen' @@ -460,7 +466,7 @@ or `null` if the contents are not owned by a window. * `browserView` [BrowserView](browser-view.md) -> **Note** +> [!NOTE] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -522,7 +528,8 @@ A `boolean` property that determines whether the window is focusable. A `boolean` property that determines whether the window is visible on all workspaces. -**Note:** Always returns false on Windows. +> [!NOTE] +> Always returns false on Windows. #### `win.shadow` @@ -532,7 +539,8 @@ A `boolean` property that determines whether the window has a shadow. A `boolean` property that determines whether the menu bar should be visible. -**Note:** If the menu bar is auto-hide, users can still bring up the menu bar by pressing the single `Alt` key. +> [!NOTE] +> If the menu bar is auto-hide, users can still bring up the menu bar by pressing the single `Alt` key. #### `win.kiosk` @@ -553,7 +561,8 @@ and the icon of the file will show in window's title bar. A `string` property that determines the title of the native window. -**Note:** The title of the web page can be different from the title of the native window. +> [!NOTE] +> The title of the web page can be different from the title of the native window. #### `win.minimizable` _macOS_ _Windows_ @@ -621,8 +630,9 @@ A `boolean` property that indicates whether the window is arranged via [Snap.](h Objects created with `new BrowserWindow` have the following instance methods: -**Note:** Some methods are only available on specific operating systems and are -labeled as such. +> [!NOTE] +> Some methods are only available on specific operating systems and are +> labeled as such. #### `win.destroy()` @@ -704,13 +714,15 @@ Returns `boolean` - Whether the window is minimized. Sets whether the window should be in fullscreen mode. -**Note:** On macOS, fullscreen transitions take place asynchronously. If further actions depend on the fullscreen state, use the ['enter-full-screen'](browser-window.md#event-enter-full-screen) or ['leave-full-screen'](browser-window.md#event-leave-full-screen) events. +> [!NOTE] +> On macOS, fullscreen transitions take place asynchronously. If further actions depend on the fullscreen state, use the ['enter-full-screen'](browser-window.md#event-enter-full-screen) or ['leave-full-screen'](browser-window.md#event-leave-full-screen) events. #### `win.isFullScreen()` Returns `boolean` - Whether the window is in fullscreen mode. -**Note:** On macOS, fullscreen transitions take place asynchronously. When querying for a BrowserWindow's fullscreen status, you should ensure that either the ['enter-full-screen'](browser-window.md#event-enter-full-screen) or ['leave-full-screen'](browser-window.md#event-leave-full-screen) events have been emitted. +> [!NOTE] +> On macOS, fullscreen transitions take place asynchronously. When querying for a BrowserWindow's fullscreen status, you should ensure that either the ['enter-full-screen'](browser-window.md#event-enter-full-screen) or ['leave-full-screen'](browser-window.md#event-leave-full-screen) events have been emitted. #### `win.setSimpleFullScreen(flag)` _macOS_ @@ -820,13 +832,15 @@ win.setBounds({ width: 100 }) console.log(win.getBounds()) ``` -**Note:** On macOS, the y-coordinate value cannot be smaller than the [Tray](tray.md) height. The tray height has changed over time and depends on the operating system, but is between 20-40px. Passing a value lower than the tray height will result in a window that is flush to the tray. +> [!NOTE] +> On macOS, the y-coordinate value cannot be smaller than the [Tray](tray.md) height. The tray height has changed over time and depends on the operating system, but is between 20-40px. Passing a value lower than the tray height will result in a window that is flush to the tray. #### `win.getBounds()` Returns [`Rectangle`](structures/rectangle.md) - The `bounds` of the window as `Object`. -**Note:** On macOS, the y-coordinate value returned will be at minimum the [Tray](tray.md) height. For example, calling `win.setBounds({ x: 25, y: 20, width: 800, height: 600 })` with a tray height of 38 means that `win.getBounds()` will return `{ x: 25, y: 38, width: 800, height: 600 }`. +> [!NOTE] +> On macOS, the y-coordinate value returned will be at minimum the [Tray](tray.md) height. For example, calling `win.setBounds({ x: 25, y: 20, width: 800, height: 600 })` with a tray height of 38 means that `win.getBounds()` will return `{ x: 25, y: 38, width: 800, height: 600 }`. #### `win.getBackgroundColor()` @@ -834,7 +848,8 @@ Returns `string` - Gets the background color of the window in Hex (`#RRGGBB`) fo See [Setting `backgroundColor`](#setting-the-backgroundcolor-property). -**Note:** The alpha value is _not_ returned alongside the red, green, and blue values. +> [!NOTE] +> The alpha value is _not_ returned alongside the red, green, and blue values. #### `win.setContentBounds(bounds[, animate])` @@ -852,7 +867,8 @@ Returns [`Rectangle`](structures/rectangle.md) - The `bounds` of the window's cl Returns [`Rectangle`](structures/rectangle.md) - Contains the window bounds of the normal state -**Note:** whatever the current state of the window : maximized, minimized or in fullscreen, this function always returns the position and size of the window in normal state. In normal state, getBounds and getNormalBounds returns the same [`Rectangle`](structures/rectangle.md). +> [!NOTE] +> Whatever the current state of the window (maximized, minimized or in fullscreen), this function always returns the position and size of the window in normal state. In normal state, `getBounds` and `getNormalBounds` return the same [`Rectangle`](structures/rectangle.md). #### `win.setEnabled(enable)` @@ -1049,8 +1065,9 @@ Changes the title of native window to `title`. Returns `string` - The title of the native window. -**Note:** The title of the web page can be different from the title of the native -window. +> [!NOTE] +> The title of the web page can be different from the title of the native +> window. #### `win.setSheetOffset(offsetY[, offsetX])` _macOS_ @@ -1409,8 +1426,9 @@ in the taskbar. Sets the properties for the window's taskbar button. -**Note:** `relaunchCommand` and `relaunchDisplayName` must always be set -together. If one of those properties is not set, then neither will be used. +> [!NOTE] +> `relaunchCommand` and `relaunchDisplayName` must always be set +> together. If one of those properties is not set, then neither will be used. #### `win.showDefinitionForSelection()` _macOS_ @@ -1474,13 +1492,15 @@ maximize button, or by dragging it to the edges of the screen. Sets whether the window should be visible on all workspaces. -**Note:** This API does nothing on Windows. +> [!NOTE] +> This API does nothing on Windows. #### `win.isVisibleOnAllWorkspaces()` _macOS_ _Linux_ Returns `boolean` - Whether the window is visible on all workspaces. -**Note:** This API always returns false on Windows. +> [!NOTE] +> This API always returns false on Windows. #### `win.setIgnoreMouseEvents(ignore[, options])` @@ -1601,7 +1621,8 @@ This method sets the browser window's system-drawn background material, includin See the [Windows documentation](https://learn.microsoft.com/en-us/windows/win32/api/dwmapi/ne-dwmapi-dwm_systembackdrop_type) for more details. -**Note:** This method is only supported on Windows 11 22H2 and up. +> [!NOTE] +> This method is only supported on Windows 11 22H2 and up. #### `win.setWindowButtonPosition(position)` _macOS_ @@ -1623,8 +1644,9 @@ Sets the touchBar layout for the current window. Specifying `null` or `undefined` clears the touch bar. This method only has an effect if the machine has a touch bar. -**Note:** The TouchBar API is currently experimental and may change or be -removed in future Electron releases. +> [!NOTE] +> The TouchBar API is currently experimental and may change or be +> removed in future Electron releases. #### `win.setBrowserView(browserView)` _Experimental_ _Deprecated_ @@ -1632,7 +1654,7 @@ removed in future Electron releases. If there are other `BrowserView`s attached, they will be removed from this window. -> **Note** +> [!WARNING] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -1641,7 +1663,7 @@ this window. Returns `BrowserView | null` - The `BrowserView` attached to `win`. Returns `null` if one is not attached. Throws an error if multiple `BrowserView`s are attached. -> **Note** +> [!WARNING] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -1651,7 +1673,7 @@ if one is not attached. Throws an error if multiple `BrowserView`s are attached. Replacement API for setBrowserView supporting work with multi browser views. -> **Note** +> [!WARNING] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -1659,7 +1681,7 @@ Replacement API for setBrowserView supporting work with multi browser views. * `browserView` [BrowserView](browser-view.md) -> **Note** +> [!WARNING] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -1670,7 +1692,7 @@ Replacement API for setBrowserView supporting work with multi browser views. Raises `browserView` above other `BrowserView`s attached to `win`. Throws an error if `browserView` is not attached to `win`. -> **Note** +> [!WARNING] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. @@ -1679,7 +1701,7 @@ Throws an error if `browserView` is not attached to `win`. Returns `BrowserView[]` - a sorted by z-index array of all BrowserViews that have been attached with `addBrowserView` or `setBrowserView`. The top-most BrowserView is the last element of the array. -> **Note** +> [!WARNING] > The `BrowserView` class is deprecated, and replaced by the new > [`WebContentsView`](web-contents-view.md) class. diff --git a/docs/api/clipboard.md b/docs/api/clipboard.md index c4328e2871720..275a7afe62108 100644 --- a/docs/api/clipboard.md +++ b/docs/api/clipboard.md @@ -18,7 +18,8 @@ console.log(clipboard.readText('selection')) The `clipboard` module has the following methods: -**Note:** Experimental APIs are marked as such and could be removed in future. +> [!NOTE] +> Experimental APIs are marked as such and could be removed in future. ### `clipboard.readText([type])` @@ -141,9 +142,10 @@ bookmark is unavailable. The `title` value will always be empty on Windows. Writes the `title` (macOS only) and `url` into the clipboard as a bookmark. -**Note:** Most apps on Windows don't support pasting bookmarks into them so -you can use `clipboard.write` to write both a bookmark and fallback text to the -clipboard. +> [!NOTE] +> Most apps on Windows don't support pasting bookmarks into them so +> you can use `clipboard.write` to write both a bookmark and fallback text to the +> clipboard. ```js const { clipboard } = require('electron') diff --git a/docs/api/command-line-switches.md b/docs/api/command-line-switches.md index a07a3eb9523df..dd39f076777c4 100644 --- a/docs/api/command-line-switches.md +++ b/docs/api/command-line-switches.md @@ -73,7 +73,8 @@ Passing `--enable-logging=file` will result in logs being saved to the file specified by `--log-file=...`, or to `electron_debug.log` in the user-data directory if `--log-file` is not specified. -> **Note:** On Windows, logs from child processes cannot be sent to stderr. +> [!NOTE] +> On Windows, logs from child processes cannot be sent to stderr. > Logging to a file is the most reliable way to collect logs on Windows. See also `--log-file`, `--log-level`, `--v`, and `--vmodule`. @@ -252,7 +253,8 @@ the required version is unavailable. Current default is set to `3`. Electron supports some of the [CLI flags][node-cli] supported by Node.js. -**Note:** Passing unsupported command line switches to Electron when it is not running in `ELECTRON_RUN_AS_NODE` will have no effect. +> [!NOTE] +> Passing unsupported command line switches to Electron when it is not running in `ELECTRON_RUN_AS_NODE` will have no effect. ### `--inspect-brk\[=\[host:]port]` diff --git a/docs/api/command-line.md b/docs/api/command-line.md index 424c4e9d5921d..373bee8417423 100644 --- a/docs/api/command-line.md +++ b/docs/api/command-line.md @@ -25,8 +25,9 @@ document. Append a switch (with optional `value`) to Chromium's command line. -**Note:** This will not affect `process.argv`. The intended usage of this function is to -control Chromium's behavior. +> [!NOTE] +> This will not affect `process.argv`. The intended usage of this function is to +> control Chromium's behavior. ```js const { app } = require('electron') @@ -49,8 +50,9 @@ const { app } = require('electron') app.commandLine.appendArgument('--enable-experimental-web-platform-features') ``` -**Note:** This will not affect `process.argv`. The intended usage of this function is to -control Chromium's behavior. +> [!NOTE] +> This will not affect `process.argv`. The intended usage of this function is to +> control Chromium's behavior. #### `commandLine.hasSwitch(switch)` @@ -84,7 +86,8 @@ const portValue = app.commandLine.getSwitchValue('remote-debugging-port') console.log(portValue) // '8315' ``` -**Note:** When the switch is not present or has no value, it returns empty string. +> [!NOTE] +> When the switch is not present or has no value, it returns empty string. #### `commandLine.removeSwitch(switch)` @@ -102,5 +105,6 @@ app.commandLine.removeSwitch('remote-debugging-port') console.log(app.commandLine.hasSwitch('remote-debugging-port')) // false ``` -**Note:** This will not affect `process.argv`. The intended usage of this function is to -control Chromium's behavior. +> [!NOTE] +> This will not affect `process.argv`. The intended usage of this function is to +> control Chromium's behavior. diff --git a/docs/api/content-tracing.md b/docs/api/content-tracing.md index f4646f2ad3e67..9ccb2c1cbdd0d 100644 --- a/docs/api/content-tracing.md +++ b/docs/api/content-tracing.md @@ -7,8 +7,9 @@ Process: [Main](../glossary.md#main-process) This module does not include a web interface. To view recorded traces, use [trace viewer][], available at `chrome://tracing` in Chrome. -**Note:** You should not use this module until the `ready` event of the app -module is emitted. +> [!NOTE] +> You should not use this module until the `ready` event of the app +> module is emitted. ```js const { app, contentTracing } = require('electron') diff --git a/docs/api/crash-reporter.md b/docs/api/crash-reporter.md index 26c685f8a48a3..2af51c383617c 100644 --- a/docs/api/crash-reporter.md +++ b/docs/api/crash-reporter.md @@ -19,7 +19,8 @@ following projects: * [socorro](https://github.com/mozilla-services/socorro) * [mini-breakpad-server](https://github.com/electron/mini-breakpad-server) -> **Note:** Electron uses Crashpad, not Breakpad, to collect and upload +> [!NOTE] +> Electron uses Crashpad, not Breakpad, to collect and upload > crashes, but for the time being, the [upload protocol is the same](https://chromium.googlesource.com/crashpad/crashpad/+/HEAD/doc/overview_design.md#Upload-to-collection-server). Or use a 3rd party hosted solution: @@ -84,19 +85,23 @@ before `app.on('ready')`. If the crash reporter is not initialized at the time a renderer process is created, then that renderer process will not be monitored by the crash reporter. -**Note:** You can test out the crash reporter by generating a crash using -`process.crash()`. +> [!NOTE] +> You can test out the crash reporter by generating a crash using +> `process.crash()`. -**Note:** If you need to send additional/updated `extra` parameters after your -first call `start` you can call `addExtraParameter`. +> [!NOTE] +> If you need to send additional/updated `extra` parameters after your +> first call `start` you can call `addExtraParameter`. -**Note:** Parameters passed in `extra`, `globalExtra` or set with -`addExtraParameter` have limits on the length of the keys and values. Key names -must be at most 39 bytes long, and values must be no longer than 127 bytes. -Keys with names longer than the maximum will be silently ignored. Key values -longer than the maximum length will be truncated. +> [!NOTE] +> Parameters passed in `extra`, `globalExtra` or set with +> `addExtraParameter` have limits on the length of the keys and values. Key names +> must be at most 39 bytes long, and values must be no longer than 127 bytes. +> Keys with names longer than the maximum will be silently ignored. Key values +> longer than the maximum length will be truncated. -**Note:** This method is only available in the main process. +> [!NOTE] +> This method is only available in the main process. ### `crashReporter.getLastCrashReport()` @@ -105,7 +110,8 @@ last crash report. Only crash reports that have been uploaded will be returned; even if a crash report is present on disk it will not be returned until it is uploaded. In the case that there are no uploaded reports, `null` is returned. -**Note:** This method is only available in the main process. +> [!NOTE] +> This method is only available in the main process. ### `crashReporter.getUploadedReports()` @@ -114,14 +120,16 @@ Returns [`CrashReport[]`](structures/crash-report.md): Returns all uploaded crash reports. Each report contains the date and uploaded ID. -**Note:** This method is only available in the main process. +> [!NOTE] +> This method is only available in the main process. ### `crashReporter.getUploadToServer()` Returns `boolean` - Whether reports should be submitted to the server. Set through the `start` method or `setUploadToServer`. -**Note:** This method is only available in the main process. +> [!NOTE] +> This method is only available in the main process. ### `crashReporter.setUploadToServer(uploadToServer)` @@ -130,7 +138,8 @@ the `start` method or `setUploadToServer`. This would normally be controlled by user preferences. This has no effect if called before `start` is called. -**Note:** This method is only available in the main process. +> [!NOTE] +> This method is only available in the main process. ### `crashReporter.addExtraParameter(key, value)` @@ -148,10 +157,11 @@ with crashes from renderer or other child processes. Similarly, adding extra parameters in a renderer process will not result in those parameters being sent with crashes that occur in other renderer processes or in the main process. -**Note:** Parameters have limits on the length of the keys and values. Key -names must be no longer than 39 bytes, and values must be no longer than 20320 -bytes. Keys with names longer than the maximum will be silently ignored. Key -values longer than the maximum length will be truncated. +> [!NOTE] +> Parameters have limits on the length of the keys and values. Key +> names must be no longer than 39 bytes, and values must be no longer than 20320 +> bytes. Keys with names longer than the maximum will be silently ignored. Key +> values longer than the maximum length will be truncated. ### `crashReporter.removeExtraParameter(key)` diff --git a/docs/api/desktop-capturer.md b/docs/api/desktop-capturer.md index 89f6f120062f7..822eabeac8751 100644 --- a/docs/api/desktop-capturer.md +++ b/docs/api/desktop-capturer.md @@ -70,8 +70,9 @@ stopButton.addEventListener('click', () => { See [`navigator.mediaDevices.getDisplayMedia`](https://developer.mozilla.org/en-US/docs/Web/API/MediaDevices/getDisplayMedia) for more information. -**Note:** `navigator.mediaDevices.getDisplayMedia` does not permit the use of `deviceId` for -selection of a source - see [specification](https://w3c.github.io/mediacapture-screen-share/#constraints). +> [!NOTE] +> `navigator.mediaDevices.getDisplayMedia` does not permit the use of `deviceId` for +> selection of a source - see [specification](https://w3c.github.io/mediacapture-screen-share/#constraints). ## Methods @@ -92,8 +93,9 @@ The `desktopCapturer` module has the following methods: Returns `Promise` - Resolves with an array of [`DesktopCapturerSource`](structures/desktop-capturer-source.md) objects, each `DesktopCapturerSource` represents a screen or an individual window that can be captured. -**Note** Capturing the screen contents requires user consent on macOS 10.15 Catalina or higher, -which can detected by [`systemPreferences.getMediaAccessStatus`][]. +> [!NOTE] +> Capturing the screen contents requires user consent on macOS 10.15 Catalina or higher, +> which can detected by [`systemPreferences.getMediaAccessStatus`][]. [`navigator.mediaDevices.getUserMedia`]: https://developer.mozilla.org/en/docs/Web/API/MediaDevices/getUserMedia [`systemPreferences.getMediaAccessStatus`]: system-preferences.md#systempreferencesgetmediaaccessstatusmediatype-windows-macos diff --git a/docs/api/dialog.md b/docs/api/dialog.md index a3a18584e648d..e1c641c724731 100644 --- a/docs/api/dialog.md +++ b/docs/api/dialog.md @@ -67,10 +67,11 @@ The `extensions` array should contain extensions without wildcards or dots (e.g. `'png'` is good but `'.png'` and `'*.png'` are bad). To show all files, use the `'*'` wildcard (no other wildcard is supported). -**Note:** On Windows and Linux an open dialog can not be both a file selector -and a directory selector, so if you set `properties` to -`['openFile', 'openDirectory']` on these platforms, a directory selector will be -shown. +> [!NOTE] +> On Windows and Linux an open dialog can not be both a file selector +> and a directory selector, so if you set `properties` to +> `['openFile', 'openDirectory']` on these platforms, a directory selector will be +> shown. ```js @ts-type={mainWindow:Electron.BaseWindow} dialog.showOpenDialogSync(mainWindow, { @@ -78,10 +79,11 @@ dialog.showOpenDialogSync(mainWindow, { }) ``` -**Note:** On Linux `defaultPath` is not supported when using portal file chooser -dialogs unless the portal backend is version 4 or higher. You can use `--xdg-portal-required-version` -[command-line switch](./command-line-switches.md#--xdg-portal-required-versionversion) -to force gtk or kde dialogs. +> [!NOTE] +> On Linux `defaultPath` is not supported when using portal file chooser +> dialogs unless the portal backend is version 4 or higher. You can use `--xdg-portal-required-version` +> [command-line switch](./command-line-switches.md#--xdg-portal-required-versionversion) +> to force gtk or kde dialogs. ### `dialog.showOpenDialog([window, ]options)` @@ -139,10 +141,11 @@ The `extensions` array should contain extensions without wildcards or dots (e.g. `'png'` is good but `'.png'` and `'*.png'` are bad). To show all files, use the `'*'` wildcard (no other wildcard is supported). -**Note:** On Windows and Linux an open dialog can not be both a file selector -and a directory selector, so if you set `properties` to -`['openFile', 'openDirectory']` on these platforms, a directory selector will be -shown. +> [!NOTE] +> On Windows and Linux an open dialog can not be both a file selector +> and a directory selector, so if you set `properties` to +> `['openFile', 'openDirectory']` on these platforms, a directory selector will be +> shown. ```js @ts-type={mainWindow:Electron.BaseWindow} dialog.showOpenDialog(mainWindow, { @@ -155,10 +158,11 @@ dialog.showOpenDialog(mainWindow, { }) ``` -**Note:** On Linux `defaultPath` is not supported when using portal file chooser -dialogs unless the portal backend is version 4 or higher. You can use `--xdg-portal-required-version` -[command-line switch](./command-line-switches.md#--xdg-portal-required-versionversion) -to force gtk or kde dialogs. +> [!NOTE] +> On Linux `defaultPath` is not supported when using portal file chooser +> dialogs unless the portal backend is version 4 or higher. You can use `--xdg-portal-required-version` +> [command-line switch](./command-line-switches.md#--xdg-portal-required-versionversion) +> to force gtk or kde dialogs. ### `dialog.showSaveDialogSync([window, ]options)` @@ -225,8 +229,9 @@ The `window` argument allows the dialog to attach itself to a parent window, mak The `filters` specifies an array of file types that can be displayed, see `dialog.showOpenDialog` for an example. -**Note:** On macOS, using the asynchronous version is recommended to avoid issues when -expanding and collapsing the dialog. +> [!NOTE] +> On macOS, using the asynchronous version is recommended to avoid issues when +> expanding and collapsing the dialog. ### `dialog.showMessageBoxSync([window, ]options)` diff --git a/docs/api/dock.md b/docs/api/dock.md index 4224694728da9..6bac22e9b9f47 100644 --- a/docs/api/dock.md +++ b/docs/api/dock.md @@ -28,7 +28,8 @@ When `informational` is passed, the dock icon will bounce for one second. However, the request remains active until either the application becomes active or the request is canceled. -**Note:** This method can only be used while the app is not focused; when the app is focused it will return -1. +> [!NOTE] +> This method can only be used while the app is not focused; when the app is focused it will return -1. #### `dock.cancelBounce(id)` _macOS_ diff --git a/docs/api/download-item.md b/docs/api/download-item.md index dc2c0d1a893e4..06d52a44ea803 100644 --- a/docs/api/download-item.md +++ b/docs/api/download-item.md @@ -115,7 +115,8 @@ Returns `boolean` - Whether the download is paused. Resumes the download that has been paused. -**Note:** To enable resumable downloads the server you are downloading from must support range requests and provide both `Last-Modified` and `ETag` header values. Otherwise `resume()` will dismiss previously received bytes and restart the download from the beginning. +> [!NOTE] +> To enable resumable downloads the server you are downloading from must support range requests and provide both `Last-Modified` and `ETag` header values. Otherwise `resume()` will dismiss previously received bytes and restart the download from the beginning. #### `downloadItem.canResume()` @@ -141,9 +142,10 @@ Returns `boolean` - Whether the download has user gesture. Returns `string` - The file name of the download item. -**Note:** The file name is not always the same as the actual one saved in local -disk. If user changes the file name in a prompted download saving dialog, the -actual name of saved file will be different. +> [!NOTE] +> The file name is not always the same as the actual one saved in local +> disk. If user changes the file name in a prompted download saving dialog, the +> actual name of saved file will be different. #### `downloadItem.getCurrentBytesPerSecond()` @@ -172,8 +174,9 @@ header. Returns `string` - The current state. Can be `progressing`, `completed`, `cancelled` or `interrupted`. -**Note:** The following methods are useful specifically to resume a -`cancelled` item when session is restarted. +> [!NOTE] +> The following methods are useful specifically to resume a +> `cancelled` item when session is restarted. #### `downloadItem.getURLChain()` diff --git a/docs/api/extensions-api.md b/docs/api/extensions-api.md index 30add8f9bcd9d..afbb40574e17b 100644 --- a/docs/api/extensions-api.md +++ b/docs/api/extensions-api.md @@ -92,11 +92,13 @@ app.whenReady().then(async () => { This API does not support loading packed (.crx) extensions. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. -**Note:** Loading extensions into in-memory (non-persistent) sessions is not -supported and will throw an error. +> [!NOTE] +> Loading extensions into in-memory (non-persistent) sessions is not +> supported and will throw an error. #### `extensions.removeExtension(extensionId)` @@ -104,8 +106,9 @@ supported and will throw an error. Unloads an extension. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. #### `extensions.getExtension(extensionId)` @@ -113,12 +116,14 @@ is emitted. Returns `Extension | null` - The loaded extension with the given ID. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. #### `extensions.getAllExtensions()` Returns `Extension[]` - A list of all loaded extensions. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. diff --git a/docs/api/extensions.md b/docs/api/extensions.md index 2bc93d499a2d2..43f7ccfb40d8a 100644 --- a/docs/api/extensions.md +++ b/docs/api/extensions.md @@ -6,7 +6,8 @@ but it also happens to support some other extension capabilities. [chrome-extensions-api-index]: https://developer.chrome.com/extensions/api_index -> **Note:** Electron does not support arbitrary Chrome extensions from the +> [!NOTE] +> Electron does not support arbitrary Chrome extensions from the > store, and it is a **non-goal** of the Electron project to be perfectly > compatible with Chrome's implementation of Extensions. @@ -160,7 +161,8 @@ The following methods of `chrome.tabs` are supported: - `chrome.tabs.update` (partial support) - supported properties: `url`, `muted`. -> **Note:** In Chrome, passing `-1` as a tab ID signifies the "currently active +> [!NOTE] +> In Chrome, passing `-1` as a tab ID signifies the "currently active > tab". Since Electron has no such concept, passing `-1` as a tab ID is not > supported and will raise an error. @@ -170,6 +172,7 @@ See [official documentation](https://developer.chrome.com/docs/extensions/refere All features of this API are supported. -> **NOTE:** Electron's [`webRequest`](web-request.md) module takes precedence over `chrome.webRequest` if there are conflicting handlers. +> [!NOTE] +> Electron's [`webRequest`](web-request.md) module takes precedence over `chrome.webRequest` if there are conflicting handlers. See [official documentation](https://developer.chrome.com/docs/extensions/reference/webRequest) for more information. diff --git a/docs/api/global-shortcut.md b/docs/api/global-shortcut.md index 142bdbaba1adf..50a5dacdfd246 100644 --- a/docs/api/global-shortcut.md +++ b/docs/api/global-shortcut.md @@ -8,13 +8,13 @@ The `globalShortcut` module can register/unregister a global keyboard shortcut with the operating system so that you can customize the operations for various shortcuts. -**Note:** The shortcut is global; it will work even if the app does -not have the keyboard focus. This module cannot be used before the `ready` -event of the app module is emitted. - -Please also note that it is also possible to use Chromium's -`GlobalShortcutsPortal` implementation, which allows apps to bind global -shortcuts when running within a Wayland session. +> [!NOTE] +> The shortcut is global; it will work even if the app does +> not have the keyboard focus. This module cannot be used before the `ready` +> event of the app module is emitted. +> Please also note that it is also possible to use Chromium's +> `GlobalShortcutsPortal` implementation, which allows apps to bind global +> shortcuts when running within a Wayland session. ```js const { app, globalShortcut } = require('electron') diff --git a/docs/api/ipc-renderer.md b/docs/api/ipc-renderer.md index 7f2afc41e7c10..53722a414bbea 100644 --- a/docs/api/ipc-renderer.md +++ b/docs/api/ipc-renderer.md @@ -156,7 +156,7 @@ If you need to transfer a [`MessagePort`][] to the main process, use [`ipcRender If you do not need a response to the message, consider using [`ipcRenderer.send`](#ipcrenderersendchannel-args). -> **Note** +> [!NOTE] > Sending non-standard JavaScript types such as DOM objects or > special Electron objects will throw an exception. > @@ -165,7 +165,7 @@ If you do not need a response to the message, consider using [`ipcRenderer.send` > Electron's IPC to the main process, as the main process would have no way to decode > them. Attempting to send such objects over IPC will result in an error. -> **Note** +> [!NOTE] > If the handler in the main process throws an error, > the promise returned by `invoke` will reject. > However, the `Error` object in the renderer process @@ -195,7 +195,8 @@ throw an exception. The main process handles it by listening for `channel` with [`ipcMain`](./ipc-main.md) module, and replies by setting `event.returnValue`. -> :warning: **WARNING**: Sending a synchronous message will block the whole +> [!WARNING] +> Sending a synchronous message will block the whole > renderer process until the reply is received, so use this method only as a > last resort. It's much better to use the asynchronous version, > [`invoke()`](./ipc-renderer.md#ipcrendererinvokechannel-args). diff --git a/docs/api/menu-item.md b/docs/api/menu-item.md index 0bc80b2bd37c1..0bf0753012170 100644 --- a/docs/api/menu-item.md +++ b/docs/api/menu-item.md @@ -51,7 +51,8 @@ See [`Menu`](menu.md) for examples. the placement of their containing group after the containing group of the item with the specified id. -**Note:** `acceleratorWorksWhenHidden` is specified as being macOS-only because accelerators always work when items are hidden on Windows and Linux. The option is exposed to users to give them the option to turn it off, as this is possible in native macOS development. +> [!NOTE] +> `acceleratorWorksWhenHidden` is specified as being macOS-only because accelerators always work when items are hidden on Windows and Linux. The option is exposed to users to give them the option to turn it off, as this is possible in native macOS development. ### Roles @@ -125,7 +126,8 @@ When specifying a `role` on macOS, `label` and `accelerator` are the only options that will affect the menu item. All other options will be ignored. Lowercase `role`, e.g. `toggledevtools`, is still supported. -**Note:** The `enabled` and `visibility` properties are not available for top-level menu items in the tray on macOS. +> [!NOTE] +> The `enabled` and `visibility` properties are not available for top-level menu items in the tray on macOS. ### Instance Properties @@ -170,7 +172,8 @@ An `Accelerator` (optional) indicating the item's accelerator, if set. An `Accelerator | null` indicating the item's [user-assigned accelerator](https://developer.apple.com/documentation/appkit/nsmenuitem/1514850-userkeyequivalent?language=objc) for the menu item. -**Note:** This property is only initialized after the `MenuItem` has been added to a `Menu`. Either via `Menu.buildFromTemplate` or via `Menu.append()/insert()`. Accessing before initialization will just return `null`. +> [!NOTE] +> This property is only initialized after the `MenuItem` has been added to a `Menu`. Either via `Menu.buildFromTemplate` or via `Menu.append()/insert()`. Accessing before initialization will just return `null`. #### `menuItem.icon` diff --git a/docs/api/menu.md b/docs/api/menu.md index fef600f68dd62..477729cede80a 100644 --- a/docs/api/menu.md +++ b/docs/api/menu.md @@ -32,16 +32,18 @@ In order to escape the `&` character in an item name, add a proceeding `&`. For Passing `null` will suppress the default menu. On Windows and Linux, this has the additional effect of removing the menu bar from the window. -**Note:** The default menu will be created automatically if the app does not set one. -It contains standard items such as `File`, `Edit`, `View`, `Window` and `Help`. +> [!NOTE] +> The default menu will be created automatically if the app does not set one. +> It contains standard items such as `File`, `Edit`, `View`, `Window` and `Help`. #### `Menu.getApplicationMenu()` Returns `Menu | null` - The application menu, if set, or `null`, if not set. -**Note:** The returned `Menu` instance doesn't support dynamic addition or -removal of menu items. [Instance properties](#instance-properties) can still -be dynamically modified. +> [!NOTE] +> The returned `Menu` instance doesn't support dynamic addition or +> removal of menu items. [Instance properties](#instance-properties) can still +> be dynamically modified. #### `Menu.sendActionToFirstResponder(action)` _macOS_ @@ -119,8 +121,9 @@ Inserts the `menuItem` to the `pos` position of the menu. Objects created with `new Menu` or returned by `Menu.buildFromTemplate` emit the following events: -**Note:** Some events are only available on specific operating systems and are -labeled as such. +> [!NOTE] +> Some events are only available on specific operating systems and are +> labeled as such. #### Event: 'menu-will-show' diff --git a/docs/api/native-image.md b/docs/api/native-image.md index 58c9dadfd3c01..a867cfca5e2f1 100644 --- a/docs/api/native-image.md +++ b/docs/api/native-image.md @@ -134,7 +134,8 @@ Creates an empty `NativeImage` instance. Returns `Promise` - fulfilled with the file's thumbnail preview image, which is a [NativeImage](native-image.md). -Note: The Windows implementation will ignore `size.height` and scale the height according to `size.width`. +> [!NOTE] +> Windows implementation will ignore `size.height` and scale the height according to `size.width`. ### `nativeImage.createFromPath(path)` diff --git a/docs/api/net-log.md b/docs/api/net-log.md index f9b04212c043f..2ae5beabfc9ee 100644 --- a/docs/api/net-log.md +++ b/docs/api/net-log.md @@ -17,8 +17,9 @@ app.whenReady().then(async () => { See [`--log-net-log`](command-line-switches.md#--log-net-logpath) to log network events throughout the app's lifecycle. -**Note:** All methods unless specified can only be used after the `ready` event -of the `app` module gets emitted. +> [!NOTE] +> All methods unless specified can only be used after the `ready` event +> of the `app` module gets emitted. ## Methods diff --git a/docs/api/net.md b/docs/api/net.md index 464c078a54258..2b42e445ff19c 100644 --- a/docs/api/net.md +++ b/docs/api/net.md @@ -117,8 +117,9 @@ protocol.handle('https', (req) => { }) ``` -Note: in the [utility process](../glossary.md#utility-process) custom protocols -are not supported. +> [!NOTE] +> In the [utility process](../glossary.md#utility-process), custom protocols +> are not supported. ### `net.isOnline()` diff --git a/docs/api/power-save-blocker.md b/docs/api/power-save-blocker.md index ee57287258df0..348a6b78907a6 100644 --- a/docs/api/power-save-blocker.md +++ b/docs/api/power-save-blocker.md @@ -33,10 +33,11 @@ Returns `Integer` - The blocker ID that is assigned to this power blocker. Starts preventing the system from entering lower-power mode. Returns an integer identifying the power save blocker. -**Note:** `prevent-display-sleep` has higher precedence over -`prevent-app-suspension`. Only the highest precedence type takes effect. In -other words, `prevent-display-sleep` always takes precedence over -`prevent-app-suspension`. +> [!NOTE] +> `prevent-display-sleep` has higher precedence over +> `prevent-app-suspension`. Only the highest precedence type takes effect. In +> other words, `prevent-display-sleep` always takes precedence over +> `prevent-app-suspension`. For example, an API calling A requests for `prevent-app-suspension`, and another calling B requests for `prevent-display-sleep`. `prevent-display-sleep` diff --git a/docs/api/process.md b/docs/api/process.md index 03a606de9ac19..3c24d5db57985 100644 --- a/docs/api/process.md +++ b/docs/api/process.md @@ -233,7 +233,8 @@ console.log(version) // On Linux -> '4.15.0-45-generic' ``` -**Note:** It returns the actual operating system version instead of kernel version on macOS unlike `os.release()`. +> [!NOTE] +> It returns the actual operating system version instead of kernel version on macOS unlike `os.release()`. ### `process.takeHeapSnapshot(filePath)` diff --git a/docs/api/protocol.md b/docs/api/protocol.md index 1af780827c80b..a14cd01b6250c 100644 --- a/docs/api/protocol.md +++ b/docs/api/protocol.md @@ -20,8 +20,9 @@ app.whenReady().then(() => { }) ``` -**Note:** All methods unless specified can only be used after the `ready` event -of the `app` module gets emitted. +> [!NOTE] +> All methods unless specified can only be used after the `ready` event +> of the `app` module gets emitted. ## Using `protocol` with a custom `partition` or `session` @@ -61,8 +62,9 @@ The `protocol` module has the following methods: * `customSchemes` [CustomScheme[]](structures/custom-scheme.md) -**Note:** This method can only be used before the `ready` event of the `app` -module gets emitted and can be called only once. +> [!NOTE] +> This method can only be used before the `ready` event of the `app` +> module gets emitted and can be called only once. Registers the `scheme` as standard, secure, bypasses content security policy for resources, allows registering ServiceWorker, supports fetch API, streaming diff --git a/docs/api/screen.md b/docs/api/screen.md index d923b8995f540..43b025ef7f721 100644 --- a/docs/api/screen.md +++ b/docs/api/screen.md @@ -9,8 +9,9 @@ module is emitted. `screen` is an [EventEmitter][event-emitter]. -**Note:** In the renderer / DevTools, `window.screen` is a reserved DOM -property, so writing `let { screen } = require('electron')` will not work. +> [!NOTE] +> In the renderer / DevTools, `window.screen` is a reserved DOM +> property, so writing `let { screen } = require('electron')` will not work. An example of creating a window that fills the whole screen: @@ -101,7 +102,8 @@ Returns [`Point`](structures/point.md) The current absolute position of the mouse pointer. -**Note:** The return value is a DIP point, not a screen physical point. +> [!NOTE] +> The return value is a DIP point, not a screen physical point. ### `screen.getPrimaryDisplay()` diff --git a/docs/api/session.md b/docs/api/session.md index 16c382d0c3a96..105dfb5f7673c 100644 --- a/docs/api/session.md +++ b/docs/api/session.md @@ -762,7 +762,8 @@ Preconnects the given number of sockets to an origin. Returns `Promise` - Resolves when all connections are closed. -**Note:** It will terminate / fail all requests currently in flight. +> [!NOTE] +> It will terminate / fail all requests currently in flight. #### `ses.fetch(input[, init])` @@ -1305,8 +1306,9 @@ Initiates a download of the resource at `url`. The API will generate a [DownloadItem](download-item.md) that can be accessed with the [will-download](#event-will-download) event. -**Note:** This does not perform any security checks that relate to a page's origin, -unlike [`webContents.downloadURL`](web-contents.md#contentsdownloadurlurl-options). +> [!NOTE] +> This does not perform any security checks that relate to a page's origin, +> unlike [`webContents.downloadURL`](web-contents.md#contentsdownloadurlurl-options). #### `ses.createInterruptedDownload(options)` @@ -1434,7 +1436,8 @@ The built in spellchecker does not automatically detect what language a user is spell checker to correctly check their words you must call this API with an array of language codes. You can get the list of supported language codes with the `ses.availableSpellCheckerLanguages` property. -**Note:** On macOS the OS spellchecker is used and will detect your language automatically. This API is a no-op on macOS. +> [!NOTE] +> On macOS, the OS spellchecker is used and will detect your language automatically. This API is a no-op on macOS. #### `ses.getSpellCheckerLanguages()` @@ -1442,7 +1445,8 @@ Returns `string[]` - An array of language codes the spellchecker is enabled for. will fallback to using `en-US`. By default on launch if this setting is an empty list Electron will try to populate this setting with the current OS locale. This setting is persisted across restarts. -**Note:** On macOS the OS spellchecker is used and has its own list of languages. On macOS, this API will return whichever languages have been configured by the OS. +> [!NOTE] +> On macOS, the OS spellchecker is used and has its own list of languages. On macOS, this API will return whichever languages have been configured by the OS. #### `ses.setSpellCheckerDictionaryDownloadURL(url)` @@ -1460,7 +1464,8 @@ If the files present in `hunspell_dictionaries.zip` are available at `https://ex then you should call this api with `ses.setSpellCheckerDictionaryDownloadURL('https://example.com/dictionaries/')`. Please note the trailing slash. The URL to the dictionaries is formed as `${url}${filename}`. -**Note:** On macOS the OS spellchecker is used and therefore we do not download any dictionary files. This API is a no-op on macOS. +> [!NOTE] +> On macOS, the OS spellchecker is used and therefore we do not download any dictionary files. This API is a no-op on macOS. #### `ses.listWordsInSpellCheckerDictionary()` @@ -1474,7 +1479,8 @@ Resolves when the full dictionary is loaded from disk. Returns `boolean` - Whether the word was successfully written to the custom dictionary. This API will not work on non-persistent (in-memory) sessions. -**Note:** On macOS and Windows 10 this word will be written to the OS custom dictionary as well +> [!NOTE] +> On macOS and Windows, this word will be written to the OS custom dictionary as well. #### `ses.removeWordFromSpellCheckerDictionary(word)` @@ -1483,7 +1489,8 @@ will not work on non-persistent (in-memory) sessions. Returns `boolean` - Whether the word was successfully removed from the custom dictionary. This API will not work on non-persistent (in-memory) sessions. -**Note:** On macOS and Windows 10 this word will be removed from the OS custom dictionary as well +> [!NOTE] +> On macOS and Windows, this word will be removed from the OS custom dictionary as well. #### `ses.loadExtension(path[, options])` _Deprecated_ @@ -1526,11 +1533,13 @@ app.whenReady().then(async () => { This API does not support loading packed (.crx) extensions. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. -**Note:** Loading extensions into in-memory (non-persistent) sessions is not -supported and will throw an error. +> [!NOTE] +> Loading extensions into in-memory (non-persistent) sessions is not +> supported and will throw an error. **Deprecated:** Use the new `ses.extensions.loadExtension` API. @@ -1540,8 +1549,9 @@ supported and will throw an error. Unloads an extension. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. **Deprecated:** Use the new `ses.extensions.removeExtension` API. @@ -1551,8 +1561,9 @@ is emitted. Returns `Extension | null` - The loaded extension with the given ID. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. **Deprecated:** Use the new `ses.extensions.getExtension` API. @@ -1560,8 +1571,9 @@ is emitted. Returns `Extension[]` - A list of all loaded extensions. -**Note:** This API cannot be called before the `ready` event of the `app` module -is emitted. +> [!NOTE] +> This API cannot be called before the `ready` event of the `app` module +> is emitted. **Deprecated:** Use the new `ses.extensions.getAllExtensions` API. @@ -1599,9 +1611,11 @@ Clears various different types of data. This method clears more types of data and is more thorough than the `clearStorageData` method. -**Note:** Cookies are stored at a broader scope than origins. When removing cookies and filtering by `origins` (or `excludeOrigins`), the cookies will be removed at the [registrable domain](https://url.spec.whatwg.org/#host-registrable-domain) level. For example, clearing cookies for the origin `https://really.specific.origin.example.com/` will end up clearing all cookies for `example.com`. Clearing cookies for the origin `https://my.website.example.co.uk/` will end up clearing all cookies for `example.co.uk`. +> [!NOTE] +> Cookies are stored at a broader scope than origins. When removing cookies and filtering by `origins` (or `excludeOrigins`), the cookies will be removed at the [registrable domain](https://url.spec.whatwg.org/#host-registrable-domain) level. For example, clearing cookies for the origin `https://really.specific.origin.example.com/` will end up clearing all cookies for `example.com`. Clearing cookies for the origin `https://my.website.example.co.uk/` will end up clearing all cookies for `example.co.uk`. -**Note:** Clearing cache data will also clear the shared dictionary cache. This means that any dictionaries used for compression may be reloaded after clearing the cache. If you wish to clear the shared dictionary cache but leave other cached data intact, you may want to use the `clearSharedDictionaryCache` method. +> [!NOTE] +> Clearing cache data will also clear the shared dictionary cache. This means that any dictionaries used for compression may be reloaded after clearing the cache. If you wish to clear the shared dictionary cache but leave other cached data intact, you may want to use the `clearSharedDictionaryCache` method. For more information, refer to Chromium's [`BrowsingDataRemover` interface][browsing-data-remover]. diff --git a/docs/api/shell.md b/docs/api/shell.md index 1008b73c164d2..80e720b8f419a 100644 --- a/docs/api/shell.md +++ b/docs/api/shell.md @@ -14,7 +14,8 @@ const { shell } = require('electron') shell.openExternal('https://github.com') ``` -**Note:** While the `shell` module can be used in the renderer process, it will not function in a sandboxed renderer. +> [!WARNING] +> While the `shell` module can be used in the renderer process, it will not function in a sandboxed renderer. ## Methods diff --git a/docs/api/structures/jump-list-category.md b/docs/api/structures/jump-list-category.md index 117483f1a8e5e..ad5747ceed62f 100644 --- a/docs/api/structures/jump-list-category.md +++ b/docs/api/structures/jump-list-category.md @@ -15,11 +15,13 @@ * `items` JumpListItem[] (optional) - Array of [`JumpListItem`](jump-list-item.md) objects if `type` is `tasks` or `custom`, otherwise it should be omitted. -**Note:** If a `JumpListCategory` object has neither the `type` nor the `name` -property set then its `type` is assumed to be `tasks`. If the `name` property -is set but the `type` property is omitted then the `type` is assumed to be -`custom`. +> [!NOTE] +> If a `JumpListCategory` object has neither the `type` nor the `name` +> property set then its `type` is assumed to be `tasks`. If the `name` property +> is set but the `type` property is omitted then the `type` is assumed to be +> `custom`. -**Note:** The maximum length of a Jump List item's `description` property is -260 characters. Beyond this limit, the item will not be added to the Jump -List, nor will it be displayed. +> [!NOTE] +> The maximum length of a Jump List item's `description` property is +> 260 characters. Beyond this limit, the item will not be added to the Jump +> List, nor will it be displayed. diff --git a/docs/api/structures/point.md b/docs/api/structures/point.md index 5b792cea0f9c7..9294dc7db54ba 100644 --- a/docs/api/structures/point.md +++ b/docs/api/structures/point.md @@ -3,6 +3,7 @@ * `x` number * `y` number -**Note:** Both `x` and `y` must be whole integers, when providing a point object -as input to an Electron API we will automatically round your `x` and `y` values -to the nearest whole integer. +> [!NOTE] +> Both `x` and `y` must be whole integers, when providing a point object +> as input to an Electron API we will automatically round your `x` and `y` values +> to the nearest whole integer. diff --git a/docs/api/touch-bar-other-items-proxy.md b/docs/api/touch-bar-other-items-proxy.md index a00cd4b0b1588..efad02d070c70 100644 --- a/docs/api/touch-bar-other-items-proxy.md +++ b/docs/api/touch-bar-other-items-proxy.md @@ -4,8 +4,9 @@ > from Chromium at the space indicated by the proxy. By default, this proxy is added > to each TouchBar at the end of the input. For more information, see the AppKit docs on > [NSTouchBarItemIdentifierOtherItemsProxy](https://developer.apple.com/documentation/appkit/nstouchbaritemidentifierotheritemsproxy) -> -> Note: Only one instance of this class can be added per TouchBar. + +> [!NOTE] +> Only one instance of this class can be added per TouchBar. Process: [Main](../glossary.md#main-process)
_This class is not exported from the `'electron'` module. It is only available as a return value of other methods in the Electron API._ diff --git a/docs/api/touch-bar.md b/docs/api/touch-bar.md index c229430326437..c304f57430832 100644 --- a/docs/api/touch-bar.md +++ b/docs/api/touch-bar.md @@ -15,12 +15,14 @@ Process: [Main](../glossary.md#main-process) Creates a new touch bar with the specified items. Use `BrowserWindow.setTouchBar` to add the `TouchBar` to a window. -**Note:** The TouchBar API is currently experimental and may change or be -removed in future Electron releases. - -**Tip:** If you don't have a MacBook with Touch Bar, you can use -[Touch Bar Simulator](https://github.com/sindresorhus/touch-bar-simulator) -to test Touch Bar usage in your app. +> [!NOTE] +> The TouchBar API is currently experimental and may change or be +> removed in future Electron releases. + +> [!TIP] +> If you don't have a MacBook with Touch Bar, you can use +> [Touch Bar Simulator](https://github.com/sindresorhus/touch-bar-simulator) +> to test Touch Bar usage in your app. ### Static Properties diff --git a/docs/api/tray.md b/docs/api/tray.md index 27c1d948a1246..6b112def35918 100644 --- a/docs/api/tray.md +++ b/docs/api/tray.md @@ -176,7 +176,8 @@ Returns: Emitted when the mouse is released from clicking the tray icon. -Note: This will not be emitted if you have set a context menu for your Tray using `tray.setContextMenu`, as a result of macOS-level constraints. +> [!NOTE] +> This will not be emitted if you have set a context menu for your Tray using `tray.setContextMenu`, as a result of macOS-level constraints. #### Event: 'mouse-down' _macOS_ diff --git a/docs/api/utility-process.md b/docs/api/utility-process.md index 658c0c8804fba..e6cf1b79bab87 100644 --- a/docs/api/utility-process.md +++ b/docs/api/utility-process.md @@ -44,7 +44,8 @@ Process: [Main](../glossary.md#main-process)
Returns [`UtilityProcess`](utility-process.md#class-utilityprocess) -**Note:** `utilityProcess.fork` can only be called after the `ready` event has been emitted on `App`. +> [!NOTE] +> `utilityProcess.fork` can only be called after the `ready` event has been emitted on `App`. ## Class: UtilityProcess @@ -108,7 +109,8 @@ child.on('exit', () => { }) ``` -**Note:** You can use the `pid` to determine if the process is currently running. +> [!NOTE] +> You can use the `pid` to determine if the process is currently running. #### `child.stdout` diff --git a/docs/api/view.md b/docs/api/view.md index 32ac190d618e6..8e0a23a5d8def 100644 --- a/docs/api/view.md +++ b/docs/api/view.md @@ -94,13 +94,15 @@ Examples of valid `color` values: * Similar to CSS Color Module Level 3 keywords, but case-sensitive. * e.g. `blueviolet` or `red` -**Note:** Hex format with alpha takes `AARRGGBB` or `ARGB`, _not_ `RRGGBBAA` or `RGB`. +> [!NOTE] +> Hex format with alpha takes `AARRGGBB` or `ARGB`, _not_ `RRGGBBAA` or `RGB`. #### `view.setBorderRadius(radius)` * `radius` Integer - Border radius size in pixels. -**Note:** The area cutout of the view's border still captures clicks. +> [!NOTE] +> The area cutout of the view's border still captures clicks. #### `view.setVisible(visible)` diff --git a/docs/api/web-contents.md b/docs/api/web-contents.md index 0dc3cd9dfc7cb..3e89f5e6f7abc 100644 --- a/docs/api/web-contents.md +++ b/docs/api/web-contents.md @@ -463,7 +463,8 @@ win.webContents.on('will-prevent-unload', (event) => { }) ``` -**Note:** This will be emitted for `BrowserViews` but will _not_ be respected - this is because we have chosen not to tie the `BrowserView` lifecycle to its owning BrowserWindow should one exist per the [specification](https://developer.mozilla.org/en-US/docs/Web/API/Window/beforeunload_event). +> [!NOTE] +> This will be emitted for `BrowserViews` but will _not_ be respected - this is because we have chosen not to tie the `BrowserView` lifecycle to its owning BrowserWindow should one exist per the [specification](https://developer.mozilla.org/en-US/docs/Web/API/Window/beforeunload_event). #### Event: 'render-process-gone' @@ -1491,7 +1492,8 @@ increment above or below represents zooming 20% larger or smaller to default limits of 300% and 50% of original size, respectively. The formula for this is `scale := 1.2 ^ level`. -> **NOTE**: The zoom policy at the Chromium level is same-origin, meaning that the +> [!NOTE] +> The zoom policy at the Chromium level is same-origin, meaning that the > zoom level for a specific domain propagates across all instances of windows with > the same domain. Differentiating the window URLs will make zoom work per-window. @@ -1508,7 +1510,8 @@ Returns `Promise` Sets the maximum and minimum pinch-to-zoom level. -> **NOTE**: Visual zoom is disabled by default in Electron. To re-enable it, call: +> [!NOTE] +> Visual zoom is disabled by default in Electron. To re-enable it, call: > > ```js > const win = new BrowserWindow() @@ -2076,7 +2079,9 @@ Disable device emulation enabled by `webContents.enableDeviceEmulation`. * `inputEvent` [MouseInputEvent](structures/mouse-input-event.md) | [MouseWheelInputEvent](structures/mouse-wheel-input-event.md) | [KeyboardInputEvent](structures/keyboard-input-event.md) Sends an input `event` to the page. -**Note:** The [`BrowserWindow`](browser-window.md) containing the contents needs to be focused for + +> [!NOTE] +> The [`BrowserWindow`](browser-window.md) containing the contents needs to be focused for `sendInputEvent()` to work. #### `contents.beginFrameSubscription([onlyDirty ,]callback)` @@ -2218,7 +2223,9 @@ By default this value is `{ min: 0, max: 0 }` , which would apply no restriction * `max` Integer - The maximum UDP port number that WebRTC should use. Setting the WebRTC UDP Port Range allows you to restrict the udp port range used by WebRTC. By default the port range is unrestricted. -**Note:** To reset to an unrestricted port range this value should be set to `{ min: 0, max: 0 }`. + +> [!NOTE] +> To reset to an unrestricted port range this value should be set to `{ min: 0, max: 0 }`. #### `contents.getMediaSourceId(requestWebContents)` @@ -2364,8 +2371,9 @@ A [`WebContents`](web-contents.md) instance that might own this `WebContents`. A `WebContents | null` property that represents the of DevTools `WebContents` associated with a given `WebContents`. -**Note:** Users should never store this object because it may become `null` -when the DevTools has been closed. +> [!NOTE] +> Users should never store this object because it may become `null` +> when the DevTools has been closed. #### `contents.debugger` _Readonly_ diff --git a/docs/api/web-frame.md b/docs/api/web-frame.md index b0148f4bfe043..301c002bd1401 100644 --- a/docs/api/web-frame.md +++ b/docs/api/web-frame.md @@ -41,7 +41,8 @@ Changes the zoom level to the specified level. The original size is 0 and each increment above or below represents zooming 20% larger or smaller to default limits of 300% and 50% of original size, respectively. -> **NOTE**: The zoom policy at the Chromium level is same-origin, meaning that the +> [!NOTE] +> The zoom policy at the Chromium level is same-origin, meaning that the > zoom level for a specific domain propagates across all instances of windows with > the same domain. Differentiating the window URLs will make zoom work per-window. @@ -56,13 +57,15 @@ Returns `number` - The current zoom level. Sets the maximum and minimum pinch-to-zoom level. -> **NOTE**: Visual zoom is disabled by default in Electron. To re-enable it, call: +> [!NOTE] +> Visual zoom is disabled by default in Electron. To re-enable it, call: > > ```js > webFrame.setVisualZoomLevelLimits(1, 3) > ``` -> **NOTE**: Visual zoom only applies to pinch-to-zoom behavior. Cmd+/-/0 zoom shortcuts are +> [!NOTE] +> Visual zoom only applies to pinch-to-zoom behavior. Cmd+/-/0 zoom shortcuts are > controlled by the 'zoomIn', 'zoomOut', and 'resetZoom' MenuItem roles in the application > Menu. To disable shortcuts, manually [define the Menu](./menu.md#examples) and omit zoom roles > from the definition. @@ -189,7 +192,9 @@ dispatch errors of isolated worlds to foreign worlds. * `name` string (optional) - Name for isolated world. Useful in devtools. Set the security origin, content security policy and name of the isolated world. -Note: If the `csp` is specified, then the `securityOrigin` also has to be specified. + +> [!NOTE] +> If the `csp` is specified, then the `securityOrigin` also has to be specified. ### `webFrame.getResourceUsage()` diff --git a/docs/api/webview-tag.md b/docs/api/webview-tag.md index 14103680f7f4e..385358728a2ed 100644 --- a/docs/api/webview-tag.md +++ b/docs/api/webview-tag.md @@ -30,8 +30,10 @@ rendered. Unlike an `iframe`, the `webview` runs in a separate process than your app. It doesn't have the same permissions as your web page and all interactions between your app and embedded content will be asynchronous. This keeps your app -safe from the embedded content. **Note:** Most methods called on the -webview from the host page require a synchronous call to the main process. +safe from the embedded content. + +> [!NOTE] +> Most methods called on the webview from the host page require a synchronous call to the main process. ## Example @@ -252,7 +254,8 @@ The full list of supported feature strings can be found in the The `webview` tag has the following methods: -**Note:** The webview element must be loaded before using the methods. +> [!NOTE] +> The webview element must be loaded before using the methods. **Example** @@ -679,7 +682,8 @@ increment above or below represents zooming 20% larger or smaller to default limits of 300% and 50% of original size, respectively. The formula for this is `scale := 1.2 ^ level`. -> **NOTE**: The zoom policy at the Chromium level is same-origin, meaning that the +> [!NOTE] +> The zoom policy at the Chromium level is same-origin, meaning that the > zoom level for a specific domain propagates across all instances of windows with > the same domain. Differentiating the window URLs will make zoom work per-window. diff --git a/docs/development/build-instructions-gn.md b/docs/development/build-instructions-gn.md index 64c897b5ea59f..2efd0ba8d9dc8 100644 --- a/docs/development/build-instructions-gn.md +++ b/docs/development/build-instructions-gn.md @@ -155,7 +155,8 @@ $ gn gen out/Release --args="import(\"//electron/build/args/release.gn\")" $ gn gen out/Release --args="import(\`"//electron/build/args/release.gn\`")" ``` -**Note:** This will generate a `out/Testing` or `out/Release` build directory under `src/` with the testing or release build depending upon the configuration passed above. You can replace `Testing|Release` with another names, but it should be a subdirectory of `out`. +> [!NOTE] +> This will generate a `out/Testing` or `out/Release` build directory under `src/` with the testing or release build depending upon the configuration passed above. You can replace `Testing|Release` with another names, but it should be a subdirectory of `out`. Also you shouldn't have to run `gn gen` again—if you want to change the build arguments, you can run `gn args out/Testing` to bring up an editor. To see the list of available build configuration options, run `gn args out/Testing --list`. diff --git a/docs/development/build-instructions-windows.md b/docs/development/build-instructions-windows.md index 8d7e7943308a4..0d1a079c5d705 100644 --- a/docs/development/build-instructions-windows.md +++ b/docs/development/build-instructions-windows.md @@ -39,8 +39,9 @@ Building Electron is done entirely with command-line scripts and cannot be done with Visual Studio. You can develop Electron with any editor but support for building with Visual Studio will come in the future. -**Note:** Even though Visual Studio is not used for building, it's still -**required** because we need the build toolchains it provides. +> [!NOTE] +> Even though Visual Studio is not used for building, it's still +> **required** because we need the build toolchains it provides. ## Exclude source tree from Windows Security diff --git a/docs/development/creating-api.md b/docs/development/creating-api.md index 62af7250c15b0..49f383f33f923 100644 --- a/docs/development/creating-api.md +++ b/docs/development/creating-api.md @@ -148,7 +148,8 @@ In your [`shell/common/node_bindings.cc`](https://github.com/electron/electron/b V(electron_browser_{api_name}) ``` -> Note: More technical details on how Node links with Electron can be found on [our blog](https://www.electronjs.org/blog/electron-internals-using-node-as-a-library#link-node-with-electron). +> [!NOTE] +> More technical details on how Node links with Electron can be found on [our blog](https://www.electronjs.org/blog/electron-internals-using-node-as-a-library#link-node-with-electron). ## Expose your API to TypeScript diff --git a/docs/development/patches.md b/docs/development/patches.md index e7c744f34a551..e32549e1fe7a7 100644 --- a/docs/development/patches.md +++ b/docs/development/patches.md @@ -49,7 +49,8 @@ $ git commit $ ../../electron/script/git-export-patches -o ../../electron/patches/node ``` -> **NOTE**: `git-export-patches` ignores any uncommitted files, so you must create a commit if you want your changes to be exported. The subject line of the commit message will be used to derive the patch file name, and the body of the commit message should include the reason for the patch's existence. +> [!NOTE] +> `git-export-patches` ignores any uncommitted files, so you must create a commit if you want your changes to be exported. The subject line of the commit message will be used to derive the patch file name, and the body of the commit message should include the reason for the patch's existence. Re-exporting patches will sometimes cause shasums in unrelated patches to change. This is generally harmless and can be ignored (but go ahead and add those changes to your PR, it'll stop them from showing up for other people). diff --git a/docs/tutorial/keyboard-shortcuts.md b/docs/tutorial/keyboard-shortcuts.md index 8caa93f65c040..687454c7ae75c 100644 --- a/docs/tutorial/keyboard-shortcuts.md +++ b/docs/tutorial/keyboard-shortcuts.md @@ -133,9 +133,10 @@ function handleKeyPress (event) { window.addEventListener('keyup', handleKeyPress, true) ``` -> Note: the third parameter `true` indicates that the listener will always receive -key presses before other listeners so they can't have `stopPropagation()` -called on them. +> [!NOTE] +> The third parameter `true` indicates that the listener will always receive +> key presses before other listeners so they can't have `stopPropagation()` +> called on them. #### Intercepting events in the main process diff --git a/docs/tutorial/multithreading.md b/docs/tutorial/multithreading.md index ab70b88a502c9..fd0a52205f48b 100644 --- a/docs/tutorial/multithreading.md +++ b/docs/tutorial/multithreading.md @@ -20,7 +20,8 @@ const win = new BrowserWindow({ The `nodeIntegrationInWorker` can be used independent of `nodeIntegration`, but `sandbox` must not be set to `true`. -**Note:** This option is not available in [`SharedWorker`s](https://developer.mozilla.org/en-US/docs/Web/API/SharedWorker) or [`Service Worker`s](https://developer.mozilla.org/en-US/docs/Web/API/ServiceWorker) owing to incompatibilities in sandboxing policies. +> [!NOTE] +> This option is not available in [`SharedWorker`s](https://developer.mozilla.org/en-US/docs/Web/API/SharedWorker) or [`Service Worker`s](https://developer.mozilla.org/en-US/docs/Web/API/ServiceWorker) owing to incompatibilities in sandboxing policies. ## Available APIs diff --git a/docs/tutorial/online-offline-events.md b/docs/tutorial/online-offline-events.md index 8cb40ebe8389d..eb0f6dac25714 100644 --- a/docs/tutorial/online-offline-events.md +++ b/docs/tutorial/online-offline-events.md @@ -83,4 +83,5 @@ After launching the Electron application, you should see the notification: ![Connection status](../images/connection-status.png) -> Note: If you need to communicate the connection status to the main process, use the [IPC renderer](../api/ipc-renderer.md) API. +> [!NOTE] +> If you need to communicate the connection status to the main process, use the [IPC renderer](../api/ipc-renderer.md) API. diff --git a/docs/tutorial/process-model.md b/docs/tutorial/process-model.md index f9a6348e88971..e8dd209ccec32 100644 --- a/docs/tutorial/process-model.md +++ b/docs/tutorial/process-model.md @@ -64,7 +64,8 @@ const contents = win.webContents console.log(contents) ``` -> Note: A renderer process is also created for [web embeds][web-embed] such as the +> [!NOTE] +> A renderer process is also created for [web embeds][web-embed] such as the > `BrowserView` module. The `webContents` object is also accessible for embedded > web content. diff --git a/docs/tutorial/repl.md b/docs/tutorial/repl.md index 82d9c035e1b3d..fda0c53f077dc 100644 --- a/docs/tutorial/repl.md +++ b/docs/tutorial/repl.md @@ -14,8 +14,9 @@ dependency, you should be able to access the REPL with the following command: ./node_modules/.bin/electron --interactive ``` -**Note:** `electron --interactive` is not available on Windows -(see [electron/electron#5776](https://github.com/electron/electron/pull/5776) for more details). +> [!NOTE] +> `electron --interactive` is not available on Windows +> (see [electron/electron#5776](https://github.com/electron/electron/pull/5776) for more details). ## Renderer process diff --git a/docs/tutorial/web-embeds.md b/docs/tutorial/web-embeds.md index 462b029c03a55..0f9d5b735b8df 100644 --- a/docs/tutorial/web-embeds.md +++ b/docs/tutorial/web-embeds.md @@ -19,12 +19,12 @@ and only allow the capabilities you want to support. ### WebViews -> Important Note: -[we do not recommend you to use WebViews](../api/webview-tag.md#warning), -as this tag undergoes dramatic architectural changes that may affect stability -of your application. Consider switching to alternatives, like `iframe` and -Electron's [`WebContentsView`](../api/web-contents-view.md), or an architecture -that avoids embedded content by design. +> [!IMPORTANT] +> [We do not recommend you to use WebViews](../api/webview-tag.md#warning), +> as this tag undergoes dramatic architectural changes that may affect stability +> of your application. Consider switching to alternatives, like `iframe` and +> Electron's [`WebContentsView`](../api/web-contents-view.md), or an architecture +> that avoids embedded content by design. [WebViews](../api/webview-tag.md) are based on Chromium's WebViews and are not explicitly supported by Electron. We do not guarantee that the WebView API will From 546d9f4ba60cc90be995190a9abaee33af8614d0 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 9 May 2025 17:46:53 -0500 Subject: [PATCH 037/186] fix: webview crash on focus (#47036) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- patches/chromium/.patches | 1 + ...ontentsviewchildframe_notimplemented.patch | 50 +++++++++++++++++++ 2 files changed, 51 insertions(+) create mode 100644 patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 5489765e6d4d8..e6980db620ef5 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -146,3 +146,4 @@ fix_enable_wrap_iter_in_string_view_and_array.patch fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch +make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch diff --git a/patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch b/patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch new file mode 100644 index 0000000000000..8e53a214b87ae --- /dev/null +++ b/patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch @@ -0,0 +1,50 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Shelley Vohr +Date: Wed, 7 May 2025 05:08:18 -0700 +Subject: Make focus methods in WebContentsViewChildFrame NOTIMPLEMENTED + +Change focus methods in WebContentsViewChildFrame to NOTIMPLEMENTED. +It's possible to for focus to be called on the child frame, e.g. in the +context of chrome.webviewTag, and shouldn't necessarily crash. + +This also fixes an associated crash in Electron, where the NOTREACHED is +hit when PointerLockController::LockPointer calls web_contents->Focus(). + +Change-Id: Ide58aae2187fbdd807be4ec176d13c76e459ba9c +Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6508949 +Commit-Queue: Bo Liu +Reviewed-by: Bo Liu +Reviewed-by: Rakina Zata Amni +Cr-Commit-Position: refs/heads/main@{#1456886} + +diff --git a/content/browser/web_contents/web_contents_view_child_frame.cc b/content/browser/web_contents/web_contents_view_child_frame.cc +index b89d4621dc2acc84f7d8c749f34f7f5563543c72..9c206f6ee424fc423d5f772c7559e60ec0df6eef 100644 +--- a/content/browser/web_contents/web_contents_view_child_frame.cc ++++ b/content/browser/web_contents/web_contents_view_child_frame.cc +@@ -6,6 +6,7 @@ + + #include + ++#include "base/notimplemented.h" + #include "build/build_config.h" + #include "content/browser/renderer_host/render_frame_proxy_host.h" + #include "content/browser/renderer_host/render_widget_host_view_child_frame.h" +@@ -160,15 +161,15 @@ void WebContentsViewChildFrame::DestroyBackForwardTransitionAnimationManager() { + } + + void WebContentsViewChildFrame::RestoreFocus() { +- NOTREACHED(); ++ NOTIMPLEMENTED(); + } + + void WebContentsViewChildFrame::Focus() { +- NOTREACHED(); ++ NOTIMPLEMENTED(); + } + + void WebContentsViewChildFrame::StoreFocus() { +- NOTREACHED(); ++ NOTIMPLEMENTED(); + } + + void WebContentsViewChildFrame::FocusThroughTabTraversal(bool reverse) { From 25c7f0017aadfaef7d77930624bded389c747830 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sun, 11 May 2025 15:00:11 -0500 Subject: [PATCH 038/186] fix: white window flicker on window creation (#47051) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/native_window_views.cc | 2 ++ .../win/electron_desktop_window_tree_host_win.cc | 14 ++++++++++++++ .../ui/win/electron_desktop_window_tree_host_win.h | 3 +++ 3 files changed, 19 insertions(+) diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 39c066aed2929..df78d19d9dcfc 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -37,6 +37,7 @@ #include "shell/common/options_switches.h" #include "ui/aura/window_tree_host.h" #include "ui/base/hit_test.h" +#include "ui/compositor/compositor.h" #include "ui/display/screen.h" #include "ui/gfx/image/image.h" #include "ui/gfx/native_widget_types.h" @@ -1217,6 +1218,7 @@ void NativeWindowViews::SetBackgroundColor(SkColor background_color) { DeleteObject((HBRUSH)previous_brush); InvalidateRect(GetAcceleratedWidget(), nullptr, 1); #endif + GetWidget()->GetCompositor()->SetBackgroundColor(background_color); } void NativeWindowViews::SetHasShadow(bool has_shadow) { diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc index 3618bb840cb6d..641aaf5b753ca 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc @@ -23,6 +23,20 @@ ElectronDesktopWindowTreeHostWin::ElectronDesktopWindowTreeHostWin( ElectronDesktopWindowTreeHostWin::~ElectronDesktopWindowTreeHostWin() = default; +bool ElectronDesktopWindowTreeHostWin::ShouldUpdateWindowTransparency() const { + // If transparency is updated for an opaque window before widget init is + // completed, the window flickers white before the background color is applied + // and we don't want that. We do, however, want translucent windows to be + // properly transparent, so ensure it gets updated in that case. + if (!widget_init_done_ && !native_window_view_->IsTranslucent()) + return false; + return views::DesktopWindowTreeHostWin::ShouldUpdateWindowTransparency(); +} + +void ElectronDesktopWindowTreeHostWin::OnWidgetInitDone() { + widget_init_done_ = true; +} + bool ElectronDesktopWindowTreeHostWin::PreHandleMSG(UINT message, WPARAM w_param, LPARAM l_param, diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.h b/shell/browser/ui/win/electron_desktop_window_tree_host_win.h index acfbfda8be348..4776d66593067 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.h +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.h @@ -31,6 +31,8 @@ class ElectronDesktopWindowTreeHostWin : public views::DesktopWindowTreeHostWin, protected: // views::DesktopWindowTreeHostWin: + void OnWidgetInitDone() override; + bool ShouldUpdateWindowTransparency() const override; bool PreHandleMSG(UINT message, WPARAM w_param, LPARAM l_param, @@ -51,6 +53,7 @@ class ElectronDesktopWindowTreeHostWin : public views::DesktopWindowTreeHostWin, private: raw_ptr native_window_view_; // weak ref std::optional force_should_paint_as_active_; + bool widget_init_done_ = false; }; } // namespace electron From 8de0bb5bc33a557caffa16f7a6f56d3597108113 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 14 May 2025 10:07:45 -0400 Subject: [PATCH 039/186] chore: bump chromium to 138.0.7175.0 (37-x-y) (#47078) * chore: bump chromium in DEPS to 138.0.7166.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: bump chromium in DEPS to 138.0.7166.2 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6508373: Add WebContents, Tab getters for future Clank navigation capture rework https://chromium-review.googlesource.com/c/chromium/src/+/6508373 Co-authored-by: Shelley Vohr * 6470924: Introduce auto-populated Search Engine icons. https://chromium-review.googlesource.com/c/chromium/src/+/6470924 Co-authored-by: Shelley Vohr * 6502977: Force same tab navigation while actor coordinator is acting on a tab https://chromium-review.googlesource.com/c/chromium/src/+/6502977 Co-authored-by: Shelley Vohr * chore: bump chromium in DEPS to 138.0.7168.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: update patches Co-authored-by: John Kleinschmidt * fix grit patch Co-authored-by: Shelley Vohr * chore: bump Chromium to 138.0.7169.2 Co-authored-by: Shelley Vohr * fixup! 6508373: Add WebContents, Tab getters for future Clank navigation capture rework Co-authored-by: Shelley Vohr * 6493688: NavigationThrottleRunner2: void CreateThrottlesForNavigation https://chromium-review.googlesource.com/c/chromium/src/+/6493688 Co-authored-by: Shelley Vohr * 6488755: Reland "WebSQL: Remove WebPreference" https://chromium-review.googlesource.com/c/chromium/src/+/6488755 Co-authored-by: Shelley Vohr * 6428707: FSA: Only normalize the hardcoded rules once during initialization https://chromium-review.googlesource.com/c/chromium/src/+/6428707 Co-authored-by: Shelley Vohr * chore: fixup patch indices Co-authored-by: Shelley Vohr * chore: bump chromium in DEPS to 138.0.7170.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6514121: Remove origin calculation debug info and related methods https://chromium-review.googlesource.com/c/chromium/src/+/6514121 Co-authored-by: Shelley Vohr * chore: bump chromium in DEPS to 138.0.7172.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: bump chromium in DEPS to 138.0.7173.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: bump chromium in DEPS to 138.0.7175.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * fixup! 6514121: Remove origin calculation debug info and related methods Refs https://chromium-review.googlesource.com/c/chromium/src/+/6514121 Co-authored-by: David Sanders * 6531585: Don't retry LayerTreeSink creation on the high priority queue Refs https://chromium-review.googlesource.com/c/chromium/src/+/6531585 Co-authored-by: David Sanders * 6512253: Modernize base::apple's base bundle ID Refs https://chromium-review.googlesource.com/c/chromium/src/+/6512253 Co-authored-by: David Sanders * fixup! 6428707: FSA: Only normalize the hardcoded rules once during initialization Refs https://chromium-review.googlesource.com/c/chromium/src/+/6428707 Co-authored-by: David Sanders * fixup! 6508373: Add WebContents, Tab getters for future Clank navigation capture rework Refs https://chromium-review.googlesource.com/c/chromium/src/+/6508373 Co-authored-by: David Sanders * chore: update patches Co-authored-by: David Sanders * chore: update patches --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr Co-authored-by: John Kleinschmidt Co-authored-by: David Sanders --- DEPS | 2 +- patches/chromium/.patches | 3 - ...client_precreatemessageloop_callback.patch | 6 +- .../add_didinstallconditionalfeatures.patch | 10 +- ...adjust_accessibility_ui_for_electron.patch | 2 +- ..._scheduler_throttling_per_renderview.patch | 26 +- ..._windows_to_have_different_web_prefs.patch | 16 +- ...leges_in_unsandboxed_child_processes.patch | 2 +- patches/chromium/blink_local_frame.patch | 6 +- .../build_add_electron_tracing_category.patch | 4 +- ..._depend_on_packed_resource_integrity.patch | 16 +- .../build_libc_as_static_library.patch | 30 +- patches/chromium/can_create_window.patch | 46 +- ...fy_chromium_handling_of_mouse_events.patch | 8 +- .../chromium/chore_partial_revert_of.patch | 4 +- ...screationoverridden_with_full_params.patch | 138 ++-- ...e_reference_to_chrome_browser_themes.patch | 2 +- patches/chromium/desktop_media_list.patch | 2 +- patches/chromium/disable_hidden.patch | 4 +- .../chromium/enable_reset_aspect_ratio.patch | 2 +- .../extend_apply_webpreferences.patch | 2 +- ...e_launch_options_for_service_process.patch | 10 +- ...moothing_css_rule_and_blink_painting.patch | 12 +- ...etdefersloading_on_webdocumentloader.patch | 6 +- ..._raw_response_headers_from_urlloader.patch | 2 +- ...ivate_background_material_on_windows.patch | 6 +- .../fix_aspect_ratio_with_max_size.patch | 4 +- ...ding_non-standard_schemes_in_iframes.patch | 24 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ..._properly_honor_printing_page_ranges.patch | 4 +- ...x_remove_caption-removing_style_call.patch | 4 +- ...from_localframe_requestexecutescript.patch | 16 +- ...t_menu_item_when_opened_via_keyboard.patch | 4 +- ...x_software_compositing_infinite_loop.patch | 31 - ...ated_generic_capturer_when_available.patch | 6 +- patches/chromium/frame_host_manager.patch | 8 +- .../chromium/gritsettings_resource_ids.patch | 10 +- ...sync_with_host_os_mac_on_linux_in_ci.patch | 2 +- ...ontentsviewchildframe_notimplemented.patch | 50 -- .../chromium/make_gtk_getlibgtk_public.patch | 6 +- ..._avoid_private_macos_api_usage.patch.patch | 28 +- .../chromium/notification_provenance.patch | 2 +- ...eated_to_allow_for_browser_initiated.patch | 26 - patches/chromium/printing.patch | 4 +- ...r_changes_to_the_webcontentsobserver.patch | 8 +- ..._expose_file_system_access_blocklist.patch | 642 ++++++++++++------ ...efactor_unfilter_unresponsive_events.patch | 4 +- patches/chromium/resource_file_conflict.patch | 6 +- ...ean_up_stale_macwebcontentsocclusion.patch | 8 +- patches/chromium/scroll_bounce_flag.patch | 4 +- .../support_mixed_sandbox_with_zygote.patch | 2 +- patches/chromium/web_contents.patch | 8 +- patches/chromium/webview_fullscreen.patch | 10 +- .../worker_context_will_destroy.patch | 4 +- ...feat_add_hook_to_notify_script_ready.patch | 4 +- ...i_to_allow_electron_to_set_dock_side.patch | 2 +- shell/app/electron_main_delegate_mac.mm | 2 +- .../browser/api/electron_api_web_contents.cc | 1 + shell/browser/api/electron_api_web_contents.h | 1 + shell/browser/electron_browser_client.cc | 18 +- shell/browser/electron_browser_client.h | 3 +- .../file_system_access_permission_context.cc | 148 ++-- .../file_system_access_permission_context.h | 24 +- 63 files changed, 818 insertions(+), 681 deletions(-) delete mode 100644 patches/chromium/fix_software_compositing_infinite_loop.patch delete mode 100644 patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch delete mode 100644 patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch diff --git a/DEPS b/DEPS index 194612f5d50af..13a5facaa339b 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7165.0', + '138.0.7175.0', 'node_version': 'v22.15.0', 'nan_version': diff --git a/patches/chromium/.patches b/patches/chromium/.patches index e6980db620ef5..1faeae3c941f5 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -120,7 +120,6 @@ build_run_reclient_cfg_generator_after_chrome.patch fix_getcursorscreenpoint_wrongly_returns_0_0.patch fix_add_support_for_skipping_first_2_no-op_refreshes_in_thumb_cap.patch refactor_expose_file_system_access_blocklist.patch -partially_revert_is_newly_created_to_allow_for_browser_initiated.patch feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch fix_font_face_resolution_when_renderer_is_blocked.patch feat_enable_passing_exit_code_on_service_process_crash.patch @@ -130,7 +129,6 @@ build_allow_electron_mojom_interfaces_to_depend_on_blink.patch osr_shared_texture_remove_keyed_mutex_on_win_dxgi.patch feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch chore_partial_revert_of.patch -fix_software_compositing_infinite_loop.patch fix_adjust_headless_mode_handling_in_native_widget.patch refactor_unfilter_unresponsive_events.patch build_disable_thin_lto_mac.patch @@ -146,4 +144,3 @@ fix_enable_wrap_iter_in_string_view_and_array.patch fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch -make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch diff --git a/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch b/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch index 0f9ffc477fbe0..6ce5197ed3607 100644 --- a/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch +++ b/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch @@ -10,10 +10,10 @@ Allows Electron to restore WER when ELECTRON_DEFAULT_ERROR_MODE is set. This should be upstreamed. diff --git a/content/gpu/gpu_main.cc b/content/gpu/gpu_main.cc -index cadb96febde3fb3fe90929873b1db452a6d8fb8f..09f5504127b5a5ec3d0d69d9eb6d0cd93e0e75cd 100644 +index 73be6273b320574c22fd12e07b93dc3cffaa1be9..58a34cc5b583a7111decf14b755afbb82ba94765 100644 --- a/content/gpu/gpu_main.cc +++ b/content/gpu/gpu_main.cc -@@ -254,6 +254,10 @@ int GpuMain(MainFunctionParams parameters) { +@@ -268,6 +268,10 @@ int GpuMain(MainFunctionParams parameters) { // to the GpuProcessHost once the GpuServiceImpl has started. viz::GpuServiceImpl::InstallPreInitializeLogHandler(); @@ -24,7 +24,7 @@ index cadb96febde3fb3fe90929873b1db452a6d8fb8f..09f5504127b5a5ec3d0d69d9eb6d0cd9 // We are experiencing what appear to be memory-stomp issues in the GPU // process. These issues seem to be impacting the task executor and listeners // registered to it. Create the task executor on the heap to guard against -@@ -363,7 +367,6 @@ int GpuMain(MainFunctionParams parameters) { +@@ -377,7 +381,6 @@ int GpuMain(MainFunctionParams parameters) { #endif const bool dead_on_arrival = !init_success; diff --git a/patches/chromium/add_didinstallconditionalfeatures.patch b/patches/chromium/add_didinstallconditionalfeatures.patch index dd021e0e177e4..33795783b824d 100644 --- a/patches/chromium/add_didinstallconditionalfeatures.patch +++ b/patches/chromium/add_didinstallconditionalfeatures.patch @@ -23,10 +23,10 @@ index db655a7b52eacb74f2a8637db36abd87f6b86792..8014cb08e2090a12ea8b9e92cb8f93c9 int32_t world_id) {} virtual void DidClearWindowObject() {} diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index 6c569b4a0f4ddea5d071753bb4a72002ba174171..d1085ca830b5a98f1550e6c01728cd760df6141a 100644 +index 3fa43adedd6ff0258edd195bde1e68977cff3a7c..7fe443aad2ad6207aa46daddea46baa3eb998bc3 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc -@@ -4807,6 +4807,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, +@@ -4808,6 +4808,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, observer.DidCreateScriptContext(context, world_id); } @@ -40,10 +40,10 @@ index 6c569b4a0f4ddea5d071753bb4a72002ba174171..d1085ca830b5a98f1550e6c01728cd76 int world_id) { for (auto& observer : observers_) diff --git a/content/renderer/render_frame_impl.h b/content/renderer/render_frame_impl.h -index a7383e4a5ccb8ca1de10bc3efb3043f1dbbf2f6f..41075015aa2dd347c9847072dd76f9cea9ad2d94 100644 +index 6a9e696762cc0276f10971933363257591d12bfe..3cd045ed24c47465788c40cc68b050be11ed6f97 100644 --- a/content/renderer/render_frame_impl.h +++ b/content/renderer/render_frame_impl.h -@@ -652,6 +652,8 @@ class CONTENT_EXPORT RenderFrameImpl +@@ -653,6 +653,8 @@ class CONTENT_EXPORT RenderFrameImpl void DidObserveLayoutShift(double score, bool after_input_or_scroll) override; void DidCreateScriptContext(v8::Local context, int world_id) override; @@ -92,7 +92,7 @@ index e52a535450964b0938b66f7506225fda0cde04a2..841e9b36df4c32040d2b3c71514266fc int32_t world_id) = 0; virtual bool AllowScriptExtensions() = 0; diff --git a/third_party/blink/renderer/core/frame/local_frame_client_impl.cc b/third_party/blink/renderer/core/frame/local_frame_client_impl.cc -index 479dd8a7294ca6f0abb72350cc1a6c61e09c7c27..45226050aea1036f2c3a2fc15cabee893d12b1a7 100644 +index 96fc9e0646f943e86e927de2686a8da94625ae6c..30e9721cccd285a347f35e2d7a539547ac41247c 100644 --- a/third_party/blink/renderer/core/frame/local_frame_client_impl.cc +++ b/third_party/blink/renderer/core/frame/local_frame_client_impl.cc @@ -295,6 +295,13 @@ void LocalFrameClientImpl::DidCreateScriptContext( diff --git a/patches/chromium/adjust_accessibility_ui_for_electron.patch b/patches/chromium/adjust_accessibility_ui_for_electron.patch index 4f89d368bc66f..f6f4c861ccb00 100644 --- a/patches/chromium/adjust_accessibility_ui_for_electron.patch +++ b/patches/chromium/adjust_accessibility_ui_for_electron.patch @@ -10,7 +10,7 @@ usage of BrowserList and Browser as we subclass related methods and use our WindowList. diff --git a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc -index ce3840087d3becac116e57ed8c690b73e360f95f..a929b2d4f6c4b34f9e278aada9f8f793477c6d19 100644 +index d7a9cff6401f0953297acd18708ec2952f60407f..b4777ce0bcda2bdb9645a4ed86040f62ce4027eb 100644 --- a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc +++ b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc @@ -48,6 +48,7 @@ diff --git a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch index b63183201c679..748ee8a24a67e 100644 --- a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch +++ b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch @@ -6,10 +6,10 @@ Subject: allow disabling blink scheduler throttling per RenderView This allows us to disable throttling for hidden windows. diff --git a/content/browser/renderer_host/navigation_controller_impl_unittest.cc b/content/browser/renderer_host/navigation_controller_impl_unittest.cc -index 495daa75895a4545287da53f305e6cd348db7183..fd749047a7d505d02c4e8e4631da823275c27822 100644 +index b9e7ef002a8d7842b4e97dbcaa59aa289ba652a1..81bd39f47d8411da53824d47e053b39f8fa24721 100644 --- a/content/browser/renderer_host/navigation_controller_impl_unittest.cc +++ b/content/browser/renderer_host/navigation_controller_impl_unittest.cc -@@ -166,6 +166,12 @@ class MockPageBroadcast : public blink::mojom::PageBroadcast { +@@ -167,6 +167,12 @@ class MockPageBroadcast : public blink::mojom::PageBroadcast { (network::mojom::AttributionSupport support), (override)); @@ -23,10 +23,10 @@ index 495daa75895a4545287da53f305e6cd348db7183..fd749047a7d505d02c4e8e4631da8232 return receiver_.BindNewEndpointAndPassDedicatedRemote(); } diff --git a/content/browser/renderer_host/render_view_host_impl.cc b/content/browser/renderer_host/render_view_host_impl.cc -index 4a70fd017915c1d631a47096c735d9c4b6e2c2af..0b2eb574f86e4c192d7cd986abea72e85163a7bd 100644 +index 6e6d9a3ea76b3b578c452050afde6b89468c8841..f3abefb6e4a0e11ae2cdc12558af844c4153a103 100644 --- a/content/browser/renderer_host/render_view_host_impl.cc +++ b/content/browser/renderer_host/render_view_host_impl.cc -@@ -759,6 +759,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { +@@ -761,6 +761,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { GetWidget()->GetAssociatedFrameWidget()->SetBackgroundOpaque(opaque); } @@ -39,7 +39,7 @@ index 4a70fd017915c1d631a47096c735d9c4b6e2c2af..0b2eb574f86e4c192d7cd986abea72e8 return is_active(); } diff --git a/content/browser/renderer_host/render_view_host_impl.h b/content/browser/renderer_host/render_view_host_impl.h -index 56e52f079d1ad7c7a22764b976f0c8b2cc48dff2..1231fe522ad103e94d3c30ad7d5e5d23df9b3554 100644 +index f9dc4c4aa4e3c65124c975f5bc5ea255fbb43cfb..1e7151d8d45bfc5ef01b79eee9d80df3df5c856c 100644 --- a/content/browser/renderer_host/render_view_host_impl.h +++ b/content/browser/renderer_host/render_view_host_impl.h @@ -135,6 +135,7 @@ class CONTENT_EXPORT RenderViewHostImpl @@ -80,10 +80,10 @@ index 20ca763ff7f55e8176b77349b41917b11e051ae6..a50c122064b5f0092f57e3d508fb1938 // This interface should only be implemented inside content. friend class RenderViewHostImpl; diff --git a/content/test/test_page_broadcast.h b/content/test/test_page_broadcast.h -index 58895f0ed0e18703c45eee37210003150c24550a..6a138d4cd852f6f2b9fd2294062c9b6ab4f08855 100644 +index 3f4fdfcdf2f701a394e182bd61baf226338ef7f8..f2faa1225e8ca6abb190e6f7a0775545fa3f785d 100644 --- a/content/test/test_page_broadcast.h +++ b/content/test/test_page_broadcast.h -@@ -50,6 +50,7 @@ class TestPageBroadcast : public blink::mojom::PageBroadcast { +@@ -51,6 +51,7 @@ class TestPageBroadcast : public blink::mojom::PageBroadcast { network::mojom::AttributionSupport support) override; void UpdateColorProviders( const blink::ColorProviderColorMaps& color_provider_colors) override; @@ -92,10 +92,10 @@ index 58895f0ed0e18703c45eee37210003150c24550a..6a138d4cd852f6f2b9fd2294062c9b6a mojo::AssociatedReceiver receiver_; }; diff --git a/third_party/blink/public/mojom/page/page.mojom b/third_party/blink/public/mojom/page/page.mojom -index 4614f84c3d8f709fb2a12d662e5a13dc12c59e8a..76444fcbf68b91ad64c46debc565ffc35a3e2c68 100644 +index b6a4e3609af1f090f1f845d77fa0589e5b178d8a..989b2cf76ce88614b57e75ce2fcace101225f43e 100644 --- a/third_party/blink/public/mojom/page/page.mojom +++ b/third_party/blink/public/mojom/page/page.mojom -@@ -172,4 +172,7 @@ interface PageBroadcast { +@@ -175,4 +175,7 @@ interface PageBroadcast { // 2. The ColorProvider associated with the WebContents changes as a result // of theme changes. UpdateColorProviders(ColorProviderColorMaps color_provider_colors); @@ -116,7 +116,7 @@ index 7c1eb9baabfb9e0f3645421b5cbe467862252638..00d2cd41d795cb550e16fb80944b2382 // Visibility ----------------------------------------------------------- diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index 6b056decc43e9ba9e7970a7d8fefaed6a86d9a2d..0b2956425d2feb84f1d0db7be4f3d4b0875b1d10 100644 +index 73f25b18478ae93dbf7a5f225adce40da89681c9..3c3c0247ca56ba99b48583a4218712f172458845 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -2466,6 +2466,10 @@ void WebViewImpl::SetPageLifecycleStateInternal( @@ -155,10 +155,10 @@ index 6b056decc43e9ba9e7970a7d8fefaed6a86d9a2d..0b2956425d2feb84f1d0db7be4f3d4b0 // Do not throttle if the page should be painting. bool is_visible = diff --git a/third_party/blink/renderer/core/exported/web_view_impl.h b/third_party/blink/renderer/core/exported/web_view_impl.h -index aff99e7e1feb7addcdf631b7e3ac4209da6b502d..b759aca8d1e61c19904db146840e6f0c57a3d86a 100644 +index eaa593b41ec2e9a12fca53eb9925e6b868a4d9f1..8ce3ea0e5d6e5bdff982b956de305047347b4385 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.h +++ b/third_party/blink/renderer/core/exported/web_view_impl.h -@@ -447,6 +447,7 @@ class CORE_EXPORT WebViewImpl final : public WebView, +@@ -448,6 +448,7 @@ class CORE_EXPORT WebViewImpl final : public WebView, LocalDOMWindow* PagePopupWindow() const; PageScheduler* Scheduler() const override; @@ -166,7 +166,7 @@ index aff99e7e1feb7addcdf631b7e3ac4209da6b502d..b759aca8d1e61c19904db146840e6f0c void SetVisibilityState(mojom::blink::PageVisibilityState visibility_state, bool is_initial_state) override; mojom::blink::PageVisibilityState GetVisibilityState() override; -@@ -935,6 +936,8 @@ class CORE_EXPORT WebViewImpl final : public WebView, +@@ -936,6 +937,8 @@ class CORE_EXPORT WebViewImpl final : public WebView, // If true, we send IPC messages when |preferred_size_| changes. bool send_preferred_size_changes_ = false; diff --git a/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch b/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch index b34d863af46d7..426dc24c4eb0a 100644 --- a/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch +++ b/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch @@ -8,10 +8,10 @@ WebPreferences of in-process child windows, rather than relying on process-level command line switches, as before. diff --git a/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc b/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc -index 009f3563df63bc2ba2eadeecaea4f328d6a409ec..769ff8faaddf543fba1a41aff939f23741127247 100644 +index 9fe216ae76191985751c5aff735cb38ba747a5cb..274dbe4fe45f5ca03e4f93fa1ef94f22ca3559ed 100644 --- a/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc +++ b/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc -@@ -150,6 +150,19 @@ bool StructTraitsv8_cache_options = data.v8_cache_options(); out->record_whole_document = data.record_whole_document(); out->stylus_handwriting_enabled = data.stylus_handwriting_enabled(); @@ -32,7 +32,7 @@ index 009f3563df63bc2ba2eadeecaea4f328d6a409ec..769ff8faaddf543fba1a41aff939f237 out->accelerated_video_decode_enabled = data.accelerated_video_decode_enabled(); diff --git a/third_party/blink/public/common/web_preferences/web_preferences.h b/third_party/blink/public/common/web_preferences/web_preferences.h -index 85f312a9ea1eca0ff7ba4c679fabb3156aabbc0b..a9dc007a93003610d68e3118b4a47a86d4e16f6e 100644 +index 2d9ef567d7aba3d78ecb0637fc7a31cbaaba564b..9c6c5e3b2668bdfa3ec1f5f0482bc1294bfed9b0 100644 --- a/third_party/blink/public/common/web_preferences/web_preferences.h +++ b/third_party/blink/public/common/web_preferences/web_preferences.h @@ -9,6 +9,7 @@ @@ -43,7 +43,7 @@ index 85f312a9ea1eca0ff7ba4c679fabb3156aabbc0b..a9dc007a93003610d68e3118b4a47a86 #include "build/build_config.h" #include "net/nqe/effective_connection_type.h" #include "third_party/blink/public/common/common_export.h" -@@ -451,6 +452,20 @@ struct BLINK_COMMON_EXPORT WebPreferences { +@@ -450,6 +451,20 @@ struct BLINK_COMMON_EXPORT WebPreferences { // WebView and by `kWebPayments` feature flag everywhere. bool payment_request_enabled = false; @@ -65,7 +65,7 @@ index 85f312a9ea1eca0ff7ba4c679fabb3156aabbc0b..a9dc007a93003610d68e3118b4a47a86 // chrome, except for the cases where it would require lots of extra work for // the embedder to use the same default value. diff --git a/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h b/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h -index 1173ace39b6256edc188a4c6649e7cd4c4484899..c1d53122af52f7785a016f6fc62d9aa684a4be8c 100644 +index 86e4152b85d85ed3c620458567509e0eaa2ad5d8..6f39bf14c42278dc8ada95902868608bd6a6f171 100644 --- a/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h +++ b/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h @@ -8,6 +8,7 @@ @@ -76,7 +76,7 @@ index 1173ace39b6256edc188a4c6649e7cd4c4484899..c1d53122af52f7785a016f6fc62d9aa6 #include "mojo/public/cpp/bindings/struct_traits.h" #include "net/nqe/effective_connection_type.h" #include "third_party/blink/public/common/common_export.h" -@@ -442,6 +443,52 @@ struct BLINK_COMMON_EXPORT StructTraitsDetach(FrameDetachType::kRemove); -@@ -165,6 +157,14 @@ bool Frame::Detach(FrameDetachType type) { +@@ -166,6 +158,14 @@ bool Frame::Detach(FrameDetachType type) { GetWindowProxyManager()->ClearForSwap(); } @@ -49,7 +49,7 @@ index 2072f6b14289b1f3a76dbccc98f29aa178c1c35c..d7017437a7e7e6ac130677e52731d048 // its owning reference back to our owning LocalFrame. client_->Detached(type); diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index f075d02c0695ca5fe06152295179b6ec76e3597a..e5d629937aaa175d11731bc1048a1b459927e93a 100644 +index 9cb436569b94eec3e72ef3d1c018127b65a04314..e567f331968b1b1b9d6b85e31397b6a4f7ea7a84 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc @@ -727,10 +727,6 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { diff --git a/patches/chromium/build_add_electron_tracing_category.patch b/patches/chromium/build_add_electron_tracing_category.patch index 3799123b2b0a6..c8b228545b265 100644 --- a/patches/chromium/build_add_electron_tracing_category.patch +++ b/patches/chromium/build_add_electron_tracing_category.patch @@ -8,7 +8,7 @@ categories in use are known / declared. This patch is required for us to introduce a new Electron category for Electron-specific tracing. diff --git a/base/trace_event/builtin_categories.h b/base/trace_event/builtin_categories.h -index e9f891a025771899ffc888ea0095200342e48558..39d6f580c0cb5a0de41f32e9d7e103e05cefd0f0 100644 +index d4c70f285fa6798798558974d7d79604dd388909..31f396bb437b7089930c05e6b1067bc156155be1 100644 --- a/base/trace_event/builtin_categories.h +++ b/base/trace_event/builtin_categories.h @@ -102,6 +102,7 @@ PERFETTO_DEFINE_CATEGORIES_IN_NAMESPACE_WITH_ATTRS( @@ -16,6 +16,6 @@ index e9f891a025771899ffc888ea0095200342e48558..39d6f580c0cb5a0de41f32e9d7e103e0 perfetto::Category("drmcursor"), perfetto::Category("dwrite"), + perfetto::Category("electron"), - perfetto::Category("evdev"), + perfetto::Category("evdev").SetTags("input"), perfetto::Category("event"), perfetto::Category("exo"), diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index 9964154875dab..984e9b037c4f9 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -11,10 +11,10 @@ if we ever align our .pak file generation with Chrome we can remove this patch. diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b47749874 100644 +index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff62717ba00 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn -@@ -200,11 +200,16 @@ if (!is_android && !is_mac) { +@@ -197,11 +197,16 @@ if (!is_android && !is_mac) { "common/crash_keys.h", ] @@ -33,10 +33,10 @@ index 4b3f01018a9dea91b46b5917e099f272582991b2..8250f2e447ff19829cfae3f00b3df70b "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index 73f7fc927f1c14c038e0ca91066dbb4e9bd8be62..d7d46198d11b7454d07188641f46617c924d63b1 100644 +index e44a7794f3a1f019835fb4ecbf5b62e1bd17c53d..1c6bda2d5e4f4a5282792260efbf2fa49a37823e 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4633,7 +4633,7 @@ static_library("browser") { +@@ -4650,7 +4650,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,10 +46,10 @@ index 73f7fc927f1c14c038e0ca91066dbb4e9bd8be62..d7d46198d11b7454d07188641f46617c # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 4866689b354bc9d963638edabf1eb02d16ba984c..c5b383f2c78592a57f0d138538733937b8e76ecd 100644 +index e62e29e8a16572f8fcaf0efe977163b17bb5bf27..5444ca916f559050a47f5caa90a8fb7b8f6f185f 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7210,9 +7210,12 @@ test("unit_tests") { +@@ -7196,9 +7196,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index 4866689b354bc9d963638edabf1eb02d16ba984c..c5b383f2c78592a57f0d138538733937 "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8170,6 +8173,10 @@ test("unit_tests") { +@@ -8168,6 +8171,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index 4866689b354bc9d963638edabf1eb02d16ba984c..c5b383f2c78592a57f0d138538733937 sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8225,7 +8232,6 @@ test("unit_tests") { +@@ -8223,7 +8230,6 @@ test("unit_tests") { # Non-android deps for "unit_tests" target. deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/build_libc_as_static_library.patch b/patches/chromium/build_libc_as_static_library.patch index fe045a0b51562..1b7d654c50d52 100644 --- a/patches/chromium/build_libc_as_static_library.patch +++ b/patches/chromium/build_libc_as_static_library.patch @@ -7,23 +7,10 @@ Build libc++ as static library to compile and pass nan tests diff --git a/buildtools/third_party/libc++/BUILD.gn b/buildtools/third_party/libc++/BUILD.gn -index f411f2d51a397db52ba28eb7ed430f6f16c5396d..219e99e56cbf35aac8e18cff96601143f9f44ebf 100644 +index 2b4c153a67fda5effaac8d2932a985d87539fe69..c0c310ecbf74b8c1649bcd23ebe1c142c088fc9f 100644 --- a/buildtools/third_party/libc++/BUILD.gn +++ b/buildtools/third_party/libc++/BUILD.gn -@@ -295,7 +295,11 @@ libcxx_modules("std_wctype_h") { - if (libcxx_is_shared) { - _libcxx_target_type = "shared_library" - } else { -- _libcxx_target_type = "source_set" -+ if (is_win) { -+ _libcxx_target_type = "source_set" -+ } else { -+ _libcxx_target_type = "static_library" -+ } - } - - target(_libcxx_target_type, "libc++") { -@@ -304,6 +308,7 @@ target(_libcxx_target_type, "libc++") { +@@ -298,6 +298,7 @@ target(libcxx_target_type, "libc++") { # need to explicitly depend on libc++. visibility = [ "//build/config:common_deps", @@ -31,16 +18,3 @@ index f411f2d51a397db52ba28eb7ed430f6f16c5396d..219e99e56cbf35aac8e18cff96601143 "//third_party/catapult/devil:devil", ] if (is_linux) { -diff --git a/buildtools/third_party/libc++abi/BUILD.gn b/buildtools/third_party/libc++abi/BUILD.gn -index 331ea447ea15e9f439396d4c7d41832de60adf4a..b96a994c43ac2ed0b0d5ec599f907ea0b501156e 100644 ---- a/buildtools/third_party/libc++abi/BUILD.gn -+++ b/buildtools/third_party/libc++abi/BUILD.gn -@@ -6,7 +6,7 @@ import("//build/config/android/config.gni") - import("//build/config/c++/c++.gni") - import("//build/config/unwind.gni") - --source_set("libc++abi") { -+static_library("libc++abi") { - if (export_libcxxabi_from_executables) { - visibility = [ "//build/config:executable_deps" ] - } else { diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 6e968d7e6d069..1a08871accff7 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,10 +9,10 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index ddfefbacebd5d89e112a15f29328c9674f7df3ae..ef8a80d2148c0ec0d8a3493ae58a4e723a9601e1 100644 +index c66512a270828be3b436c1e880917f0638771cfd..f4231fa2549083e8132affa6e424ac18f28b4f41 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -9776,6 +9776,7 @@ void RenderFrameHostImpl::CreateNewWindow( +@@ -9703,6 +9703,7 @@ void RenderFrameHostImpl::CreateNewWindow( last_committed_origin_, params->window_container_type, params->target_url, params->referrer.To(), params->frame_name, params->disposition, *params->features, @@ -21,12 +21,12 @@ index ddfefbacebd5d89e112a15f29328c9674f7df3ae..ef8a80d2148c0ec0d8a3493ae58a4e72 &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index cb039c0ac747feefd5e8a13ed03715508ae874d0..b6fc96993cdea489450978495ca4c1f3c58166af 100644 +index c7e153a0ff9de1b1d5ed760099121db6d531589e..e42e462f3c8109444e6dadb0557e38cdd05c362a 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5139,6 +5139,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( - SetPartitionedPopinOpenerOnNewWindowIfNeeded(new_contents_impl, params, - opener); +@@ -5162,6 +5162,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( + // Sets the newly created WebContents WindowOpenDisposition. + new_contents_impl->original_window_open_disposition_ = params.disposition; + if (delegate_) { + delegate_->WebContentsCreatedWithFullParams(this, render_process_id, @@ -37,7 +37,7 @@ index cb039c0ac747feefd5e8a13ed03715508ae874d0..b6fc96993cdea489450978495ca4c1f3 // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5180,12 +5186,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5203,12 +5209,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -51,10 +51,10 @@ index cb039c0ac747feefd5e8a13ed03715508ae874d0..b6fc96993cdea489450978495ca4c1f3 new_contents_impl, opener, params.target_url, params.referrer.To(), params.disposition, diff --git a/content/common/frame.mojom b/content/common/frame.mojom -index d1e8581724adeca8b6776ded7e7c7e921f68905c..6c4abeaf847328f73b4e53a552a038b29421d9aa 100644 +index 09f1899c9b044a05b2e40c291f17fdf1f9f2fcac..89643bf7059d4fc0d6de6116ffe0fdac883b3fc9 100644 --- a/content/common/frame.mojom +++ b/content/common/frame.mojom -@@ -645,6 +645,10 @@ struct CreateNewWindowParams { +@@ -653,6 +653,10 @@ struct CreateNewWindowParams { pending_associated_remote widget; pending_associated_receiver frame_widget_host; pending_associated_remote frame_widget; @@ -66,7 +66,7 @@ index d1e8581724adeca8b6776ded7e7c7e921f68905c..6c4abeaf847328f73b4e53a552a038b2 // Operation result when the renderer asks the browser to create a new window. diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc -index 1f5468c6f81db64929fbfc6715a586c69a29afc9..4c37155c240c3ef2c54523cfe12e0c0054a6e603 100644 +index 4aa669a0f869359e8d8304cab6cca0a89e1e3ff3..e8701e20e5d339edc1d9089d2b236f2cf8fe6c34 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc @@ -828,6 +828,8 @@ bool ContentBrowserClient::CanCreateWindow( @@ -79,10 +79,10 @@ index 1f5468c6f81db64929fbfc6715a586c69a29afc9..4c37155c240c3ef2c54523cfe12e0c00 bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index a0f6c7e63a32d4cfc8a8e25cdbd90f23dbce8f24..4a995e6c35abba567bb8be826effb06ba7e2119a 100644 +index 3e363b85b57478ca7228379ed089746a6eb52f2d..17b11b2a4e70f419721649568179c31228612c73 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h -@@ -199,6 +199,7 @@ class NetworkService; +@@ -200,6 +200,7 @@ class NetworkService; class TrustedURLLoaderHeaderClient; } // namespace mojom struct ResourceRequest; @@ -90,7 +90,7 @@ index a0f6c7e63a32d4cfc8a8e25cdbd90f23dbce8f24..4a995e6c35abba567bb8be826effb06b } // namespace network namespace sandbox { -@@ -1385,6 +1386,8 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -1386,6 +1387,8 @@ class CONTENT_EXPORT ContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -100,7 +100,7 @@ index a0f6c7e63a32d4cfc8a8e25cdbd90f23dbce8f24..4a995e6c35abba567bb8be826effb06b bool opener_suppressed, bool* no_javascript_access); diff --git a/content/public/browser/web_contents_delegate.cc b/content/public/browser/web_contents_delegate.cc -index b390356721fa226c348923f33601c4a1a2d9702d..97a3ea6f292563a41fd41f812ac72526a96d8471 100644 +index aabcebe8e49f42e3c0680d8d20f64ed6a48a7266..8c1d83692daccfbdda90f292b5a3fb9a8f1b118f 100644 --- a/content/public/browser/web_contents_delegate.cc +++ b/content/public/browser/web_contents_delegate.cc @@ -32,6 +32,17 @@ namespace content { @@ -122,7 +122,7 @@ index b390356721fa226c348923f33601c4a1a2d9702d..97a3ea6f292563a41fd41f812ac72526 WebContents* source, const OpenURLParams& params, diff --git a/content/public/browser/web_contents_delegate.h b/content/public/browser/web_contents_delegate.h -index da319cb20733150366d85bee95609f0f2d9def7f..8a18958035cc1dd26be558349f64f7727570c4ba 100644 +index a9be46fcd13f397c34a2cf3e7444efad81a5e19b..c4cee108b0caac7d6a2a9115586882dd32bab714 100644 --- a/content/public/browser/web_contents_delegate.h +++ b/content/public/browser/web_contents_delegate.h @@ -18,6 +18,7 @@ @@ -133,7 +133,7 @@ index da319cb20733150366d85bee95609f0f2d9def7f..8a18958035cc1dd26be558349f64f772 #include "content/public/browser/eye_dropper.h" #include "content/public/browser/fullscreen_types.h" #include "content/public/browser/invalidate_type.h" -@@ -376,6 +377,13 @@ class CONTENT_EXPORT WebContentsDelegate { +@@ -380,6 +381,13 @@ class CONTENT_EXPORT WebContentsDelegate { const StoragePartitionConfig& partition_config, SessionStorageNamespace* session_storage_namespace); @@ -148,10 +148,10 @@ index da319cb20733150366d85bee95609f0f2d9def7f..8a18958035cc1dd26be558349f64f772 // typically happens when popups are created. virtual void WebContentsCreated(WebContents* source_contents, diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index 4d40964aa6bb93759dd73f63e48a36c66b50a61d..6c569b4a0f4ddea5d071753bb4a72002ba174171 100644 +index b6da726a70555c2074077a2105b078e1850824d9..3fa43adedd6ff0258edd195bde1e68977cff3a7c 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc -@@ -6938,6 +6938,10 @@ WebView* RenderFrameImpl::CreateNewWindow( +@@ -6937,6 +6937,10 @@ WebView* RenderFrameImpl::CreateNewWindow( request.HasUserGesture(), GetWebFrame()->IsAdFrame(), GetWebFrame()->IsAdScriptInStack()); @@ -163,10 +163,10 @@ index 4d40964aa6bb93759dd73f63e48a36c66b50a61d..6c569b4a0f4ddea5d071753bb4a72002 // moved on send. bool is_background_tab = diff --git a/content/web_test/browser/web_test_content_browser_client.cc b/content/web_test/browser/web_test_content_browser_client.cc -index e5f7596c1b3e525e1d64efbd6b7e0703b980dac9..0b4523200651c1edfd7678b177a24b7e64de6ddf 100644 +index 7f265db63f3fa34ab568e30e356db3cb259e7067..b55188e4b75913a531c2def09343b9ed3d589940 100644 --- a/content/web_test/browser/web_test_content_browser_client.cc +++ b/content/web_test/browser/web_test_content_browser_client.cc -@@ -538,6 +538,8 @@ bool WebTestContentBrowserClient::CanCreateWindow( +@@ -531,6 +531,8 @@ bool WebTestContentBrowserClient::CanCreateWindow( const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -176,10 +176,10 @@ index e5f7596c1b3e525e1d64efbd6b7e0703b980dac9..0b4523200651c1edfd7678b177a24b7e bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/web_test/browser/web_test_content_browser_client.h b/content/web_test/browser/web_test_content_browser_client.h -index e4eaba65b25262ce5ed27d78da13a260ec57f6db..ddd3be9aa7aac43140a1e664eefce7ac195ba119 100644 +index b50d5628cfe6dc3009d889b6a8c4a0925d19592b..43d67de5ef7552bec5ced1496318724c01a806ce 100644 --- a/content/web_test/browser/web_test_content_browser_client.h +++ b/content/web_test/browser/web_test_content_browser_client.h -@@ -95,6 +95,8 @@ class WebTestContentBrowserClient : public ShellContentBrowserClient { +@@ -94,6 +94,8 @@ class WebTestContentBrowserClient : public ShellContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -210,7 +210,7 @@ index 82e9d3dfb5f7da76d89fe15ae61d379fa46e177d..fd035512099a54dff6cc951a2226c23a } // namespace blink diff --git a/third_party/blink/renderer/core/frame/local_dom_window.cc b/third_party/blink/renderer/core/frame/local_dom_window.cc -index de39a688207f81143c59ad54385642389b0fcc4e..93c5b79727674ff1c5344d39fd7bcd07c3101424 100644 +index 6de4ad918b8c1d2a3dfb977ed80ea232dbbee9c1..f983903112efd76c8bd73656a0de5e54026e6d1b 100644 --- a/third_party/blink/renderer/core/frame/local_dom_window.cc +++ b/third_party/blink/renderer/core/frame/local_dom_window.cc @@ -2280,6 +2280,8 @@ DOMWindow* LocalDOMWindow::open(v8::Isolate* isolate, diff --git a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch index a5e8a8d112232..4560eaab58f21 100644 --- a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch +++ b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch @@ -61,10 +61,10 @@ index dab595aacaeca4f6f735fd04004c27a4949278d2..177134d439866db9dbbde657ff358a76 Widget* GetWidget(); const Widget* GetWidget() const; diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 5919efa661c3b1ed210f7a67f85fdd3882011bae..5b17d5bf0b32405ae9515b941a17b68a04a3b317 100644 +index 9747e945b2ebfc113ffd12839c28a98fcccf2872..6f2e2702d3b982fe7e8d258f303c8055d3d37df8 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -3178,15 +3178,19 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3167,15 +3167,19 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, } // We must let Windows handle the caption buttons if it's drawing them, or // they won't work. @@ -86,7 +86,7 @@ index 5919efa661c3b1ed210f7a67f85fdd3882011bae..5b17d5bf0b32405ae9515b941a17b68a return 0; } } -@@ -3209,6 +3213,7 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3198,6 +3202,7 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, // handle alt-space, or in the frame itself. is_right_mouse_pressed_on_caption_ = false; ReleaseCapture(); @@ -94,7 +94,7 @@ index 5919efa661c3b1ed210f7a67f85fdd3882011bae..5b17d5bf0b32405ae9515b941a17b68a // |point| is in window coordinates, but WM_NCHITTEST and TrackPopupMenu() // expect screen coordinates. POINT screen_point = CR_POINT_INITIALIZER_FROM_LPARAM(l_param); -@@ -3216,7 +3221,17 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3205,7 +3210,17 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, w_param = static_cast(SendMessage( hwnd(), WM_NCHITTEST, 0, MAKELPARAM(screen_point.x, screen_point.y))); if (w_param == HTCAPTION || w_param == HTSYSMENU) { diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 5cc2ada8cb2d0..792455130dabf 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index e3085847de7875afa655b3cfa4aa39892be626eb..46fc6d6683c50fb8a340680de2eda340f5be4cca 100644 +index 70b3c4a2da0e1d79a7626e0bb2ed45b8fbbe0024..d0f42ceedfac643443e3c7c5757b831f481a72eb 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5058,7 +5058,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5078,7 +5078,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index fa1e1b29d0c8f..a4666be2625aa 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -7,10 +7,10 @@ Pending upstream patch, this gives us fuller access to the window.open params so that we will be able to decide whether to cancel it or not. diff --git a/chrome/browser/media/offscreen_tab.cc b/chrome/browser/media/offscreen_tab.cc -index bfcdf050e603b953d15a0898200c8f031a1f84c6..b1f163b6da4d2197d404a5a0fbd31a5b346d3d69 100644 +index 7a9effeec99682ef063ebe71f209e6ed9fc4cad4..71ef44be47a8665ee36449a38333ddf9cff33ad4 100644 --- a/chrome/browser/media/offscreen_tab.cc +++ b/chrome/browser/media/offscreen_tab.cc -@@ -286,8 +286,7 @@ bool OffscreenTab::IsWebContentsCreationOverridden( +@@ -287,8 +287,7 @@ bool OffscreenTab::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -21,10 +21,10 @@ index bfcdf050e603b953d15a0898200c8f031a1f84c6..b1f163b6da4d2197d404a5a0fbd31a5b // uses this to spawn new windows/tabs, which is also not allowed for // offscreen tabs. diff --git a/chrome/browser/media/offscreen_tab.h b/chrome/browser/media/offscreen_tab.h -index 2fa0d6e1be27cc429e4a0237b5bfafa7aaa06c56..3decb327b10e3cd3edc1765491a7eb6056be7a51 100644 +index 231e3595f218aeebe28d0b13ce6182e7a4d6f4e1..609bd205d1cd0404cab3471765bef8b0e053d061 100644 --- a/chrome/browser/media/offscreen_tab.h +++ b/chrome/browser/media/offscreen_tab.h -@@ -107,8 +107,7 @@ class OffscreenTab final : public ProfileObserver, +@@ -108,8 +108,7 @@ class OffscreenTab final : public ProfileObserver, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -35,10 +35,10 @@ index 2fa0d6e1be27cc429e4a0237b5bfafa7aaa06c56..3decb327b10e3cd3edc1765491a7eb60 content::RenderFrameHost* requesting_frame, const blink::mojom::FullscreenOptions& options) final; diff --git a/chrome/browser/ui/ash/keyboard/chrome_keyboard_web_contents.cc b/chrome/browser/ui/ash/keyboard/chrome_keyboard_web_contents.cc -index a0c24e09a5dffa8be119309738abe57e82ef76b3..3e362f622b72d7cb97a838e71014b035c47728c0 100644 +index a17c406b59530a8f57f6cb48905a697dd208a41f..0e22e90c1d570eb4c86ac1f24c5a6e9159be8ea1 100644 --- a/chrome/browser/ui/ash/keyboard/chrome_keyboard_web_contents.cc +++ b/chrome/browser/ui/ash/keyboard/chrome_keyboard_web_contents.cc -@@ -79,8 +79,7 @@ class ChromeKeyboardContentsDelegate : public content::WebContentsDelegate, +@@ -80,8 +80,7 @@ class ChromeKeyboardContentsDelegate : public content::WebContentsDelegate, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -49,10 +49,10 @@ index a0c24e09a5dffa8be119309738abe57e82ef76b3..3e362f622b72d7cb97a838e71014b035 } diff --git a/chrome/browser/ui/ash/web_view/ash_web_view_impl.cc b/chrome/browser/ui/ash/web_view/ash_web_view_impl.cc -index 44be6359d6a7acf88072569d8d4f85c688f5ed81..ee377313b25e13c011b1ed4aa31ea059f020a5b7 100644 +index 08c84ca91f7e477e4e8d6370513d90d2fb9801f1..41e04444274f40fdedbf8d97bfd149f2ac682e53 100644 --- a/chrome/browser/ui/ash/web_view/ash_web_view_impl.cc +++ b/chrome/browser/ui/ash/web_view/ash_web_view_impl.cc -@@ -120,10 +120,9 @@ bool AshWebViewImpl::IsWebContentsCreationOverridden( +@@ -121,10 +121,9 @@ bool AshWebViewImpl::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -66,10 +66,10 @@ index 44be6359d6a7acf88072569d8d4f85c688f5ed81..ee377313b25e13c011b1ed4aa31ea059 /*from_user_gesture=*/true); return true; diff --git a/chrome/browser/ui/ash/web_view/ash_web_view_impl.h b/chrome/browser/ui/ash/web_view/ash_web_view_impl.h -index 4fd8dff1089cd6afa6a66dc185734d7671657281..0a1f4268ea771a3d5d4a2668928c6e5d1b618c68 100644 +index b6582b4013d9682d32bd524b4053b443a4df00f8..afcbce72e0f247b4d5a637b27c9f25d913cfa14b 100644 --- a/chrome/browser/ui/ash/web_view/ash_web_view_impl.h +++ b/chrome/browser/ui/ash/web_view/ash_web_view_impl.h -@@ -59,8 +59,7 @@ class AshWebViewImpl : public ash::AshWebView, +@@ -60,8 +60,7 @@ class AshWebViewImpl : public ash::AshWebView, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -80,29 +80,33 @@ index 4fd8dff1089cd6afa6a66dc185734d7671657281..0a1f4268ea771a3d5d4a2668928c6e5d content::WebContents* source, const content::OpenURLParams& params, diff --git a/chrome/browser/ui/browser.cc b/chrome/browser/ui/browser.cc -index de3f9f56b47628e1104b5f64b3c17cc35e10bfc7..3a19c28386fd3a0b8755a06510895c685f2c0cdb 100644 +index 75c32a1af7011cb8a5bcf96f5c92f66ec86609c0..ac87e2f219fb79a69ab1afb68f29525b09ab8538 100644 --- a/chrome/browser/ui/browser.cc +++ b/chrome/browser/ui/browser.cc -@@ -2327,12 +2327,11 @@ bool Browser::IsWebContentsCreationOverridden( +@@ -2413,8 +2413,7 @@ bool Browser::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, - const std::string& frame_name, - const GURL& target_url) { + const content::mojom::CreateNewWindowParams& params) { - return window_container_type == - content::mojom::WindowContainerType::BACKGROUND && - ShouldCreateBackgroundContents(source_site_instance, opener_url, -- frame_name); -+ params.frame_name); + if (IsActorCoordinatorActingOnTab( + profile(), content::WebContents::FromRenderFrameHost(opener))) { + // If an ActorCoordinator is acting on the opener, prevent it from creating +@@ -2426,7 +2425,7 @@ bool Browser::IsWebContentsCreationOverridden( + return (window_container_type == + content::mojom::WindowContainerType::BACKGROUND && + ShouldCreateBackgroundContents(source_site_instance, opener_url, +- frame_name)); ++ params.frame)); } WebContents* Browser::CreateCustomWebContents( diff --git a/chrome/browser/ui/browser.h b/chrome/browser/ui/browser.h -index 0bcb2fc072e47c2c259b724209b4814486329fe1..db674988cf87f198ed1af7e0f4def24776fbaa89 100644 +index 8cb8eb633a7b90ee8ad5d39b01d02d0785e97980..a90ff9bc0361a78ca12cae930d604e8834beddc8 100644 --- a/chrome/browser/ui/browser.h +++ b/chrome/browser/ui/browser.h -@@ -1027,8 +1027,7 @@ class Browser : public TabStripModelObserver, +@@ -1047,8 +1047,7 @@ class Browser : public TabStripModelObserver, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -113,10 +117,10 @@ index 0bcb2fc072e47c2c259b724209b4814486329fe1..db674988cf87f198ed1af7e0f4def247 content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, diff --git a/chrome/browser/ui/media_router/presentation_receiver_window_controller.cc b/chrome/browser/ui/media_router/presentation_receiver_window_controller.cc -index 0d2a68ea6b9f08b5c1f1113181b08d55a3265192..0dfa27fa14d1308c059534953e190922ddb3bc0a 100644 +index a05510eadf5c9ff24bb7999aa76229946319280f..a80ecc46f8a6b84de83d608257d45ae61ccc2170 100644 --- a/chrome/browser/ui/media_router/presentation_receiver_window_controller.cc +++ b/chrome/browser/ui/media_router/presentation_receiver_window_controller.cc -@@ -205,8 +205,7 @@ bool PresentationReceiverWindowController::IsWebContentsCreationOverridden( +@@ -206,8 +206,7 @@ bool PresentationReceiverWindowController::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -127,10 +131,10 @@ index 0d2a68ea6b9f08b5c1f1113181b08d55a3265192..0dfa27fa14d1308c059534953e190922 // uses this to spawn new windows/tabs, which is also not allowed for // local presentations. diff --git a/chrome/browser/ui/media_router/presentation_receiver_window_controller.h b/chrome/browser/ui/media_router/presentation_receiver_window_controller.h -index ca72b324bf7c3b81ac94b53f0ff454d2df177950..d60ef3075d126e2bbd50c8469f2bf67cfa05c6f7 100644 +index 3fc06be01f20e8cd314d95d73a3f58c2f0742fe9..c07910ae59a185442f37ea6e7b96fdf3a33aba82 100644 --- a/chrome/browser/ui/media_router/presentation_receiver_window_controller.h +++ b/chrome/browser/ui/media_router/presentation_receiver_window_controller.h -@@ -105,8 +105,7 @@ class PresentationReceiverWindowController final +@@ -106,8 +106,7 @@ class PresentationReceiverWindowController final content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -141,10 +145,10 @@ index ca72b324bf7c3b81ac94b53f0ff454d2df177950..d60ef3075d126e2bbd50c8469f2bf67c // The profile used for the presentation. raw_ptr otr_profile_; diff --git a/chrome/browser/ui/views/hats/hats_next_web_dialog.cc b/chrome/browser/ui/views/hats/hats_next_web_dialog.cc -index 1085003ab18d471d5c018ac68041924d458fcec7..4aac70febec9f0abadd1ecb96d9066e6c270efca 100644 +index 1c30afe192809d85ced6af595347353ec3cb5364..af48bb2755c33f6c372be6b51048b3cf3fd0be0b 100644 --- a/chrome/browser/ui/views/hats/hats_next_web_dialog.cc +++ b/chrome/browser/ui/views/hats/hats_next_web_dialog.cc -@@ -100,8 +100,7 @@ class HatsNextWebDialog::HatsWebView : public views::WebView { +@@ -101,8 +101,7 @@ class HatsNextWebDialog::HatsWebView : public views::WebView { content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -155,10 +159,10 @@ index 1085003ab18d471d5c018ac68041924d458fcec7..4aac70febec9f0abadd1ecb96d9066e6 } content::WebContents* CreateCustomWebContents( diff --git a/components/embedder_support/android/delegate/web_contents_delegate_android.cc b/components/embedder_support/android/delegate/web_contents_delegate_android.cc -index e0264aff5b60bb5e76ac7687222403dfba516e66..915abd2475f6be95d973f827522f7ef12052a81c 100644 +index 37260552fcc42edcac08422bdf6cb9f0f4b09c39..461fb20c1093cf2de06f9bb6f41f80ab0017b6a1 100644 --- a/components/embedder_support/android/delegate/web_contents_delegate_android.cc +++ b/components/embedder_support/android/delegate/web_contents_delegate_android.cc -@@ -189,14 +189,13 @@ bool WebContentsDelegateAndroid::IsWebContentsCreationOverridden( +@@ -190,14 +190,13 @@ bool WebContentsDelegateAndroid::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -176,10 +180,10 @@ index e0264aff5b60bb5e76ac7687222403dfba516e66..915abd2475f6be95d973f827522f7ef1 java_gurl); } diff --git a/components/embedder_support/android/delegate/web_contents_delegate_android.h b/components/embedder_support/android/delegate/web_contents_delegate_android.h -index 67a01b48ae88c7e25aeb5c5103b26afa037f4f97..0ceb539c9c3051b5521236cf866ccb107727c8a9 100644 +index 996b3d453b375fec2a823a0dd0d3122ba626b5f2..5a5c6ed67f698fdd914e79df528e2ca391e056b7 100644 --- a/components/embedder_support/android/delegate/web_contents_delegate_android.h +++ b/components/embedder_support/android/delegate/web_contents_delegate_android.h -@@ -82,8 +82,7 @@ class WebContentsDelegateAndroid : public content::WebContentsDelegate { +@@ -83,8 +83,7 @@ class WebContentsDelegateAndroid : public content::WebContentsDelegate { content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -190,10 +194,10 @@ index 67a01b48ae88c7e25aeb5c5103b26afa037f4f97..0ceb539c9c3051b5521236cf866ccb10 bool DidAddMessageToConsole(content::WebContents* source, blink::mojom::ConsoleMessageLevel log_level, diff --git a/components/offline_pages/content/background_loader/background_loader_contents.cc b/components/offline_pages/content/background_loader/background_loader_contents.cc -index e0e9a5a8c1d8c242d39935e2456052619af33cc6..80518793447c70e8fc1dae9b42a59d40427ae52b 100644 +index 9dcf196de0d70fda966162473408968bfd9d16e0..2d2007e60c3512d002b7e1a858afb2908201e964 100644 --- a/components/offline_pages/content/background_loader/background_loader_contents.cc +++ b/components/offline_pages/content/background_loader/background_loader_contents.cc -@@ -89,8 +89,7 @@ bool BackgroundLoaderContents::IsWebContentsCreationOverridden( +@@ -90,8 +90,7 @@ bool BackgroundLoaderContents::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -204,10 +208,10 @@ index e0e9a5a8c1d8c242d39935e2456052619af33cc6..80518793447c70e8fc1dae9b42a59d40 return true; } diff --git a/components/offline_pages/content/background_loader/background_loader_contents.h b/components/offline_pages/content/background_loader/background_loader_contents.h -index c6838c83ef971b88769b1f3fba8095025ae25464..2da6a4e08340e72ba7de5d03444c2f17250c5eca 100644 +index b3fef77c892a21565235c1a13ff50e11536d360c..2400dbbc53acca6871ae16a610a337134b61aafe 100644 --- a/components/offline_pages/content/background_loader/background_loader_contents.h +++ b/components/offline_pages/content/background_loader/background_loader_contents.h -@@ -66,8 +66,7 @@ class BackgroundLoaderContents : public content::WebContentsDelegate { +@@ -67,8 +67,7 @@ class BackgroundLoaderContents : public content::WebContentsDelegate { content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -218,24 +222,24 @@ index c6838c83ef971b88769b1f3fba8095025ae25464..2da6a4e08340e72ba7de5d03444c2f17 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 94b4429fffb474304c1d43d1cf1337fde90d9e45..2a683ac9a810d7bc7286e56ce50dd51adfc4f25f 100644 +index 2eb45ae773f9fbd28fa05b14e5684f4b7d17cc85..7b416ade6fe632d7fab319460876cb42f5b5dd83 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5021,8 +5021,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( - // TODO(crbug.com/40202416): Support a way for MPArch guests to support this. - if (delegate_ && delegate_->IsWebContentsCreationOverridden( - source_site_instance, params.window_container_type, -- opener->GetLastCommittedURL(), params.frame_name, -- params.target_url)) { -+ opener->GetLastCommittedURL(), params)) { +@@ -5041,8 +5041,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( + if (delegate_ && + delegate_->IsWebContentsCreationOverridden( + opener, source_site_instance, params.window_container_type, +- opener->GetLastCommittedURL(), params.frame_name, +- params.target_url)) { ++ opener->GetLastCommittedURL(), params)) { auto* web_contents_impl = static_cast(delegate_->CreateCustomWebContents( opener, source_site_instance, is_new_browsing_instance, diff --git a/content/public/browser/web_contents_delegate.cc b/content/public/browser/web_contents_delegate.cc -index 97a3ea6f292563a41fd41f812ac72526a96d8471..b299dd5659100d317a3574e902bf2c29c5defd2c 100644 +index 8c1d83692daccfbdda90f292b5a3fb9a8f1b118f..c836a731050027fd101aea0cd65782a4a7b5627b 100644 --- a/content/public/browser/web_contents_delegate.cc +++ b/content/public/browser/web_contents_delegate.cc -@@ -159,8 +159,7 @@ bool WebContentsDelegate::IsWebContentsCreationOverridden( +@@ -160,8 +160,7 @@ bool WebContentsDelegate::IsWebContentsCreationOverridden( SiteInstance* source_site_instance, mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -246,10 +250,10 @@ index 97a3ea6f292563a41fd41f812ac72526a96d8471..b299dd5659100d317a3574e902bf2c29 } diff --git a/content/public/browser/web_contents_delegate.h b/content/public/browser/web_contents_delegate.h -index 8a18958035cc1dd26be558349f64f7727570c4ba..7d9c9b06bcc57ef5eb0a2ca74ee20632a1393f9e 100644 +index c4cee108b0caac7d6a2a9115586882dd32bab714..a9ce49d79b613c58c2e6ae4b7b9a1076a2252ee1 100644 --- a/content/public/browser/web_contents_delegate.h +++ b/content/public/browser/web_contents_delegate.h -@@ -355,8 +355,7 @@ class CONTENT_EXPORT WebContentsDelegate { +@@ -359,8 +359,7 @@ class CONTENT_EXPORT WebContentsDelegate { SiteInstance* source_site_instance, mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -260,10 +264,10 @@ index 8a18958035cc1dd26be558349f64f7727570c4ba..7d9c9b06bcc57ef5eb0a2ca74ee20632 // Allow delegate to creates a custom WebContents when // WebContents::CreateNewWindow() is called. This function is only called diff --git a/extensions/browser/guest_view/app_view/app_view_guest.cc b/extensions/browser/guest_view/app_view/app_view_guest.cc -index 8d6fc67cb9b1d653bce64d1ba22aa7ec2d79257c..d5ce746373a1a4310e1eb530aee011a785e1d68c 100644 +index 0f2c21513e07e8ddb387c165754d7ec67942a719..c381abf67c261b92f1c65c485b69321f44080343 100644 --- a/extensions/browser/guest_view/app_view/app_view_guest.cc +++ b/extensions/browser/guest_view/app_view/app_view_guest.cc -@@ -153,8 +153,7 @@ bool AppViewGuest::IsWebContentsCreationOverridden( +@@ -154,8 +154,7 @@ bool AppViewGuest::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -274,7 +278,7 @@ index 8d6fc67cb9b1d653bce64d1ba22aa7ec2d79257c..d5ce746373a1a4310e1eb530aee011a7 return true; diff --git a/extensions/browser/guest_view/app_view/app_view_guest.h b/extensions/browser/guest_view/app_view/app_view_guest.h -index 775cfbf5adac0017f343bc091daee1b8883c75bb..dc97e5d60d3663ef7f7c78c28603f9e1c5aea4ff 100644 +index 7695578f626f2a0c7fefae2bc1d5c35e5ac154f2..78958bff12ce41ae5ad77f43279a4b35b9408a12 100644 --- a/extensions/browser/guest_view/app_view/app_view_guest.h +++ b/extensions/browser/guest_view/app_view/app_view_guest.h @@ -10,6 +10,7 @@ @@ -285,7 +289,7 @@ index 775cfbf5adac0017f343bc091daee1b8883c75bb..dc97e5d60d3663ef7f7c78c28603f9e1 #include "extensions/browser/guest_view/app_view/app_view_guest_delegate.h" #include "extensions/browser/lazy_context_task_queue.h" -@@ -79,8 +80,7 @@ class AppViewGuest : public guest_view::GuestView { +@@ -80,8 +81,7 @@ class AppViewGuest : public guest_view::GuestView { content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -296,10 +300,10 @@ index 775cfbf5adac0017f343bc091daee1b8883c75bb..dc97e5d60d3663ef7f7c78c28603f9e1 content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, diff --git a/extensions/browser/guest_view/extension_options/extension_options_guest.cc b/extensions/browser/guest_view/extension_options/extension_options_guest.cc -index 2fca443b4bebf29c2835440a9db8a56f7373032f..6b704b57c08714b0a314e98d49e58676987d2995 100644 +index 5bd9d59a961a03f3cd3a806bc1af58c3eaee2b58..40d7ae8d6248163524a8c1350b625e107a8ae64a 100644 --- a/extensions/browser/guest_view/extension_options/extension_options_guest.cc +++ b/extensions/browser/guest_view/extension_options/extension_options_guest.cc -@@ -262,8 +262,7 @@ bool ExtensionOptionsGuest::IsWebContentsCreationOverridden( +@@ -263,8 +263,7 @@ bool ExtensionOptionsGuest::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -310,10 +314,10 @@ index 2fca443b4bebf29c2835440a9db8a56f7373032f..6b704b57c08714b0a314e98d49e58676 // This method handles opening links from within the guest. Since this guest diff --git a/extensions/browser/guest_view/extension_options/extension_options_guest.h b/extensions/browser/guest_view/extension_options/extension_options_guest.h -index e39031afd8fff7cb6e278555cc58a48d86407d65..f67f6a5603c1fa9e66ccdde9b601df9a11cae738 100644 +index 56d86e3d1179df2d5f34eb6216989aef2687f49f..236f3ccf8354b156737e03929ee538f99f1f4adf 100644 --- a/extensions/browser/guest_view/extension_options/extension_options_guest.h +++ b/extensions/browser/guest_view/extension_options/extension_options_guest.h -@@ -73,8 +73,7 @@ class ExtensionOptionsGuest +@@ -74,8 +74,7 @@ class ExtensionOptionsGuest content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -324,10 +328,10 @@ index e39031afd8fff7cb6e278555cc58a48d86407d65..f67f6a5603c1fa9e66ccdde9b601df9a content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, diff --git a/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.cc b/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.cc -index 60de0d74ee40fedcbae96e5049e21dc238bf33bf..c568d4d08f772e1d381820bed826a0b64a631449 100644 +index 0bba5f4b0abdaa55b7e406d39ccf3de33bf53194..ed4b8e0215a12adf95273109f7e4968d7b0cbf2a 100644 --- a/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.cc +++ b/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.cc -@@ -452,8 +452,7 @@ bool MimeHandlerViewGuest::IsWebContentsCreationOverridden( +@@ -453,8 +453,7 @@ bool MimeHandlerViewGuest::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -338,10 +342,10 @@ index 60de0d74ee40fedcbae96e5049e21dc238bf33bf..c568d4d08f772e1d381820bed826a0b6 return true; diff --git a/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.h b/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.h -index 2dcf51f335f5dac39f431c3e0f56f8789f33d40b..2b433624d0604e0b9da5117b9e83cc1559b74740 100644 +index 7eeffdfbda9611806c6f260f0c68f6d84689cb7e..5d8f6d132068d7fabaa52bc61354c71a8ac8cd20 100644 --- a/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.h +++ b/extensions/browser/guest_view/mime_handler_view/mime_handler_view_guest.h -@@ -186,8 +186,7 @@ class MimeHandlerViewGuest +@@ -187,8 +187,7 @@ class MimeHandlerViewGuest content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -352,10 +356,10 @@ index 2dcf51f335f5dac39f431c3e0f56f8789f33d40b..2b433624d0604e0b9da5117b9e83cc15 content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, diff --git a/fuchsia_web/webengine/browser/frame_impl.cc b/fuchsia_web/webengine/browser/frame_impl.cc -index c10903a8e7e5fb66a1b038eab9015658a93672df..5a3afdb8ababf6e465c6166ca6229af7b4d6941d 100644 +index c61784e1d0717063e5aefd05d7c09358bae5b8c5..b987c5660942e94f89ff19cc55e032e4cb693863 100644 --- a/fuchsia_web/webengine/browser/frame_impl.cc +++ b/fuchsia_web/webengine/browser/frame_impl.cc -@@ -576,8 +576,7 @@ bool FrameImpl::IsWebContentsCreationOverridden( +@@ -579,8 +579,7 @@ bool FrameImpl::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -366,10 +370,10 @@ index c10903a8e7e5fb66a1b038eab9015658a93672df..5a3afdb8ababf6e465c6166ca6229af7 // can catch bad client behavior while not interfering with normal operation. constexpr size_t kMaxPendingWebContentsCount = 10; diff --git a/fuchsia_web/webengine/browser/frame_impl.h b/fuchsia_web/webengine/browser/frame_impl.h -index 1012a909ef1fcae51c218ae519fe7e0db65ab087..127b1ae940bc9313aecb635e2b01bb6f541d9adb 100644 +index 756d4192271d6a65cfe8e1511737c565b543cb1f..5688f6f745056565c3c01947f741c4d13e27b6ae 100644 --- a/fuchsia_web/webengine/browser/frame_impl.h +++ b/fuchsia_web/webengine/browser/frame_impl.h -@@ -307,8 +307,7 @@ class WEB_ENGINE_EXPORT FrameImpl : public fuchsia::web::Frame, +@@ -308,8 +308,7 @@ class WEB_ENGINE_EXPORT FrameImpl : public fuchsia::web::Frame, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -380,10 +384,10 @@ index 1012a909ef1fcae51c218ae519fe7e0db65ab087..127b1ae940bc9313aecb635e2b01bb6f int opener_render_process_id, int opener_render_frame_id, diff --git a/headless/lib/browser/headless_web_contents_impl.cc b/headless/lib/browser/headless_web_contents_impl.cc -index 7ca1e83ba1fd2dc5ea7c7ce644c3b7c54b9999f9..c1639653714d6973bcb5a0b37cb7028db8406742 100644 +index b8f48c883d7adfd765b1561fd00e563ab54d20f5..0b3d8eef0ed0021d3546ff963e721eae277dcb1b 100644 --- a/headless/lib/browser/headless_web_contents_impl.cc +++ b/headless/lib/browser/headless_web_contents_impl.cc -@@ -206,8 +206,7 @@ class HeadlessWebContentsImpl::Delegate : public content::WebContentsDelegate { +@@ -207,8 +207,7 @@ class HeadlessWebContentsImpl::Delegate : public content::WebContentsDelegate { content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -394,10 +398,10 @@ index 7ca1e83ba1fd2dc5ea7c7ce644c3b7c54b9999f9..c1639653714d6973bcb5a0b37cb7028d ->options() ->block_new_web_contents(); diff --git a/ui/views/controls/webview/web_dialog_view.cc b/ui/views/controls/webview/web_dialog_view.cc -index 250e7f524a9ab1cc6fda2bfefb3c78a8e971b625..55a0db02885a85e538d267402cfd0ac8ce52b921 100644 +index 42e0654da5659ba647529c4b0b97ec5df61d59a1..406e2ca73c182005014b56824e89ddfb25fd28f5 100644 --- a/ui/views/controls/webview/web_dialog_view.cc +++ b/ui/views/controls/webview/web_dialog_view.cc -@@ -489,8 +489,7 @@ bool WebDialogView::IsWebContentsCreationOverridden( +@@ -490,8 +490,7 @@ bool WebDialogView::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -408,10 +412,10 @@ index 250e7f524a9ab1cc6fda2bfefb3c78a8e971b625..55a0db02885a85e538d267402cfd0ac8 return delegate_->HandleShouldOverrideWebContentsCreation(); } diff --git a/ui/views/controls/webview/web_dialog_view.h b/ui/views/controls/webview/web_dialog_view.h -index c96aeb2571961fa2ad033ca38600006e0e657699..2c733734103bf2cc0af9bcfb32d753053a287775 100644 +index 0fa7e807d22f6f04b84f2d949fbdf892b94996bf..b0490ae36c9999a766bbf346e35807740f4f9af6 100644 --- a/ui/views/controls/webview/web_dialog_view.h +++ b/ui/views/controls/webview/web_dialog_view.h -@@ -167,8 +167,7 @@ class WEBVIEW_EXPORT WebDialogView : public ClientView, +@@ -168,8 +168,7 @@ class WEBVIEW_EXPORT WebDialogView : public ClientView, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, diff --git a/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch b/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch index 2ebb63b2ae6ec..0ffd60d534c9a 100644 --- a/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch +++ b/patches/chromium/chore_remove_reference_to_chrome_browser_themes.patch @@ -11,7 +11,7 @@ not need this dependency. refs https://chromium-review.googlesource.com/c/chromium/src/+/5573603 diff --git a/chrome/browser/ui/color/BUILD.gn b/chrome/browser/ui/color/BUILD.gn -index 77c7485b0fa885ddff38f336d1c7a52f2e969c73..045c0751a0c43f3360e334dd227b6cff7ddfd681 100644 +index 29c3dafa96df631e36aa1ced6798990c768adeaa..0281a50f04fecfc4ded3805a8f9637e184288581 100644 --- a/chrome/browser/ui/color/BUILD.gn +++ b/chrome/browser/ui/color/BUILD.gn @@ -84,9 +84,6 @@ source_set("mixers") { diff --git a/patches/chromium/desktop_media_list.patch b/patches/chromium/desktop_media_list.patch index 24567fbfdcaec..1d96e0737f348 100644 --- a/patches/chromium/desktop_media_list.patch +++ b/patches/chromium/desktop_media_list.patch @@ -41,7 +41,7 @@ index a82e0b1a7e999817c8ee420ceddeb7ca9ee78caf..e07f4ded61a7a64983da1b6d07315aee int DesktopMediaListBase::GetSourceCount() const { diff --git a/chrome/browser/media/webrtc/desktop_media_list_base.h b/chrome/browser/media/webrtc/desktop_media_list_base.h -index 9368d56f2b434b1a7101f28908f070ad9908be7e..804eb2c7ede137b8c9d0cf43042ff7f20dad5b91 100644 +index de56c9b94f92e9abf69b1d4894e5d386cad6d3cd..f8955ef7cc43b1854b29841ed65260a1966a4b19 100644 --- a/chrome/browser/media/webrtc/desktop_media_list_base.h +++ b/chrome/browser/media/webrtc/desktop_media_list_base.h @@ -39,7 +39,7 @@ class DesktopMediaListBase : public DesktopMediaList { diff --git a/patches/chromium/disable_hidden.patch b/patches/chromium/disable_hidden.patch index e212dd9060bee..b5b5876ad1d2f 100644 --- a/patches/chromium/disable_hidden.patch +++ b/patches/chromium/disable_hidden.patch @@ -21,10 +21,10 @@ index 00583269d16f4b8eacb4875b12a3e69155839d12..23d5baa267333e18551d449317f3e3a6 // Prompts should remain open and functional across tab switches. if (!delegate_ || !delegate_->IsWaitingForPointerLockPrompt(this)) { diff --git a/content/browser/renderer_host/render_widget_host_impl.h b/content/browser/renderer_host/render_widget_host_impl.h -index 86a80795fb931f569b21c3138697b90d8b38d750..6268d7e3a64bac17b94f0bfb8e24c44a61cf7d3f 100644 +index 70acc7b54d862e9aac9ec8a0867893e22512f77c..03ee050653c48a22d68881151cdf8f787161a32b 100644 --- a/content/browser/renderer_host/render_widget_host_impl.h +++ b/content/browser/renderer_host/render_widget_host_impl.h -@@ -1012,6 +1012,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl +@@ -1016,6 +1016,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl // Requests a commit and forced redraw in the renderer compositor. void ForceRedrawForTesting(); diff --git a/patches/chromium/enable_reset_aspect_ratio.patch b/patches/chromium/enable_reset_aspect_ratio.patch index b29eb60e9d0e4..9a6495bed86ad 100644 --- a/patches/chromium/enable_reset_aspect_ratio.patch +++ b/patches/chromium/enable_reset_aspect_ratio.patch @@ -19,7 +19,7 @@ index 6ad16425f2fb3438be178cb06a85ef72f8d09e22..61509e2eb982797845098abf5f36e031 excluded_margin); } diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index ac502dee8a21725db9de2e232cb5092a0670f1d9..db2b841e973f05049f712c732ae8d4815a8aff7a 100644 +index 9a42a64f52ccbab2cab6119c91b69ab44eeeb9e5..2cd46f4692c84cffff0775bbb67d3585f24e900d 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc @@ -992,8 +992,11 @@ void HWNDMessageHandler::SetFullscreen(bool fullscreen, diff --git a/patches/chromium/extend_apply_webpreferences.patch b/patches/chromium/extend_apply_webpreferences.patch index 26bcd05582b59..602b449541f9c 100644 --- a/patches/chromium/extend_apply_webpreferences.patch +++ b/patches/chromium/extend_apply_webpreferences.patch @@ -12,7 +12,7 @@ Ideally we could add an embedder observer pattern here but that can be done in future work. diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index 0b2956425d2feb84f1d0db7be4f3d4b0875b1d10..f2e37be51049caab4fd6385b5b55f1151708bd82 100644 +index 3c3c0247ca56ba99b48583a4218712f172458845..c996ded8e1cf83ca0ebb4b3fc18b8d6d80409c9a 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -171,6 +171,7 @@ diff --git a/patches/chromium/feat_configure_launch_options_for_service_process.patch b/patches/chromium/feat_configure_launch_options_for_service_process.patch index 68b50ef8a8023..cef5d94f3f627 100644 --- a/patches/chromium/feat_configure_launch_options_for_service_process.patch +++ b/patches/chromium/feat_configure_launch_options_for_service_process.patch @@ -19,7 +19,7 @@ to STDOUT_FILENO/STD_OUTPUT_HANDLE and STDERR_FILENO/STD_ERROR_HANDLE allowing t parent process to read from the pipe. diff --git a/content/browser/child_process_launcher.h b/content/browser/child_process_launcher.h -index ac6f72c99800d5437ddc4aa203870242fb9220b9..93055bda5478f4b7b401ae06dcddce36a26f5ad7 100644 +index 4c3d9917baee848b673d2895a54d96528ef14286..a3735de9aa88cef41be61fe742d8beb85de96a6e 100644 --- a/content/browser/child_process_launcher.h +++ b/content/browser/child_process_launcher.h @@ -33,6 +33,7 @@ @@ -30,7 +30,7 @@ index ac6f72c99800d5437ddc4aa203870242fb9220b9..93055bda5478f4b7b401ae06dcddce36 #endif #if BUILDFLAG(IS_POSIX) -@@ -188,7 +189,10 @@ struct ChildProcessLauncherFileData { +@@ -193,7 +194,10 @@ struct ChildProcessLauncherFileData { delete; ~ChildProcessLauncherFileData(); @@ -42,7 +42,7 @@ index ac6f72c99800d5437ddc4aa203870242fb9220b9..93055bda5478f4b7b401ae06dcddce36 // Files opened by the browser and passed as corresponding file descriptors // in the child process. If a FilePath is provided, the file will be opened // and the descriptor cached for future process launches. If a ScopedFD is -@@ -203,6 +207,15 @@ struct ChildProcessLauncherFileData { +@@ -208,6 +212,15 @@ struct ChildProcessLauncherFileData { std::map> files_to_preload; #endif @@ -59,7 +59,7 @@ index ac6f72c99800d5437ddc4aa203870242fb9220b9..93055bda5478f4b7b401ae06dcddce36 // Launches a process asynchronously and notifies the client of the process diff --git a/content/browser/child_process_launcher_helper_linux.cc b/content/browser/child_process_launcher_helper_linux.cc -index 31a2a14a95540477297943df9b09b1e4659a884d..c02a81b1bd14a300dbbb47ad7aac2d2d7f3bb10f 100644 +index 8f551374e1ffc729081f7d50e73671313c641bb6..6e7a3f46b82f82035f612f9700281d0edb363de5 100644 --- a/content/browser/child_process_launcher_helper_linux.cc +++ b/content/browser/child_process_launcher_helper_linux.cc @@ -64,6 +64,11 @@ bool ChildProcessLauncherHelper::BeforeLaunchOnLauncherThread( @@ -111,7 +111,7 @@ index 1d981cec12769d145b694b61772b4c09616df9f0..cf9d9bfe7af12e16520354ebd1f7bc40 } diff --git a/content/browser/child_process_launcher_helper_win.cc b/content/browser/child_process_launcher_helper_win.cc -index cb0e7d5c5dc0154c6e88ad08ce097afdce4041f9..09b9cff76d9585297fe60f91970c610ac445f06a 100644 +index 0791b5317fc6846389f65f93734ae5e816d04623..48948b409d6da58ade72c60ed848df4931d0eaab 100644 --- a/content/browser/child_process_launcher_helper_win.cc +++ b/content/browser/child_process_launcher_helper_win.cc @@ -24,6 +24,8 @@ diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index b5576097e870b..ffa3f9ee34645 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -112,10 +112,10 @@ index 6e991652d242795e292cea4c94cff59aaea078fa..b6834c78575520bb6e584dd2ce3333ac 'internal-forced-visited-'): internal_visited_order = 0 diff --git a/third_party/blink/renderer/core/css/css_properties.json5 b/third_party/blink/renderer/core/css/css_properties.json5 -index c3dfa4c1f53a6ebba5735214037e0d1c6a88961d..17a08450227844dceccbaab7ff9de60d6e058b1f 100644 +index cc8657b515dd791e910343122e73be6fc8c1d38e..78299aca166e20c1e5f1f049beab915334d1612d 100644 --- a/third_party/blink/renderer/core/css/css_properties.json5 +++ b/third_party/blink/renderer/core/css/css_properties.json5 -@@ -8822,6 +8822,24 @@ +@@ -8823,6 +8823,24 @@ property_methods: ["ParseShorthand", "CSSValueFromComputedStyleInternal"], }, @@ -154,10 +154,10 @@ index ff1cc33c1787df522300a220000ad3d3123cd7bd..6b9e72f60db9af5ceeac7cc663ac666b return a.EmptyCells() == b.EmptyCells(); case CSSPropertyID::kFill: diff --git a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -index 4bc9534e12a7f71f9837ea8de4c85572d2e4af11..0d9368c96b175b767c8ed912daf434a334093123 100644 +index cefbbebae039bb9cdbdf57612feff660dfe94d87..3c3dea18f97a3df1ef6eb095c34951492285cee0 100644 --- a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -@@ -12050,5 +12050,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( +@@ -12071,5 +12071,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( CSSValueID::kNone>(stream); } @@ -239,7 +239,7 @@ index 5e8d2bfbccd0625c2598544a9cba3d71373eded2..e68a97ee75754fc7196f11cf5c731550 bool RenderVSyncNotificationEnabled() const { return render_v_sync_notification_enabled_; diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index f2e37be51049caab4fd6385b5b55f1151708bd82..c0078bff37cfd1a4e5da111f6ec1aa817987a7ab 100644 +index c996ded8e1cf83ca0ebb4b3fc18b8d6d80409c9a..d589a8a5264b2a7c2b21aa83e8c1faa5fb8f93a1 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -3574,6 +3574,9 @@ void WebViewImpl::UpdateRendererPreferences( @@ -307,7 +307,7 @@ index 2c2f4f405074e5baa4a26f255283404f86b40e21..ebeb7d6988ee9e6a4e78cb82fc01fdad ContouredRect PixelSnappedContouredBorderInternal( diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn -index b5a309cb7bad79f80fb43dcbcccbd8dc2fcdfef8..c90d8f2f283e9bd05184171d3971d0060731f67d 100644 +index 3788f76b50f6a1776baef2131033a62875e101b9..f3e2226021d1de6a5cb787538ca6c0f18f208670 100644 --- a/third_party/blink/renderer/platform/BUILD.gn +++ b/third_party/blink/renderer/platform/BUILD.gn @@ -1658,6 +1658,8 @@ component("platform") { diff --git a/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch b/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch index 342d76d0d85da..db2bb3935c133 100644 --- a/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch +++ b/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch @@ -7,7 +7,7 @@ This allows embedders to call SetDefersLoading without reaching into Blink inter This might be upstreamable? diff --git a/third_party/blink/public/web/web_document_loader.h b/third_party/blink/public/web/web_document_loader.h -index 0527831e1f8d7923ba0f687a5c0da8573189d867..f72af0e6cfcf06d47bd917def993f081530ab66b 100644 +index 33e23680b927d417b0882c7572fe32dc2d2b90c3..9413492f8e0fd6c5371c66329e1ad6d4163ba670 100644 --- a/third_party/blink/public/web/web_document_loader.h +++ b/third_party/blink/public/web/web_document_loader.h @@ -38,6 +38,7 @@ @@ -28,10 +28,10 @@ index 0527831e1f8d7923ba0f687a5c0da8573189d867..f72af0e6cfcf06d47bd917def993f081 // Returns the http referrer of original request which initited this load. diff --git a/third_party/blink/renderer/core/loader/document_loader.h b/third_party/blink/renderer/core/loader/document_loader.h -index 10682e129daf40104a71d0067aa126cc13a1e8b7..fb8696d850fc3fbbcd66087c8cafc53acee462aa 100644 +index 01b97e569a69fb1395e63492ac75432d648bb71f..6e58d859e2afd3bd8b9b17c53ba9ccc6dbdcd458 100644 --- a/third_party/blink/renderer/core/loader/document_loader.h +++ b/third_party/blink/renderer/core/loader/document_loader.h -@@ -328,7 +328,7 @@ class CORE_EXPORT DocumentLoader : public GarbageCollected, +@@ -325,7 +325,7 @@ class CORE_EXPORT DocumentLoader : public GarbageCollected, soft_navigation_heuristics_task_id, bool should_skip_screenshot); diff --git a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch index 7b937ea8c4ff9..e1711b0bf9d9a 100644 --- a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch +++ b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch @@ -112,7 +112,7 @@ index 99bf736ebe303d46ab1ced924ba929a0cd258909..e10c8782d2704ff9cff8062d201a4339 string mime_type; diff --git a/services/network/url_loader.cc b/services/network/url_loader.cc -index 7d04e7f5f7f4261909fe06d6894849db34d7552b..6af6e0a32e59523ff7b3ba3a5d32e711ba422f87 100644 +index 565d77c76805898c7dccc472daf2853cdafd9fbb..fd62b19ef22e162f3f4ea6ac510996bccec8fe2f 100644 --- a/services/network/url_loader.cc +++ b/services/network/url_loader.cc @@ -388,6 +388,9 @@ URLLoader::URLLoader( diff --git a/patches/chromium/fix_activate_background_material_on_windows.patch b/patches/chromium/fix_activate_background_material_on_windows.patch index 284a177d083a0..5cc74422f369b 100644 --- a/patches/chromium/fix_activate_background_material_on_windows.patch +++ b/patches/chromium/fix_activate_background_material_on_windows.patch @@ -14,7 +14,7 @@ This patch likely can't be upstreamed as-is, as Chromium doesn't have this use case in mind currently. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 6e706c32ca4c2a5d0831588ee2eea8a8059f04fe..09509acd13511525b0eb7b9afa972e20d8d3601c 100644 +index 88f658aeb32a3181e3a0cd45fbd2aacad95116aa..cef61dcf3ab89f06cba16f309e800dbab5a7cc05 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc @@ -936,13 +936,13 @@ void HWNDMessageHandler::FrameTypeChanged() { @@ -33,7 +33,7 @@ index 6e706c32ca4c2a5d0831588ee2eea8a8059f04fe..09509acd13511525b0eb7b9afa972e20 } void HWNDMessageHandler::SetWindowIcons(const gfx::ImageSkia& window_icon, -@@ -1739,7 +1739,7 @@ void HWNDMessageHandler::OnActivateApp(BOOL active, DWORD thread_id) { +@@ -1728,7 +1728,7 @@ void HWNDMessageHandler::OnActivateApp(BOOL active, DWORD thread_id) { if (delegate_->HasNonClientView() && !active && thread_id != GetCurrentThreadId()) { // Update the native frame if it is rendering the non-client area. @@ -42,7 +42,7 @@ index 6e706c32ca4c2a5d0831588ee2eea8a8059f04fe..09509acd13511525b0eb7b9afa972e20 DefWindowProcWithRedrawLock(WM_NCACTIVATE, FALSE, 0); } } -@@ -2347,17 +2347,18 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message, +@@ -2336,17 +2336,18 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message, delegate_->SchedulePaint(); } diff --git a/patches/chromium/fix_aspect_ratio_with_max_size.patch b/patches/chromium/fix_aspect_ratio_with_max_size.patch index 15f5cfd49d1d5..7cef957d01da0 100644 --- a/patches/chromium/fix_aspect_ratio_with_max_size.patch +++ b/patches/chromium/fix_aspect_ratio_with_max_size.patch @@ -11,10 +11,10 @@ enlarge window above dimensions set during creation of the BrowserWindow. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index db2b841e973f05049f712c732ae8d4815a8aff7a..5919efa661c3b1ed210f7a67f85fdd3882011bae 100644 +index 2cd46f4692c84cffff0775bbb67d3585f24e900d..9747e945b2ebfc113ffd12839c28a98fcccf2872 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -3782,15 +3782,30 @@ void HWNDMessageHandler::SizeWindowToAspectRatio(UINT param, +@@ -3771,15 +3771,30 @@ void HWNDMessageHandler::SizeWindowToAspectRatio(UINT param, delegate_->GetMinMaxSize(&min_window_size, &max_window_size); min_window_size = delegate_->DIPToScreenSize(min_window_size); max_window_size = delegate_->DIPToScreenSize(max_window_size); diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index a8d7aceba2887..d42b8451d3f2e 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -28,27 +28,26 @@ The patch should be removed in favor of either: Upstream bug https://bugs.chromium.org/p/chromium/issues/detail?id=1081397. diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc -index 0dbbaddc1bef8b5a1b253297f47c33601dc6fe67..0c84f727b29c742ba4c2edd38dfa16d1f48df76f 100644 +index e5776378633dba0b60a79a9044991ceaafe86e72..2beccf1bb05e8695e3e2191683e0a9bc1184544a 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc -@@ -11110,6 +11110,12 @@ NavigationRequest::GetOriginForURLLoaderFactoryUncheckedWithDebugInfo() { - "blob"); +@@ -11076,6 +11076,11 @@ url::Origin NavigationRequest::GetOriginForURLLoaderFactoryUnchecked() { + target_rph_id); } + if (!common_params().url.IsStandard() && !common_params().url.IsAboutBlank()) { -+ return std::make_pair(url::Origin::Resolve(common_params().url, -+ url::Origin()), -+ "url_non_standard"); ++ return url::Origin::Resolve(common_params().url, ++ url::Origin()); + } + // In cases not covered above, URLLoaderFactory should be associated with the // origin of |common_params.url| and/or |common_params.initiator_origin|. url::Origin resolved_origin = url::Origin::Resolve( diff --git a/third_party/blink/renderer/core/loader/document_loader.cc b/third_party/blink/renderer/core/loader/document_loader.cc -index abcc4436479e7c9bc0dbf77c70c628e48d6ea1b8..510c088fd06d5989e710ba6674e1798bd5d63954 100644 +index 59e909f5b9b3b9e2cb648359d3a0b4db2f1671b7..297aa66d55a62557deafe1d723809d68f898095c 100644 --- a/third_party/blink/renderer/core/loader/document_loader.cc +++ b/third_party/blink/renderer/core/loader/document_loader.cc -@@ -2333,6 +2333,10 @@ Frame* DocumentLoader::CalculateOwnerFrame() { +@@ -2332,6 +2332,10 @@ Frame* DocumentLoader::CalculateOwnerFrame() { scoped_refptr DocumentLoader::CalculateOrigin( Document* owner_document) { scoped_refptr origin; @@ -56,17 +55,16 @@ index abcc4436479e7c9bc0dbf77c70c628e48d6ea1b8..510c088fd06d5989e710ba6674e1798b + std::string protocol = url_.Protocol().Ascii(); + is_standard = url::IsStandard( + protocol.data(), url::Component(0, static_cast(protocol.size()))); - StringBuilder debug_info_builder; // Whether the origin is newly created within this call, instead of copied // from an existing document's origin or from `origin_to_commit_`. If this is -@@ -2386,6 +2390,10 @@ scoped_refptr DocumentLoader::CalculateOrigin( + // true, we won't try to compare the nonce of this origin (if it's opaque) to +@@ -2368,6 +2372,9 @@ scoped_refptr DocumentLoader::CalculateOrigin( + // non-renderer only origin bits will be the same, which will be asserted at // the end of this function. origin = origin_to_commit_; - debug_info_builder.Append("use_origin_to_commit"); + } else if (!SecurityOrigin::ShouldUseInnerURL(url_) && + !is_standard) { -+ debug_info_builder.Append("use_url_with_non_standard_scheme"); + origin = SecurityOrigin::Create(url_); } else { - debug_info_builder.Append("use_url_with_precursor"); // Otherwise, create an origin that propagates precursor information + // as needed. For non-opaque origins, this creates a standard tuple diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 4a2a682c365f2..a235d69872ff6 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index e96a656473e0d18a8053dab92dbeb1afb174d27f..e3085847de7875afa655b3cfa4aa39892be626eb 100644 +index 020d8d111d756dbe8bbae47a0e7dc74b63501b54..70b3c4a2da0e1d79a7626e0bb2ed45b8fbbe0024 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -9997,7 +9997,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -10019,7 +10019,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_properly_honor_printing_page_ranges.patch b/patches/chromium/fix_properly_honor_printing_page_ranges.patch index 4d72e1c3f9203..78f83203e5b39 100644 --- a/patches/chromium/fix_properly_honor_printing_page_ranges.patch +++ b/patches/chromium/fix_properly_honor_printing_page_ranges.patch @@ -102,10 +102,10 @@ index 2808248f6eb3f5c75f20775d61c9d0d20aaaecf6..7c186bd5653e9bdf1c4046398b138cac } else { // No need to bother, we don't know how many pages are available. diff --git a/ui/gtk/printing/print_dialog_gtk.cc b/ui/gtk/printing/print_dialog_gtk.cc -index 2f9738b2b0612eb1ae579e49edaa22b4df136739..470c88b898bb7e7bfd87204816f5042684f69fb6 100644 +index 6fc177bdd111c3f0478dc614a2e71ab6f43cf8b9..3de8c0157cd781638f0281edfe6cc34f4f792da7 100644 --- a/ui/gtk/printing/print_dialog_gtk.cc +++ b/ui/gtk/printing/print_dialog_gtk.cc -@@ -258,6 +258,24 @@ void PrintDialogGtk::UpdateSettings( +@@ -256,6 +256,24 @@ void PrintDialogGtk::UpdateSettings( gtk_print_settings_set_n_copies(gtk_settings_, settings->copies()); gtk_print_settings_set_collate(gtk_settings_, settings->collate()); diff --git a/patches/chromium/fix_remove_caption-removing_style_call.patch b/patches/chromium/fix_remove_caption-removing_style_call.patch index 3682723f795b0..cf72a25a5708b 100644 --- a/patches/chromium/fix_remove_caption-removing_style_call.patch +++ b/patches/chromium/fix_remove_caption-removing_style_call.patch @@ -18,10 +18,10 @@ or resizing, but Electron does not seem to run into that issue for opaque frameless windows even with that block commented out. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 5b17d5bf0b32405ae9515b941a17b68a04a3b317..6e706c32ca4c2a5d0831588ee2eea8a8059f04fe 100644 +index 6f2e2702d3b982fe7e8d258f303c8055d3d37df8..88f658aeb32a3181e3a0cd45fbd2aacad95116aa 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -1807,7 +1807,23 @@ LRESULT HWNDMessageHandler::OnCreate(CREATESTRUCT* create_struct) { +@@ -1796,7 +1796,23 @@ LRESULT HWNDMessageHandler::OnCreate(CREATESTRUCT* create_struct) { SendMessage(hwnd(), WM_CHANGEUISTATE, MAKELPARAM(UIS_CLEAR, UISF_HIDEFOCUS), 0); diff --git a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch index fe1bffc491c77..cf1b13ccd35dc 100644 --- a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch +++ b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch @@ -20,7 +20,7 @@ index fc9cb7e68bdad4c40fab63f70243e09ad005ab80..199fbceda530da31aab9126d78b4bd21 injector_->ExpectsResults(), injector_->ShouldWaitForPromise()); } diff --git a/third_party/blink/public/web/web_local_frame.h b/third_party/blink/public/web/web_local_frame.h -index 6ea4a0f04eab4e85ec4c9b67f50c5c4e5c6e01e1..5f055fe422904c95e05af5cb0e92241a5d9d53c1 100644 +index 202a7b6771ce1890a4bb33b66c533584bce746ed..3c5edffc6d623aaabc62bfc134fb968db6bc5345 100644 --- a/third_party/blink/public/web/web_local_frame.h +++ b/third_party/blink/public/web/web_local_frame.h @@ -461,6 +461,7 @@ class BLINK_EXPORT WebLocalFrame : public WebFrame { @@ -59,10 +59,10 @@ index cba373664bec3a32abad6fe0396bd67b53b7e67f..a54f1b3351efd2d8f324436f7f35cd43 #endif // THIRD_PARTY_BLINK_PUBLIC_WEB_WEB_SCRIPT_EXECUTION_CALLBACK_H_ diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index e5d629937aaa175d11731bc1048a1b459927e93a..5fa2f36b65a876edc8f2e5905b695b9e5d88afbd 100644 +index e567f331968b1b1b9d6b85e31397b6a4f7ea7a84..9650e99108cefb8b2963913fb39049f69496a65e 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc -@@ -3081,6 +3081,7 @@ void LocalFrame::RequestExecuteScript( +@@ -3085,6 +3085,7 @@ void LocalFrame::RequestExecuteScript( mojom::blink::EvaluationTiming evaluation_timing, mojom::blink::LoadEventBlockingOption blocking_option, WebScriptExecutionCallback callback, @@ -70,7 +70,7 @@ index e5d629937aaa175d11731bc1048a1b459927e93a..5fa2f36b65a876edc8f2e5905b695b9e BackForwardCacheAware back_forward_cache_aware, mojom::blink::WantResultOption want_result_option, mojom::blink::PromiseResultOption promise_behavior) { -@@ -3113,7 +3114,7 @@ void LocalFrame::RequestExecuteScript( +@@ -3117,7 +3118,7 @@ void LocalFrame::RequestExecuteScript( PausableScriptExecutor::CreateAndRun( script_state, std::move(script_sources), execute_script_policy, user_gesture, evaluation_timing, blocking_option, want_result_option, @@ -80,10 +80,10 @@ index e5d629937aaa175d11731bc1048a1b459927e93a..5fa2f36b65a876edc8f2e5905b695b9e void LocalFrame::SetEvictCachedSessionStorageOnFreezeOrUnload() { diff --git a/third_party/blink/renderer/core/frame/local_frame.h b/third_party/blink/renderer/core/frame/local_frame.h -index 80c57253678d1aa6e655c84f4ccd9c0899eb5a5b..4d6b860409d35da509b7ef8c5d52fa9f92f1b542 100644 +index a65d5821a23a965ad715377ab15ca9df20ade075..63be18b05aa31ca48202e2809b235348fec61b0e 100644 --- a/third_party/blink/renderer/core/frame/local_frame.h +++ b/third_party/blink/renderer/core/frame/local_frame.h -@@ -830,6 +830,7 @@ class CORE_EXPORT LocalFrame final +@@ -834,6 +834,7 @@ class CORE_EXPORT LocalFrame final mojom::blink::EvaluationTiming, mojom::blink::LoadEventBlockingOption, WebScriptExecutionCallback, @@ -215,7 +215,7 @@ index 5e12b61ba14cd1afb07b71ff15e73e905da0addc..685a2ebb6694c173471d045014932125 mojom::blink::WantResultOption::kWantResult, wait_for_promise); } diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc -index dd0c441d45ebb30c5a32822365f2ebe273b8cd16..164daddaccb84a28cf4bd387f382afddfc2613d3 100644 +index b9adaba2543608f91815ca5e1aca443da5813d9d..966210be0d0b2d89c0b24ea12686ebe0289087a1 100644 --- a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc +++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc @@ -1111,14 +1111,15 @@ void WebLocalFrameImpl::RequestExecuteScript( @@ -237,7 +237,7 @@ index dd0c441d45ebb30c5a32822365f2ebe273b8cd16..164daddaccb84a28cf4bd387f382afdd bool WebLocalFrameImpl::IsInspectorConnected() { diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.h b/third_party/blink/renderer/core/frame/web_local_frame_impl.h -index 87d933b2e413f404a9b80480bdf676eb0c8a2bfa..17329fb46c0d19645ad5411bbfba33dadfea4529 100644 +index 7ec474cece9a73818ef7e8bdca751d4ac8a4b789..640cdc71a67ed4cbf009a93a7b66154d4b36e03c 100644 --- a/third_party/blink/renderer/core/frame/web_local_frame_impl.h +++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.h @@ -198,6 +198,7 @@ class CORE_EXPORT WebLocalFrameImpl final diff --git a/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch b/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch index 5ab66964901ef..347b6e6a2a01f 100644 --- a/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch +++ b/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch @@ -6,7 +6,7 @@ Subject: fix: select the first menu item when opened via keyboard This fixes an accessibility issue where the root view is 'focused' to the screen reader instead of the first menu item as with all other native menus. This patch will be upstreamed. diff --git a/ui/views/controls/menu/menu_controller.cc b/ui/views/controls/menu/menu_controller.cc -index d3e06148b22f06e6676bcda5fd8907595389887e..35f22b679494940ae1b1d64fa4eb17c41c0cc623 100644 +index 05dfc40b27072ee8f67930508e9005a9ba569348..9d5ad3940c1dd2228cc651d6d99cb52137626a7e 100644 --- a/ui/views/controls/menu/menu_controller.cc +++ b/ui/views/controls/menu/menu_controller.cc @@ -711,6 +711,16 @@ void MenuController::Run(Widget* parent, @@ -26,7 +26,7 @@ index d3e06148b22f06e6676bcda5fd8907595389887e..35f22b679494940ae1b1d64fa4eb17c4 if (button_controller) { pressed_lock_ = button_controller->TakeLock( false, ui::LocatedEvent::FromIfValid(event)); -@@ -2426,19 +2436,15 @@ void MenuController::OpenMenuImpl(MenuItemView* item, bool show) { +@@ -2440,19 +2450,15 @@ void MenuController::OpenMenuImpl(MenuItemView* item, bool show) { } item->GetSubmenu()->ShowAt(params); diff --git a/patches/chromium/fix_software_compositing_infinite_loop.patch b/patches/chromium/fix_software_compositing_infinite_loop.patch deleted file mode 100644 index 2e42f1aa7df7a..0000000000000 --- a/patches/chromium/fix_software_compositing_infinite_loop.patch +++ /dev/null @@ -1,31 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Samuel Maddock -Date: Fri, 18 Oct 2024 11:11:11 -0400 -Subject: fix: software compositing infinite loop - -When GPU compositing is unavailable, LayerTreeView::RequestNewLayerTreeFrameSink -may run in an infinite loop due to a race condition. Need to allow time to -process CompositingModeFallbackToSoftware IPC to disable GPU compositing. - -https://issues.chromium.org/345275130 - -diff --git a/third_party/blink/renderer/platform/widget/compositing/layer_tree_view.cc b/third_party/blink/renderer/platform/widget/compositing/layer_tree_view.cc -index 7253162094080c992bbb9f58dd9856d75a1f7476..14b74a675f7363b7aa3449459e0034f21d31dd87 100644 ---- a/third_party/blink/renderer/platform/widget/compositing/layer_tree_view.cc -+++ b/third_party/blink/renderer/platform/widget/compositing/layer_tree_view.cc -@@ -387,9 +387,13 @@ void LayerTreeView::DidFailToInitializeLayerTreeFrameSink() { - // unable to be killed after Chrome is closed. - // https://issues.chromium.org/336164423 - if (!Platform::Current()->IsGpuRemoteDisconnected()) { -- layer_tree_host_->GetTaskRunnerProvider()->MainThreadTaskRunner()->PostTask( -+ // CompositingModeFallbackToSoftware IPC will disable GPU compositing in -+ // RenderThread. Post task with delay to give time to receive this IPC and -+ // prevent infinite loop of retries for software renderers. -+ // https://issues.chromium.org/345275130 -+ layer_tree_host_->GetTaskRunnerProvider()->MainThreadTaskRunner()->PostDelayedTask( - FROM_HERE, base::BindOnce(&LayerTreeView::RequestNewLayerTreeFrameSink, -- weak_factory_.GetWeakPtr())); -+ weak_factory_.GetWeakPtr()), base::Milliseconds(10)); - } - } - diff --git a/patches/chromium/fix_use_delegated_generic_capturer_when_available.patch b/patches/chromium/fix_use_delegated_generic_capturer_when_available.patch index a88837a8da813..7382b179301c2 100644 --- a/patches/chromium/fix_use_delegated_generic_capturer_when_available.patch +++ b/patches/chromium/fix_use_delegated_generic_capturer_when_available.patch @@ -15,10 +15,10 @@ capturer was window or screen-specific, as the IDs remain valid for generic capturer as well. diff --git a/content/browser/media/capture/desktop_capture_device.cc b/content/browser/media/capture/desktop_capture_device.cc -index 03c74299de1558ed4ce0e8273e936a60e53e6154..fa168fd69a3a9e6679f942651b23b4012a8a9c48 100644 +index a6a63ac98221f2a5c240eab2a437a3279c18cda6..259791f19d5940161887cd455e200b5185d4cbda 100644 --- a/content/browser/media/capture/desktop_capture_device.cc +++ b/content/browser/media/capture/desktop_capture_device.cc -@@ -915,8 +915,14 @@ std::unique_ptr DesktopCaptureDevice::Create( +@@ -955,8 +955,14 @@ std::unique_ptr DesktopCaptureDevice::Create( switch (source.type) { case DesktopMediaID::TYPE_SCREEN: { @@ -35,7 +35,7 @@ index 03c74299de1558ed4ce0e8273e936a60e53e6154..fa168fd69a3a9e6679f942651b23b401 if (screen_capturer && screen_capturer->SelectSource(source.id)) { capturer = std::make_unique( std::move(screen_capturer), options); -@@ -929,8 +935,14 @@ std::unique_ptr DesktopCaptureDevice::Create( +@@ -969,8 +975,14 @@ std::unique_ptr DesktopCaptureDevice::Create( } case DesktopMediaID::TYPE_WINDOW: { diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index f9cef5ce656bd..755f58a3ab2ac 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -6,10 +6,10 @@ Subject: frame_host_manager.patch Allows embedder to intercept site instances created by chromium. diff --git a/content/browser/renderer_host/render_frame_host_manager.cc b/content/browser/renderer_host/render_frame_host_manager.cc -index b61dfcc8e3306a2c3eb8808c204254af4ad8c248..cec49ddafd46b0296cc548a17efd67527a48f157 100644 +index a8eea524f693c4f15c08e1c2f48b13c97d28ce75..47e0b121ced6ea129ccffe6364c5a91f826036eb 100644 --- a/content/browser/renderer_host/render_frame_host_manager.cc +++ b/content/browser/renderer_host/render_frame_host_manager.cc -@@ -4684,6 +4684,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( +@@ -4714,6 +4714,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( request->ResetStateForSiteInstanceChange(); } @@ -20,10 +20,10 @@ index b61dfcc8e3306a2c3eb8808c204254af4ad8c248..cec49ddafd46b0296cc548a17efd6752 } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 4a995e6c35abba567bb8be826effb06ba7e2119a..c9636db4a29ae4af408a84eb58d863ae07caf2a2 100644 +index 17b11b2a4e70f419721649568179c31228612c73..e094c512f71eef3714ed0dd6090fd6c5efab3063 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h -@@ -341,6 +341,11 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -342,6 +342,11 @@ class CONTENT_EXPORT ContentBrowserClient { virtual ~ContentBrowserClient() = default; diff --git a/patches/chromium/gritsettings_resource_ids.patch b/patches/chromium/gritsettings_resource_ids.patch index 0c71a0a667737..fd588f74de93c 100644 --- a/patches/chromium/gritsettings_resource_ids.patch +++ b/patches/chromium/gritsettings_resource_ids.patch @@ -6,13 +6,13 @@ Subject: gritsettings_resource_ids.patch Add electron resources file to the list of resource ids generation. diff --git a/tools/gritsettings/resource_ids.spec b/tools/gritsettings/resource_ids.spec -index e9d1729c376bc36ac2c5b0a2c03ae03eb7e3dbff..18f1797d64573ee676e7f3337256d3199f91f29f 100644 +index 78d72ec8ed37f4a551ff091038e6741e3f0b9efb..1c9de5cc18ab8656e7a91d5ce3f5a5424b7d8739 100644 --- a/tools/gritsettings/resource_ids.spec +++ b/tools/gritsettings/resource_ids.spec -@@ -1508,6 +1508,11 @@ - "<(SHARED_INTERMEDIATE_DIR)/third_party/blink/public/strings/permission_element_generated_strings.grd": { - "META": {"sizes": {"messages": [2000],}}, - "messages": [10080], +@@ -1524,6 +1524,11 @@ + + "third_party/search_engines_data/resources/search_engines_scaled_resources.grd": { + "structures": [10100], + }, + + "electron/build/electron_resources.grd": { diff --git a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch index 4523a105b4f90..f52c337c296b2 100644 --- a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch +++ b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch @@ -11,7 +11,7 @@ If removing this patch causes no sync failures, it's safe to delete :+1: Ref https://chromium-review.googlesource.com/c/chromium/src/+/2953903 diff --git a/tools/clang/scripts/update.py b/tools/clang/scripts/update.py -index f274064efd55d7c4691e207c7274f2cee677f4d8..a69cc4107d94268190a0f19a6e53dae231e227ef 100755 +index 420c106a5f6fbbcfc77f2409e6272689ec71cf87..dad329cec5786323a981e150129c97357122c617 100755 --- a/tools/clang/scripts/update.py +++ b/tools/clang/scripts/update.py @@ -307,6 +307,8 @@ def GetDefaultHostOs(): diff --git a/patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch b/patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch deleted file mode 100644 index 8e53a214b87ae..0000000000000 --- a/patches/chromium/make_focus_methods_in_webcontentsviewchildframe_notimplemented.patch +++ /dev/null @@ -1,50 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Shelley Vohr -Date: Wed, 7 May 2025 05:08:18 -0700 -Subject: Make focus methods in WebContentsViewChildFrame NOTIMPLEMENTED - -Change focus methods in WebContentsViewChildFrame to NOTIMPLEMENTED. -It's possible to for focus to be called on the child frame, e.g. in the -context of chrome.webviewTag, and shouldn't necessarily crash. - -This also fixes an associated crash in Electron, where the NOTREACHED is -hit when PointerLockController::LockPointer calls web_contents->Focus(). - -Change-Id: Ide58aae2187fbdd807be4ec176d13c76e459ba9c -Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6508949 -Commit-Queue: Bo Liu -Reviewed-by: Bo Liu -Reviewed-by: Rakina Zata Amni -Cr-Commit-Position: refs/heads/main@{#1456886} - -diff --git a/content/browser/web_contents/web_contents_view_child_frame.cc b/content/browser/web_contents/web_contents_view_child_frame.cc -index b89d4621dc2acc84f7d8c749f34f7f5563543c72..9c206f6ee424fc423d5f772c7559e60ec0df6eef 100644 ---- a/content/browser/web_contents/web_contents_view_child_frame.cc -+++ b/content/browser/web_contents/web_contents_view_child_frame.cc -@@ -6,6 +6,7 @@ - - #include - -+#include "base/notimplemented.h" - #include "build/build_config.h" - #include "content/browser/renderer_host/render_frame_proxy_host.h" - #include "content/browser/renderer_host/render_widget_host_view_child_frame.h" -@@ -160,15 +161,15 @@ void WebContentsViewChildFrame::DestroyBackForwardTransitionAnimationManager() { - } - - void WebContentsViewChildFrame::RestoreFocus() { -- NOTREACHED(); -+ NOTIMPLEMENTED(); - } - - void WebContentsViewChildFrame::Focus() { -- NOTREACHED(); -+ NOTIMPLEMENTED(); - } - - void WebContentsViewChildFrame::StoreFocus() { -- NOTREACHED(); -+ NOTIMPLEMENTED(); - } - - void WebContentsViewChildFrame::FocusThroughTabTraversal(bool reverse) { diff --git a/patches/chromium/make_gtk_getlibgtk_public.patch b/patches/chromium/make_gtk_getlibgtk_public.patch index 061d60815ece8..fc6108e88b1b5 100644 --- a/patches/chromium/make_gtk_getlibgtk_public.patch +++ b/patches/chromium/make_gtk_getlibgtk_public.patch @@ -7,10 +7,10 @@ Allows embedders to get a handle to the gdk_pixbuf library already loaded in the process. diff --git a/ui/gtk/gtk_compat.cc b/ui/gtk/gtk_compat.cc -index 946eb3eef6b0c546ace65de0c7f14b4642208090..9c9a35d439602ea3612ed648931990ec224c8799 100644 +index 37bb48273cf4833c88622f1158aebfee9423d085..2009a095abfae3207d73c47245e061ff3f9cef80 100644 --- a/ui/gtk/gtk_compat.cc +++ b/ui/gtk/gtk_compat.cc -@@ -70,11 +70,6 @@ void* GetLibGio() { +@@ -69,11 +69,6 @@ void* GetLibGio() { return libgio; } @@ -22,7 +22,7 @@ index 946eb3eef6b0c546ace65de0c7f14b4642208090..9c9a35d439602ea3612ed648931990ec void* GetLibGdk3() { static void* libgdk3 = DlOpen("libgdk-3.so.0"); return libgdk3; -@@ -170,6 +165,11 @@ gfx::Insets InsetsFromGtkBorder(const GtkBorder& border) { +@@ -169,6 +164,11 @@ gfx::Insets InsetsFromGtkBorder(const GtkBorder& border) { } // namespace diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 665e92fc25d62..6d3f53957a6c4 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,7 +35,7 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index 02ac517502a51603a689c74d8073b2e5862f1e45..f0d167bb6c3a53950c431170eaa45a69408f93d9 100644 +index 7860ff639da1116f007fda4ecf3010d065203f8c..c61bc8d60d69d348da992c980c6222c7c21623af 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn @@ -1046,6 +1046,7 @@ component("base") { @@ -582,10 +582,10 @@ index d83f420d25e2c108ad400ebecae02b1ac327c058..77852c5c315ac09dddb7227adf3b840e return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 86e30304014f4811578595013a20a76790b1e84d..7964ac6af0fc3821b8208e34be766a712ccd2026 100644 +index b40575d6a1201e3543927f8d71ebf76d61a61ab7..088555a527f6a93486cd2cede7f4ba0b46b22fa1 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -343,6 +343,7 @@ source_set("browser") { +@@ -342,6 +342,7 @@ source_set("browser") { "//ui/webui/resources", "//v8", "//v8:v8_version", @@ -797,7 +797,7 @@ index a1068589ad844518038ee7bc15a3de9bc5cba525..1ff781c49f086ec8015c7d3c44567dbe } // namespace content diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn -index 2c8e8e9b4260366b5312be7f2a3bbf9d332fe916..fb9e07491c93593904db7fd55c24e67820de982c 100644 +index 4df384721ee529863d35ae7afe8249e3989697b0..2369ebc00ff008a94409d68404d3017f85592f74 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn @@ -664,6 +664,7 @@ static_library("test_support") { @@ -937,7 +937,7 @@ index f89dbdfb0c4e8e31d387d1ce2e5304277ac4df26..7b75bfeba59345d63f4ac81153697941 namespace ui { diff --git a/media/audio/BUILD.gn b/media/audio/BUILD.gn -index 8bcbb663710445e977a3080209cd518d3fc2c6e0..0680d3af1f219235e20c0e83b80c0ea9cbf7b3a1 100644 +index 4f663e28aa078bd2e692a79d06dbdde055287f3c..8588214d7f30384cc37aaf0062c941a854d4bba5 100644 --- a/media/audio/BUILD.gn +++ b/media/audio/BUILD.gn @@ -198,6 +198,7 @@ source_set("audio") { @@ -1448,10 +1448,10 @@ index 1b5e616ebd3c610739a9dcf3fd6694f1e442d783..8449d7eb65687fa82db0f23c7627807e if (is_mac) { diff --git a/third_party/blink/renderer/core/editing/build.gni b/third_party/blink/renderer/core/editing/build.gni -index 0645e5e49137b753bbc17138c88eabc53969bed8..8dcf005f4ae7bcf996b4d868e6f4855a6148d4b1 100644 +index 8e0ca95409bf8d350658effa26c53453e2d434a0..373e3b8f9522be27ab78448557139054e98ad589 100644 --- a/third_party/blink/renderer/core/editing/build.gni +++ b/third_party/blink/renderer/core/editing/build.gni -@@ -362,10 +362,14 @@ blink_core_sources_editing = [ +@@ -364,10 +364,14 @@ blink_core_sources_editing = [ if (is_mac) { blink_core_sources_editing += [ "commands/smart_replace_cf.cc", @@ -1801,10 +1801,10 @@ index fc25ba79d2b0e1acdb7ba54b89e7d6e16f94771b..de771ef414b9a69e331261524f08e9a1 } // namespace diff --git a/ui/display/BUILD.gn b/ui/display/BUILD.gn -index e598004da50257f4ee37a6431222c2b9e9f24b62..3f2ea7a469d6580d25fe51b657555d77a9ce9b80 100644 +index 491b8006c83c8602122a77d60e161c2167744756..abbf5248199598eadb57af99c3e3dc4c72f58af9 100644 --- a/ui/display/BUILD.gn +++ b/ui/display/BUILD.gn -@@ -127,6 +127,12 @@ component("display") { +@@ -129,6 +129,12 @@ component("display") { "//ui/gfx/geometry", ] @@ -1818,18 +1818,18 @@ index e598004da50257f4ee37a6431222c2b9e9f24b62..3f2ea7a469d6580d25fe51b657555d77 deps += [ "//build:ios_buildflags" ] } diff --git a/ui/display/mac/screen_mac.mm b/ui/display/mac/screen_mac.mm -index 874ac9d572931fe175ccab8beb7738fe0a7b3c1b..b70e2a8a7be9e00a379f47c77589dde6b8b1f081 100644 +index 033ebc0036bcd373b011ca829d255e8c83701a6d..ad06707f31872c58217d2d034f050c5570010ba5 100644 --- a/ui/display/mac/screen_mac.mm +++ b/ui/display/mac/screen_mac.mm -@@ -30,6 +30,7 @@ +@@ -32,6 +32,7 @@ #include "base/trace_event/trace_event.h" #include "build/build_config.h" #include "components/device_event_log/device_event_log.h" +#include "electron/mas.h" #include "ui/display/display.h" #include "ui/display/display_change_notifier.h" - #include "ui/display/util/display_util.h" -@@ -177,7 +178,17 @@ DisplayMac BuildDisplayForScreen(NSScreen* screen) { + #include "ui/display/mac/screen_mac_headless.h" +@@ -181,7 +182,17 @@ DisplayMac BuildDisplayForScreen(NSScreen* screen) { display.set_color_depth(Display::kDefaultBitsPerPixel); display.set_depth_per_component(Display::kDefaultBitsPerComponent); } @@ -1848,7 +1848,7 @@ index 874ac9d572931fe175ccab8beb7738fe0a7b3c1b..b70e2a8a7be9e00a379f47c77589dde6 // Query the display's refresh rate. if (@available(macos 12.0, *)) { diff --git a/ui/gfx/BUILD.gn b/ui/gfx/BUILD.gn -index c8f01a88e0d1797baf53c517341c735d9c6e6b4a..345743dd19f862cf2b4304d70cb47ce68e6895d1 100644 +index af66f53bbec8e3cf9b1e2e69e602173725958706..381498a4d51b32a30a206d9ec3878d9ab3109386 100644 --- a/ui/gfx/BUILD.gn +++ b/ui/gfx/BUILD.gn @@ -337,6 +337,12 @@ component("gfx") { diff --git a/patches/chromium/notification_provenance.patch b/patches/chromium/notification_provenance.patch index 293237d00ddd8..9880ad53ec02f 100644 --- a/patches/chromium/notification_provenance.patch +++ b/patches/chromium/notification_provenance.patch @@ -133,7 +133,7 @@ index 5be62a3fb27e37f3c1db6b811172f6dfebe18f61..34349f9832fe4b9a3d48db613a789afb const GURL& document_url, const WeakDocumentPtr& weak_document_ptr, diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index 3b2c512edec286bcc283a1cff14d96d469d8b4db..6e435b12521d663086be770bb89106368b06d159 100644 +index 2dcb080a4bd9b2cd6a9f8f8ae41305dfd4400066..332f611678e53c0ea56c8baea71ca123d8cc0a95 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc @@ -2217,7 +2217,7 @@ void RenderProcessHostImpl::CreateNotificationService( diff --git a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch b/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch deleted file mode 100644 index b158e8a185200..0000000000000 --- a/patches/chromium/partially_revert_is_newly_created_to_allow_for_browser_initiated.patch +++ /dev/null @@ -1,26 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Samuel Attard -Date: Wed, 1 May 2024 11:12:44 -0700 -Subject: partially revert is_newly_created to allow for browser initiated - about:blank loads - -We should either wire in debug info from about:blank loads or more cleanly add -an about:blank check to this area. - -Ref: https://chromium-review.googlesource.com/c/chromium/src/+/5403876 - -diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 71174dc9f0e15622c67a2d33dc119594de68fc69..d73dced1fa1ad073a75df83657380a78659a8a1e 100644 ---- a/content/browser/renderer_host/render_frame_host_impl.cc -+++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -808,8 +808,8 @@ void VerifyThatBrowserAndRendererCalculatedOriginsToCommitMatch( - // TODO(crbug.com/40092527): Consider adding a separate boolean that - // tracks this instead of piggybacking `origin_calculation_debug_info`. - if (renderer_side_origin.opaque() && -- browser_side_origin_and_debug_info.first->opaque() && -- params.origin_calculation_debug_info.ends_with("is_newly_created")) { -+ browser_side_origin_and_debug_info.first->opaque() /*&& -+ params.origin_calculation_debug_info.ends_with("is_newly_created")*/) { - origins_match = (renderer_side_origin.GetTupleOrPrecursorTupleIfOpaque() == - browser_side_origin_and_debug_info.first - ->GetTupleOrPrecursorTupleIfOpaque()); diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index ceff97c56ad66..5cd755ed1d69b 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -881,10 +881,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 7964ac6af0fc3821b8208e34be766a712ccd2026..5bb585cb7f0ec4e15038bba89179817d43256719 100644 +index 088555a527f6a93486cd2cede7f4ba0b46b22fa1..c04a351865e2fc49481f5068f91e53ec909dfce1 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3158,8 +3158,9 @@ source_set("browser") { +@@ -3161,8 +3161,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 4bf2d50bdaddb..c2ca450009b8f 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -44,10 +44,10 @@ index 23d5baa267333e18551d449317f3e3a6520f34a6..2551b4a2b9dfca9767c39e2e9bd79ed1 void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index b6fc96993cdea489450978495ca4c1f3c58166af..94b4429fffb474304c1d43d1cf1337fde90d9e45 100644 +index e42e462f3c8109444e6dadb0557e38cdd05c362a..2eb45ae773f9fbd28fa05b14e5684f4b7d17cc85 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5891,6 +5891,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -5914,6 +5914,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,10 +60,10 @@ index b6fc96993cdea489450978495ca4c1f3c58166af..94b4429fffb474304c1d43d1cf1337fd RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index 54e9de12419c5e70775116b404d8ea4d370197bb..e1535116bbffeda9b6a881849c0a7d9de001c248 100644 +index 08497c589757778543bedbfa920554c5fb9a298e..aa428be6f3701dc5d856e288180c54cf7559cc6f 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h -@@ -1183,6 +1183,7 @@ class CONTENT_EXPORT WebContentsImpl +@@ -1188,6 +1188,7 @@ class CONTENT_EXPORT WebContentsImpl void SendScreenRects() override; void SendActiveState(bool active) override; TextInputManager* GetTextInputManager() override; diff --git a/patches/chromium/refactor_expose_file_system_access_blocklist.patch b/patches/chromium/refactor_expose_file_system_access_blocklist.patch index 2b66b7778412f..2e7293355ab49 100644 --- a/patches/chromium/refactor_expose_file_system_access_blocklist.patch +++ b/patches/chromium/refactor_expose_file_system_access_blocklist.patch @@ -8,18 +8,24 @@ it in Electron and prevent drift from Chrome's blocklist. We should look for a w to upstream this change to Chrome. diff --git a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc -index 3514864559de0d2f2f36fda9b0add0b7b88f3b2a..5ffe260596202bacc58aa83d68855d05f7e76108 100644 +index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255cab529c646 100644 --- a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc +++ b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc -@@ -45,7 +45,6 @@ - #include "chrome/browser/ui/file_system_access/file_system_access_dangerous_file_dialog.h" - #include "chrome/browser/ui/file_system_access/file_system_access_dialogs.h" - #include "chrome/browser/ui/file_system_access/file_system_access_restricted_directory_dialog.h" --#include "chrome/common/chrome_paths.h" - #include "chrome/grit/generated_resources.h" - #include "components/content_settings/core/browser/host_content_settings_map.h" - #include "components/content_settings/core/common/content_settings.h" -@@ -261,114 +260,13 @@ bool MaybeIsLocalUNCPath(const base::FilePath& path) { +@@ -82,11 +82,13 @@ + #include "chrome/browser/ui/browser_window.h" + #include "chrome/browser/ui/tabs/public/tab_features.h" + #include "chrome/browser/ui/views/file_system_access/file_system_access_page_action_controller.h" ++#if 0 + #include "chrome/browser/web_applications/proto/web_app_install_state.pb.h" + #include "chrome/browser/web_applications/web_app_install_manager.h" + #include "chrome/browser/web_applications/web_app_install_manager_observer.h" + #include "chrome/browser/web_applications/web_app_provider.h" + #include "chrome/browser/web_applications/web_app_registrar.h" ++#endif + #include "components/tabs/public/tab_interface.h" + #if BUILDFLAG(ENABLE_PLATFORM_APPS) + #include "extensions/browser/extension_registry.h" // nogncheck +@@ -262,182 +264,10 @@ bool MaybeIsLocalUNCPath(const base::FilePath& path) { } #endif @@ -27,264 +33,448 @@ index 3514864559de0d2f2f36fda9b0add0b7b88f3b2a..5ffe260596202bacc58aa83d68855d05 -// the struct below. -constexpr const int kNoBasePathKey = -1; - +-// A wrapper around `base::NormalizeFilePath` that returns its result instead of +-// using an out parameter. +-base::FilePath NormalizeFilePath(const base::FilePath& path) { +- CHECK(path.IsAbsolute()); +- // TODO(crbug.com/368130513O): On Windows, this call will fail if the target +- // file path is greater than MAX_PATH. We should decide how to handle this +- // scenario. +- base::FilePath normalized_path; +- if (!base::NormalizeFilePath(path, &normalized_path)) { +- return path; +- } +- CHECK_EQ(path.empty(), normalized_path.empty()); +- return normalized_path; +-} +- -using BlockType = ChromeFileSystemAccessPermissionContext::BlockType; - --std::vector --GenerateBlockedPath() { -- return { -- // Don't allow users to share their entire home directory, entire desktop -- // or entire documents folder, but do allow sharing anything inside those -- // directories not otherwise blocked. -- {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, -- {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, -- {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, -- // Similar restrictions for the downloads directory. -- {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, BlockType::kDontBlockChildren}, -- {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, -- BlockType::kDontBlockChildren}, -- // The Chrome installation itself should not be modified by the web. -- {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, -- // And neither should the configuration of at least the currently running -- // Chrome instance (note that this does not take --user-data-dir command -- // line overrides into account). -- {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, -- // ~/.ssh is pretty sensitive on all platforms, so block access to that. -- {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), BlockType::kBlockAllChildren}, -- // And limit access to ~/.gnupg as well. -- {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), -- BlockType::kBlockAllChildren}, +-std::unique_ptr +-GenerateBlockPaths(bool should_normalize_file_path) { +- static constexpr ChromeFileSystemAccessPermissionContext::BlockPath +- kBlockPaths[] = { +- // Don't allow users to share their entire home directory, entire +- // desktop or entire documents folder, but do allow sharing anything +- // inside those directories not otherwise blocked. +- {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, +- {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, +- {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, +- // Similar restrictions for the downloads directory. +- {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, +- BlockType::kDontBlockChildren}, +- {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, +- BlockType::kDontBlockChildren}, +- // The Chrome installation itself should not be modified by the web. +- {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, +- // And neither should the configuration of at least the currently +- // running +- // Chrome instance (note that this does not take --user-data-dir +- // command +- // line overrides into account). +- {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, +- // ~/.ssh is pretty sensitive on all platforms, so block access to +- // that. +- {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), +- BlockType::kBlockAllChildren}, +- // And limit access to ~/.gnupg as well. +- {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), +- BlockType::kBlockAllChildren}, -#if BUILDFLAG(IS_WIN) -- // Some Windows specific directories to block, basically all apps, the -- // operating system itself, as well as configuration data for apps. -- {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- // Opening a file from an MTP device, such as a smartphone or a camera, is -- // implemented by Windows as opening a file in the temporary internet -- // files directory. To support that, allow opening files in that -- // directory, but not whole directories. -- {base::DIR_IE_INTERNET_CACHE, nullptr, -- BlockType::kBlockNestedDirectories}, +- // Some Windows specific directories to block, basically all apps, the +- // operating system itself, as well as configuration data for apps. +- {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- // Opening a file from an MTP device, such as a smartphone or a +- // camera, is +- // implemented by Windows as opening a file in the temporary internet +- // files directory. To support that, allow opening files in that +- // directory, but not whole directories. +- {base::DIR_IE_INTERNET_CACHE, nullptr, +- BlockType::kBlockNestedDirectories}, -#endif -#if BUILDFLAG(IS_MAC) -- // Similar Mac specific blocks. -- {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- // Block access to the current bundle directory. -- {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, -- // Block access to the user's Applications directory. -- {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), -- BlockType::kBlockAllChildren}, -- // Block access to the root Applications directory. -- {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), -- BlockType::kBlockAllChildren}, -- {base::DIR_HOME, FILE_PATH_LITERAL("Library"), -- BlockType::kBlockAllChildren}, -- // Allow access to other cloud files, such as Google Drive. -- {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), -- BlockType::kDontBlockChildren}, -- // Allow the site to interact with data from its corresponding natively -- // installed (sandboxed) application. It would be nice to limit a site to -- // access only _its_ corresponding natively installed application, but -- // unfortunately there's no straightforward way to do that. See -- // https://crbug.com/984641#c22. -- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), -- BlockType::kDontBlockChildren}, -- // Allow access to iCloud files... -- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), -- BlockType::kDontBlockChildren}, -- // ... which may also appear at this directory. -- {base::DIR_HOME, -- FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), -- BlockType::kDontBlockChildren}, +- // Similar Mac specific blocks. +- {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- // Block access to the current bundle directory. +- {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, +- // Block access to the user's Applications directory. +- {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), +- BlockType::kBlockAllChildren}, +- // Block access to the root Applications directory. +- {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), +- BlockType::kBlockAllChildren}, +- {base::DIR_HOME, FILE_PATH_LITERAL("Library"), +- BlockType::kBlockAllChildren}, +- // Allow access to other cloud files, such as Google Drive. +- {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), +- BlockType::kDontBlockChildren}, +- // Allow the site to interact with data from its corresponding +- // natively +- // installed (sandboxed) application. It would be nice to limit a site +- // to +- // access only _its_ corresponding natively installed application, but +- // unfortunately there's no straightforward way to do that. See +- // https://crbug.com/984641#c22. +- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), +- BlockType::kDontBlockChildren}, +- // Allow access to iCloud files... +- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), +- BlockType::kDontBlockChildren}, +- // ... which may also appear at this directory. +- {base::DIR_HOME, +- FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), +- BlockType::kDontBlockChildren}, -#endif -#if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_ANDROID) -- // On Linux also block access to devices via /dev. -- {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), BlockType::kBlockAllChildren}, -- // And security sensitive data in /proc and /sys. -- {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), -- BlockType::kBlockAllChildren}, -- {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), BlockType::kBlockAllChildren}, -- // And system files in /boot and /etc. -- {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), -- BlockType::kBlockAllChildren}, -- {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), BlockType::kBlockAllChildren}, -- // And block all of ~/.config, matching the similar restrictions on mac -- // and windows. -- {base::DIR_HOME, FILE_PATH_LITERAL(".config"), -- BlockType::kBlockAllChildren}, -- // Block ~/.dbus as well, just in case, although there probably isn't much -- // a website can do with access to that directory and its contents. -- {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), -- BlockType::kBlockAllChildren}, +- // On Linux also block access to devices via /dev. +- {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), +- BlockType::kBlockAllChildren}, +- // And security sensitive data in /proc and /sys. +- {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), +- BlockType::kBlockAllChildren}, +- {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), +- BlockType::kBlockAllChildren}, +- // And system files in /boot and /etc. +- {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), +- BlockType::kBlockAllChildren}, +- {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), +- BlockType::kBlockAllChildren}, +- // And block all of ~/.config, matching the similar restrictions on +- // mac +- // and windows. +- {base::DIR_HOME, FILE_PATH_LITERAL(".config"), +- BlockType::kBlockAllChildren}, +- // Block ~/.dbus as well, just in case, although there probably isn't +- // much +- // a website can do with access to that directory and its contents. +- {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), +- BlockType::kBlockAllChildren}, -#endif -#if BUILDFLAG(IS_ANDROID) -- {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, -#endif -- // TODO(crbug.com/40095723): Refine this list, for example add -- // XDG_CONFIG_HOME when it is not set ~/.config? -- }; +- // TODO(crbug.com/40095723): Refine this list, for example add +- // XDG_CONFIG_HOME when it is not set ~/.config? +- }; +- +- // ChromeOS supports multi-user sign-in. base::DIR_HOME only returns the +- // profile path for the primary user, the first user to sign in. We want to +- // use the `profile_path` instead since that's associated with user that +- // initiated this blocklist check. +- // +- // TODO(crbug.com/375490221): Improve the ChromeOS blocklist logic. +- constexpr bool kUseProfilePathForDirHome = BUILDFLAG(IS_CHROMEOS); +- // Populate the hard-coded rules. +- auto block_path_rules = std::make_unique< +- ChromeFileSystemAccessPermissionContext::BlockPathRules>(); +- +- for (const auto& blocked_path : kBlockPaths) { +- base::FilePath path; +- if (blocked_path.base_path_key != kNoBasePathKey) { +- if (kUseProfilePathForDirHome && +- blocked_path.base_path_key == base::DIR_HOME) { +- block_path_rules->profile_based_block_path_rules_.emplace_back( +- blocked_path.path, blocked_path.type); +- continue; +- } +- +- if (!base::PathService::Get(blocked_path.base_path_key, &path)) { +- continue; +- } +- +- if (blocked_path.path) { +- path = path.Append(blocked_path.path); +- } +- } else { +- DCHECK(blocked_path.path); +- path = base::FilePath(blocked_path.path); +- } +- block_path_rules->block_path_rules_.emplace_back( +- should_normalize_file_path ? NormalizeFilePath(path) : path, +- blocked_path.type); +- } +- +- return block_path_rules; -} +// This patch moves the deleted content from this file over to +// chrome/browser/file_system_access/chrome_file_system_access_permission_context.h. +// NOTE IF THERE IS A CONFLICT ABOVE, you will need to copy the changes in the +// removed block over to chrome_file_system_access_permission_context.h. -+ -+// Describes a rule for blocking a directory, which can be constructed -+// dynamically (based on state) or statically (from kBlockedPaths). - // A wrapper around `base::NormalizeFilePath` that returns its result instead of - // using an out parameter. + // Checks if `path` should be blocked by the `rules`. + // The BlockType of the nearest ancestor of a path to check is what +@@ -1261,16 +1091,6 @@ struct ChromeFileSystemAccessPermissionContext::OriginState { + std::unique_ptr cleanup_timer; + }; + +-ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules() = +- default; +-ChromeFileSystemAccessPermissionContext::BlockPathRules::~BlockPathRules() = +- default; +-ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules( +- const BlockPathRules& other) = default; +-ChromeFileSystemAccessPermissionContext::BlockPathRules& +-ChromeFileSystemAccessPermissionContext::BlockPathRules::operator=( +- const BlockPathRules& other) = default; +- + ChromeFileSystemAccessPermissionContext:: + ChromeFileSystemAccessPermissionContext(content::BrowserContext* context, + const base::Clock* clock) +@@ -1289,7 +1109,7 @@ ChromeFileSystemAccessPermissionContext:: + #if BUILDFLAG(IS_ANDROID) + one_time_permissions_tracker_.Observe( + OneTimePermissionsTrackerFactory::GetForBrowserContext(context)); +-#else ++#elif 0 + auto* provider = web_app::WebAppProvider::GetForWebApps( + Profile::FromBrowserContext(profile_)); + if (provider) { +@@ -2551,7 +2371,7 @@ void ChromeFileSystemAccessPermissionContext::OnShutdown() { + one_time_permissions_tracker_.Reset(); + } + +-#if !BUILDFLAG(IS_ANDROID) ++#if 0 + void ChromeFileSystemAccessPermissionContext::OnWebAppInstalled( + const webapps::AppId& app_id) { + if (!base::FeatureList::IsEnabled( +@@ -3108,11 +2928,7 @@ bool ChromeFileSystemAccessPermissionContext::OriginHasExtendedPermission( + const url::Origin& origin) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + +-#if BUILDFLAG(IS_ANDROID) +- // TODO(crbug.com/40101963): Enable when android persisted permissions are +- // implemented. +- return false; +-#else ++#if 0 + if (!base::FeatureList::IsEnabled( + features::kFileSystemAccessPersistentPermissions)) { + return false; +@@ -3156,6 +2972,7 @@ bool ChromeFileSystemAccessPermissionContext::OriginHasExtendedPermission( + : WebAppInstallStatus::kUninstalled; + return app_has_os_integration; + #endif // BUILDFLAG(IS_ANDROID) ++ return false; + } + + void ChromeFileSystemAccessPermissionContext::SetOriginExtendedPermissionByUser( diff --git a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h -index 46a2019587b534add3c89f464cdf7261a67e7cce..7d313934b24b32830976ce19479cf3b00d3ddca8 100644 +index 5e1aa12c6337e8d0dee9f24d7ec233a894763053..e1e6a8163be4c95031a464481f55357af253cfb2 100644 --- a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h +++ b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h -@@ -21,7 +21,7 @@ +@@ -9,10 +9,13 @@ + #include + + #include "base/auto_reset.h" ++#include "base/base_paths.h" + #include "base/callback_list.h" + #include "base/files/file_path.h" ++#include "base/files/file_util.h" + #include "base/memory/raw_ptr.h" + #include "base/memory/weak_ptr.h" ++#include "base/path_service.h" + #include "base/scoped_observation.h" + #include "base/sequence_checker.h" + #include "base/time/clock.h" +@@ -22,6 +25,7 @@ #include "chrome/browser/file_system_access/file_system_access_permission_request_manager.h" #include "chrome/browser/permissions/one_time_permissions_tracker.h" #include "chrome/browser/permissions/one_time_permissions_tracker_observer.h" --#include "components/enterprise/buildflags/buildflags.h" +#include "chrome/common/chrome_paths.h" + #include "components/enterprise/buildflags/buildflags.h" #include "components/permissions/features.h" #include "components/permissions/object_permission_context_base.h" - #include "content/public/browser/file_system_access_permission_context.h" -@@ -31,7 +31,7 @@ - #include "chrome/browser/web_applications/web_app_install_manager_observer.h" - #endif - --#if BUILDFLAG(ENTERPRISE_CLOUD_CONTENT_ANALYSIS) -+#if 0 - #include "components/enterprise/common/files_scan_data.h" - #endif - -@@ -371,6 +371,115 @@ class ChromeFileSystemAccessPermissionContext - // KeyedService: - void Shutdown() override; +@@ -399,6 +403,183 @@ class ChromeFileSystemAccessPermissionContext + // This is needed when updating path with ScopedPathOverride. + void ResetBlockPathsForTesting(); + // Sentinel used to indicate that no PathService key is specified for a path in + // the struct below. + static constexpr const int kNoBasePathKey = -1; + ++ // A wrapper around `base::NormalizeFilePath` that returns its result instead of ++ // using an out parameter. ++ static base::FilePath NormalizeFilePath(const base::FilePath& path) { ++ CHECK(path.IsAbsolute()); ++ // TODO(crbug.com/368130513O): On Windows, this call will fail if the target ++ // file path is greater than MAX_PATH. We should decide how to handle this ++ // scenario. ++ base::FilePath normalized_path; ++ if (!base::NormalizeFilePath(path, &normalized_path)) { ++ return path; ++ } ++ CHECK_EQ(path.empty(), normalized_path.empty()); ++ return normalized_path; ++ } ++ + using BlockType = ChromeFileSystemAccessPermissionContext::BlockType; + -+ static std::vector -+ GenerateBlockedPath() { -+ return { -+ // Don't allow users to share their entire home directory, entire desktop -+ // or entire documents folder, but do allow sharing anything inside those -+ // directories not otherwise blocked. -+ {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, -+ {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, -+ {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, -+ // Similar restrictions for the downloads directory. -+ {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, BlockType::kDontBlockChildren}, -+ {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, -+ BlockType::kDontBlockChildren}, -+ // The Chrome installation itself should not be modified by the web. -+ {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, -+ // And neither should the configuration of at least the currently running -+ // Chrome instance (note that this does not take --user-data-dir command -+ // line overrides into account). -+ {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, -+ // ~/.ssh is pretty sensitive on all platforms, so block access to that. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), BlockType::kBlockAllChildren}, -+ // And limit access to ~/.gnupg as well. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), -+ BlockType::kBlockAllChildren}, ++ static std::unique_ptr ++ GenerateBlockPaths(bool should_normalize_file_path) { ++ static constexpr ChromeFileSystemAccessPermissionContext::BlockPath ++ kBlockPaths[] = { ++ // Don't allow users to share their entire home directory, entire ++ // desktop or entire documents folder, but do allow sharing anything ++ // inside those directories not otherwise blocked. ++ {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, ++ {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, ++ {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, ++ // Similar restrictions for the downloads directory. ++ {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, ++ BlockType::kDontBlockChildren}, ++ {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, ++ BlockType::kDontBlockChildren}, ++ // The Chrome installation itself should not be modified by the web. ++ {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, ++ // And neither should the configuration of at least the currently ++ // running ++ // Chrome instance (note that this does not take --user-data-dir ++ // command ++ // line overrides into account). ++ {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, ++ // ~/.ssh is pretty sensitive on all platforms, so block access to ++ // that. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), ++ BlockType::kBlockAllChildren}, ++ // And limit access to ~/.gnupg as well. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), ++ BlockType::kBlockAllChildren}, + #if BUILDFLAG(IS_WIN) -+ // Some Windows specific directories to block, basically all apps, the -+ // operating system itself, as well as configuration data for apps. -+ {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ // Opening a file from an MTP device, such as a smartphone or a camera, is -+ // implemented by Windows as opening a file in the temporary internet -+ // files directory. To support that, allow opening files in that -+ // directory, but not whole directories. -+ {base::DIR_IE_INTERNET_CACHE, nullptr, -+ BlockType::kBlockNestedDirectories}, ++ // Some Windows specific directories to block, basically all apps, the ++ // operating system itself, as well as configuration data for apps. ++ {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ // Opening a file from an MTP device, such as a smartphone or a ++ // camera, is ++ // implemented by Windows as opening a file in the temporary internet ++ // files directory. To support that, allow opening files in that ++ // directory, but not whole directories. ++ {base::DIR_IE_INTERNET_CACHE, nullptr, ++ BlockType::kBlockNestedDirectories}, + #endif + #if BUILDFLAG(IS_MAC) -+ // Similar Mac specific blocks. -+ {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ // Block access to the current bundle directory. -+ {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, -+ // Block access to the user's Applications directory. -+ {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), -+ BlockType::kBlockAllChildren}, -+ // Block access to the root Applications directory. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), -+ BlockType::kBlockAllChildren}, -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library"), -+ BlockType::kBlockAllChildren}, -+ // Allow access to other cloud files, such as Google Drive. -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), -+ BlockType::kDontBlockChildren}, -+ // Allow the site to interact with data from its corresponding natively -+ // installed (sandboxed) application. It would be nice to limit a site to -+ // access only _its_ corresponding natively installed application, but -+ // unfortunately there's no straightforward way to do that. See -+ // https://crbug.com/984641#c22. -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), -+ BlockType::kDontBlockChildren}, -+ // Allow access to iCloud files... -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), -+ BlockType::kDontBlockChildren}, -+ // ... which may also appear at this directory. -+ {base::DIR_HOME, -+ FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), -+ BlockType::kDontBlockChildren}, ++ // Similar Mac specific blocks. ++ {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ // Block access to the current bundle directory. ++ {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, ++ // Block access to the user's Applications directory. ++ {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), ++ BlockType::kBlockAllChildren}, ++ // Block access to the root Applications directory. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), ++ BlockType::kBlockAllChildren}, ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library"), ++ BlockType::kBlockAllChildren}, ++ // Allow access to other cloud files, such as Google Drive. ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), ++ BlockType::kDontBlockChildren}, ++ // Allow the site to interact with data from its corresponding ++ // natively ++ // installed (sandboxed) application. It would be nice to limit a site ++ // to ++ // access only _its_ corresponding natively installed application, but ++ // unfortunately there's no straightforward way to do that. See ++ // https://crbug.com/984641#c22. ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), ++ BlockType::kDontBlockChildren}, ++ // Allow access to iCloud files... ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), ++ BlockType::kDontBlockChildren}, ++ // ... which may also appear at this directory. ++ {base::DIR_HOME, ++ FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), ++ BlockType::kDontBlockChildren}, + #endif + #if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_ANDROID) -+ // On Linux also block access to devices via /dev. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), BlockType::kBlockAllChildren}, -+ // And security sensitive data in /proc and /sys. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), -+ BlockType::kBlockAllChildren}, -+ {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), BlockType::kBlockAllChildren}, -+ // And system files in /boot and /etc. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), -+ BlockType::kBlockAllChildren}, -+ {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), BlockType::kBlockAllChildren}, -+ // And block all of ~/.config, matching the similar restrictions on mac -+ // and windows. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".config"), -+ BlockType::kBlockAllChildren}, -+ // Block ~/.dbus as well, just in case, although there probably isn't much -+ // a website can do with access to that directory and its contents. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), -+ BlockType::kBlockAllChildren}, ++ // On Linux also block access to devices via /dev. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), ++ BlockType::kBlockAllChildren}, ++ // And security sensitive data in /proc and /sys. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), ++ BlockType::kBlockAllChildren}, ++ {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), ++ BlockType::kBlockAllChildren}, ++ // And system files in /boot and /etc. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), ++ BlockType::kBlockAllChildren}, ++ {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), ++ BlockType::kBlockAllChildren}, ++ // And block all of ~/.config, matching the similar restrictions on ++ // mac ++ // and windows. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".config"), ++ BlockType::kBlockAllChildren}, ++ // Block ~/.dbus as well, just in case, although there probably isn't ++ // much ++ // a website can do with access to that directory and its contents. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), ++ BlockType::kBlockAllChildren}, + #endif + #if BUILDFLAG(IS_ANDROID) -+ {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, + #endif -+ // TODO(crbug.com/40095723): Refine this list, for example add -+ // XDG_CONFIG_HOME when it is not set ~/.config? -+ }; ++ // TODO(crbug.com/40095723): Refine this list, for example add ++ // XDG_CONFIG_HOME when it is not set ~/.config? ++ }; ++ ++ // ChromeOS supports multi-user sign-in. base::DIR_HOME only returns the ++ // profile path for the primary user, the first user to sign in. We want to ++ // use the `profile_path` instead since that's associated with user that ++ // initiated this blocklist check. ++ // ++ // TODO(crbug.com/375490221): Improve the ChromeOS blocklist logic. ++ constexpr bool kUseProfilePathForDirHome = BUILDFLAG(IS_CHROMEOS); ++ // Populate the hard-coded rules. ++ auto block_path_rules = std::make_unique< ++ ChromeFileSystemAccessPermissionContext::BlockPathRules>(); ++ ++ for (const auto& blocked_path : kBlockPaths) { ++ base::FilePath path; ++ if (blocked_path.base_path_key != kNoBasePathKey) { ++ if (kUseProfilePathForDirHome && ++ blocked_path.base_path_key == base::DIR_HOME) { ++ block_path_rules->profile_based_block_path_rules_.emplace_back( ++ blocked_path.path, blocked_path.type); ++ continue; ++ } ++ ++ if (!base::PathService::Get(blocked_path.base_path_key, &path)) { ++ continue; ++ } ++ ++ if (blocked_path.path) { ++ path = path.Append(blocked_path.path); ++ } ++ } else { ++ DCHECK(blocked_path.path); ++ path = base::FilePath(blocked_path.path); ++ } ++ block_path_rules->block_path_rules_.emplace_back( ++ should_normalize_file_path ? NormalizeFilePath(path) : path, ++ blocked_path.type); ++ } ++ ++ return block_path_rules; + } + protected: SEQUENCE_CHECKER(sequence_checker_); -@@ -390,7 +499,7 @@ class ChromeFileSystemAccessPermissionContext - - void PermissionGrantDestroyed(PermissionGrantImpl* grant); - --#if BUILDFLAG(ENTERPRISE_CLOUD_CONTENT_ANALYSIS) -+#if 0 - void OnContentAnalysisComplete( - std::vector entries, - EntriesAllowedByEnterprisePolicyCallback callback, diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index 552175e6ca3ce..1e61394bec701 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 46fc6d6683c50fb8a340680de2eda340f5be4cca..2be25d84a831b0fa2baefeb95d413a5503d64b1b 100644 +index d0f42ceedfac643443e3c7c5757b831f481a72eb..b6e0304e561bd81dc09924cab04887437dca84b7 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10134,25 +10134,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10156,25 +10156,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/resource_file_conflict.patch b/patches/chromium/resource_file_conflict.patch index 2f21e75bd6457..19e08c4342b0d 100644 --- a/patches/chromium/resource_file_conflict.patch +++ b/patches/chromium/resource_file_conflict.patch @@ -52,10 +52,10 @@ Some alternatives to this patch: None of these options seems like a substantial maintainability win over this patch to me (@nornagon). diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index 97f843f8133c49d684b415f61ef4b4084c4d345c..4b3f01018a9dea91b46b5917e099f272582991b2 100644 +index f47270687b9a12fb74be2e90cc1e9f25e2e2d34e..84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn -@@ -1554,7 +1554,7 @@ if (is_chrome_branded && !is_android) { +@@ -1551,7 +1551,7 @@ if (is_chrome_branded && !is_android) { } } @@ -64,7 +64,7 @@ index 97f843f8133c49d684b415f61ef4b4084c4d345c..4b3f01018a9dea91b46b5917e099f272 chrome_paks("packed_resources") { if (is_mac) { output_dir = "$root_gen_dir/repack" -@@ -1600,6 +1600,12 @@ repack("browser_tests_pak") { +@@ -1597,6 +1597,12 @@ repack("browser_tests_pak") { deps = [ "//chrome/test/data/webui:resources" ] } diff --git a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch index 49cfde7de2e25..202cdf5061450 100644 --- a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch +++ b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch @@ -233,10 +233,10 @@ index 7c99a9512e6f65713fe8483cef7b7c9b494b4491..8fb6cf252961c9773d1a6a09d47bec6a } diff --git a/content/common/features.cc b/content/common/features.cc -index 9119155650ed4249c699cc57eaef9149b99e7297..13e2c0da07938d73b5a689cea19df4a445c4e5e5 100644 +index 201f17f35a4657f43c70b7b44871a7dfea681635..2ec678b805c8c8eda47c3dbf88f567a061cc63dc 100644 --- a/content/common/features.cc +++ b/content/common/features.cc -@@ -294,6 +294,14 @@ BASE_FEATURE(kIOSurfaceCapturer, +@@ -301,6 +301,14 @@ BASE_FEATURE(kIOSurfaceCapturer, base::FEATURE_ENABLED_BY_DEFAULT); #endif @@ -252,10 +252,10 @@ index 9119155650ed4249c699cc57eaef9149b99e7297..13e2c0da07938d73b5a689cea19df4a4 // invalidated upon notifications sent by base::SystemMonitor. If disabled, the // cache is considered invalid on every enumeration request. diff --git a/content/common/features.h b/content/common/features.h -index 0764c2fd1086bb0da16df91c95b171eea0a06bb1..3bc7a54999ec5e1f3afa45fe59d43ba12ec10286 100644 +index 4dc19d79152a1f4cf29e8c484d0acdf7d42ed61e..dbe555a29e96f83d7b8122b3d05578ac83863888 100644 --- a/content/common/features.h +++ b/content/common/features.h -@@ -99,6 +99,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); +@@ -100,6 +100,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); #if BUILDFLAG(IS_MAC) CONTENT_EXPORT BASE_DECLARE_FEATURE(kIOSurfaceCapturer); #endif diff --git a/patches/chromium/scroll_bounce_flag.patch b/patches/chromium/scroll_bounce_flag.patch index bd18c208f5d1f..903b292f474f8 100644 --- a/patches/chromium/scroll_bounce_flag.patch +++ b/patches/chromium/scroll_bounce_flag.patch @@ -6,10 +6,10 @@ Subject: scroll_bounce_flag.patch Patch to make scrollBounce option work. diff --git a/content/renderer/render_thread_impl.cc b/content/renderer/render_thread_impl.cc -index 0a5556cb6eac8be8af3a1691687205e683157794..a88f184db56cc3aab5d67cd1a0f73dff0f002a34 100644 +index 4176c771c26f67be6bb378c7b923f848bcf7cd1b..915e6b3098cea99e2ea2fca79cfb87026c1ba758 100644 --- a/content/renderer/render_thread_impl.cc +++ b/content/renderer/render_thread_impl.cc -@@ -1324,7 +1324,7 @@ bool RenderThreadImpl::IsLcdTextEnabled() { +@@ -1331,7 +1331,7 @@ bool RenderThreadImpl::IsLcdTextEnabled() { } bool RenderThreadImpl::IsElasticOverscrollEnabled() { diff --git a/patches/chromium/support_mixed_sandbox_with_zygote.patch b/patches/chromium/support_mixed_sandbox_with_zygote.patch index 04f040a0ab5cf..516afca1eff18 100644 --- a/patches/chromium/support_mixed_sandbox_with_zygote.patch +++ b/patches/chromium/support_mixed_sandbox_with_zygote.patch @@ -22,7 +22,7 @@ However, the patch would need to be reviewed by the security team, as it does touch a security-sensitive class. diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index 6e435b12521d663086be770bb89106368b06d159..2c53f5575bdc96ba53bacf8a40e752e7a41576d9 100644 +index 332f611678e53c0ea56c8baea71ca123d8cc0a95..6a1b182868157c91742c6b652cbdfc0f4373a27a 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc @@ -1825,6 +1825,10 @@ bool RenderProcessHostImpl::Init() { diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index 700deb20f1961..57beac05e4ed3 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 2a683ac9a810d7bc7286e56ce50dd51adfc4f25f..8bf17cff8a1bea7cc73a91cec52887671f2c8aa4 100644 +index 7b416ade6fe632d7fab319460876cb42f5b5dd83..f26744c0046ed8bda0495de4bf10b8d12f1a7911 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -3960,6 +3960,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3965,6 +3965,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index 2a683ac9a810d7bc7286e56ce50dd51adfc4f25f..8bf17cff8a1bea7cc73a91cec5288767 std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -3970,6 +3977,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3975,6 +3982,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } @@ -35,7 +35,7 @@ index 2a683ac9a810d7bc7286e56ce50dd51adfc4f25f..8bf17cff8a1bea7cc73a91cec5288767 CHECK(view_.get()); diff --git a/content/public/browser/web_contents.h b/content/public/browser/web_contents.h -index 9360a2b080ebe4d6c0a475b0a536a5d7212c8a86..6e5eebfb199d322028f6b2bc72d666c24f334bba 100644 +index ea5856a886ae49c161c7b7a1e4ea108a77c2534c..1da1ee16f70ea430c163ec0676ddb2b0a13c8c43 100644 --- a/content/public/browser/web_contents.h +++ b/content/public/browser/web_contents.h @@ -121,10 +121,13 @@ class BrowserPluginGuestDelegate; diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index 08d3636f2fac8..3b63735fbcb44 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,10 +15,10 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index ef8a80d2148c0ec0d8a3493ae58a4e723a9601e1..71174dc9f0e15622c67a2d33dc119594de68fc69 100644 +index f4231fa2549083e8132affa6e424ac18f28b4f41..32d4d22f4d0106c8f598e8e44545788c32665947 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -8882,6 +8882,17 @@ void RenderFrameHostImpl::EnterFullscreen( +@@ -8809,6 +8809,17 @@ void RenderFrameHostImpl::EnterFullscreen( } } @@ -37,10 +37,10 @@ index ef8a80d2148c0ec0d8a3493ae58a4e723a9601e1..71174dc9f0e15622c67a2d33dc119594 if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 8bf17cff8a1bea7cc73a91cec52887671f2c8aa4..e96a656473e0d18a8053dab92dbeb1afb174d27f 100644 +index f26744c0046ed8bda0495de4bf10b8d12f1a7911..020d8d111d756dbe8bbae47a0e7dc74b63501b54 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4235,21 +4235,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4254,21 +4254,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index 8bf17cff8a1bea7cc73a91cec52887671f2c8aa4..e96a656473e0d18a8053dab92dbeb1af } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4408,7 +4412,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4427,7 +4431,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/patches/chromium/worker_context_will_destroy.patch b/patches/chromium/worker_context_will_destroy.patch index 7b96c40775d91..4cdcc4de4f9b4 100644 --- a/patches/chromium/worker_context_will_destroy.patch +++ b/patches/chromium/worker_context_will_destroy.patch @@ -26,10 +26,10 @@ index 7a2d251ba2d13d0a34df176111e6524a27b87f55..cbbe0fbdd25a0f7859b113fdb3dcd9ce // An empty URL is returned if the URL is not overriden. virtual GURL OverrideFlashEmbedWithHTML(const GURL& url); diff --git a/content/renderer/renderer_blink_platform_impl.cc b/content/renderer/renderer_blink_platform_impl.cc -index 5747f9452788737375f0e67e588f98e9b89b381c..a01f865ae54476ffb55feae026329d06d0dabea8 100644 +index 64655ef0370c22eb4adb995b5ca640e9756e800e..d9deae4ffb30dc3b22c2c1bc8fc53ff9c64b1183 100644 --- a/content/renderer/renderer_blink_platform_impl.cc +++ b/content/renderer/renderer_blink_platform_impl.cc -@@ -893,6 +893,12 @@ void RendererBlinkPlatformImpl::WillStopWorkerThread() { +@@ -903,6 +903,12 @@ void RendererBlinkPlatformImpl::WillStopWorkerThread() { WorkerThreadRegistry::Instance()->WillStopCurrentWorkerThread(); } diff --git a/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch b/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch index 4e0db01231ce8..072de0abc4f48 100644 --- a/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch +++ b/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch @@ -35,10 +35,10 @@ index cbbe0fbdd25a0f7859b113fdb3dcd9ce57e597d6..1345bb5008e1b4fc3a450f7e353d52ec // from the worker thread. virtual void WillDestroyWorkerContextOnWorkerThread( diff --git a/content/renderer/renderer_blink_platform_impl.cc b/content/renderer/renderer_blink_platform_impl.cc -index a01f865ae54476ffb55feae026329d06d0dabea8..57eadd71e6f46bda772f5c1326df7483010089ba 100644 +index d9deae4ffb30dc3b22c2c1bc8fc53ff9c64b1183..3a0bb8b4d8eba3d67e444541b06326b9a3440eee 100644 --- a/content/renderer/renderer_blink_platform_impl.cc +++ b/content/renderer/renderer_blink_platform_impl.cc -@@ -905,6 +905,12 @@ void RendererBlinkPlatformImpl::WorkerContextCreated( +@@ -915,6 +915,12 @@ void RendererBlinkPlatformImpl::WorkerContextCreated( worker); } diff --git a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch index c4d93ad468547..13e43a0d55b1b 100644 --- a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch +++ b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch @@ -10,7 +10,7 @@ to handle this without patching, but this is fairly clean for now and no longer patching legacy devtools code. diff --git a/front_end/entrypoints/main/MainImpl.ts b/front_end/entrypoints/main/MainImpl.ts -index 69673b4aa636c2b55065aa11ce65dbc4a45c39b8..bdf133c0cdd524a72d3ad78fa97102b44c336f51 100644 +index 691e308b52493ed235196b7b75505b7a08911180..8cba1cd242a17c83f330bb3f4aac15505b363cab 100644 --- a/front_end/entrypoints/main/MainImpl.ts +++ b/front_end/entrypoints/main/MainImpl.ts @@ -730,6 +730,8 @@ export class MainImpl { diff --git a/shell/app/electron_main_delegate_mac.mm b/shell/app/electron_main_delegate_mac.mm index 98ec5007ed5ae..8f3800bc51d99 100644 --- a/shell/app/electron_main_delegate_mac.mm +++ b/shell/app/electron_main_delegate_mac.mm @@ -76,7 +76,7 @@ NSString* team_id = [bundle objectForInfoDictionaryKey:@"ElectronTeamID"]; if (team_id) base_bundle_id = base::SysNSStringToUTF8(team_id) + "." + base_bundle_id; - base::apple::SetBaseBundleID(base_bundle_id.c_str()); + base::apple::SetBaseBundleIDOverride(base_bundle_id); } } diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index bf7a1bb38b155..1b764296d5dc3 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -1172,6 +1172,7 @@ void WebContents::WebContentsCreatedWithFullParams( } bool WebContents::IsWebContentsCreationOverridden( + content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, diff --git a/shell/browser/api/electron_api_web_contents.h b/shell/browser/api/electron_api_web_contents.h index 0e2ebb3a62d08..00547c5a82463 100644 --- a/shell/browser/api/electron_api_web_contents.h +++ b/shell/browser/api/electron_api_web_contents.h @@ -488,6 +488,7 @@ class WebContents final : public ExclusiveAccessContext, // content::WebContentsDelegate: bool IsWebContentsCreationOverridden( + content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, diff --git a/shell/browser/electron_browser_client.cc b/shell/browser/electron_browser_client.cc index 0895213cb9c9a..36e25a4bd33eb 100644 --- a/shell/browser/electron_browser_client.cc +++ b/shell/browser/electron_browser_client.cc @@ -412,7 +412,6 @@ void ElectronBrowserClient::OverrideWebPreferences( prefs->javascript_can_access_clipboard = false; prefs->allow_scripts_to_close_windows = true; prefs->local_storage_enabled = true; - prefs->databases_enabled = true; prefs->allow_universal_access_from_file_urls = electron::fuses::IsGrantFileProtocolExtraPrivilegesEnabled(); prefs->allow_file_access_from_file_urls = @@ -953,26 +952,23 @@ bool ElectronBrowserClient::HandleExternalProtocol( return true; } -std::vector> -ElectronBrowserClient::CreateThrottlesForNavigation( +void ElectronBrowserClient::CreateThrottlesForNavigation( content::NavigationThrottleRegistry& registry) { - std::vector> throttles; - content::NavigationHandle* handle = ®istry.GetNavigationHandle(); - throttles.push_back(std::make_unique(handle)); + registry.MaybeAddThrottle( + std::make_unique(handle)); #if BUILDFLAG(ENABLE_ELECTRON_EXTENSIONS) - throttles.push_back( + registry.MaybeAddThrottle( std::make_unique(handle)); #endif #if BUILDFLAG(ENABLE_PDF_VIEWER) - throttles.push_back(std::make_unique(handle)); - throttles.push_back(std::make_unique( + registry.MaybeAddThrottle( + std::make_unique(handle)); + registry.MaybeAddThrottle(std::make_unique( handle, std::make_unique())); #endif - - return throttles; } content::MediaObserver* ElectronBrowserClient::GetMediaObserver() { diff --git a/shell/browser/electron_browser_client.h b/shell/browser/electron_browser_client.h index 219a137d77222..5e2fc2ad905ad 100644 --- a/shell/browser/electron_browser_client.h +++ b/shell/browser/electron_browser_client.h @@ -76,8 +76,7 @@ class ElectronBrowserClient : public content::ContentBrowserClient, base::OnceCallback callback); // content::NavigatorDelegate - std::vector> - CreateThrottlesForNavigation( + void CreateThrottlesForNavigation( content::NavigationThrottleRegistry& registry) override; // content::ContentBrowserClient: diff --git a/shell/browser/file_system_access/file_system_access_permission_context.cc b/shell/browser/file_system_access/file_system_access_permission_context.cc index 1fb8c1d4a57aa..383d9a5b67898 100644 --- a/shell/browser/file_system_access/file_system_access_permission_context.cc +++ b/shell/browser/file_system_access/file_system_access_permission_context.cc @@ -10,6 +10,7 @@ #include "base/base_paths.h" #include "base/files/file_path.h" +#include "base/files/file_util.h" #include "base/json/values_util.h" #include "base/path_service.h" #include "base/task/bind_post_task.h" @@ -39,6 +40,16 @@ #include "ui/base/l10n/l10n_util.h" #include "url/origin.h" +ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules() = + default; +ChromeFileSystemAccessPermissionContext::BlockPathRules::~BlockPathRules() = + default; +ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules( + const BlockPathRules& other) = default; +ChromeFileSystemAccessPermissionContext::BlockPathRules& +ChromeFileSystemAccessPermissionContext::BlockPathRules::operator=( + const BlockPathRules& other) = default; + namespace gin { template <> @@ -141,51 +152,53 @@ bool MaybeIsLocalUNCPath(const base::FilePath& path) { } #endif // BUILDFLAG(IS_WIN) -// Describes a rule for blocking a directory, which can be constructed -// dynamically (based on state) or statically (from kBlockedPaths). -struct BlockPathRule { - base::FilePath path; - BlockType type; -}; - -bool ShouldBlockAccessToPath(const base::FilePath& path, - HandleType handle_type, - std::vector rules) { +bool ShouldBlockAccessToPath( + base::FilePath path, + HandleType handle_type, + std::vector + extra_rules, + ChromeFileSystemAccessPermissionContext::BlockPathRules block_path_rules) { DCHECK(!path.empty()); DCHECK(path.IsAbsolute()); + path = ChromeFileSystemAccessPermissionContext::NormalizeFilePath(path); + for (auto& rule : extra_rules) { + rule.path = + ChromeFileSystemAccessPermissionContext::NormalizeFilePath(rule.path); + } + #if BUILDFLAG(IS_WIN) // On Windows, local UNC paths are rejected, as UNC path can be written in a // way that can bypass the blocklist. - if (MaybeIsLocalUNCPath(path)) + if (MaybeIsLocalUNCPath(path)) { return true; -#endif // BUILDFLAG(IS_WIN) - - // Add the hard-coded rules to the dynamic rules. - for (auto const& [key, rule_path, type] : - ChromeFileSystemAccessPermissionContext::GenerateBlockedPath()) { - if (key == ChromeFileSystemAccessPermissionContext::kNoBasePathKey) { - rules.emplace_back(base::FilePath{rule_path}, type); - } else if (base::FilePath block_path; - base::PathService::Get(key, &block_path)) { - rules.emplace_back(rule_path ? block_path.Append(rule_path) : block_path, - type); - } } +#endif base::FilePath nearest_ancestor; BlockType nearest_ancestor_block_type = BlockType::kDontBlockChildren; - for (const auto& block : rules) { - if (path == block.path || path.IsParent(block.path)) { - DLOG(INFO) << "Blocking access to " << path - << " because it is a parent of " << block.path; + auto should_block_with_rule = [&](const base::FilePath& block_path, + BlockType block_type) -> bool { + if (path == block_path || path.IsParent(block_path)) { + VLOG(1) << "Blocking access to " << path << " because it is a parent of " + << block_path; return true; } - if (block.path.IsParent(path) && - (nearest_ancestor.empty() || nearest_ancestor.IsParent(block.path))) { - nearest_ancestor = block.path; - nearest_ancestor_block_type = block.type; + if (block_path.IsParent(path) && + (nearest_ancestor.empty() || nearest_ancestor.IsParent(block_path))) { + nearest_ancestor = block_path; + nearest_ancestor_block_type = block_type; + } + return false; + }; + + for (const auto* block_rules_ptr : + {&extra_rules, &block_path_rules.block_path_rules_}) { + for (const auto& block : *block_rules_ptr) { + if (should_block_with_rule(block.path, block.type)) { + return true; + } } } @@ -193,6 +206,8 @@ bool ShouldBlockAccessToPath(const base::FilePath& path, // nearest ancestor does not block access to its children. Grant access. if (nearest_ancestor.empty() || nearest_ancestor_block_type == BlockType::kDontBlockChildren) { + VLOG(1) << "Not blocking access to " << path << " because it is inside " + << nearest_ancestor << " and it's kDontBlockChildren"; return false; } @@ -200,12 +215,14 @@ bool ShouldBlockAccessToPath(const base::FilePath& path, // access to directories. Grant access. if (handle_type == HandleType::kFile && nearest_ancestor_block_type == BlockType::kBlockNestedDirectories) { + VLOG(1) << "Not blocking access to " << path << " because it is inside " + << nearest_ancestor << " and it's kBlockNestedDirectories"; return false; } // The nearest ancestor blocks access to its children, so block access. - DLOG(INFO) << "Blocking access to " << path << " because it is inside " - << nearest_ancestor; + VLOG(1) << "Blocking access to " << path << " because it is inside " + << nearest_ancestor << " and it's kBlockAllChildren"; return true; } @@ -446,11 +463,30 @@ FileSystemAccessPermissionContext::FileSystemAccessPermissionContext( const base::Clock* clock) : browser_context_(browser_context), clock_(clock) { DETACH_FROM_SEQUENCE(sequence_checker_); + ResetBlockPaths(); } FileSystemAccessPermissionContext::~FileSystemAccessPermissionContext() = default; +void FileSystemAccessPermissionContext::ResetBlockPaths() { + is_block_path_rules_init_complete_ = false; + base::ThreadPool::PostTaskAndReplyWithResult( + FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE}, + base::BindOnce( + &ChromeFileSystemAccessPermissionContext::GenerateBlockPaths, true), + base::BindOnce(&FileSystemAccessPermissionContext::UpdateBlockPaths, + weak_factory_.GetWeakPtr())); +} + +void FileSystemAccessPermissionContext::UpdateBlockPaths( + std::unique_ptr + block_path_rules) { + block_path_rules_ = std::move(block_path_rules); + is_block_path_rules_init_complete_ = true; + block_rules_check_callbacks_.Notify(*block_path_rules_.get()); +} + scoped_refptr FileSystemAccessPermissionContext::GetReadPermissionGrant( const url::Origin& origin, @@ -604,12 +640,26 @@ void FileSystemAccessPermissionContext::ConfirmSensitiveEntryAccess( std::move(after_blocklist_check_callback)); } +void FileSystemAccessPermissionContext::CheckShouldBlockAccessToPathAndReply( + base::FilePath path, + HandleType handle_type, + std::vector + extra_rules, + base::OnceCallback callback, + ChromeFileSystemAccessPermissionContext::BlockPathRules block_path_rules) { + base::ThreadPool::PostTaskAndReplyWithResult( + FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE}, + base::BindOnce(&ShouldBlockAccessToPath, path, handle_type, extra_rules, + block_path_rules), + std::move(callback)); +} + void FileSystemAccessPermissionContext::CheckPathAgainstBlocklist( const content::PathInfo& path_info, HandleType handle_type, base::OnceCallback callback) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - // TODO(https://crbug.com/1009970): Figure out what external paths should be + // TODO(crbug.com/40101272): Figure out what external paths should be // blocked. We could resolve the external path to a local path, and check for // blocked directories based on that, but that doesn't work well. Instead we // should have a separate Chrome OS only code path to block for example the @@ -619,15 +669,27 @@ void FileSystemAccessPermissionContext::CheckPathAgainstBlocklist( return; } - std::vector extra_rules; - extra_rules.emplace_back(browser_context_->GetPath().DirName(), - BlockType::kBlockAllChildren); - - base::ThreadPool::PostTaskAndReplyWithResult( - FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE}, - base::BindOnce(&ShouldBlockAccessToPath, path_info.path, handle_type, - extra_rules), - std::move(callback)); + // Unlike the DIR_USER_DATA check, this handles the --user-data-dir override. + // We check for the user data dir in two different ways: directly, via the + // profile manager, where it exists (it does not in unit tests), and via the + // profile's directory, assuming the profile dir is a child of the user data + // dir. + std::vector + extra_rules; + if (is_block_path_rules_init_complete_) { + // The rules initialization is completed, we can just post the task to a + // anonymous blocking traits. + CheckShouldBlockAccessToPathAndReply(path_info.path, handle_type, + extra_rules, std::move(callback), + *block_path_rules_.get()); + return; + } + // The check must be performed after the rules initialization is done. + block_rules_check_subscription_.push_back(block_rules_check_callbacks_.Add( + base::BindOnce(&FileSystemAccessPermissionContext:: + CheckShouldBlockAccessToPathAndReply, + weak_factory_.GetWeakPtr(), path_info.path, handle_type, + extra_rules, std::move(callback)))); } void FileSystemAccessPermissionContext::PerformAfterWriteChecks( diff --git a/shell/browser/file_system_access/file_system_access_permission_context.h b/shell/browser/file_system_access/file_system_access_permission_context.h index 18d55ad477100..591c1288e2dda 100644 --- a/shell/browser/file_system_access/file_system_access_permission_context.h +++ b/shell/browser/file_system_access/file_system_access_permission_context.h @@ -12,13 +12,14 @@ #include #include +#include "base/callback_list.h" #include "base/functional/callback_forward.h" #include "base/memory/weak_ptr.h" #include "base/time/clock.h" #include "base/time/default_clock.h" #include "base/values.h" +#include "chrome/browser/file_system_access/chrome_file_system_access_permission_context.h" // nogncheck #include "components/keyed_service/core/keyed_service.h" -#include "content/public/browser/file_system_access_permission_context.h" class GURL; @@ -135,6 +136,14 @@ class FileSystemAccessPermissionContext void PermissionGrantDestroyed(PermissionGrantImpl* grant); + void CheckShouldBlockAccessToPathAndReply( + base::FilePath path, + HandleType handle_type, + std::vector + extra_rules, + base::OnceCallback callback, + ChromeFileSystemAccessPermissionContext::BlockPathRules block_path_rules); + void CheckPathAgainstBlocklist(const content::PathInfo& path, HandleType handle_type, base::OnceCallback callback); @@ -159,6 +168,11 @@ class FileSystemAccessPermissionContext const base::FilePath& path, GrantType grant_type) const; + void ResetBlockPaths(); + void UpdateBlockPaths( + std::unique_ptr + block_path_rules); + base::WeakPtr GetWeakPtr(); const raw_ptr browser_context_; @@ -176,6 +190,14 @@ class FileSystemAccessPermissionContext std::map> callback_map_; + std::unique_ptr + block_path_rules_; + bool is_block_path_rules_init_complete_ = false; + std::vector block_rules_check_subscription_; + base::OnceCallbackList + block_rules_check_callbacks_; + base::WeakPtrFactory weak_factory_{this}; }; From df8ed0acc3c3bb2fc87d7e411b9c4c7bb84de08a Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 14 May 2025 12:53:59 -0500 Subject: [PATCH 040/186] refactor: use kKeyModifiers in IsAltModifier() (#47089) We probably didn't use this before because IsAltModifier() was written two years before the KeyModifiers mask was added upstream in 98ec378a. Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/ui/views/root_view.cc | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/shell/browser/ui/views/root_view.cc b/shell/browser/ui/views/root_view.cc index 87c3aa9989091..770c03997e22c 100644 --- a/shell/browser/ui/views/root_view.cc +++ b/shell/browser/ui/views/root_view.cc @@ -20,13 +20,8 @@ bool IsAltKey(const input::NativeWebKeyboardEvent& event) { } bool IsAltModifier(const input::NativeWebKeyboardEvent& event) { - using Modifiers = input::NativeWebKeyboardEvent::Modifiers; - int modifiers = event.GetModifiers(); - modifiers &= ~Modifiers::kNumLockOn; - modifiers &= ~Modifiers::kCapsLockOn; - return (modifiers == Modifiers::kAltKey) || - (modifiers == (Modifiers::kAltKey | Modifiers::kIsLeft)) || - (modifiers == (Modifiers::kAltKey | Modifiers::kIsRight)); + using Mods = input::NativeWebKeyboardEvent::Modifiers; + return (event.GetModifiers() & Mods::kKeyModifiers) == Mods::kAltKey; } } // namespace From be5b02386d815f9938bd0baa3610d87331919bb0 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 14 May 2025 13:55:23 -0400 Subject: [PATCH 041/186] chore: bump chromium to 138.0.7177.0 (37-x-y) (#47085) * chore: bump chromium in DEPS to 138.0.7177.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6530423: [WebContents] Fix IsNeverComposited() calls during initialization Refs https://chromium-review.googlesource.com/c/chromium/src/+/6530423 Co-authored-by: David Sanders * 6512551: [ios] Enable -Wobjc-property-assign-on-object-type Refs https://chromium-review.googlesource.com/c/chromium/src/+/6512551 Co-authored-by: David Sanders * chore: update patches Co-authored-by: David Sanders --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- DEPS | 2 +- ...adjust_accessibility_ui_for_electron.patch | 2 +- ..._scheduler_throttling_per_renderview.patch | 10 ++--- ..._depend_on_packed_resource_integrity.patch | 10 ++--- patches/chromium/build_gn.patch | 2 +- patches/chromium/can_create_window.patch | 10 ++--- ...fy_chromium_handling_of_mouse_events.patch | 2 +- .../chromium/chore_partial_revert_of.patch | 4 +- ...screationoverridden_with_full_params.patch | 16 ++++---- .../chromium/enable_reset_aspect_ratio.patch | 2 +- .../extend_apply_webpreferences.patch | 6 +-- ...moothing_css_rule_and_blink_painting.patch | 38 +++++++++---------- ...ingshelper_behind_branding_buildflag.patch | 2 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ...reate_a_console_if_logging_to_stderr.patch | 4 +- ..._avoid_private_macos_api_usage.patch.patch | 2 +- .../chromium/notification_provenance.patch | 4 +- patches/chromium/picture-in-picture.patch | 4 +- patches/chromium/printing.patch | 4 +- ...r_changes_to_the_webcontentsobserver.patch | 6 +-- ...efactor_unfilter_unresponsive_events.patch | 4 +- patches/chromium/web_contents.patch | 10 ++--- patches/chromium/webview_fullscreen.patch | 6 +-- ...i_to_allow_electron_to_set_dock_side.patch | 4 +- shell/browser/ui/file_dialog_mac.mm | 2 +- shell/browser/ui/webui/accessibility_ui.cc | 2 +- 26 files changed, 81 insertions(+), 81 deletions(-) diff --git a/DEPS b/DEPS index 13a5facaa339b..f2186d321a7e7 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7175.0', + '138.0.7177.0', 'node_version': 'v22.15.0', 'nan_version': diff --git a/patches/chromium/adjust_accessibility_ui_for_electron.patch b/patches/chromium/adjust_accessibility_ui_for_electron.patch index f6f4c861ccb00..13cd0e0b16c03 100644 --- a/patches/chromium/adjust_accessibility_ui_for_electron.patch +++ b/patches/chromium/adjust_accessibility_ui_for_electron.patch @@ -10,7 +10,7 @@ usage of BrowserList and Browser as we subclass related methods and use our WindowList. diff --git a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc -index d7a9cff6401f0953297acd18708ec2952f60407f..b4777ce0bcda2bdb9645a4ed86040f62ce4027eb 100644 +index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49c4515aa4 100644 --- a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc +++ b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc @@ -48,6 +48,7 @@ diff --git a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch index 748ee8a24a67e..a1132eb60d996 100644 --- a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch +++ b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch @@ -23,7 +23,7 @@ index b9e7ef002a8d7842b4e97dbcaa59aa289ba652a1..81bd39f47d8411da53824d47e053b39f return receiver_.BindNewEndpointAndPassDedicatedRemote(); } diff --git a/content/browser/renderer_host/render_view_host_impl.cc b/content/browser/renderer_host/render_view_host_impl.cc -index 6e6d9a3ea76b3b578c452050afde6b89468c8841..f3abefb6e4a0e11ae2cdc12558af844c4153a103 100644 +index 1654ffbb2184cc1db6c0b862cc745ba2e467b740..567f5279d943a58e451a78fb506606cf17a0ef79 100644 --- a/content/browser/renderer_host/render_view_host_impl.cc +++ b/content/browser/renderer_host/render_view_host_impl.cc @@ -761,6 +761,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { @@ -39,7 +39,7 @@ index 6e6d9a3ea76b3b578c452050afde6b89468c8841..f3abefb6e4a0e11ae2cdc12558af844c return is_active(); } diff --git a/content/browser/renderer_host/render_view_host_impl.h b/content/browser/renderer_host/render_view_host_impl.h -index f9dc4c4aa4e3c65124c975f5bc5ea255fbb43cfb..1e7151d8d45bfc5ef01b79eee9d80df3df5c856c 100644 +index 6eade0d29bc266a6a8928e768c923687bd12e656..53465bc76a22ae97ba4602d02a41f52e194af68b 100644 --- a/content/browser/renderer_host/render_view_host_impl.h +++ b/content/browser/renderer_host/render_view_host_impl.h @@ -135,6 +135,7 @@ class CONTENT_EXPORT RenderViewHostImpl @@ -116,10 +116,10 @@ index 7c1eb9baabfb9e0f3645421b5cbe467862252638..00d2cd41d795cb550e16fb80944b2382 // Visibility ----------------------------------------------------------- diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index 73f25b18478ae93dbf7a5f225adce40da89681c9..3c3c0247ca56ba99b48583a4218712f172458845 100644 +index feba9635b40664b1db83ab727798a34b98e5e0b8..f6a248b1de8b313658453dd380529ec7c2e40033 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc -@@ -2466,6 +2466,10 @@ void WebViewImpl::SetPageLifecycleStateInternal( +@@ -2467,6 +2467,10 @@ void WebViewImpl::SetPageLifecycleStateInternal( TRACE_EVENT2("navigation", "WebViewImpl::SetPageLifecycleStateInternal", "old_state", old_state, "new_state", new_state); @@ -130,7 +130,7 @@ index 73f25b18478ae93dbf7a5f225adce40da89681c9..3c3c0247ca56ba99b48583a4218712f1 bool storing_in_bfcache = new_state->is_in_back_forward_cache && !old_state->is_in_back_forward_cache; bool restoring_from_bfcache = !new_state->is_in_back_forward_cache && -@@ -3987,10 +3991,23 @@ PageScheduler* WebViewImpl::Scheduler() const { +@@ -3990,10 +3994,23 @@ PageScheduler* WebViewImpl::Scheduler() const { return GetPage()->GetPageScheduler(); } diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index 984e9b037c4f9..ac1a82b506db2 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -33,10 +33,10 @@ index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff6 "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index e44a7794f3a1f019835fb4ecbf5b62e1bd17c53d..1c6bda2d5e4f4a5282792260efbf2fa49a37823e 100644 +index 3d58b24d9a835274ef1128b0a55bdf4c33a7f35c..11adb84bd02dfa2c54d9eba9562043575b53afc3 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4650,7 +4650,7 @@ static_library("browser") { +@@ -4653,7 +4653,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,7 +46,7 @@ index e44a7794f3a1f019835fb4ecbf5b62e1bd17c53d..1c6bda2d5e4f4a5282792260efbf2fa4 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index e62e29e8a16572f8fcaf0efe977163b17bb5bf27..5444ca916f559050a47f5caa90a8fb7b8f6f185f 100644 +index 028d1e517e434e8bb4152ebe8b5d4ee478d2abba..664d051317f1655f5ea03d8e3f1323e670973319 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn @@ -7196,9 +7196,12 @@ test("unit_tests") { @@ -63,7 +63,7 @@ index e62e29e8a16572f8fcaf0efe977163b17bb5bf27..5444ca916f559050a47f5caa90a8fb7b "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8168,6 +8171,10 @@ test("unit_tests") { +@@ -8167,6 +8170,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index e62e29e8a16572f8fcaf0efe977163b17bb5bf27..5444ca916f559050a47f5caa90a8fb7b sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8223,7 +8230,6 @@ test("unit_tests") { +@@ -8222,7 +8229,6 @@ test("unit_tests") { # Non-android deps for "unit_tests" target. deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/build_gn.patch b/patches/chromium/build_gn.patch index 2a059f803d50e..1a70bd08dc783 100644 --- a/patches/chromium/build_gn.patch +++ b/patches/chromium/build_gn.patch @@ -7,7 +7,7 @@ These are variables we add to the root BUILDCONFIG so that they're available everywhere, without having to import("//electron/.../flags.gni"). diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn -index c3a3bf4970783804bc76ee4e71bb8233b5f215a8..78c72710b411e05ca0b6f01811076599fa66fc15 100644 +index 66a885e5bc6145f8358b8c76feb3ec27c95964bd..6c9316c40c9ab11c48876d00bf55191e33b133ff 100644 --- a/build/config/BUILDCONFIG.gn +++ b/build/config/BUILDCONFIG.gn @@ -123,6 +123,9 @@ if (current_os == "") { diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 1a08871accff7..87fb968f23946 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -21,10 +21,10 @@ index c66512a270828be3b436c1e880917f0638771cfd..f4231fa2549083e8132affa6e424ac18 &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index c7e153a0ff9de1b1d5ed760099121db6d531589e..e42e462f3c8109444e6dadb0557e38cdd05c362a 100644 +index 8a0128a57c6398c56e520522503ba54e03d176b3..43ca2bbe1611cbc2b533435319111dd9458de471 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5162,6 +5162,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5163,6 +5163,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( // Sets the newly created WebContents WindowOpenDisposition. new_contents_impl->original_window_open_disposition_ = params.disposition; @@ -37,7 +37,7 @@ index c7e153a0ff9de1b1d5ed760099121db6d531589e..e42e462f3c8109444e6dadb0557e38cd // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5203,12 +5209,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5204,12 +5210,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -100,7 +100,7 @@ index 3e363b85b57478ca7228379ed089746a6eb52f2d..17b11b2a4e70f419721649568179c312 bool opener_suppressed, bool* no_javascript_access); diff --git a/content/public/browser/web_contents_delegate.cc b/content/public/browser/web_contents_delegate.cc -index aabcebe8e49f42e3c0680d8d20f64ed6a48a7266..8c1d83692daccfbdda90f292b5a3fb9a8f1b118f 100644 +index f42be2a1cc5ba3ccb52e48985e0532a34675e826..f6ab6ab2b036c7621b429181c3ff89d9f1ff77f9 100644 --- a/content/public/browser/web_contents_delegate.cc +++ b/content/public/browser/web_contents_delegate.cc @@ -32,6 +32,17 @@ namespace content { @@ -122,7 +122,7 @@ index aabcebe8e49f42e3c0680d8d20f64ed6a48a7266..8c1d83692daccfbdda90f292b5a3fb9a WebContents* source, const OpenURLParams& params, diff --git a/content/public/browser/web_contents_delegate.h b/content/public/browser/web_contents_delegate.h -index a9be46fcd13f397c34a2cf3e7444efad81a5e19b..c4cee108b0caac7d6a2a9115586882dd32bab714 100644 +index d33274984bf6523beeb3ab5ee586499d224bff3c..83bdd195339eb7d61ac88e2994fd8dabe93f6ecc 100644 --- a/content/public/browser/web_contents_delegate.h +++ b/content/public/browser/web_contents_delegate.h @@ -18,6 +18,7 @@ diff --git a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch index 4560eaab58f21..afe116bc3ed65 100644 --- a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch +++ b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch @@ -34,7 +34,7 @@ index 39b5a8fdd165efd74b00256552b51b5413107958..bfc4ef4f50efff4a77f2aef64335bb7e class ScrollEvent; diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index 61509e2eb982797845098abf5f36e031be63686b..24283be8d1660acce0a5ae89386b8eef9989fc12 100644 +index 5f9612ff000c1544f572bab0cbc9982dc4e647ce..2ce65548dd1283adb4c095e37198e08a8a13635c 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc @@ -1415,6 +1415,10 @@ void DesktopWindowTreeHostWin::HandleHeadlessWindowBoundsChanged( diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 792455130dabf..1bdf6d3d21131 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 70b3c4a2da0e1d79a7626e0bb2ed45b8fbbe0024..d0f42ceedfac643443e3c7c5757b831f481a72eb 100644 +index 46d4c5e8c4f0d91d00ef51cc410ef54ebadb8eef..6d5ed56518116ce534fac98a994b7b7d9f1c6d11 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5078,7 +5078,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5079,7 +5079,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index a4666be2625aa..fced588e4e318 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -194,10 +194,10 @@ index 996b3d453b375fec2a823a0dd0d3122ba626b5f2..5a5c6ed67f698fdd914e79df528e2ca3 bool DidAddMessageToConsole(content::WebContents* source, blink::mojom::ConsoleMessageLevel log_level, diff --git a/components/offline_pages/content/background_loader/background_loader_contents.cc b/components/offline_pages/content/background_loader/background_loader_contents.cc -index 9dcf196de0d70fda966162473408968bfd9d16e0..2d2007e60c3512d002b7e1a858afb2908201e964 100644 +index 14f2758f2d71d4d4ba77e4fcb9be40bb878526e0..536db4f8fe9771b60f0359df5c680b298c89cad4 100644 --- a/components/offline_pages/content/background_loader/background_loader_contents.cc +++ b/components/offline_pages/content/background_loader/background_loader_contents.cc -@@ -90,8 +90,7 @@ bool BackgroundLoaderContents::IsWebContentsCreationOverridden( +@@ -86,8 +86,7 @@ bool BackgroundLoaderContents::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -208,10 +208,10 @@ index 9dcf196de0d70fda966162473408968bfd9d16e0..2d2007e60c3512d002b7e1a858afb290 return true; } diff --git a/components/offline_pages/content/background_loader/background_loader_contents.h b/components/offline_pages/content/background_loader/background_loader_contents.h -index b3fef77c892a21565235c1a13ff50e11536d360c..2400dbbc53acca6871ae16a610a337134b61aafe 100644 +index b969f1d97b7e3396119b579cfbe61e19ff7d2dd4..b8d6169652da28266a514938b45b39c58df53573 100644 --- a/components/offline_pages/content/background_loader/background_loader_contents.h +++ b/components/offline_pages/content/background_loader/background_loader_contents.h -@@ -67,8 +67,7 @@ class BackgroundLoaderContents : public content::WebContentsDelegate { +@@ -66,8 +66,7 @@ class BackgroundLoaderContents : public content::WebContentsDelegate { content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -222,10 +222,10 @@ index b3fef77c892a21565235c1a13ff50e11536d360c..2400dbbc53acca6871ae16a610a33713 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 2eb45ae773f9fbd28fa05b14e5684f4b7d17cc85..7b416ade6fe632d7fab319460876cb42f5b5dd83 100644 +index 27dfdfaa258312b3e096cfe784e085376026d9ef..420879681bab99129e314b8717c4edf075037d35 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5041,8 +5041,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5042,8 +5042,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( if (delegate_ && delegate_->IsWebContentsCreationOverridden( opener, source_site_instance, params.window_container_type, @@ -236,7 +236,7 @@ index 2eb45ae773f9fbd28fa05b14e5684f4b7d17cc85..7b416ade6fe632d7fab319460876cb42 static_cast(delegate_->CreateCustomWebContents( opener, source_site_instance, is_new_browsing_instance, diff --git a/content/public/browser/web_contents_delegate.cc b/content/public/browser/web_contents_delegate.cc -index 8c1d83692daccfbdda90f292b5a3fb9a8f1b118f..c836a731050027fd101aea0cd65782a4a7b5627b 100644 +index f6ab6ab2b036c7621b429181c3ff89d9f1ff77f9..d151ba757ae81c6f023ee08328ab155405b0fb95 100644 --- a/content/public/browser/web_contents_delegate.cc +++ b/content/public/browser/web_contents_delegate.cc @@ -160,8 +160,7 @@ bool WebContentsDelegate::IsWebContentsCreationOverridden( @@ -250,7 +250,7 @@ index 8c1d83692daccfbdda90f292b5a3fb9a8f1b118f..c836a731050027fd101aea0cd65782a4 } diff --git a/content/public/browser/web_contents_delegate.h b/content/public/browser/web_contents_delegate.h -index c4cee108b0caac7d6a2a9115586882dd32bab714..a9ce49d79b613c58c2e6ae4b7b9a1076a2252ee1 100644 +index 83bdd195339eb7d61ac88e2994fd8dabe93f6ecc..682e5eecb7ce514094f76253447aa7ac4b6f29b1 100644 --- a/content/public/browser/web_contents_delegate.h +++ b/content/public/browser/web_contents_delegate.h @@ -359,8 +359,7 @@ class CONTENT_EXPORT WebContentsDelegate { diff --git a/patches/chromium/enable_reset_aspect_ratio.patch b/patches/chromium/enable_reset_aspect_ratio.patch index 9a6495bed86ad..5954ee90821d7 100644 --- a/patches/chromium/enable_reset_aspect_ratio.patch +++ b/patches/chromium/enable_reset_aspect_ratio.patch @@ -6,7 +6,7 @@ Subject: feat: enable setting aspect ratio to 0 Make SetAspectRatio accept 0 as valid input, which would reset to null. diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index 6ad16425f2fb3438be178cb06a85ef72f8d09e22..61509e2eb982797845098abf5f36e031be63686b 100644 +index 6240e33c74a0a487affb3ec7e01d6a662d3950b7..5f9612ff000c1544f572bab0cbc9982dc4e647ce 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc @@ -664,7 +664,7 @@ void DesktopWindowTreeHostWin::SetOpacity(float opacity) { diff --git a/patches/chromium/extend_apply_webpreferences.patch b/patches/chromium/extend_apply_webpreferences.patch index 602b449541f9c..1eb1413326471 100644 --- a/patches/chromium/extend_apply_webpreferences.patch +++ b/patches/chromium/extend_apply_webpreferences.patch @@ -12,10 +12,10 @@ Ideally we could add an embedder observer pattern here but that can be done in future work. diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index 3c3c0247ca56ba99b48583a4218712f172458845..c996ded8e1cf83ca0ebb4b3fc18b8d6d80409c9a 100644 +index f6a248b1de8b313658453dd380529ec7c2e40033..15a6b41cacb7b66d95e6dc2cff8148c3d6c8c28b 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc -@@ -171,6 +171,7 @@ +@@ -172,6 +172,7 @@ #include "third_party/blink/renderer/core/view_transition/view_transition_supplement.h" #include "third_party/blink/renderer/platform/fonts/font_cache.h" #include "third_party/blink/renderer/platform/fonts/generic_font_family_settings.h" @@ -23,7 +23,7 @@ index 3c3c0247ca56ba99b48583a4218712f172458845..c996ded8e1cf83ca0ebb4b3fc18b8d6d #include "third_party/blink/renderer/platform/graphics/image.h" #include "third_party/blink/renderer/platform/graphics/paint/cull_rect.h" #include "third_party/blink/renderer/platform/graphics/paint/paint_record_builder.h" -@@ -1861,6 +1862,7 @@ void WebView::ApplyWebPreferences(const web_pref::WebPreferences& prefs, +@@ -1862,6 +1863,7 @@ void WebView::ApplyWebPreferences(const web_pref::WebPreferences& prefs, #if BUILDFLAG(IS_MAC) web_view_impl->SetMaximumLegibleScale( prefs.default_maximum_page_scale_factor); diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index ffa3f9ee34645..9653ef7b69b90 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -21,7 +21,7 @@ making three primary changes to Blink: * Mostly simple "plumbing" for the setting through blink. diff --git a/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc b/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc -index 5e233d63c09088d73cd1a54a58b235018c193ac3..4f2dcb339ad79f31ba5e4c347cb91d5639d27ce6 100644 +index c13dfd7f20e6f281f51ae373ceebeb86104c5cd9..fac89df9f23f3f098096d2a07a07e623b1067270 100644 --- a/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc +++ b/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc @@ -128,6 +128,8 @@ bool StructTraitscanvas_noise_token = data.canvas_noise_token(); - return true; + out->view_source_line_wrap_enabled = data.view_source_line_wrap_enabled(); diff --git a/third_party/blink/public/common/renderer_preferences/renderer_preferences.h b/third_party/blink/public/common/renderer_preferences/renderer_preferences.h -index ff84a20511448d4211d0e25dfc12e7eabc34a9e0..886e9d819c3bde7f33eec3497d1cadb76de4237f 100644 +index 75acd696a5258e52f5c17b88559dfb3f6373c669..34b5ed725702dca72c383c1def08fdb835f7fa6b 100644 --- a/third_party/blink/public/common/renderer_preferences/renderer_preferences.h +++ b/third_party/blink/public/common/renderer_preferences/renderer_preferences.h @@ -91,6 +91,7 @@ struct BLINK_COMMON_EXPORT RendererPreferences { @@ -43,10 +43,10 @@ index ff84a20511448d4211d0e25dfc12e7eabc34a9e0..886e9d819c3bde7f33eec3497d1cadb7 std::vector explicitly_allowed_network_ports; + bool electron_corner_smoothing_css{true}; uint64_t canvas_noise_token{0}; - - RendererPreferences(); + // The default value must be false to avoid performance problems on very large + // source pages. diff --git a/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h b/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h -index c88ddaf7fd5fc27889bcacac9366330e4013eba3..e4f492a11637886c60ece665371d117f3a34ec8d 100644 +index defe40d7091cb4ba4b099a22aeaee71f78ff5e77..e8326fa7a3c45c08c7d9250edd52a6d73fcc3ff9 100644 --- a/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h +++ b/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h @@ -275,6 +275,11 @@ struct BLINK_COMMON_EXPORT @@ -62,7 +62,7 @@ index c88ddaf7fd5fc27889bcacac9366330e4013eba3..e4f492a11637886c60ece665371d117f const ::blink::RendererPreferences& data) { return data.canvas_noise_token; diff --git a/third_party/blink/public/mojom/renderer_preferences.mojom b/third_party/blink/public/mojom/renderer_preferences.mojom -index 65766b955e81bfc332bc2c4e0b9da48389c1bd68..a475e1bfee46f0a77d1cfbdea47e9de6516d1194 100644 +index f8361faf6151210d65a597562c533aaa0a5235df..328238c34a9381fbbeb5970af3de721c8412104e 100644 --- a/third_party/blink/public/mojom/renderer_preferences.mojom +++ b/third_party/blink/public/mojom/renderer_preferences.mojom @@ -202,6 +202,8 @@ struct RendererPreferences { @@ -112,10 +112,10 @@ index 6e991652d242795e292cea4c94cff59aaea078fa..b6834c78575520bb6e584dd2ce3333ac 'internal-forced-visited-'): internal_visited_order = 0 diff --git a/third_party/blink/renderer/core/css/css_properties.json5 b/third_party/blink/renderer/core/css/css_properties.json5 -index cc8657b515dd791e910343122e73be6fc8c1d38e..78299aca166e20c1e5f1f049beab915334d1612d 100644 +index 5bacbf438f37363e8a6c2f61ff8eff0dae781aaa..e16363cbff7a4af50656f64f7f69ecfa15081245 100644 --- a/third_party/blink/renderer/core/css/css_properties.json5 +++ b/third_party/blink/renderer/core/css/css_properties.json5 -@@ -8823,6 +8823,24 @@ +@@ -8810,6 +8810,24 @@ property_methods: ["ParseShorthand", "CSSValueFromComputedStyleInternal"], }, @@ -141,7 +141,7 @@ index cc8657b515dd791e910343122e73be6fc8c1d38e..78299aca166e20c1e5f1f049beab9153 { name: "-internal-visited-color", diff --git a/third_party/blink/renderer/core/css/css_property_equality.cc b/third_party/blink/renderer/core/css/css_property_equality.cc -index ff1cc33c1787df522300a220000ad3d3123cd7bd..6b9e72f60db9af5ceeac7cc663ac666b0eeb7b09 100644 +index 936bd39e77a5a181a94a48129e38efc9c8c82847..75d332ef497018e4c863a47d4491d25da365206a 100644 --- a/third_party/blink/renderer/core/css/css_property_equality.cc +++ b/third_party/blink/renderer/core/css/css_property_equality.cc @@ -346,6 +346,8 @@ bool CSSPropertyEquality::PropertiesEqual(const PropertyHandle& property, @@ -154,10 +154,10 @@ index ff1cc33c1787df522300a220000ad3d3123cd7bd..6b9e72f60db9af5ceeac7cc663ac666b return a.EmptyCells() == b.EmptyCells(); case CSSPropertyID::kFill: diff --git a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -index cefbbebae039bb9cdbdf57612feff660dfe94d87..3c3dea18f97a3df1ef6eb095c34951492285cee0 100644 +index aa12ac9e27c55870269dd780e868b5eaee5acaab..1a06511ee56717df547817813eb80c3db1fa01df 100644 --- a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -@@ -12071,5 +12071,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( +@@ -12086,5 +12086,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( CSSValueID::kNone>(stream); } @@ -184,10 +184,10 @@ index cefbbebae039bb9cdbdf57612feff660dfe94d87..3c3dea18f97a3df1ef6eb095c3495149 } // namespace css_longhand } // namespace blink diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -index 5d803e8baebc35075d7475e091f97811407add79..50991917a87ff1a219fe2b3dd80dd055fd3e4289 100644 +index 56429f6e0da31c28aef86b1b5a5e538207b42706..33c6a8ff7cf6ffff2952b5a8b9389eb04ee6946d 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -@@ -3869,4 +3869,12 @@ PositionArea StyleBuilderConverter::ConvertPositionArea( +@@ -3900,4 +3900,12 @@ PositionArea StyleBuilderConverter::ConvertPositionArea( return PositionArea(span[0], span[1], span[2], span[3]); } @@ -201,10 +201,10 @@ index 5d803e8baebc35075d7475e091f97811407add79..50991917a87ff1a219fe2b3dd80dd055 + } // namespace blink diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h -index a33d85561b005010653c5e3a562227b1f379ec90..0c2d3b0e9b691477d46c892afc16d8b0421e7263 100644 +index d761af01cc6b4ef01304dfe384c3aa92f414b8a2..de0f1c09f41b4f348a7163967f6d90d98fe7c06c 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h -@@ -419,6 +419,8 @@ class StyleBuilderConverter { +@@ -421,6 +421,8 @@ class StyleBuilderConverter { const CSSValue&); static PositionArea ConvertPositionArea(StyleResolverState&, const CSSValue&); @@ -239,11 +239,11 @@ index 5e8d2bfbccd0625c2598544a9cba3d71373eded2..e68a97ee75754fc7196f11cf5c731550 bool RenderVSyncNotificationEnabled() const { return render_v_sync_notification_enabled_; diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index c996ded8e1cf83ca0ebb4b3fc18b8d6d80409c9a..d589a8a5264b2a7c2b21aa83e8c1faa5fb8f93a1 100644 +index 15a6b41cacb7b66d95e6dc2cff8148c3d6c8c28b..88bb3d17a4ca0784f1f28fde14b9fa58e15b5c44 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc -@@ -3574,6 +3574,9 @@ void WebViewImpl::UpdateRendererPreferences( - CanvasNoiseToken::Set(renderer_preferences_.canvas_noise_token); +@@ -3577,6 +3577,9 @@ void WebViewImpl::UpdateRendererPreferences( + renderer_preferences_.view_source_line_wrap_enabled); MaybePreloadSystemFonts(GetPage()); + diff --git a/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch b/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch index 4abaf36574521..e2dad99a8fe12 100644 --- a/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch +++ b/patches/chromium/fix_move_autopipsettingshelper_behind_branding_buildflag.patch @@ -75,7 +75,7 @@ index 659e8d79766a78d261e58adab08f9abccda8390b..bc4dc2e3a93877d2e20890560f61d3f2 PictureInPictureOcclusionTracker* diff --git a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc -index 106f2c27297ab437839b3e320a5e5c657947b1c3..f2d4bb25647e9075df68ace24ed910d62a90c89e 100644 +index 4ef685a3cdf981d876550d17c3df997ed5d97191..9bb8ef5af976c0b9d038d34a9a1056f7dae4abcb 100644 --- a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc +++ b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc @@ -432,11 +432,13 @@ std::unique_ptr VideoOverlayWindowViews::Create( diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index a235d69872ff6..0c4030c0ad38a 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 020d8d111d756dbe8bbae47a0e7dc74b63501b54..70b3c4a2da0e1d79a7626e0bb2ed45b8fbbe0024 100644 +index 0169ccad6ae4430d5c5a05a46ad21c2421ae3631..46d4c5e8c4f0d91d00ef51cc410ef54ebadb8eef 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10019,7 +10019,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -10017,7 +10017,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/logging_win32_only_create_a_console_if_logging_to_stderr.patch b/patches/chromium/logging_win32_only_create_a_console_if_logging_to_stderr.patch index 3b90c3847d68c..34005e07a3182 100644 --- a/patches/chromium/logging_win32_only_create_a_console_if_logging_to_stderr.patch +++ b/patches/chromium/logging_win32_only_create_a_console_if_logging_to_stderr.patch @@ -9,10 +9,10 @@ be created for each child process, despite logs being redirected to a file. diff --git a/content/app/content_main.cc b/content/app/content_main.cc -index ffc5c377428008a9cee3969e958e19357b3ecead..892fa6258a77a6ec3ddfa209a9d3fd63a372406c 100644 +index 36248b2a3e099674467a095cb4902d89914a51d8..aa670179d74337f66dcebcd9c2a182a2f54eee5d 100644 --- a/content/app/content_main.cc +++ b/content/app/content_main.cc -@@ -330,16 +330,14 @@ NO_STACK_PROTECTOR int RunContentProcess( +@@ -345,16 +345,14 @@ NO_STACK_PROTECTOR int RunContentProcess( #if BUILDFLAG(IS_WIN) base::CommandLine* command_line = base::CommandLine::ForCurrentProcess(); diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 6d3f53957a6c4..c255aae9708ac 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -582,7 +582,7 @@ index d83f420d25e2c108ad400ebecae02b1ac327c058..77852c5c315ac09dddb7227adf3b840e return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index b40575d6a1201e3543927f8d71ebf76d61a61ab7..088555a527f6a93486cd2cede7f4ba0b46b22fa1 100644 +index 4c02b0aef40b31a0dd55859c718842e25652fe74..0ad5b87248ac7c15774a870d5a4268c60a2c36c0 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn @@ -342,6 +342,7 @@ source_set("browser") { diff --git a/patches/chromium/notification_provenance.patch b/patches/chromium/notification_provenance.patch index 9880ad53ec02f..71e3f12bbf422 100644 --- a/patches/chromium/notification_provenance.patch +++ b/patches/chromium/notification_provenance.patch @@ -7,10 +7,10 @@ Pass RenderFrameHost through to PlatformNotificationService so Electron can identify which renderer a notification came from. diff --git a/chrome/browser/notifications/platform_notification_service_impl.cc b/chrome/browser/notifications/platform_notification_service_impl.cc -index 2f9eb931d8cd30617fc8df6c9ff976ba2e29d194..2985c28ed040793819dcde2ccd1694b28275e66b 100644 +index fb563ef26eb218ffb4115284b048b71101219363..eaf2541cef53b864cf7a986226c40621063c826d 100644 --- a/chrome/browser/notifications/platform_notification_service_impl.cc +++ b/chrome/browser/notifications/platform_notification_service_impl.cc -@@ -245,6 +245,7 @@ bool PlatformNotificationServiceImpl::WasClosedProgrammatically( +@@ -247,6 +247,7 @@ bool PlatformNotificationServiceImpl::WasClosedProgrammatically( // TODO(awdf): Rename to DisplayNonPersistentNotification (Similar for Close) void PlatformNotificationServiceImpl::DisplayNotification( diff --git a/patches/chromium/picture-in-picture.patch b/patches/chromium/picture-in-picture.patch index 5fd000554592b..a71a38d1cc2a3 100644 --- a/patches/chromium/picture-in-picture.patch +++ b/patches/chromium/picture-in-picture.patch @@ -38,7 +38,7 @@ index 8168b4cfbafd42fa93a5aa9a3691c2552fabfb86..ba49212bd76d209f99c1cee649fc1466 ui::ImageModel::FromVectorIcon(*icon, kColorPipWindowForeground, kCloseButtonIconSize)); diff --git a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc -index c80abff87a34a8dfb94eec4c856438b458ad7936..106f2c27297ab437839b3e320a5e5c657947b1c3 100644 +index cb0704f2f21e105aebf566366a2359874eed1c3a..4ef685a3cdf981d876550d17c3df997ed5d97191 100644 --- a/chrome/browser/ui/views/overlay/video_overlay_window_views.cc +++ b/chrome/browser/ui/views/overlay/video_overlay_window_views.cc @@ -19,9 +19,11 @@ @@ -71,7 +71,7 @@ index c80abff87a34a8dfb94eec4c856438b458ad7936..106f2c27297ab437839b3e320a5e5c65 std::wstring app_user_model_id; Browser* browser = chrome::FindBrowserWithTab(controller->GetWebContents()); if (browser) { -@@ -1099,10 +1101,12 @@ void VideoOverlayWindowViews::SetUpViews() { +@@ -1092,10 +1094,12 @@ void VideoOverlayWindowViews::SetUpViews() { l10n_util::GetStringUTF16( IDS_PICTURE_IN_PICTURE_LIVE_CAPTION_CONTROL_TEXT)); live_caption_button->SetSize(kActionButtonSize); diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index 5cd755ed1d69b..0af0d420aace5 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -881,10 +881,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 088555a527f6a93486cd2cede7f4ba0b46b22fa1..c04a351865e2fc49481f5068f91e53ec909dfce1 100644 +index 0ad5b87248ac7c15774a870d5a4268c60a2c36c0..2d18faace5c0021e0bf04b8e089a8db1593d1fc1 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3161,8 +3161,9 @@ source_set("browser") { +@@ -3163,8 +3163,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index c2ca450009b8f..69d36ad07572b 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -44,10 +44,10 @@ index 23d5baa267333e18551d449317f3e3a6520f34a6..2551b4a2b9dfca9767c39e2e9bd79ed1 void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index e42e462f3c8109444e6dadb0557e38cdd05c362a..2eb45ae773f9fbd28fa05b14e5684f4b7d17cc85 100644 +index 43ca2bbe1611cbc2b533435319111dd9458de471..27dfdfaa258312b3e096cfe784e085376026d9ef 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5914,6 +5914,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -5915,6 +5915,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,7 +60,7 @@ index e42e462f3c8109444e6dadb0557e38cdd05c362a..2eb45ae773f9fbd28fa05b14e5684f4b RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index 08497c589757778543bedbfa920554c5fb9a298e..aa428be6f3701dc5d856e288180c54cf7559cc6f 100644 +index 05a401f48ba5a784c547c3fe1f4fb5252af3014d..3e556e807577123599f957d5f9d24b084014e150 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h @@ -1188,6 +1188,7 @@ class CONTENT_EXPORT WebContentsImpl diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index 1e61394bec701..49da2e0eb56d8 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index d0f42ceedfac643443e3c7c5757b831f481a72eb..b6e0304e561bd81dc09924cab04887437dca84b7 100644 +index 6d5ed56518116ce534fac98a994b7b7d9f1c6d11..91b66c472ba0398efad3a0a3cfe0d39eee529eaa 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10156,25 +10156,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10154,25 +10154,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index 57beac05e4ed3..465a33eadf63f 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 7b416ade6fe632d7fab319460876cb42f5b5dd83..f26744c0046ed8bda0495de4bf10b8d12f1a7911 100644 +index 420879681bab99129e314b8717c4edf075037d35..602e2f8049a673d4ccfaaf6891fa1b5a8140781f 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -3965,6 +3965,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3966,6 +3966,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index 7b416ade6fe632d7fab319460876cb42f5b5dd83..f26744c0046ed8bda0495de4bf10b8d1 std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -3975,6 +3982,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3976,6 +3983,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } @@ -35,7 +35,7 @@ index 7b416ade6fe632d7fab319460876cb42f5b5dd83..f26744c0046ed8bda0495de4bf10b8d1 CHECK(view_.get()); diff --git a/content/public/browser/web_contents.h b/content/public/browser/web_contents.h -index ea5856a886ae49c161c7b7a1e4ea108a77c2534c..1da1ee16f70ea430c163ec0676ddb2b0a13c8c43 100644 +index 560e0056bb9b0feb7510f81a80a6365cd38676d2..5ff33943a133b45d7a48a48844f5fa9e62a1f413 100644 --- a/content/public/browser/web_contents.h +++ b/content/public/browser/web_contents.h @@ -121,10 +121,13 @@ class BrowserPluginGuestDelegate; @@ -52,7 +52,7 @@ index ea5856a886ae49c161c7b7a1e4ea108a77c2534c..1da1ee16f70ea430c163ec0676ddb2b0 class WebUI; struct DropData; struct MHTMLGenerationParams; -@@ -274,6 +277,10 @@ class WebContents : public PageNavigator, public base::SupportsUserData { +@@ -278,6 +281,10 @@ class WebContents : public PageNavigator, public base::SupportsUserData { network::mojom::WebSandboxFlags starting_sandbox_flags = network::mojom::WebSandboxFlags::kNone; diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index 3b63735fbcb44..c369d3f9109c7 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -37,10 +37,10 @@ index f4231fa2549083e8132affa6e424ac18f28b4f41..32d4d22f4d0106c8f598e8e44545788c if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index f26744c0046ed8bda0495de4bf10b8d12f1a7911..020d8d111d756dbe8bbae47a0e7dc74b63501b54 100644 +index 602e2f8049a673d4ccfaaf6891fa1b5a8140781f..0169ccad6ae4430d5c5a05a46ad21c2421ae3631 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4254,21 +4254,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4255,21 +4255,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index f26744c0046ed8bda0495de4bf10b8d12f1a7911..020d8d111d756dbe8bbae47a0e7dc74b } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4427,7 +4431,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4428,7 +4432,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch index 13e43a0d55b1b..bff9bbb53a086 100644 --- a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch +++ b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch @@ -10,10 +10,10 @@ to handle this without patching, but this is fairly clean for now and no longer patching legacy devtools code. diff --git a/front_end/entrypoints/main/MainImpl.ts b/front_end/entrypoints/main/MainImpl.ts -index 691e308b52493ed235196b7b75505b7a08911180..8cba1cd242a17c83f330bb3f4aac15505b363cab 100644 +index 90dfc1abb2f03ccc4b120e16b25434023d8f47a8..d9da92c75c27bc21bc7a165c489a6e04935c41f2 100644 --- a/front_end/entrypoints/main/MainImpl.ts +++ b/front_end/entrypoints/main/MainImpl.ts -@@ -730,6 +730,8 @@ export class MainImpl { +@@ -721,6 +721,8 @@ export class MainImpl { globalThis.Main = globalThis.Main || {}; // @ts-expect-error Exported for Tests.js globalThis.Main.Main = MainImpl; diff --git a/shell/browser/ui/file_dialog_mac.mm b/shell/browser/ui/file_dialog_mac.mm index 881054f0445d6..01f2f1243c3fb 100644 --- a/shell/browser/ui/file_dialog_mac.mm +++ b/shell/browser/ui/file_dialog_mac.mm @@ -29,7 +29,7 @@ @interface PopUpButtonHandler : NSObject -@property(nonatomic, assign) NSSavePanel* savePanel; +@property(nonatomic, weak) NSSavePanel* savePanel; @property(nonatomic, strong) NSArray* contentTypesList; - (instancetype)initWithPanel:(NSSavePanel*)panel diff --git a/shell/browser/ui/webui/accessibility_ui.cc b/shell/browser/ui/webui/accessibility_ui.cc index 083652ad00a72..05424f8182fd8 100644 --- a/shell/browser/ui/webui/accessibility_ui.cc +++ b/shell/browser/ui/webui/accessibility_ui.cc @@ -231,7 +231,7 @@ void HandleAccessibilityRequestCallback( continue; } // Ignore views that are never user-visible, like background pages. - if (delegate->IsNeverComposited(web_contents)) { + if (web_contents->IsNeverComposited()) { continue; } content::BrowserContext* context = rvh->GetProcess()->GetBrowserContext(); From ec1b0f4923dd371f3db88e9c31ce4fefff2f5474 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 14 May 2025 16:01:44 -0500 Subject: [PATCH 042/186] refactor: remove `CreateViewForWidget` patch (#47084) * refactor: remove CreateViewForWidget patch Co-authored-by: Shelley Vohr * chore: rm unintended osr change Co-authored-by: deepak1556 --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr Co-authored-by: deepak1556 --- patches/chromium/.patches | 1 - .../render_widget_host_view_base.patch | 73 ------------------- .../browser/osr/osr_render_widget_host_view.h | 2 +- shell/browser/osr/osr_web_contents_view.cc | 15 ++-- shell/browser/web_view_guest_delegate.cc | 13 +++- 5 files changed, 20 insertions(+), 84 deletions(-) delete mode 100644 patches/chromium/render_widget_host_view_base.patch diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 1faeae3c941f5..e49e542bf3caa 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -4,7 +4,6 @@ blink_local_frame.patch can_create_window.patch disable_hidden.patch dom_storage_limits.patch -render_widget_host_view_base.patch render_widget_host_view_mac.patch webview_cross_drag.patch gin_enable_disable_v8_platform.patch diff --git a/patches/chromium/render_widget_host_view_base.patch b/patches/chromium/render_widget_host_view_base.patch deleted file mode 100644 index 429955c98fb21..0000000000000 --- a/patches/chromium/render_widget_host_view_base.patch +++ /dev/null @@ -1,73 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Anonymous -Date: Thu, 20 Sep 2018 17:46:21 -0700 -Subject: render_widget_host_view_base.patch - -... something to do with OSR? and maybe as well? terrifying. - -diff --git a/content/browser/renderer_host/render_widget_host_view_base.cc b/content/browser/renderer_host/render_widget_host_view_base.cc -index bb7475f1f8be4038c77d2dc68b09a7ac2338b160..c35ef5290ef1f812c5e7ff31d71ae0661b26d124 100644 ---- a/content/browser/renderer_host/render_widget_host_view_base.cc -+++ b/content/browser/renderer_host/render_widget_host_view_base.cc -@@ -655,6 +655,13 @@ void RenderWidgetHostViewBase::OnFrameTokenChangedForView( - host()->DidProcessFrame(frame_token, activation_time); - } - -+RenderWidgetHostViewBase* RenderWidgetHostViewBase::CreateViewForWidget( -+ RenderWidgetHost* render_widget_host, -+ RenderWidgetHost* embedder_render_widget_host, -+ WebContentsView* web_contents_view) { -+ return web_contents_view->CreateViewForWidget(render_widget_host); -+} -+ - void RenderWidgetHostViewBase::ProcessMouseEvent( - const blink::WebMouseEvent& event, - const ui::LatencyInfo& latency) { -diff --git a/content/browser/renderer_host/render_widget_host_view_base.h b/content/browser/renderer_host/render_widget_host_view_base.h -index 5627ee381a99c49760bbaa6e5e3476d8b4bc8cb1..230e059ee11ed64a1694232dad791fbb5644b578 100644 ---- a/content/browser/renderer_host/render_widget_host_view_base.h -+++ b/content/browser/renderer_host/render_widget_host_view_base.h -@@ -30,6 +30,8 @@ - #include "components/viz/common/surfaces/scoped_surface_id_allocator.h" - #include "components/viz/common/surfaces/surface_id.h" - #include "content/browser/renderer_host/display_feature.h" -+#include "content/browser/renderer_host/visible_time_request_trigger.h" -+#include "content/browser/web_contents/web_contents_view.h" - #include "content/common/content_export.h" - #include "content/public/browser/render_frame_metadata_provider.h" - #include "content/public/browser/render_widget_host.h" -@@ -73,11 +75,13 @@ namespace content { - class DevicePosturePlatformProvider; - class MouseWheelPhaseHandler; - class RenderWidgetHostImpl; -+class RenderWidgetHostViewGuest; - class ScopedViewTransitionResources; - class TextInputManager; - class TouchSelectionControllerClientManager; - class TouchSelectionControllerInputObserver; - class WebContentsAccessibility; -+class WebContentsView; - class DelegatedFrameHost; - class SyntheticGestureTarget; - -@@ -149,6 +153,10 @@ class CONTENT_EXPORT RenderWidgetHostViewBase - void ProcessGestureEvent(const blink::WebGestureEvent& event, - const ui::LatencyInfo& latency) override; - RenderWidgetHostViewBase* GetRootView() override; -+ virtual RenderWidgetHostViewBase* CreateViewForWidget( -+ RenderWidgetHost* render_widget_host, -+ RenderWidgetHost* embedder_render_widget_host, -+ WebContentsView* web_contents_view); - void OnAutoscrollStart() override; - const viz::DisplayHitTestQueryMap& GetDisplayHitTestQuery() const override; - -@@ -198,6 +206,9 @@ class CONTENT_EXPORT RenderWidgetHostViewBase - void ShowInterestInElement(int) override {} - bool IsHTMLFormPopup() const override; - -+ virtual void InitAsGuest(RenderWidgetHostView* parent_host_view, -+ RenderWidgetHostViewGuest* guest_view) {} -+ - // This only needs to be overridden by RenderWidgetHostViewBase subclasses - // that handle content embedded within other RenderWidgetHostViews. - gfx::PointF TransformPointToRootCoordSpaceF( diff --git a/shell/browser/osr/osr_render_widget_host_view.h b/shell/browser/osr/osr_render_widget_host_view.h index f46c7a6c91810..a1bdee8300b60 100644 --- a/shell/browser/osr/osr_render_widget_host_view.h +++ b/shell/browser/osr/osr_render_widget_host_view.h @@ -170,7 +170,7 @@ class OffScreenRenderWidgetHostView content::RenderWidgetHostViewBase* CreateViewForWidget( content::RenderWidgetHost*, content::RenderWidgetHost*, - content::WebContentsView*) override; + content::WebContentsView*); const viz::LocalSurfaceId& GetLocalSurfaceId() const override; const viz::FrameSinkId& GetFrameSinkId() const override; diff --git a/shell/browser/osr/osr_web_contents_view.cc b/shell/browser/osr/osr_web_contents_view.cc index 9a0cfe496fcb8..3606e2754ce74 100644 --- a/shell/browser/osr/osr_web_contents_view.cc +++ b/shell/browser/osr/osr_web_contents_view.cc @@ -122,14 +122,19 @@ OffScreenWebContentsView::CreateViewForChildWidget( auto* web_contents_impl = static_cast(web_contents_); - auto* view = static_cast( - web_contents_impl->GetOuterWebContents() - ? web_contents_impl->GetOuterWebContents()->GetRenderWidgetHostView() - : web_contents_impl->GetRenderWidgetHostView()); + OffScreenRenderWidgetHostView* embedder_host_view = nullptr; + if (web_contents_impl->GetOuterWebContents()) { + embedder_host_view = static_cast( + web_contents_impl->GetOuterWebContents()->GetRenderWidgetHostView()); + } else { + embedder_host_view = static_cast( + web_contents_impl->GetRenderWidgetHostView()); + } return new OffScreenRenderWidgetHostView( transparent_, offscreen_use_shared_texture_, painting_, - view->frame_rate(), callback_, render_widget_host, view, GetSize()); + embedder_host_view->frame_rate(), callback_, render_widget_host, + embedder_host_view, GetSize()); } void OffScreenWebContentsView::RenderViewReady() { diff --git a/shell/browser/web_view_guest_delegate.cc b/shell/browser/web_view_guest_delegate.cc index e8d1d7fe90af5..8448a7323739e 100644 --- a/shell/browser/web_view_guest_delegate.cc +++ b/shell/browser/web_view_guest_delegate.cc @@ -7,6 +7,7 @@ #include #include "content/browser/web_contents/web_contents_impl.h" // nogncheck +#include "content/browser/web_contents/web_contents_view.h" // nogncheck #include "content/public/browser/navigation_handle.h" #include "content/public/browser/render_frame_host.h" #include "content/public/browser/render_process_host.h" @@ -111,10 +112,14 @@ WebViewGuestDelegate::CreateNewGuestWindow( auto* guest_contents_impl = static_cast(guest_contents.release()); auto* new_guest_view = guest_contents_impl->GetView(); - content::RenderWidgetHostView* widget_view = - new_guest_view->CreateViewForWidget( - guest_contents_impl->GetRenderViewHost()->GetWidget()); - if (!create_params.initially_hidden) + + content::RenderWidgetHostView* widget_view = nullptr; + if (new_guest_view) { + widget_view = new_guest_view->CreateViewForWidget( + guest_contents_impl->GetRenderViewHost()->GetWidget()); + } + + if (widget_view && !create_params.initially_hidden) widget_view->Show(); return base::WrapUnique( static_cast(guest_contents_impl)); From ec83c1303c5e89b2084badaacaa8de19c7600484 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 14 May 2025 16:02:32 -0500 Subject: [PATCH 043/186] feat: enable secondary label for macOS menu (#47042) * feat: enable secondary label for macOS menu Co-authored-by: Michaela Laurencin * Update shell/browser/ui/cocoa/electron_menu_controller.mm Co-authored-by: Robo Co-authored-by: Michaela Laurencin <35157522+mlaurencin@users.noreply.github.com> * fix for lint Co-authored-by: Michaela Laurencin * update docs for sublabel Co-authored-by: Michaela Laurencin --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Michaela Laurencin Co-authored-by: Michaela Laurencin <35157522+mlaurencin@users.noreply.github.com> --- docs/api/menu-item.md | 2 +- docs/api/menu.md | 21 +++++++++++++++++++ .../ui/cocoa/electron_menu_controller.mm | 9 ++++++++ 3 files changed, 31 insertions(+), 1 deletion(-) diff --git a/docs/api/menu-item.md b/docs/api/menu-item.md index 0bf0753012170..3c53afc222bc6 100644 --- a/docs/api/menu-item.md +++ b/docs/api/menu-item.md @@ -19,7 +19,7 @@ See [`Menu`](menu.md) for examples. * `type` string (optional) - Can be `normal`, `separator`, `submenu`, `checkbox` or `radio`. * `label` string (optional) - * `sublabel` string (optional) + * `sublabel` string (optional) _macOS_ - Available in macOS >= 14.4 * `toolTip` string (optional) _macOS_ - Hover text for this menu item. * `accelerator` [Accelerator](accelerator.md) (optional) * `icon` ([NativeImage](native-image.md) | string) (optional) diff --git a/docs/api/menu.md b/docs/api/menu.md index 477729cede80a..c94d8fe70d794 100644 --- a/docs/api/menu.md +++ b/docs/api/menu.md @@ -332,6 +332,27 @@ name, no matter what label you set. To change it, modify your app bundle's [About Information Property List Files][AboutInformationPropertyListFiles] for more information. +### Menu Sublabels + +Menu sublabels, or [subtitles](https://developer.apple.com/documentation/appkit/nsmenuitem/subtitle?language=objc), can be added to menu items using the `sublabel` option. Below is an example based on the renderer example above: + +```js @ts-expect-error=[12] +// main +ipcMain.on('show-context-menu', (event) => { + const template = [ + { + label: 'Menu Item 1', + sublabel: 'Subtitle 1', + click: () => { event.sender.send('context-menu-command', 'menu-item-1') } + }, + { type: 'separator' }, + { label: 'Menu Item 2', sublabel: 'Subtitle 2', type: 'checkbox', checked: true } + ] + const menu = Menu.buildFromTemplate(template) + menu.popup({ window: BrowserWindow.fromWebContents(event.sender) }) +}) +``` + ## Setting Menu for Specific Browser Window (_Linux_ _Windows_) The [`setMenu` method][setMenu] of browser windows can set the menu of certain diff --git a/shell/browser/ui/cocoa/electron_menu_controller.mm b/shell/browser/ui/cocoa/electron_menu_controller.mm index d23e007dd0bad..71c9d8b49e863 100644 --- a/shell/browser/ui/cocoa/electron_menu_controller.mm +++ b/shell/browser/ui/cocoa/electron_menu_controller.mm @@ -315,12 +315,21 @@ - (NSMenuItem*)menuItemForService:(NSSharingService*)service - (NSMenuItem*)makeMenuItemForIndex:(NSInteger)index fromModel:(electron::ElectronMenuModel*)model { std::u16string label16 = model->GetLabelAt(index); + auto rawSecondaryLabel = model->GetSecondaryLabelAt(index); NSString* label = l10n_util::FixUpWindowsStyleLabel(label16); NSMenuItem* item = [[NSMenuItem alloc] initWithTitle:label action:@selector(itemSelected:) keyEquivalent:@""]; + if (!rawSecondaryLabel.empty()) { + if (@available(macOS 14.4, *)) { + NSString* secondary_label = + l10n_util::FixUpWindowsStyleLabel(rawSecondaryLabel); + item.subtitle = secondary_label; + } + } + // If the menu item has an icon, set it. ui::ImageModel icon = model->GetIconAt(index); if (icon.IsImage()) From bf54b8d709cc190f6e333983f0f4d9b601f74dd6 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 14 May 2025 16:02:46 -0500 Subject: [PATCH 044/186] feat: enable innerWidth and innerHeight for window open (#47039) feat: enable innerWidth and innerHeight for window open (#46749) * feat: enable innerWidth and innerHeight for window open * update comment for added special innerWidth and innerHeight * update 100 min spec requirement handling * update testing to include getContentSize * update macOS min requirement handling * adjust refactored consts * update const values from nativewindowviews Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Michaela Laurencin <35157522+mlaurencin@users.noreply.github.com> --- lib/browser/parse-features-string.ts | 7 +++- shell/browser/native_window_mac.mm | 21 +++++++++-- shell/browser/native_window_views.cc | 23 +++++++++--- shell/common/options_switches.h | 2 ++ spec/chromium-spec.ts | 35 +++++++++++++++++++ .../pages/window-open-size-inner.html | 7 ++++ 6 files changed, 87 insertions(+), 8 deletions(-) create mode 100644 spec/fixtures/pages/window-open-size-inner.html diff --git a/lib/browser/parse-features-string.ts b/lib/browser/parse-features-string.ts index 4d54479c04381..be37505c64a06 100644 --- a/lib/browser/parse-features-string.ts +++ b/lib/browser/parse-features-string.ts @@ -26,7 +26,12 @@ const keysOfTypeNumberCompileTimeCheck: { [K in IntegerBrowserWindowOptionKeys] }; // Note `top` / `left` are special cases from the browser which we later convert // to y / x. -const keysOfTypeNumber = new Set(['top', 'left', ...Object.keys(keysOfTypeNumberCompileTimeCheck)]); +// NOTE(@mlaurencin) `innerWidth` / `innerHeight` are also special cases. The spec +// states that `width` and `height` represent the window content size and are equivalent +// to `innerWidth` / `innerHeight`. However, our implementation currently incorrectly maps +// `width` and `height` to `outerWidth` and `outerHeight`, or the size of the window +// with all border and related window chrome. +const keysOfTypeNumber = new Set(['top', 'left', 'innerWidth', 'innerHeight', ...Object.keys(keysOfTypeNumberCompileTimeCheck)]); /** * Note that we only allow "0" and "1" boolean conversion when the type is known diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 4c6bda59bd328..2dcbdd07ae04e 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -119,8 +119,8 @@ static bool FromV8(v8::Isolate* isolate, ui::NativeTheme::GetInstanceForNativeUi()->AddObserver(this); display::Screen::GetScreen()->AddObserver(this); - const int width = options.ValueOrDefault(options::kWidth, 800); - const int height = options.ValueOrDefault(options::kHeight, 600); + int width = options.ValueOrDefault(options::kWidth, 800); + int height = options.ValueOrDefault(options::kHeight, 600); NSRect main_screen_rect = [[[NSScreen screens] firstObject] frame]; gfx::Rect bounds(round((NSWidth(main_screen_rect) - width) / 2), @@ -283,8 +283,23 @@ static bool FromV8(v8::Isolate* isolate, } // Resize to content bounds. - const bool use_content_size = + // NOTE(@mlaurencin) Spec requirements can be found here: + // https://developer.mozilla.org/en-US/docs/Web/API/Window/open#width + constexpr int kMinSizeReqdBySpec = 100; + int inner_width = 0; + int inner_height = 0; + bool use_content_size = options.ValueOrDefault(options::kUseContentSize, false); + options.Get(options::kinnerWidth, &inner_width); + options.Get(options::kinnerHeight, &inner_height); + if (inner_width || inner_height) { + use_content_size = true; + if (inner_width) + width = std::max(kMinSizeReqdBySpec, inner_width); + if (inner_height) + height = std::max(kMinSizeReqdBySpec, inner_height); + } + if (!has_frame() || use_content_size) SetContentSize(gfx::Size(width, height)); diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index df78d19d9dcfc..7f013202e6ed0 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -259,7 +259,7 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, const int width = options.ValueOrDefault(options::kWidth, 800); const int height = options.ValueOrDefault(options::kHeight, 600); - const gfx::Rect bounds{0, 0, width, height}; + gfx::Rect bounds{0, 0, width, height}; widget_size_ = bounds.size(); widget()->AddObserver(this); @@ -400,10 +400,25 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, // Default content view. SetContentView(new views::View()); + options.Get(options::kUseContentSize, &use_content_size_); + + // NOTE(@mlaurencin) Spec requirements can be found here: + // https://developer.mozilla.org/en-US/docs/Web/API/Window/open#width + int kMinSizeReqdBySpec = 100; + int inner_width = 0; + int inner_height = 0; + options.Get(options::kinnerWidth, &inner_width); + options.Get(options::kinnerHeight, &inner_height); + if (inner_width || inner_height) { + use_content_size_ = true; + if (inner_width) + bounds.set_width(std::max(kMinSizeReqdBySpec, inner_width)); + if (inner_height) + bounds.set_height(std::max(kMinSizeReqdBySpec, inner_height)); + } + gfx::Size size = bounds.size(); - if (has_frame() && - options.Get(options::kUseContentSize, &use_content_size_) && - use_content_size_) + if (has_frame() && use_content_size_) size = ContentBoundsToWindowBounds(gfx::Rect(size)).size(); widget()->CenterWindow(size); diff --git a/shell/common/options_switches.h b/shell/common/options_switches.h index 5bb2284acb4e6..7b86b734e5a21 100644 --- a/shell/common/options_switches.h +++ b/shell/common/options_switches.h @@ -26,6 +26,8 @@ inline constexpr std::string_view kMinWidth = "minWidth"; inline constexpr std::string_view kMinHeight = "minHeight"; inline constexpr std::string_view kMaxWidth = "maxWidth"; inline constexpr std::string_view kMaxHeight = "maxHeight"; +inline constexpr std::string_view kinnerWidth = "innerWidth"; +inline constexpr std::string_view kinnerHeight = "innerHeight"; inline constexpr std::string_view kResizable = "resizable"; inline constexpr std::string_view kMovable = "movable"; inline constexpr std::string_view kMinimizable = "minimizable"; diff --git a/spec/chromium-spec.ts b/spec/chromium-spec.ts index 7aee5f66f3d90..90cfe8c8b92eb 100644 --- a/spec/chromium-spec.ts +++ b/spec/chromium-spec.ts @@ -1459,6 +1459,41 @@ describe('chromium features', () => { expect(eventData).to.equal('size: 350 450'); }); + it('window opened with innerWidth option has the same innerWidth', async () => { + const w = new BrowserWindow({ show: false }); + w.loadFile(path.resolve(__dirname, 'fixtures', 'blank.html')); + const windowUrl = `file://${fixturesPath}/pages/window-open-size-inner.html`; + const windowCreatedPromise = once(app, 'browser-window-created') as Promise<[any, BrowserWindow]>; + const eventDataPromise = w.webContents.executeJavaScript(`(async () => { + const message = new Promise(resolve => window.addEventListener('message', resolve, { once: true })); + b = window.open(${JSON.stringify(windowUrl)}, '', 'show=no,innerWidth=400,height=450'); + const e = await message; + b.close(); + return e.data; + })()`); + const [[, newWindow], eventData] = await Promise.all([windowCreatedPromise, eventDataPromise]); + + expect(newWindow.getContentSize().toString()).to.equal('400,450'); + expect(eventData).to.equal('size: 400 450'); + }); + it('window opened with innerHeight option has the same innerHeight', async () => { + const w = new BrowserWindow({ show: false }); + w.loadFile(path.resolve(__dirname, 'fixtures', 'blank.html')); + const windowUrl = `file://${fixturesPath}/pages/window-open-size-inner.html`; + const windowCreatedPromise = once(app, 'browser-window-created') as Promise<[any, BrowserWindow]>; + const eventDataPromise = w.webContents.executeJavaScript(`(async () => { + const message = new Promise(resolve => window.addEventListener('message', resolve, {once: true})); + const b = window.open(${JSON.stringify(windowUrl)}, '', 'show=no,width=350,innerHeight=400') + const e = await message; + b.close(); + return e.data; + })()`); + const [[, newWindow], eventData] = await Promise.all([windowCreatedPromise, eventDataPromise]); + + expect(newWindow.getContentSize().toString()).to.equal('350,400'); + expect(eventData).to.equal('size: 350 400'); + }); + it('loads preload script after setting opener to null', async () => { const w = new BrowserWindow({ show: false }); w.webContents.setWindowOpenHandler(() => ({ diff --git a/spec/fixtures/pages/window-open-size-inner.html b/spec/fixtures/pages/window-open-size-inner.html new file mode 100644 index 0000000000000..f06ea6351aa0c --- /dev/null +++ b/spec/fixtures/pages/window-open-size-inner.html @@ -0,0 +1,7 @@ + + + + + From f1562543a30e8129f6934fc050124d9094af7ae7 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 14 May 2025 16:03:02 -0500 Subject: [PATCH 045/186] feat: add support for `--experimental-network-inspection` (#47031) * feat: add support for `--experimental-network-inspection` Co-authored-by: Aman Karmani * docs: fix minor formatting issues visible on both GH[1] and the docs site[2] [1] https://github.com/electron/electron/blob/main/docs/api/command-line-switches.md#nodejs-flags [2] https://www.electronjs.org/docs/latest/api/command-line-switches#--inspect-brkhostport Co-authored-by: Aman Karmani * docs: add entry for new nodejs flag Co-authored-by: Aman Karmani --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Aman Karmani --- docs/api/command-line-switches.md | 10 +++++++--- shell/common/node_bindings.cc | 1 + 2 files changed, 8 insertions(+), 3 deletions(-) diff --git a/docs/api/command-line-switches.md b/docs/api/command-line-switches.md index dd39f076777c4..8026d9351d375 100644 --- a/docs/api/command-line-switches.md +++ b/docs/api/command-line-switches.md @@ -256,7 +256,7 @@ Electron supports some of the [CLI flags][node-cli] supported by Node.js. > [!NOTE] > Passing unsupported command line switches to Electron when it is not running in `ELECTRON_RUN_AS_NODE` will have no effect. -### `--inspect-brk\[=\[host:]port]` +### `--inspect-brk[=[host:]port]` Activate inspector on host:port and break at start of user script. Default host:port is 127.0.0.1:9229. @@ -268,13 +268,13 @@ Activate inspector on `host:port` and break at start of the first internal JavaScript script executed when the inspector is available. Default `host:port` is `127.0.0.1:9229`. -### `--inspect-port=\[host:]port` +### `--inspect-port=[host:]port` Set the `host:port` to be used when the inspector is activated. Useful when activating the inspector by sending the SIGUSR1 signal. Default host is `127.0.0.1`. Aliased to `--debug-port=[host:]port`. -### `--inspect\[=\[host:]port]` +### `--inspect[=[host:]port]` Activate inspector on `host:port`. Default is `127.0.0.1:9229`. @@ -290,6 +290,10 @@ Specify ways of the inspector web socket url exposure. By default inspector websocket url is available in stderr and under /json/list endpoint on `http://host:port/json/list`. +### `--experimental-network-inspector` + +Enable support for devtools network inspector events, for visibility into requests made by the nodejs `http` and `https` modules. + ### `--no-deprecation` Silence deprecation warnings. diff --git a/shell/common/node_bindings.cc b/shell/common/node_bindings.cc index 3d837b31985ca..ef2c810a2afaf 100644 --- a/shell/common/node_bindings.cc +++ b/shell/common/node_bindings.cc @@ -349,6 +349,7 @@ bool IsAllowedOption(const std::string_view option) { "--inspect-brk-node", "--inspect-port", "--inspect-publish-uid", + "--experimental-network-inspection", }); // This should be aligned with what's possible to set via the process object. From a3d19d7a998553f2a31865405235d3285c88d5a0 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 15 May 2025 16:11:05 -0400 Subject: [PATCH 046/186] fix: opening package paths as directory on macOS (#47108) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: deepak1556 --- shell/browser/ui/file_dialog_mac.mm | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/shell/browser/ui/file_dialog_mac.mm b/shell/browser/ui/file_dialog_mac.mm index 01f2f1243c3fb..06adfb5f5f8f4 100644 --- a/shell/browser/ui/file_dialog_mac.mm +++ b/shell/browser/ui/file_dialog_mac.mm @@ -318,9 +318,10 @@ void ReadDialogPathsWithBookmarks(NSOpenPanel* dialog, BOOL exists = [[NSFileManager defaultManager] fileExistsAtPath:path isDirectory:&is_directory]; - BOOL is_package = - [[NSWorkspace sharedWorkspace] isFilePackageAtPath:path]; - if (!exists || !is_directory || is_package) + BOOL is_package_as_directory = + [[NSWorkspace sharedWorkspace] isFilePackageAtPath:path] && + [dialog treatsFilePackagesAsDirectories]; + if (!exists || !is_directory || !is_package_as_directory) continue; } From 7db96714200db4d81feb3b08b06d723d55f158be Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 15 May 2025 16:47:39 -0400 Subject: [PATCH 047/186] chore: bump chromium to 138.0.7178.0 (37-x-y) (#47106) * chore: bump chromium in DEPS to 138.0.7178.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6351556: [source-phase-imports] Support Wasm Source Phase Imports Refs https://chromium-review.googlesource.com/c/chromium/src/+/6351556 Co-authored-by: David Sanders * chore: update patches Co-authored-by: David Sanders * 6509682: extensions: Use ChromeExtensionsBrowserClient on desktop Android, part 2 Refs https://chromium-review.googlesource.com/c/chromium/src/+/6509682 Co-authored-by: David Sanders --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- DEPS | 2 +- ..._scheduler_throttling_per_renderview.patch | 2 +- patches/chromium/blink_local_frame.patch | 2 +- ..._depend_on_packed_resource_integrity.patch | 12 +++---- patches/chromium/build_gn.patch | 2 +- patches/chromium/can_create_window.patch | 18 +++++----- .../chromium/chore_partial_revert_of.patch | 4 +-- ...tition_attribute_dcheck_for_webviews.patch | 2 +- ...screationoverridden_with_full_params.patch | 14 ++++---- .../disable_compositor_recycling.patch | 2 +- patches/chromium/disable_hidden.patch | 8 ++--- ..._raw_response_headers_from_urlloader.patch | 2 +- ...ding_non-standard_schemes_in_iframes.patch | 4 +-- ..._background_throttling_in_compositor.patch | 8 ++--- ...board_hides_on_input_blur_in_webview.patch | 8 ++--- ...original_resize_performance_on_macos.patch | 2 +- ...from_localframe_requestexecutescript.patch | 2 +- patches/chromium/frame_host_manager.patch | 6 ++-- ..._avoid_private_macos_api_usage.patch.patch | 18 +++++----- patches/chromium/printing.patch | 4 +-- ...r_changes_to_the_webcontentsobserver.patch | 10 +++--- ...pose_hostimportmoduledynamically_and.patch | 36 +++++++++++-------- ...efactor_unfilter_unresponsive_events.patch | 4 +-- ...ean_up_stale_macwebcontentsocclusion.patch | 8 ++--- patches/chromium/web_contents.patch | 6 ++-- patches/chromium/webview_fullscreen.patch | 10 +++--- shell/browser/electron_browser_main_parts.cc | 1 + .../electron_extensions_browser_client.cc | 23 ++++++------ .../electron_extensions_browser_client.h | 1 + shell/common/node_bindings.cc | 31 ++++++++++++---- 30 files changed, 141 insertions(+), 111 deletions(-) diff --git a/DEPS b/DEPS index f2186d321a7e7..72033ea58cb23 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7177.0', + '138.0.7178.0', 'node_version': 'v22.15.0', 'nan_version': diff --git a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch index a1132eb60d996..ee0adbbb894c1 100644 --- a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch +++ b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch @@ -51,7 +51,7 @@ index 6eade0d29bc266a6a8928e768c923687bd12e656..53465bc76a22ae97ba4602d02a41f52e void SendRendererPreferencesToRenderer( const blink::RendererPreferences& preferences); diff --git a/content/browser/renderer_host/render_widget_host_view_aura.cc b/content/browser/renderer_host/render_widget_host_view_aura.cc -index d719b546b8c3c59003698b26dead065da7d76341..95a52f1cc2024e4a9cd694429d5304a5860a1c1e 100644 +index a13dd521b7263c66c94dac3d3caf6ebbed92d229..ce9295ee37ad58aab9f18f80daa72f91d5e0c27e 100644 --- a/content/browser/renderer_host/render_widget_host_view_aura.cc +++ b/content/browser/renderer_host/render_widget_host_view_aura.cc @@ -579,8 +579,8 @@ void RenderWidgetHostViewAura::ShowImpl(PageVisibilityState page_visibility) { diff --git a/patches/chromium/blink_local_frame.patch b/patches/chromium/blink_local_frame.patch index 28776ff32618f..9cf23742017fb 100644 --- a/patches/chromium/blink_local_frame.patch +++ b/patches/chromium/blink_local_frame.patch @@ -49,7 +49,7 @@ index c9f34fa47702504ccdefb8d61c55f5eaae501085..26df03d777c9ea487cae37f3df91d1df // its owning reference back to our owning LocalFrame. client_->Detached(type); diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index 9cb436569b94eec3e72ef3d1c018127b65a04314..e567f331968b1b1b9d6b85e31397b6a4f7ea7a84 100644 +index 6a80292d0c9d7130c762a0a84ca77f62c4c75168..574f947602f8cf9d5abebf6180dc3fb67dc85496 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc @@ -727,10 +727,6 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index ac1a82b506db2..d82d630d019c2 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -33,10 +33,10 @@ index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff6 "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index 3d58b24d9a835274ef1128b0a55bdf4c33a7f35c..11adb84bd02dfa2c54d9eba9562043575b53afc3 100644 +index 186cbeb02aa7b4e5b22800ece7cbc4791777356a..7137860ba1423a5ff36b85952790c5b25d6adf9d 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4653,7 +4653,7 @@ static_library("browser") { +@@ -4674,7 +4674,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,10 +46,10 @@ index 3d58b24d9a835274ef1128b0a55bdf4c33a7f35c..11adb84bd02dfa2c54d9eba956204357 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 028d1e517e434e8bb4152ebe8b5d4ee478d2abba..664d051317f1655f5ea03d8e3f1323e670973319 100644 +index 4a299a91dccd83f5e9595bdab2317c6ed9b26920..16f2e321030d61ee2cbab91c15fc93da3cf735b5 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7196,9 +7196,12 @@ test("unit_tests") { +@@ -7209,9 +7209,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index 028d1e517e434e8bb4152ebe8b5d4ee478d2abba..664d051317f1655f5ea03d8e3f1323e6 "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8167,6 +8170,10 @@ test("unit_tests") { +@@ -8180,6 +8183,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index 028d1e517e434e8bb4152ebe8b5d4ee478d2abba..664d051317f1655f5ea03d8e3f1323e6 sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8222,7 +8229,6 @@ test("unit_tests") { +@@ -8235,7 +8242,6 @@ test("unit_tests") { # Non-android deps for "unit_tests" target. deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/build_gn.patch b/patches/chromium/build_gn.patch index 1a70bd08dc783..2a059f803d50e 100644 --- a/patches/chromium/build_gn.patch +++ b/patches/chromium/build_gn.patch @@ -7,7 +7,7 @@ These are variables we add to the root BUILDCONFIG so that they're available everywhere, without having to import("//electron/.../flags.gni"). diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn -index 66a885e5bc6145f8358b8c76feb3ec27c95964bd..6c9316c40c9ab11c48876d00bf55191e33b133ff 100644 +index c3a3bf4970783804bc76ee4e71bb8233b5f215a8..78c72710b411e05ca0b6f01811076599fa66fc15 100644 --- a/build/config/BUILDCONFIG.gn +++ b/build/config/BUILDCONFIG.gn @@ -123,6 +123,9 @@ if (current_os == "") { diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 87fb968f23946..c808d727ab876 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,10 +9,10 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index c66512a270828be3b436c1e880917f0638771cfd..f4231fa2549083e8132affa6e424ac18f28b4f41 100644 +index db20a849f0e093a940587f94d777b7941882443d..e87536a31d03d8030b26781b9345fa7478d24afd 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -9703,6 +9703,7 @@ void RenderFrameHostImpl::CreateNewWindow( +@@ -9711,6 +9711,7 @@ void RenderFrameHostImpl::CreateNewWindow( last_committed_origin_, params->window_container_type, params->target_url, params->referrer.To(), params->frame_name, params->disposition, *params->features, @@ -21,10 +21,10 @@ index c66512a270828be3b436c1e880917f0638771cfd..f4231fa2549083e8132affa6e424ac18 &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 8a0128a57c6398c56e520522503ba54e03d176b3..43ca2bbe1611cbc2b533435319111dd9458de471 100644 +index af97a08179fd92e71daff17ca75cf4c6c06be1cc..65a3b57c38419c15b071e67852789b48533fe53a 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5163,6 +5163,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5155,6 +5155,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( // Sets the newly created WebContents WindowOpenDisposition. new_contents_impl->original_window_open_disposition_ = params.disposition; @@ -37,7 +37,7 @@ index 8a0128a57c6398c56e520522503ba54e03d176b3..43ca2bbe1611cbc2b533435319111dd9 // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5204,12 +5210,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5196,12 +5202,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -66,10 +66,10 @@ index 09f1899c9b044a05b2e40c291f17fdf1f9f2fcac..89643bf7059d4fc0d6de6116ffe0fdac // Operation result when the renderer asks the browser to create a new window. diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc -index 4aa669a0f869359e8d8304cab6cca0a89e1e3ff3..e8701e20e5d339edc1d9089d2b236f2cf8fe6c34 100644 +index e8a1b16cbe8aeb9c185de622250b73c402d56228..38a9b7ae1548f86ae700acc41565f340ed4dbff5 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc -@@ -828,6 +828,8 @@ bool ContentBrowserClient::CanCreateWindow( +@@ -842,6 +842,8 @@ bool ContentBrowserClient::CanCreateWindow( const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -79,7 +79,7 @@ index 4aa669a0f869359e8d8304cab6cca0a89e1e3ff3..e8701e20e5d339edc1d9089d2b236f2c bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 3e363b85b57478ca7228379ed089746a6eb52f2d..17b11b2a4e70f419721649568179c31228612c73 100644 +index 9061895e64ce94700692b0b990f22a32b5e0e353..bd3cccc408c61f4c4e408fd5d093d6aa1ef0e201 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -200,6 +200,7 @@ class NetworkService; @@ -90,7 +90,7 @@ index 3e363b85b57478ca7228379ed089746a6eb52f2d..17b11b2a4e70f419721649568179c312 } // namespace network namespace sandbox { -@@ -1386,6 +1387,8 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -1404,6 +1405,8 @@ class CONTENT_EXPORT ContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 1bdf6d3d21131..28fd072806d30 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 46d4c5e8c4f0d91d00ef51cc410ef54ebadb8eef..6d5ed56518116ce534fac98a994b7b7d9f1c6d11 100644 +index acb6b6257ccb13aae284d9b02baada14fe9ee0cc..9269ef00d1c0ce0606a39533b839e061ba448d7e 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5079,7 +5079,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5071,7 +5071,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch b/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch index 72a66aea141e7..a383798ee3330 100644 --- a/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch +++ b/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch @@ -14,7 +14,7 @@ This change patches it out to prevent the DCHECK. It can be removed once/if we see a better solution to the problem. diff --git a/content/browser/site_instance_impl.cc b/content/browser/site_instance_impl.cc -index 4007e92316a6ac59145fa9bc021904fd1b3b0136..afedeaea7fd419f3374ffeebb7ee931219a90f93 100644 +index 8db7e1a1ac6947a630cdf6993bf9cef772252cd9..4a4f5bb2fa0e26b921b2e40fade705e83c0bc573 100644 --- a/content/browser/site_instance_impl.cc +++ b/content/browser/site_instance_impl.cc @@ -226,7 +226,7 @@ scoped_refptr SiteInstanceImpl::CreateForGuest( diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index fced588e4e318..21d7bbf36b361 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -80,10 +80,10 @@ index b6582b4013d9682d32bd524b4053b443a4df00f8..afcbce72e0f247b4d5a637b27c9f25d9 content::WebContents* source, const content::OpenURLParams& params, diff --git a/chrome/browser/ui/browser.cc b/chrome/browser/ui/browser.cc -index 75c32a1af7011cb8a5bcf96f5c92f66ec86609c0..ac87e2f219fb79a69ab1afb68f29525b09ab8538 100644 +index 1bea3ad5b3c9960a7b1193e232b0c1f5c847e79d..0f416f0eeadca6bc7cc559d8879c694b7ccf62e6 100644 --- a/chrome/browser/ui/browser.cc +++ b/chrome/browser/ui/browser.cc -@@ -2413,8 +2413,7 @@ bool Browser::IsWebContentsCreationOverridden( +@@ -2406,8 +2406,7 @@ bool Browser::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -93,7 +93,7 @@ index 75c32a1af7011cb8a5bcf96f5c92f66ec86609c0..ac87e2f219fb79a69ab1afb68f29525b if (IsActorCoordinatorActingOnTab( profile(), content::WebContents::FromRenderFrameHost(opener))) { // If an ActorCoordinator is acting on the opener, prevent it from creating -@@ -2426,7 +2425,7 @@ bool Browser::IsWebContentsCreationOverridden( +@@ -2419,7 +2418,7 @@ bool Browser::IsWebContentsCreationOverridden( return (window_container_type == content::mojom::WindowContainerType::BACKGROUND && ShouldCreateBackgroundContents(source_site_instance, opener_url, @@ -103,10 +103,10 @@ index 75c32a1af7011cb8a5bcf96f5c92f66ec86609c0..ac87e2f219fb79a69ab1afb68f29525b WebContents* Browser::CreateCustomWebContents( diff --git a/chrome/browser/ui/browser.h b/chrome/browser/ui/browser.h -index 8cb8eb633a7b90ee8ad5d39b01d02d0785e97980..a90ff9bc0361a78ca12cae930d604e8834beddc8 100644 +index 5d3ab970d01b20bef2c715ab8bc65187814b0008..6efef3f3e9c7005fae59a404929d80bebe965f02 100644 --- a/chrome/browser/ui/browser.h +++ b/chrome/browser/ui/browser.h -@@ -1047,8 +1047,7 @@ class Browser : public TabStripModelObserver, +@@ -1041,8 +1041,7 @@ class Browser : public TabStripModelObserver, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -222,10 +222,10 @@ index b969f1d97b7e3396119b579cfbe61e19ff7d2dd4..b8d6169652da28266a514938b45b39c5 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 27dfdfaa258312b3e096cfe784e085376026d9ef..420879681bab99129e314b8717c4edf075037d35 100644 +index fcb7a38577a7b597be09b73cea9308b7112fee2a..3435a1d0ce5c8025b5a2005ebb4066e306579a69 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5042,8 +5042,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5034,8 +5034,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( if (delegate_ && delegate_->IsWebContentsCreationOverridden( opener, source_site_instance, params.window_container_type, diff --git a/patches/chromium/disable_compositor_recycling.patch b/patches/chromium/disable_compositor_recycling.patch index a07185e82f05f..5ab031791970b 100644 --- a/patches/chromium/disable_compositor_recycling.patch +++ b/patches/chromium/disable_compositor_recycling.patch @@ -6,7 +6,7 @@ Subject: fix: disabling compositor recycling Compositor recycling is useful for Chrome because there can be many tabs and spinning up a compositor for each one would be costly. In practice, Chrome uses the parent compositor code path of browser_compositor_view_mac.mm; the NSView of each tab is detached when it's hidden and attached when it's shown. For Electron, there is no parent compositor, so we're forced into the "own compositor" code path, which seems to be non-optimal and pretty ruthless in terms of the release of resources. Electron has no real concept of multiple tabs per window, so it should be okay to disable this ruthless recycling altogether in Electron. diff --git a/content/browser/renderer_host/render_widget_host_view_mac.mm b/content/browser/renderer_host/render_widget_host_view_mac.mm -index 88a6090a49da6071fded348a901c7c62b647b503..cf6f80bd3c9af0be5065e75e09a1b4150aeab0c8 100644 +index dc1dc1c15db217c4b8640b9c6ec6c051c0abb12b..52d8e830a68a6dfa3e3065548df3b69a5756ede2 100644 --- a/content/browser/renderer_host/render_widget_host_view_mac.mm +++ b/content/browser/renderer_host/render_widget_host_view_mac.mm @@ -560,7 +560,11 @@ diff --git a/patches/chromium/disable_hidden.patch b/patches/chromium/disable_hidden.patch index b5b5876ad1d2f..b5aff925031b1 100644 --- a/patches/chromium/disable_hidden.patch +++ b/patches/chromium/disable_hidden.patch @@ -6,7 +6,7 @@ Subject: disable_hidden.patch Electron uses this to disable background throttling for hidden windows. diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 00583269d16f4b8eacb4875b12a3e69155839d12..23d5baa267333e18551d449317f3e3a6520f34a6 100644 +index 43174a968fa1394d8c995adda338c15cace4e7be..a1cec61f882c38efa611401da69de123c99c9e7f 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc @@ -834,6 +834,10 @@ void RenderWidgetHostImpl::WasHidden() { @@ -21,10 +21,10 @@ index 00583269d16f4b8eacb4875b12a3e69155839d12..23d5baa267333e18551d449317f3e3a6 // Prompts should remain open and functional across tab switches. if (!delegate_ || !delegate_->IsWaitingForPointerLockPrompt(this)) { diff --git a/content/browser/renderer_host/render_widget_host_impl.h b/content/browser/renderer_host/render_widget_host_impl.h -index 70acc7b54d862e9aac9ec8a0867893e22512f77c..03ee050653c48a22d68881151cdf8f787161a32b 100644 +index 0bc94f2246a9357915423d1954cb240fad602a22..4663f18c832c12e8704fbb99a5aea824cd44aa5b 100644 --- a/content/browser/renderer_host/render_widget_host_impl.h +++ b/content/browser/renderer_host/render_widget_host_impl.h -@@ -1016,6 +1016,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl +@@ -1017,6 +1017,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl // Requests a commit and forced redraw in the renderer compositor. void ForceRedrawForTesting(); @@ -35,7 +35,7 @@ index 70acc7b54d862e9aac9ec8a0867893e22512f77c..03ee050653c48a22d68881151cdf8f78 // |routing_id| must not be MSG_ROUTING_NONE. // If this object outlives |delegate|, DetachDelegate() must be called when diff --git a/content/browser/renderer_host/render_widget_host_view_aura.cc b/content/browser/renderer_host/render_widget_host_view_aura.cc -index 5867fc3e77326991f30d835d08d3cfafe2b6687c..d719b546b8c3c59003698b26dead065da7d76341 100644 +index e6235611a2ae643f4c968fcc0dcd5b47baa0a081..a13dd521b7263c66c94dac3d3caf6ebbed92d229 100644 --- a/content/browser/renderer_host/render_widget_host_view_aura.cc +++ b/content/browser/renderer_host/render_widget_host_view_aura.cc @@ -643,7 +643,7 @@ void RenderWidgetHostViewAura::HideImpl() { diff --git a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch index e1711b0bf9d9a..9394103e1aeb9 100644 --- a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch +++ b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch @@ -112,7 +112,7 @@ index 99bf736ebe303d46ab1ced924ba929a0cd258909..e10c8782d2704ff9cff8062d201a4339 string mime_type; diff --git a/services/network/url_loader.cc b/services/network/url_loader.cc -index 565d77c76805898c7dccc472daf2853cdafd9fbb..fd62b19ef22e162f3f4ea6ac510996bccec8fe2f 100644 +index 77569bb055bf2dde5370b05c814ff793f1cf4b19..bc361afc2b2fb5045f43fc49471cfc7f51b4cd74 100644 --- a/services/network/url_loader.cc +++ b/services/network/url_loader.cc @@ -388,6 +388,9 @@ URLLoader::URLLoader( diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index d42b8451d3f2e..134d0ea09aa42 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -28,10 +28,10 @@ The patch should be removed in favor of either: Upstream bug https://bugs.chromium.org/p/chromium/issues/detail?id=1081397. diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc -index e5776378633dba0b60a79a9044991ceaafe86e72..2beccf1bb05e8695e3e2191683e0a9bc1184544a 100644 +index e35fc05100fd582669a021574fcd0a01e72d2302..fec6fb5ff81b362fc299b36b447c1141911ccb56 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc -@@ -11076,6 +11076,11 @@ url::Origin NavigationRequest::GetOriginForURLLoaderFactoryUnchecked() { +@@ -11080,6 +11080,11 @@ url::Origin NavigationRequest::GetOriginForURLLoaderFactoryUnchecked() { target_rph_id); } diff --git a/patches/chromium/fix_disabling_background_throttling_in_compositor.patch b/patches/chromium/fix_disabling_background_throttling_in_compositor.patch index a422ad8a19268..9687ea68c7cf1 100644 --- a/patches/chromium/fix_disabling_background_throttling_in_compositor.patch +++ b/patches/chromium/fix_disabling_background_throttling_in_compositor.patch @@ -12,10 +12,10 @@ invisible state of the `viz::DisplayScheduler` owned by the `ui::Compositor`. diff --git a/ui/compositor/compositor.cc b/ui/compositor/compositor.cc -index 70cf60c1e6afd16995cf3446d5ed9a87ce29e998..f886b4e9446c23f6b83d6d89165d09c6ab7f5d97 100644 +index d770a26ca3e49c0aced95dc362802187d7d81269..788afc7ff05bf622d9e495988034ab9ca2207bfb 100644 --- a/ui/compositor/compositor.cc +++ b/ui/compositor/compositor.cc -@@ -362,7 +362,8 @@ void Compositor::SetLayerTreeFrameSink( +@@ -359,7 +359,8 @@ void Compositor::SetLayerTreeFrameSink( if (display_private_) { disabled_swap_until_resize_ = false; display_private_->Resize(size()); @@ -25,7 +25,7 @@ index 70cf60c1e6afd16995cf3446d5ed9a87ce29e998..f886b4e9446c23f6b83d6d89165d09c6 display_private_->SetDisplayColorSpaces(display_color_spaces_); display_private_->SetDisplayColorMatrix( gfx::SkM44ToTransform(display_color_matrix_)); -@@ -613,7 +614,9 @@ void Compositor::SetVisible(bool visible) { +@@ -610,7 +611,9 @@ void Compositor::SetVisible(bool visible) { // updated then. We need to call this even if the visibility hasn't changed, // for the same reason. if (display_private_) @@ -36,7 +36,7 @@ index 70cf60c1e6afd16995cf3446d5ed9a87ce29e998..f886b4e9446c23f6b83d6d89165d09c6 if (changed) { observer_list_.Notify(&CompositorObserver::OnCompositorVisibilityChanged, -@@ -1077,6 +1080,15 @@ void Compositor::MaybeUpdateObserveBeginFrame() { +@@ -1074,6 +1077,15 @@ void Compositor::MaybeUpdateObserveBeginFrame() { host_begin_frame_observer_->GetBoundRemote()); } diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 0c4030c0ad38a..3a0c0cd608ae0 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -9,7 +9,7 @@ focus node change via TextInputManager. chromium-bug: https://crbug.com/1369605 diff --git a/content/browser/renderer_host/render_widget_host_view_aura.cc b/content/browser/renderer_host/render_widget_host_view_aura.cc -index 95a52f1cc2024e4a9cd694429d5304a5860a1c1e..3e096f196b9514fec5738f29e7c63bcbb9b2f640 100644 +index ce9295ee37ad58aab9f18f80daa72f91d5e0c27e..6315906ba311111ac4bed3fdff545c84c8b4b409 100644 --- a/content/browser/renderer_host/render_widget_host_view_aura.cc +++ b/content/browser/renderer_host/render_widget_host_view_aura.cc @@ -3241,6 +3241,12 @@ void RenderWidgetHostViewAura::OnTextSelectionChanged( @@ -26,7 +26,7 @@ index 95a52f1cc2024e4a9cd694429d5304a5860a1c1e..3e096f196b9514fec5738f29e7c63bcb RenderWidgetHostViewAura* popup_child_host_view) { popup_child_host_view_ = popup_child_host_view; diff --git a/content/browser/renderer_host/render_widget_host_view_aura.h b/content/browser/renderer_host/render_widget_host_view_aura.h -index 6f96b83c36ee026bd37b54de55da72cc802ed699..c54ed7d8f5d4d371626865c6ae63ef2efbef1dba 100644 +index 33d9c06d52f0ec72caad1866ef97c5fdced1b55b..f9ccdd9ef95db2ecc0976c6ed58ff8ba9a9fb2d2 100644 --- a/content/browser/renderer_host/render_widget_host_view_aura.h +++ b/content/browser/renderer_host/render_widget_host_view_aura.h @@ -654,6 +654,8 @@ class CONTENT_EXPORT RenderWidgetHostViewAura @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 0169ccad6ae4430d5c5a05a46ad21c2421ae3631..46d4c5e8c4f0d91d00ef51cc410ef54ebadb8eef 100644 +index fc4af3a293fd807780f39b0cddc7605031620879..acb6b6257ccb13aae284d9b02baada14fe9ee0cc 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10017,7 +10017,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -10009,7 +10009,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch index cf566bffed5c1..6cc351a49ae9c 100644 --- a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch +++ b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch @@ -11,7 +11,7 @@ This patch should be upstreamed as a conditional revert of the logic in desktop vs mobile runtimes. i.e. restore the old logic only on desktop platforms diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 2551b4a2b9dfca9767c39e2e9bd79ed19c439db4..81844d36b86d5590b59d3b87f3f2d5bef3a7b24d 100644 +index 583b7cf8c0e484d53a0b93b86e65f28ba5359906..31cedc79b9763bee5cc69066f5d4afa6f4ec7e39 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc @@ -2135,9 +2135,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { diff --git a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch index cf1b13ccd35dc..832e684a9a2c5 100644 --- a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch +++ b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch @@ -59,7 +59,7 @@ index cba373664bec3a32abad6fe0396bd67b53b7e67f..a54f1b3351efd2d8f324436f7f35cd43 #endif // THIRD_PARTY_BLINK_PUBLIC_WEB_WEB_SCRIPT_EXECUTION_CALLBACK_H_ diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index e567f331968b1b1b9d6b85e31397b6a4f7ea7a84..9650e99108cefb8b2963913fb39049f69496a65e 100644 +index 574f947602f8cf9d5abebf6180dc3fb67dc85496..235742d9ac2787c290c123403160d095609e8c16 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc @@ -3085,6 +3085,7 @@ void LocalFrame::RequestExecuteScript( diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index 755f58a3ab2ac..f775fad1e681e 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -6,10 +6,10 @@ Subject: frame_host_manager.patch Allows embedder to intercept site instances created by chromium. diff --git a/content/browser/renderer_host/render_frame_host_manager.cc b/content/browser/renderer_host/render_frame_host_manager.cc -index a8eea524f693c4f15c08e1c2f48b13c97d28ce75..47e0b121ced6ea129ccffe6364c5a91f826036eb 100644 +index 39eae72b5f9f05fc9dda3b6b3a51b4d1d2bf7fcf..cd95bbd34218cb3181b887832a84893cd90c67a5 100644 --- a/content/browser/renderer_host/render_frame_host_manager.cc +++ b/content/browser/renderer_host/render_frame_host_manager.cc -@@ -4714,6 +4714,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( +@@ -4752,6 +4752,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( request->ResetStateForSiteInstanceChange(); } @@ -20,7 +20,7 @@ index a8eea524f693c4f15c08e1c2f48b13c97d28ce75..47e0b121ced6ea129ccffe6364c5a91f } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 17b11b2a4e70f419721649568179c31228612c73..e094c512f71eef3714ed0dd6090fd6c5efab3063 100644 +index bd3cccc408c61f4c4e408fd5d093d6aa1ef0e201..4f65dbc23f3039a0144745cd3cdefeff657b6b3e 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -342,6 +342,11 @@ class CONTENT_EXPORT ContentBrowserClient { diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index c255aae9708ac..4210fad044947 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,7 +35,7 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index 7860ff639da1116f007fda4ecf3010d065203f8c..c61bc8d60d69d348da992c980c6222c7c21623af 100644 +index 01c19144731d186d857dda72c3ac002a9ae2e911..14faff7dd8f32437f849011df222a37744f379d5 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn @@ -1046,6 +1046,7 @@ component("base") { @@ -582,7 +582,7 @@ index d83f420d25e2c108ad400ebecae02b1ac327c058..77852c5c315ac09dddb7227adf3b840e return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 4c02b0aef40b31a0dd55859c718842e25652fe74..0ad5b87248ac7c15774a870d5a4268c60a2c36c0 100644 +index 1006244a7ed861fdd58bfb3af926a69af2061322..4074a0429ce78963d4406f957c96382333d760ed 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn @@ -342,6 +342,7 @@ source_set("browser") { @@ -594,7 +594,7 @@ index 4c02b0aef40b31a0dd55859c718842e25652fe74..0ad5b87248ac7c15774a870d5a4268c6 public_deps = [ diff --git a/content/browser/renderer_host/render_widget_host_view_mac.h b/content/browser/renderer_host/render_widget_host_view_mac.h -index 1b923f0e0dc6d7dc9e67d278b8da00b35745241e..6f7ee79df9b9e3026663e2a4637007de5b5da902 100644 +index c8f64d6c7a7a790659a05fd626e582608c46a8a7..21f26e2c619c632d6ccb331ddd7a6870340f644e 100644 --- a/content/browser/renderer_host/render_widget_host_view_mac.h +++ b/content/browser/renderer_host/render_widget_host_view_mac.h @@ -24,6 +24,7 @@ @@ -628,7 +628,7 @@ index 1b923f0e0dc6d7dc9e67d278b8da00b35745241e..6f7ee79df9b9e3026663e2a4637007de // Used to force the NSApplication's focused accessibility element to be the // content::BrowserAccessibilityCocoa accessibility tree when the NSView for diff --git a/content/browser/renderer_host/render_widget_host_view_mac.mm b/content/browser/renderer_host/render_widget_host_view_mac.mm -index 27f481c6a31cdd59684eb38ea8b2ffdcb5849ddf..88a6090a49da6071fded348a901c7c62b647b503 100644 +index 8b32428734dbc038b52f2d2b7e738cc508216820..dc1dc1c15db217c4b8640b9c6ec6c051c0abb12b 100644 --- a/content/browser/renderer_host/render_widget_host_view_mac.mm +++ b/content/browser/renderer_host/render_widget_host_view_mac.mm @@ -50,6 +50,7 @@ @@ -797,7 +797,7 @@ index a1068589ad844518038ee7bc15a3de9bc5cba525..1ff781c49f086ec8015c7d3c44567dbe } // namespace content diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn -index 4df384721ee529863d35ae7afe8249e3989697b0..2369ebc00ff008a94409d68404d3017f85592f74 100644 +index 5544ddc8faae9cc4a75c812227a94df4ad4f5e53..d6fa2a588fec9895101dc4c308eb84b015a908aa 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn @@ -664,6 +664,7 @@ static_library("test_support") { @@ -816,7 +816,7 @@ index 4df384721ee529863d35ae7afe8249e3989697b0..2369ebc00ff008a94409d68404d3017f } mojom("content_test_mojo_bindings") { -@@ -1962,6 +1964,7 @@ test("content_browsertests") { +@@ -1963,6 +1965,7 @@ test("content_browsertests") { "//ui/shell_dialogs", "//ui/snapshot", "//ui/webui:test_support", @@ -824,7 +824,7 @@ index 4df384721ee529863d35ae7afe8249e3989697b0..2369ebc00ff008a94409d68404d3017f ] if (!(is_chromeos && target_cpu == "arm64" && current_cpu == "arm")) { -@@ -3292,6 +3295,7 @@ test("content_unittests") { +@@ -3293,6 +3296,7 @@ test("content_unittests") { "//ui/shell_dialogs:shell_dialogs", "//ui/webui:test_support", "//url", @@ -1584,10 +1584,10 @@ index dcf493d62990018040a3f84b6f875af737bd2214..3d1c4dcc9ee0bbfdac15f40d9c74e9f3 void DisplayCALayerTree::GotIOSurfaceFrame( diff --git a/ui/accessibility/platform/BUILD.gn b/ui/accessibility/platform/BUILD.gn -index 30440d1b5ba071c8cf2076e7e7acb24681f78a2f..ca18e61ff2eb743fabeb10af06c208f84b526dd8 100644 +index 349a50ce687d5594296ce3c302938424be2e739b..0c5313b8f31a97747ae28f2c188e0fb591e5cc36 100644 --- a/ui/accessibility/platform/BUILD.gn +++ b/ui/accessibility/platform/BUILD.gn -@@ -295,6 +295,7 @@ component("platform") { +@@ -296,6 +296,7 @@ component("platform") { "AppKit.framework", "Foundation.framework", ] diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index 0af0d420aace5..bc230aa4e5d52 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -881,10 +881,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 0ad5b87248ac7c15774a870d5a4268c60a2c36c0..2d18faace5c0021e0bf04b8e089a8db1593d1fc1 100644 +index 4074a0429ce78963d4406f957c96382333d760ed..c8f1114cb5cd892c80500da5ec4828cf5ad77dc9 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3163,8 +3163,9 @@ source_set("browser") { +@@ -3161,8 +3161,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 69d36ad07572b..451366d54d284 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -30,7 +30,7 @@ index a54a0dedf8ef1cfffa4e80a4707debed0e83d277..e66e71fdbabb40a5307b12cd8965e773 // RenderWidgetHost on the primary main frame, and false otherwise. virtual bool IsWidgetForPrimaryMainFrame(RenderWidgetHostImpl*); diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 23d5baa267333e18551d449317f3e3a6520f34a6..2551b4a2b9dfca9767c39e2e9bd79ed19c439db4 100644 +index a1cec61f882c38efa611401da69de123c99c9e7f..583b7cf8c0e484d53a0b93b86e65f28ba5359906 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc @@ -2069,6 +2069,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { @@ -44,10 +44,10 @@ index 23d5baa267333e18551d449317f3e3a6520f34a6..2551b4a2b9dfca9767c39e2e9bd79ed1 void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 43ca2bbe1611cbc2b533435319111dd9458de471..27dfdfaa258312b3e096cfe784e085376026d9ef 100644 +index 65a3b57c38419c15b071e67852789b48533fe53a..fcb7a38577a7b597be09b73cea9308b7112fee2a 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5915,6 +5915,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -5907,6 +5907,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,10 +60,10 @@ index 43ca2bbe1611cbc2b533435319111dd9458de471..27dfdfaa258312b3e096cfe784e08537 RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index 05a401f48ba5a784c547c3fe1f4fb5252af3014d..3e556e807577123599f957d5f9d24b084014e150 100644 +index de9650b781ccb250fd5f59aaea8dc6e09d7816ef..09ae0904e236336058bbf1fe9c4d211ddbe146a4 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h -@@ -1188,6 +1188,7 @@ class CONTENT_EXPORT WebContentsImpl +@@ -1186,6 +1186,7 @@ class CONTENT_EXPORT WebContentsImpl void SendScreenRects() override; void SendActiveState(bool active) override; TextInputManager* GetTextInputManager() override; diff --git a/patches/chromium/refactor_expose_hostimportmoduledynamically_and.patch b/patches/chromium/refactor_expose_hostimportmoduledynamically_and.patch index d46ddbe7abc96..116f5b894a0cc 100644 --- a/patches/chromium/refactor_expose_hostimportmoduledynamically_and.patch +++ b/patches/chromium/refactor_expose_hostimportmoduledynamically_and.patch @@ -7,21 +7,28 @@ Subject: refactor: expose HostImportModuleDynamically and This is so that Electron can blend Blink's and Node's implementations of these isolate handlers. diff --git a/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc b/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc -index 9ab0efff477274bb08a99a64c2b78226aae1939e..8fbc3cd5328a74b2d65d534d60b0042bf986e2ad 100644 +index a7cfbeed265f3fa5caa8f0dd8002a42cd6f88d7d..5ce930e4a11dee51d291f22b09daf4f805da0d39 100644 --- a/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc +++ b/third_party/blink/renderer/bindings/core/v8/v8_initializer.cc @@ -638,7 +638,9 @@ bool WasmJSPromiseIntegrationEnabledCallback(v8::Local context) { execution_context); } --v8::MaybeLocal HostImportModuleDynamically( -+} +-v8::MaybeLocal HostImportModuleWithPhaseDynamically( ++} // namespace + -+v8::MaybeLocal V8Initializer::HostImportModuleDynamically( ++v8::MaybeLocal V8Initializer::HostImportModuleWithPhaseDynamically( v8::Local context, v8::Local v8_host_defined_options, v8::Local v8_referrer_resource_url, -@@ -716,7 +718,7 @@ v8::MaybeLocal HostImportModuleDynamically( +@@ -723,13 +725,13 @@ v8::MaybeLocal HostImportModuleDynamically( + v8::Local v8_referrer_resource_url, + v8::Local v8_specifier, + v8::Local v8_import_attributes) { +- return HostImportModuleWithPhaseDynamically( ++ return V8Initializer::HostImportModuleWithPhaseDynamically( + context, v8_host_defined_options, v8_referrer_resource_url, v8_specifier, + v8::ModuleImportPhase::kEvaluation, v8_import_attributes); } // https://html.spec.whatwg.org/C/#hostgetimportmetaproperties @@ -30,7 +37,7 @@ index 9ab0efff477274bb08a99a64c2b78226aae1939e..8fbc3cd5328a74b2d65d534d60b0042b v8::Local module, v8::Local meta) { v8::Isolate* isolate = context->GetIsolate(); -@@ -763,9 +765,6 @@ std::ostream& operator<<(std::ostream& os, const PrintV8OOM& oom_details) { +@@ -776,9 +778,6 @@ std::ostream& operator<<(std::ostream& os, const PrintV8OOM& oom_details) { return os; } @@ -40,12 +47,12 @@ index 9ab0efff477274bb08a99a64c2b78226aae1939e..8fbc3cd5328a74b2d65d534d60b0042b void V8Initializer::InitializeV8Common(v8::Isolate* isolate) { // Set up garbage collection before setting up anything else as V8 may trigger // GCs during Blink setup. -@@ -785,9 +784,9 @@ void V8Initializer::InitializeV8Common(v8::Isolate* isolate) { - isolate->SetWasmJSPIEnabledCallback(WasmJSPromiseIntegrationEnabledCallback); - isolate->SetSharedArrayBufferConstructorEnabledCallback( +@@ -800,9 +799,9 @@ void V8Initializer::InitializeV8Common(v8::Isolate* isolate) { SharedArrayBufferConstructorEnabledCallback); -- isolate->SetHostImportModuleDynamicallyCallback(HostImportModuleDynamically); -+ isolate->SetHostImportModuleDynamicallyCallback(V8Initializer::HostImportModuleDynamically); + isolate->SetHostImportModuleDynamicallyCallback(HostImportModuleDynamically); + isolate->SetHostImportModuleWithPhaseDynamicallyCallback( +- HostImportModuleWithPhaseDynamically); ++ V8Initializer::HostImportModuleWithPhaseDynamically); isolate->SetHostInitializeImportMetaObjectCallback( - HostGetImportMetaProperties); + V8Initializer::HostGetImportMetaProperties); @@ -53,18 +60,19 @@ index 9ab0efff477274bb08a99a64c2b78226aae1939e..8fbc3cd5328a74b2d65d534d60b0042b isolate->SetMetricsRecorder(std::make_shared(isolate)); diff --git a/third_party/blink/renderer/bindings/core/v8/v8_initializer.h b/third_party/blink/renderer/bindings/core/v8/v8_initializer.h -index be5df8f98c3f7e308d79d43c1811a16c644b6158..5c25a3bb7f04ea74ee8587b158e125f4aa651912 100644 +index be5df8f98c3f7e308d79d43c1811a16c644b6158..599121e3dabecf1a8192ba410ff447dcb540376c 100644 --- a/third_party/blink/renderer/bindings/core/v8/v8_initializer.h +++ b/third_party/blink/renderer/bindings/core/v8/v8_initializer.h -@@ -85,6 +85,17 @@ class CORE_EXPORT V8Initializer { +@@ -85,6 +85,18 @@ class CORE_EXPORT V8Initializer { static void PromiseRejectHandlerInMainThread(v8::PromiseRejectMessage data); static void ExceptionPropagationCallback(v8::ExceptionPropagationMessage); -+ static v8::MaybeLocal HostImportModuleDynamically( ++ static v8::MaybeLocal HostImportModuleWithPhaseDynamically( + v8::Local context, + v8::Local v8_host_defined_options, + v8::Local v8_referrer_resource_url, + v8::Local v8_specifier, ++ v8::ModuleImportPhase import_phase, + v8::Local v8_import_assertions); + + static void HostGetImportMetaProperties(v8::Local context, diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index 49da2e0eb56d8..676ea456832bd 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 6d5ed56518116ce534fac98a994b7b7d9f1c6d11..91b66c472ba0398efad3a0a3cfe0d39eee529eaa 100644 +index 9269ef00d1c0ce0606a39533b839e061ba448d7e..7c4851fb5f9e28ab77837755993d375e91a0dcac 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10154,25 +10154,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10146,25 +10146,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch index 202cdf5061450..b7b7f6aae4eb9 100644 --- a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch +++ b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch @@ -233,10 +233,10 @@ index 7c99a9512e6f65713fe8483cef7b7c9b494b4491..8fb6cf252961c9773d1a6a09d47bec6a } diff --git a/content/common/features.cc b/content/common/features.cc -index 201f17f35a4657f43c70b7b44871a7dfea681635..2ec678b805c8c8eda47c3dbf88f567a061cc63dc 100644 +index 8dcb54b4c48cde0d11e682cc23dacbec9c4814df..c55f4d02691ec3b2255c47e89491fa76d8b996ea 100644 --- a/content/common/features.cc +++ b/content/common/features.cc -@@ -301,6 +301,14 @@ BASE_FEATURE(kIOSurfaceCapturer, +@@ -308,6 +308,14 @@ BASE_FEATURE(kIOSurfaceCapturer, base::FEATURE_ENABLED_BY_DEFAULT); #endif @@ -252,10 +252,10 @@ index 201f17f35a4657f43c70b7b44871a7dfea681635..2ec678b805c8c8eda47c3dbf88f567a0 // invalidated upon notifications sent by base::SystemMonitor. If disabled, the // cache is considered invalid on every enumeration request. diff --git a/content/common/features.h b/content/common/features.h -index 4dc19d79152a1f4cf29e8c484d0acdf7d42ed61e..dbe555a29e96f83d7b8122b3d05578ac83863888 100644 +index 6ffc0e6c10c190b410c9f7269a6146447a38c800..bba9eb2e3291539a4565b306f4c2c687b7d27541 100644 --- a/content/common/features.h +++ b/content/common/features.h -@@ -100,6 +100,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); +@@ -101,6 +101,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); #if BUILDFLAG(IS_MAC) CONTENT_EXPORT BASE_DECLARE_FEATURE(kIOSurfaceCapturer); #endif diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index 465a33eadf63f..3d2707a42d38d 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 420879681bab99129e314b8717c4edf075037d35..602e2f8049a673d4ccfaaf6891fa1b5a8140781f 100644 +index 3435a1d0ce5c8025b5a2005ebb4066e306579a69..3d37f389e0d9685119a5776832e0e005f8bcc6ca 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -3966,6 +3966,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3941,6 +3941,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index 420879681bab99129e314b8717c4edf075037d35..602e2f8049a673d4ccfaaf6891fa1b5a std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -3976,6 +3983,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -3951,6 +3958,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index c369d3f9109c7..8014e7b2a7672 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,10 +15,10 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index f4231fa2549083e8132affa6e424ac18f28b4f41..32d4d22f4d0106c8f598e8e44545788c32665947 100644 +index e87536a31d03d8030b26781b9345fa7478d24afd..6182d198b65fd26e594ff04bbf4dc483299d19ed 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -8809,6 +8809,17 @@ void RenderFrameHostImpl::EnterFullscreen( +@@ -8817,6 +8817,17 @@ void RenderFrameHostImpl::EnterFullscreen( } } @@ -37,10 +37,10 @@ index f4231fa2549083e8132affa6e424ac18f28b4f41..32d4d22f4d0106c8f598e8e44545788c if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 602e2f8049a673d4ccfaaf6891fa1b5a8140781f..0169ccad6ae4430d5c5a05a46ad21c2421ae3631 100644 +index 3d37f389e0d9685119a5776832e0e005f8bcc6ca..fc4af3a293fd807780f39b0cddc7605031620879 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4255,21 +4255,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4231,21 +4231,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index 602e2f8049a673d4ccfaaf6891fa1b5a8140781f..0169ccad6ae4430d5c5a05a46ad21c24 } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4428,7 +4432,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4404,7 +4408,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/shell/browser/electron_browser_main_parts.cc b/shell/browser/electron_browser_main_parts.cc index e2e43c6e5b9cf..82407eb8e9e2d 100644 --- a/shell/browser/electron_browser_main_parts.cc +++ b/shell/browser/electron_browser_main_parts.cc @@ -438,6 +438,7 @@ int ElectronBrowserMainParts::PreMainMessageLoopRun() { // BrowserContextKeyedAPIServiceFactories require an ExtensionsBrowserClient. extensions_browser_client_ = std::make_unique(); + extensions_browser_client_->Init(); extensions::ExtensionsBrowserClient::Set(extensions_browser_client_.get()); extensions::EnsureBrowserContextKeyedServiceFactoriesBuilt(); diff --git a/shell/browser/extensions/electron_extensions_browser_client.cc b/shell/browser/extensions/electron_extensions_browser_client.cc index 1ada759c73d9a..ef37083766ff5 100644 --- a/shell/browser/extensions/electron_extensions_browser_client.cc +++ b/shell/browser/extensions/electron_extensions_browser_client.cc @@ -55,24 +55,27 @@ using extensions::ExtensionsBrowserClient; namespace electron { ElectronExtensionsBrowserClient::ElectronExtensionsBrowserClient() - : api_client_(std::make_unique()), - process_manager_delegate_( - std::make_unique()), - extension_cache_(std::make_unique()) { - // Electron does not have a concept of channel, so leave UNKNOWN to - // enable all channel-dependent extension APIs. - extensions::SetCurrentChannel(version_info::Channel::UNKNOWN); - resource_manager_ = - std::make_unique(); - + : extension_cache_(std::make_unique()) { AddAPIProvider( std::make_unique()); AddAPIProvider( std::make_unique()); + + // Electron does not have a concept of channel, so leave UNKNOWN to + // enable all channel-dependent extension APIs. + extensions::SetCurrentChannel(version_info::Channel::UNKNOWN); } ElectronExtensionsBrowserClient::~ElectronExtensionsBrowserClient() = default; +void ElectronExtensionsBrowserClient::Init() { + process_manager_delegate_ = + std::make_unique(); + api_client_ = std::make_unique(); + resource_manager_ = + std::make_unique(); +} + bool ElectronExtensionsBrowserClient::IsShuttingDown() { return electron::Browser::Get()->is_shutting_down(); } diff --git a/shell/browser/extensions/electron_extensions_browser_client.h b/shell/browser/extensions/electron_extensions_browser_client.h index ff821219edbdc..78a27007977f6 100644 --- a/shell/browser/extensions/electron_extensions_browser_client.h +++ b/shell/browser/extensions/electron_extensions_browser_client.h @@ -51,6 +51,7 @@ class ElectronExtensionsBrowserClient const ElectronExtensionsBrowserClient&) = delete; // ExtensionsBrowserClient overrides: + void Init() override; bool IsShuttingDown() override; bool AreExtensionsDisabled(const base::CommandLine& command_line, content::BrowserContext* context) override; diff --git a/shell/common/node_bindings.cc b/shell/common/node_bindings.cc index ef2c810a2afaf..029a3b9bf1d45 100644 --- a/shell/common/node_bindings.cc +++ b/shell/common/node_bindings.cc @@ -212,18 +212,19 @@ bool AllowWasmCodeGenerationCallback(v8::Local context, return node::AllowWasmCodeGenerationCallback(context, source); } -v8::MaybeLocal HostImportModuleDynamically( +v8::MaybeLocal HostImportModuleWithPhaseDynamically( v8::Local context, v8::Local v8_host_defined_options, v8::Local v8_referrer_resource_url, v8::Local v8_specifier, - v8::Local v8_import_assertions) { + v8::ModuleImportPhase import_phase, + v8::Local v8_import_attributes) { if (node::Environment::GetCurrent(context) == nullptr) { if (electron::IsBrowserProcess() || electron::IsUtilityProcess()) return {}; - return blink::V8Initializer::HostImportModuleDynamically( + return blink::V8Initializer::HostImportModuleWithPhaseDynamically( context, v8_host_defined_options, v8_referrer_resource_url, - v8_specifier, v8_import_assertions); + v8_specifier, import_phase, v8_import_attributes); } // If we're running with contextIsolation enabled in the renderer process, @@ -233,15 +234,29 @@ v8::MaybeLocal HostImportModuleDynamically( blink::WebLocalFrame::FrameForContext(context); if (!frame || frame->GetScriptContextWorldId(context) != electron::WorldIDs::ISOLATED_WORLD_ID) { - return blink::V8Initializer::HostImportModuleDynamically( + return blink::V8Initializer::HostImportModuleWithPhaseDynamically( context, v8_host_defined_options, v8_referrer_resource_url, - v8_specifier, v8_import_assertions); + v8_specifier, import_phase, v8_import_attributes); } } + // TODO: Switch to node::loader::ImportModuleDynamicallyWithPhase + // once we land the Node.js version that has it in upstream. + CHECK(import_phase == v8::ModuleImportPhase::kEvaluation); return node::loader::ImportModuleDynamically( context, v8_host_defined_options, v8_referrer_resource_url, v8_specifier, - v8_import_assertions); + v8_import_attributes); +} + +v8::MaybeLocal HostImportModuleDynamically( + v8::Local context, + v8::Local v8_host_defined_options, + v8::Local v8_referrer_resource_url, + v8::Local v8_specifier, + v8::Local v8_import_attributes) { + return HostImportModuleWithPhaseDynamically( + context, v8_host_defined_options, v8_referrer_resource_url, v8_specifier, + v8::ModuleImportPhase::kEvaluation, v8_import_attributes); } void HostInitializeImportMetaObject(v8::Local context, @@ -780,6 +795,8 @@ std::shared_ptr NodeBindings::CreateEnvironment( node::SetIsolateUpForNode(context->GetIsolate(), is); context->GetIsolate()->SetHostImportModuleDynamicallyCallback( HostImportModuleDynamically); + context->GetIsolate()->SetHostImportModuleWithPhaseDynamicallyCallback( + HostImportModuleWithPhaseDynamically); context->GetIsolate()->SetHostInitializeImportMetaObjectCallback( HostInitializeImportMetaObject); From 917e95433adbf0da16ffba214148f7e385b1407f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 15 May 2025 17:16:33 -0500 Subject: [PATCH 048/186] docs: add note on DIP and DPI (#47121) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Erick Zhao --- docs/api/screen.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/docs/api/screen.md b/docs/api/screen.md index 43b025ef7f721..c3bc334887eeb 100644 --- a/docs/api/screen.md +++ b/docs/api/screen.md @@ -58,6 +58,14 @@ app.whenReady().then(() => { }) ``` +> [!NOTE] +> Screen coordinates used by this module are [`Point`](structures/point.md) structures. +> There are two kinds of coordinates available to the process: +> +> * **Physical screen points** are raw hardware pixels on a display. +> * **Device-independent pixel (DIP) points** are virtualized screen points scaled based on the DPI +> (dots per inch) of the display. + ## Events The `screen` module emits the following events: From 7cb5a46b66538c06cde1bba898c20b9b83d013e4 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 15 May 2025 19:38:34 -0500 Subject: [PATCH 049/186] refactor: make TrackableObject::weak_map_id() constexpr (#47115) * refactor: make TrackableObject::weak_map_id() constexpr refactor: make BaseWindow::GetID() inline and constexpr Co-authored-by: Charles Kerr * refactor: make NativeWindow::window_id() constexpr too Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_base_window.cc | 4 ---- shell/browser/api/electron_api_base_window.h | 2 +- shell/browser/native_window.h | 2 +- shell/common/gin_helper/trackable_object.h | 2 +- 4 files changed, 3 insertions(+), 7 deletions(-) diff --git a/shell/browser/api/electron_api_base_window.cc b/shell/browser/api/electron_api_base_window.cc index d9f0a9987ccda..b795b5eeb263b 100644 --- a/shell/browser/api/electron_api_base_window.cc +++ b/shell/browser/api/electron_api_base_window.cc @@ -1154,10 +1154,6 @@ void BaseWindow::SetTitleBarOverlay(const gin_helper::Dictionary& options, } #endif -int32_t BaseWindow::GetID() const { - return weak_map_id(); -} - void BaseWindow::RemoveFromParentChildWindows() { if (parent_window_.IsEmpty()) return; diff --git a/shell/browser/api/electron_api_base_window.h b/shell/browser/api/electron_api_base_window.h index 0a44c592781eb..e516bf278d9a6 100644 --- a/shell/browser/api/electron_api_base_window.h +++ b/shell/browser/api/electron_api_base_window.h @@ -261,7 +261,7 @@ class BaseWindow : public gin_helper::TrackableObject, void SetTitleBarOverlay(const gin_helper::Dictionary& options, gin_helper::Arguments* args); #endif - int32_t GetID() const; + [[nodiscard]] constexpr int32_t GetID() const { return weak_map_id(); } private: // Helpers. diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index b729b068fc878..1a49d624050ef 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -405,7 +405,7 @@ class NativeWindow : public base::SupportsUserData, NativeWindow* parent() const { return parent_; } bool is_modal() const { return is_modal_; } - int32_t window_id() const { return window_id_; } + [[nodiscard]] constexpr int32_t window_id() const { return window_id_; } void add_child_window(NativeWindow* child) { child_windows_.push_back(child); diff --git a/shell/common/gin_helper/trackable_object.h b/shell/common/gin_helper/trackable_object.h index aa040aec58891..bedd6352ab2f2 100644 --- a/shell/common/gin_helper/trackable_object.h +++ b/shell/common/gin_helper/trackable_object.h @@ -28,7 +28,7 @@ class TrackableObjectBase : public CleanedUpAtExit { TrackableObjectBase& operator=(const TrackableObjectBase&) = delete; // The ID in weak map. - int32_t weak_map_id() const { return weak_map_id_; } + [[nodiscard]] constexpr int32_t weak_map_id() const { return weak_map_id_; } // Wrap TrackableObject into a class that SupportsUserData. void AttachAsUserData(base::SupportsUserData* wrapped); From d7990ca180a64f78c55968aa6ed4feb1aabb663b Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 15 May 2025 19:39:05 -0500 Subject: [PATCH 050/186] refactor: decouple NativeWindowViews and GlobalMenuBarX11 (#47119) The GlobalMenuBar used to hold a raw_ptr reference to its NativeWindow; but since it doesn't use it & only wants the gfx::AcceleratedWidget info, let's remove the NativeWindowViews reference. AFAICT, GlobalMenuBarX11::window_ has never been used Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window_views.cc | 3 ++- shell/browser/ui/views/global_menu_bar_x11.cc | 7 ++----- shell/browser/ui/views/global_menu_bar_x11.h | 5 +---- 3 files changed, 5 insertions(+), 10 deletions(-) diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 7f013202e6ed0..336fe32d20917 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -1365,7 +1365,8 @@ void NativeWindowViews::SetMenu(ElectronMenuModel* menu_model) { .supports_global_application_menus; if (can_use_global_menus && ShouldUseGlobalMenuBar()) { if (!global_menu_bar_) - global_menu_bar_ = std::make_unique(this); + global_menu_bar_ = + std::make_unique(GetAcceleratedWidget()); if (global_menu_bar_->IsServerStarted()) { root_view_.RegisterAcceleratorsWithFocusManager(menu_model); global_menu_bar_->SetMenu(menu_model); diff --git a/shell/browser/ui/views/global_menu_bar_x11.cc b/shell/browser/ui/views/global_menu_bar_x11.cc index c0c997c0da5e3..53e51db0857e1 100644 --- a/shell/browser/ui/views/global_menu_bar_x11.cc +++ b/shell/browser/ui/views/global_menu_bar_x11.cc @@ -9,7 +9,6 @@ #include "base/functional/bind.h" #include "base/strings/utf_string_conversions.h" -#include "shell/browser/native_window_views.h" #include "shell/browser/ui/electron_menu_model.h" #include "shell/browser/ui/views/global_menu_bar_registrar_x11.h" #include "third_party/abseil-cpp/absl/strings/str_format.h" @@ -173,10 +172,8 @@ std::string GetMenuModelStatus(ElectronMenuModel* model) { } // namespace -GlobalMenuBarX11::GlobalMenuBarX11(NativeWindowViews* window) - : window_(window), - xwindow_(static_cast( - window_->GetNativeWindow()->GetHost()->GetAcceleratedWidget())) { +GlobalMenuBarX11::GlobalMenuBarX11(gfx::AcceleratedWidget accelerated_widget) + : xwindow_(static_cast(accelerated_widget)) { EnsureMethodsLoaded(); if (server_new) InitServer(xwindow_); diff --git a/shell/browser/ui/views/global_menu_bar_x11.h b/shell/browser/ui/views/global_menu_bar_x11.h index 893f2cf6a040c..0851822fc3f16 100644 --- a/shell/browser/ui/views/global_menu_bar_x11.h +++ b/shell/browser/ui/views/global_menu_bar_x11.h @@ -22,8 +22,6 @@ class Accelerator; namespace electron { -class NativeWindowViews; - // Controls the Mac style menu bar on Unity. // // Unity has an Apple-like menu bar at the top of the screen that changes @@ -37,7 +35,7 @@ class NativeWindowViews; // from menu models instead, and it is also per-window specific. class GlobalMenuBarX11 { public: - explicit GlobalMenuBarX11(NativeWindowViews* window); + explicit GlobalMenuBarX11(gfx::AcceleratedWidget accelerated_widget); virtual ~GlobalMenuBarX11(); // disable copy @@ -68,7 +66,6 @@ class GlobalMenuBarX11 { void OnItemActivated(DbusmenuMenuitem* item, unsigned int timestamp); void OnSubMenuShow(DbusmenuMenuitem* item); - raw_ptr window_; x11::Window xwindow_; raw_ptr server_ = nullptr; From b6779056f2fd1ed9eb2da48a5221df3e43a5e19e Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 16 May 2025 02:32:22 -0500 Subject: [PATCH 051/186] test: fix desktopCapturer mocha syntax (#47113) do not nest `it` calls in desktopCapturer specs Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- spec/api-desktop-capturer-spec.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/spec/api-desktop-capturer-spec.ts b/spec/api-desktop-capturer-spec.ts index a3ff4df4a3888..af1567efe2a46 100644 --- a/spec/api-desktop-capturer-spec.ts +++ b/spec/api-desktop-capturer-spec.ts @@ -99,7 +99,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt expect(isEmpties.every(e => e === true)).to.be.true(); }); - it('getMediaSourceId should match DesktopCapturerSource.id', async () => { + it('getMediaSourceId should match DesktopCapturerSource.id', async function () { const w = new BrowserWindow({ show: false, width: 100, height: 100, webPreferences: { contextIsolation: false } }); const wShown = once(w, 'show'); const wFocused = once(w, 'focus'); @@ -119,7 +119,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt // bots while it is not on my workstation, as expected, with and without // the --ci parameter. if (process.platform === 'linux' && sources.length === 0) { - it.skip('desktopCapturer.getSources returned an empty source list'); + this.skip(); return; } @@ -130,7 +130,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt expect(mediaSourceId).to.equal(foundSource!.id); }); - it('getSources should not incorrectly duplicate window_id', async () => { + it('getSources should not incorrectly duplicate window_id', async function () { const w = new BrowserWindow({ show: false, width: 100, height: 100, webPreferences: { contextIsolation: false } }); const wShown = once(w, 'show'); const wFocused = once(w, 'focus'); @@ -155,7 +155,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt // bots while it is not on my workstation, as expected, with and without // the --ci parameter. if (process.platform === 'linux' && sources.length === 0) { - it.skip('desktopCapturer.getSources returned an empty source list'); + this.skip(); return; } @@ -180,7 +180,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt expect(w.resizable).to.be.false(); }); - it('moveAbove should move the window at the requested place', async () => { + it('moveAbove should move the window at the requested place', async function () { // DesktopCapturer.getSources() is guaranteed to return in the correct // z-order from foreground to background. const MAX_WIN = 4; @@ -225,7 +225,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt // the --ci parameter. if (process.platform === 'linux' && sources.length === 0) { destroyWindows(); - it.skip('desktopCapturer.getSources returned an empty source list'); + this.skip(); return; } From cc302c2f0782e149f5c066c4bc93431cb9b5a0b7 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 16 May 2025 08:47:16 -0500 Subject: [PATCH 052/186] perf: don't create unused menuitem icons (#47129) GTK >= 3.90.0 removed support for menuitem icons. When Electron is built with GTK >= 3.90.0, our code builds these icons and then throws them away unused. Instead, let's just not build them. Our gtk_util::GdkPixbufFromSkBitmap utility uses BGRAToRGBA and is expensive to call. Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/ui/gtk/menu_util.cc | 18 ++++++------------ shell/browser/ui/gtk/menu_util.h | 2 -- 2 files changed, 6 insertions(+), 14 deletions(-) diff --git a/shell/browser/ui/gtk/menu_util.cc b/shell/browser/ui/gtk/menu_util.cc index 5870a854149df..76bc5862f662a 100644 --- a/shell/browser/ui/gtk/menu_util.cc +++ b/shell/browser/ui/gtk/menu_util.cc @@ -60,29 +60,23 @@ GdkModifierType GetGdkModifierForAccelerator( } // namespace -GtkWidget* BuildMenuItemWithImage(const std::string& label, GtkWidget* image) { -// GTK4 removed support for image menu items. +GtkWidget* BuildMenuItemWithImage(const std::string& label, + const gfx::Image& icon) { +// GTK4 removed support for menuitem icons. #if GTK_CHECK_VERSION(3, 90, 0) return gtk_menu_item_new_with_mnemonic(label.c_str()); #else G_GNUC_BEGIN_IGNORE_DEPRECATIONS; GtkWidget* menu_item = gtk_image_menu_item_new_with_mnemonic(label.c_str()); + GdkPixbuf* pixbuf = gtk_util::GdkPixbufFromSkBitmap(*icon.ToSkBitmap()); + GtkWidget* image = gtk_image_new_from_pixbuf(pixbuf); gtk_image_menu_item_set_image(GTK_IMAGE_MENU_ITEM(menu_item), image); + g_object_unref(pixbuf); G_GNUC_END_IGNORE_DEPRECATIONS; return menu_item; #endif } -GtkWidget* BuildMenuItemWithImage(const std::string& label, - const gfx::Image& icon) { - GdkPixbuf* pixbuf = gtk_util::GdkPixbufFromSkBitmap(*icon.ToSkBitmap()); - - GtkWidget* menu_item = - BuildMenuItemWithImage(label, gtk_image_new_from_pixbuf(pixbuf)); - g_object_unref(pixbuf); - return menu_item; -} - GtkWidget* BuildMenuItemWithLabel(const std::string& label) { return gtk_menu_item_new_with_mnemonic(label.c_str()); } diff --git a/shell/browser/ui/gtk/menu_util.h b/shell/browser/ui/gtk/menu_util.h index 1958d9aaf2fd5..11b1bd880dcac 100644 --- a/shell/browser/ui/gtk/menu_util.h +++ b/shell/browser/ui/gtk/menu_util.h @@ -26,8 +26,6 @@ using MenuActivatedCallback = base::RepeatingCallback; // Builds GtkImageMenuItems. GtkWidget* BuildMenuItemWithImage(const std::string& label, GtkWidget* image); -GtkWidget* BuildMenuItemWithImage(const std::string& label, - const gfx::Image& icon); GtkWidget* BuildMenuItemWithLabel(const std::string& label); ui::MenuModel* ModelForMenuItem(GtkMenuItem* menu_item); From bbb6aabe41039ba8fedf0838dbb56ca17e53d1f2 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 19 May 2025 21:01:05 +0200 Subject: [PATCH 053/186] fix: explicit microtask scope DCHECK condition (#47140) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: clavin --- shell/common/node_util.cc | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/shell/common/node_util.cc b/shell/common/node_util.cc index f777796339a14..98e618471f4ef 100644 --- a/shell/common/node_util.cc +++ b/shell/common/node_util.cc @@ -15,6 +15,7 @@ #include "shell/browser/javascript_environment.h" #include "shell/common/gin_converters/callback_converter.h" #include "shell/common/node_includes.h" +#include "shell/common/process_util.h" #include "third_party/electron_node/src/node_process-inl.h" namespace electron::util { @@ -132,7 +133,17 @@ node::Environment* CreateEnvironment(v8::Isolate* isolate, ExplicitMicrotasksScope::ExplicitMicrotasksScope(v8::MicrotaskQueue* queue) : microtask_queue_(queue), original_policy_(queue->microtasks_policy()) { - DCHECK_EQ(microtask_queue_->GetMicrotasksScopeDepth(), 0); + // In browser-like processes, some nested run loops (macOS usually) may + // re-enter. This is safe because we expect the policy was explicit in the + // first place for those processes. However, in renderer processes, there may + // be unexpected behavior if this code is triggered within a pending microtask + // scope. + if (electron::IsBrowserProcess() || electron::IsUtilityProcess()) { + DCHECK_EQ(original_policy_, v8::MicrotasksPolicy::kExplicit); + } else { + DCHECK_EQ(microtask_queue_->GetMicrotasksScopeDepth(), 0); + } + microtask_queue_->set_microtasks_policy(v8::MicrotasksPolicy::kExplicit); } From 692d648edbefd3f0440ed583ea66ab78d5f78812 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 19 May 2025 18:52:14 -0500 Subject: [PATCH 054/186] refactor: NativeWindows should prefer widget() over GetWidget() for internal use (#47155) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window.cc | 6 +++--- shell/browser/native_window_views.cc | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 442503fd8ba3a..2b1c9b6a37942 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -718,7 +718,7 @@ int NativeWindow::NonClientHitTest(const gfx::Point& point) { // This is to disable dragging in HTML5 full screen mode. // Details: https://github.com/electron/electron/issues/41002 - if (GetWidget()->IsFullscreen()) + if (widget()->IsFullscreen()) return HTNOWHERE; for (auto* provider : draggable_region_providers_) { @@ -758,7 +758,7 @@ void NativeWindow::RemoveBackgroundThrottlingSource( } void NativeWindow::UpdateBackgroundThrottlingState() { - if (!GetWidget() || !GetWidget()->GetCompositor()) { + if (!widget() || !widget()->GetCompositor()) { return; } bool enable_background_throttling = true; @@ -769,7 +769,7 @@ void NativeWindow::UpdateBackgroundThrottlingState() { break; } } - GetWidget()->GetCompositor()->SetBackgroundThrottling( + widget()->GetCompositor()->SetBackgroundThrottling( enable_background_throttling); } diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 336fe32d20917..008e3f821cfcb 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -1233,7 +1233,7 @@ void NativeWindowViews::SetBackgroundColor(SkColor background_color) { DeleteObject((HBRUSH)previous_brush); InvalidateRect(GetAcceleratedWidget(), nullptr, 1); #endif - GetWidget()->GetCompositor()->SetBackgroundColor(background_color); + widget()->GetCompositor()->SetBackgroundColor(background_color); } void NativeWindowViews::SetHasShadow(bool has_shadow) { From 791235b15b679103287629503688fcf997b52953 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Tue, 20 May 2025 13:32:53 +0200 Subject: [PATCH 055/186] chore: bump node to v22.15.1 (37-x-y) (#47104) * chore: bump node in DEPS to v22.15.1 * chore: fixup patch indices * src: fix error handling on async crypto operations https://github.com/nodejs-private/node-private/pull/709 --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- DEPS | 2 +- ...g_fileexists_fn_to_legacymainresolve.patch | 2 +- .../fix_crypto_tests_to_run_with_bssl.patch | 27 ++++++++++++++++--- ...ingssl_and_openssl_incompatibilities.patch | 4 +-- ...ted_fields_of_fastapicallbackoptions.patch | 2 +- .../node/support_v8_sandboxed_pointers.patch | 4 +-- 6 files changed, 31 insertions(+), 10 deletions(-) diff --git a/DEPS b/DEPS index 72033ea58cb23..ac72ef0228819 100644 --- a/DEPS +++ b/DEPS @@ -4,7 +4,7 @@ vars = { 'chromium_version': '138.0.7178.0', 'node_version': - 'v22.15.0', + 'v22.15.1', 'nan_version': 'e14bdcd1f72d62bca1d541b66da43130384ec213', 'squirrel.mac_version': diff --git a/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch b/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch index 72074233f7954..6ca8291f2b3e6 100644 --- a/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch +++ b/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch @@ -53,7 +53,7 @@ index 2879e5cf541fb4d226cfd7cc0fe367ca448fb926..03082f0ec4f91382933eec48e77331cd const maybeMain = resolvedOption <= legacyMainResolveExtensionsIndexes.kResolvedByMainIndexNode ? packageConfig.main || './' : ''; diff --git a/src/node_file.cc b/src/node_file.cc -index a492b3aa113c4e1d50cc42721bd5eb58380a6264..c7915e2c8161a5d0fa05ccce368ce9c44345c05d 100644 +index 49816349d8bab37fea1d84e5326ee5a11acad7a2..5aea65d6800494def62829432ee48f9c06e65d63 100644 --- a/src/node_file.cc +++ b/src/node_file.cc @@ -3237,13 +3237,25 @@ static void CpSyncCheckPaths(const FunctionCallbackInfo& args) { diff --git a/patches/node/fix_crypto_tests_to_run_with_bssl.patch b/patches/node/fix_crypto_tests_to_run_with_bssl.patch index ce3b8f49c39a5..5e27975c22151 100644 --- a/patches/node/fix_crypto_tests_to_run_with_bssl.patch +++ b/patches/node/fix_crypto_tests_to_run_with_bssl.patch @@ -46,10 +46,10 @@ index d033cd204b3200cdd736b581abe027d6e46e4ff3..73fec107a36c3db4af6f492137d0ca17 largeBuffer.toString('utf8', threshold, threshold + 20); +} diff --git a/test/parallel/test-crypto-async-sign-verify.js b/test/parallel/test-crypto-async-sign-verify.js -index 4e3c32fdcd23fbe3e74bd5e624b739d224689f33..29149838ca76986928c7649a5f60a0f5e22a0705 100644 +index b35dd08e6c49796418cd9d10eb5cc9d02b39961e..a49fdde82ea4cbadd60307cdc99439be892ef5a6 100644 --- a/test/parallel/test-crypto-async-sign-verify.js +++ b/test/parallel/test-crypto-async-sign-verify.js -@@ -88,6 +88,7 @@ test('rsa_public.pem', 'rsa_private.pem', 'sha256', false, +@@ -89,6 +89,7 @@ test('rsa_public.pem', 'rsa_private.pem', 'sha256', false, // ED25519 test('ed25519_public.pem', 'ed25519_private.pem', undefined, true); // ED448 @@ -57,7 +57,7 @@ index 4e3c32fdcd23fbe3e74bd5e624b739d224689f33..29149838ca76986928c7649a5f60a0f5 test('ed448_public.pem', 'ed448_private.pem', undefined, true); // ECDSA w/ der signature encoding -@@ -109,6 +110,7 @@ test('dsa_public.pem', 'dsa_private.pem', 'sha256', +@@ -110,6 +111,7 @@ test('dsa_public.pem', 'dsa_private.pem', 'sha256', // DSA w/ ieee-p1363 signature encoding test('dsa_public.pem', 'dsa_private.pem', 'sha256', false, { dsaEncoding: 'ieee-p1363' }); @@ -65,6 +65,27 @@ index 4e3c32fdcd23fbe3e74bd5e624b739d224689f33..29149838ca76986928c7649a5f60a0f5 // Test Parallel Execution w/ KeyObject is threadsafe in openssl3 { +@@ -150,8 +152,10 @@ MCowBQYDK2VuAyEA6pwGRbadNQAI/tYN8+/p/0/hbsdHfOEGr1ADiLVk/Gc= + const data = crypto.randomBytes(32); + const signature = crypto.randomBytes(16); + +- const expected = hasOpenSSL3 ? +- /operation not supported for this keytype/ : /no default digest/; ++ let expected = /no default digest/; ++ if (hasOpenSSL3 || common.openSSLIsBoringSSL) { ++ expected = /operation[\s_]not[\s_]supported[\s_]for[\s_]this[\s_]keytype/i; ++ } + + crypto.verify(undefined, data, untrustedKey, signature, common.mustCall((err) => { + assert.ok(err); +@@ -165,6 +169,6 @@ MCowBQYDK2VuAyEA6pwGRbadNQAI/tYN8+/p/0/hbsdHfOEGr1ADiLVk/Gc= + }); + crypto.sign('sha512', 'message', privateKey, common.mustCall((err) => { + assert.ok(err); +- assert.match(err.message, /digest too big for rsa key/); ++ assert.match(err.message, /digest[\s_]too[\s_]big[\s_]for[\s_]rsa[\s_]key/i); + })); + } diff --git a/test/parallel/test-crypto-certificate.js b/test/parallel/test-crypto-certificate.js index 4a5f1f149fe6c739f7f1d2ee17df6e61a942d621..b3287f428ce6b3fde11d449c601a57ff5e3843f9 100644 --- a/test/parallel/test-crypto-certificate.js diff --git a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch index 3d8bea2f74f95..8548df12be7ec 100644 --- a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch +++ b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch @@ -274,7 +274,7 @@ index a054e4c1285208c9ba8b9679c284f459f1ace690..3de8ef4fafcdbdc2cb0ce31de162663d X509_STORE_add_cert(sc->GetCertStoreOwnedByThisSecureContext(), ca); diff --git a/src/crypto/crypto_dh.cc b/src/crypto/crypto_dh.cc -index 7041eb985d9f6d163098a94342aec976cb6c2bb9..5387d9625a28bb7d11f7f0f05a5f07d1fee2c216 100644 +index c26a88b395abfc645da56231635b36fb23c8fa09..f23cedf4f2449d8edc9a8de1b70332e75d693cdd 100644 --- a/src/crypto/crypto_dh.cc +++ b/src/crypto/crypto_dh.cc @@ -7,7 +7,9 @@ @@ -428,7 +428,7 @@ index b38a9a377738fd5fe6cc89c3a27c403bf6a97715..0cd43c2005b431e180b7483cb89825a7 void KeyObjectHandle::CheckEcKeyData(const FunctionCallbackInfo& args) { diff --git a/src/crypto/crypto_random.cc b/src/crypto/crypto_random.cc -index cb96698aa644c3b6c506c0979910f2b4421d63ad..b9b21329199b49c9e41f9ae708296e5b0edb39b0 100644 +index 78f2093d1d010be6f9c492662f4f582657ff6a13..b6aef7fd27cd974697bcee05955bfd9ccf4d5837 100644 --- a/src/crypto/crypto_random.cc +++ b/src/crypto/crypto_random.cc @@ -143,7 +143,7 @@ Maybe RandomPrimeTraits::AdditionalConfig( diff --git a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch index 1e68d7e6b68f3..250c9daa8f16a 100644 --- a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch +++ b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch @@ -40,7 +40,7 @@ index 0f0cde7be431dcb80c5314b1a9da49886c436d1c..f6d2bd439cad8b9f91c9d9a6cdb302e6 } HistogramBase* histogram; diff --git a/src/node_file.cc b/src/node_file.cc -index c7915e2c8161a5d0fa05ccce368ce9c44345c05d..23347379328794467a497c86cbae0b428b7ba791 100644 +index 5aea65d6800494def62829432ee48f9c06e65d63..80cf6648ed99241eea8c176c5c958d76fe33aa14 100644 --- a/src/node_file.cc +++ b/src/node_file.cc @@ -1071,13 +1071,8 @@ static int32_t FastInternalModuleStat( diff --git a/patches/node/support_v8_sandboxed_pointers.patch b/patches/node/support_v8_sandboxed_pointers.patch index f909667671ec9..6a3edccfab578 100644 --- a/patches/node/support_v8_sandboxed_pointers.patch +++ b/patches/node/support_v8_sandboxed_pointers.patch @@ -26,7 +26,7 @@ index 88c2c932a6b045317c83c911b1cd8267b60d9334..7f4f233b26425493a58ce71dfc0c3a92 void* ret; if (zero_fill_field_ || per_process::cli_options->zero_fill_all_buffers) diff --git a/src/crypto/crypto_dh.cc b/src/crypto/crypto_dh.cc -index 5387d9625a28bb7d11f7f0f05a5f07d1fee2c216..1b3b8c7b70073926f8dbf02759c2e1af5d938679 100644 +index f23cedf4f2449d8edc9a8de1b70332e75d693cdd..976653dd1e9363e046788fc3419a9b649ceb2ea4 100644 --- a/src/crypto/crypto_dh.cc +++ b/src/crypto/crypto_dh.cc @@ -55,13 +55,32 @@ void DiffieHellman::MemoryInfo(MemoryTracker* tracker) const { @@ -143,7 +143,7 @@ index 6346f8f7199cf7b7d3736c59571606fff102fbb6..7eea2eaefcad5780663a6b87985925ae void SecureHeapUsed(const FunctionCallbackInfo& args) { #ifndef OPENSSL_IS_BORINGSSL diff --git a/src/crypto/crypto_util.h b/src/crypto/crypto_util.h -index b85c8daeb464097c2e93bdc7ffdfcfe16b76234b..470a0c4adadcd092dd0105c384e87917ac6fe69a 100644 +index 1592134716da2de40de4ba028ee937b765423e37..8f3ba65f1fef2c066d6df6087a08ba71100d1090 100644 --- a/src/crypto/crypto_util.h +++ b/src/crypto/crypto_util.h @@ -242,7 +242,7 @@ class ByteSource { From ecc00f149f24d92b889aff067db29ea9a254954a Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 20 May 2025 11:55:54 -0500 Subject: [PATCH 056/186] fix: prevent gc monitor 2nd pass crash (#47165) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: reito --- shell/common/gin_converters/osr_converter.cc | 22 +++++++++++--------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/shell/common/gin_converters/osr_converter.cc b/shell/common/gin_converters/osr_converter.cc index afa868ae8a526..2cdb2bb0633f1 100644 --- a/shell/common/gin_converters/osr_converter.cc +++ b/shell/common/gin_converters/osr_converter.cc @@ -143,19 +143,21 @@ v8::Local Converter::ToV8( // texture, output it in second pass callback. data.SetSecondPassCallback([](const v8::WeakCallbackInfo< OffscreenReleaseHolderMonitor>& data) { - auto* iso = data.GetIsolate(); // Emit warning only once static std::once_flag flag; std::call_once(flag, [=] { - electron::util::EmitWarning( - iso, - "[OSR TEXTURE LEAKED] When using OSR with " - "`useSharedTexture`, `texture.release()` " - "must be called explicitly as soon as the texture is " - "copied to your rendering system. " - "Otherwise, it will soon drain the underlying " - "framebuffer and prevent future frames from being generated.", - "SharedTextureOSRNotReleased"); + base::SingleThreadTaskRunner::GetCurrentDefault()->PostTask( + FROM_HERE, base::BindOnce([] { + electron::util::EmitWarning( + "Offscreen rendering shared texture was garbage " + "collected before calling `release()`. When using OSR " + "with `useSharedTexture: true`, `texture.release()` " + "must be called explicitly as soon as the texture is " + "copied to your rendering system. Otherwise, it will " + "soon drain the underlying frame pool and prevent " + "future frames from being sent.", + "OSRSharedTextureNotReleased"); + })); }); }); } From 54f2c93fec333c0ecd4217157f2fd5f287dc846c Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 20 May 2025 19:46:05 +0200 Subject: [PATCH 057/186] build: update_depot_tools on initial install (#47169) this ensures that python is setup for proper use from depot_tools Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- .github/actions/install-build-tools/action.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/actions/install-build-tools/action.yml b/.github/actions/install-build-tools/action.yml index a897b6480e886..5890e46e45d50 100644 --- a/.github/actions/install-build-tools/action.yml +++ b/.github/actions/install-build-tools/action.yml @@ -15,6 +15,7 @@ runs: fi export BUILD_TOOLS_SHA=6e8526315ea3b4828882497e532b8340e64e053c npm i -g @electron/build-tools + e d update_depot_tools e auto-update disable e d auto-update disable if [ "$(expr substr $(uname -s) 1 10)" == "MSYS_NT-10" ]; then From f6e7cdb8b69b4180f1981e2ec5d7924304610381 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 20 May 2025 21:02:47 -0500 Subject: [PATCH 058/186] refactor: make `NativeWindow::pending_transitions_` a `base::queue` (#47181) refactor: make NativeWindow::pending_transitions a base::queue Follow the base/containers/README.md advice that "Chromium code should always use `base::circular_deque` or `base::queue` in preference to `std::deque` or `std::queue` due to memory usage and platform variation." Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window.h | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index 1a49d624050ef..dd67759959701 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -8,11 +8,11 @@ #include #include #include -#include #include #include #include +#include "base/containers/queue.h" #include "base/memory/raw_ptr.h" #include "base/memory/weak_ptr.h" #include "base/observer_list.h" @@ -467,7 +467,8 @@ class NativeWindow : public base::SupportsUserData, // on HiDPI displays on some environments. std::optional content_size_constraints_; - std::queue pending_transitions_; + base::queue pending_transitions_; + FullScreenTransitionType fullscreen_transition_type_ = FullScreenTransitionType::kNone; From 73dd132202821deb3c82c43f8ef8a32d91bb854f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 21 May 2025 10:31:47 +0200 Subject: [PATCH 059/186] refactor: match upstream macOS a11y handling (#47170) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/mac/electron_application.mm | 132 ++++++++++++++++++++-- 1 file changed, 122 insertions(+), 10 deletions(-) diff --git a/shell/browser/mac/electron_application.mm b/shell/browser/mac/electron_application.mm index e4c86aabde3da..5179ae1389757 100644 --- a/shell/browser/mac/electron_application.mm +++ b/shell/browser/mac/electron_application.mm @@ -8,12 +8,14 @@ #include #include "base/auto_reset.h" +#include "base/mac/mac_util.h" #include "base/observer_list.h" #include "base/strings/sys_string_conversions.h" #include "content/public/browser/browser_accessibility_state.h" #include "content/public/browser/native_event_processor_mac.h" #include "content/public/browser/native_event_processor_observer_mac.h" #include "content/public/browser/scoped_accessibility_mode.h" +#include "content/public/common/content_features.h" #include "shell/browser/browser.h" #include "shell/browser/mac/dict_util.h" #import "shell/browser/mac/electron_application_delegate.h" @@ -31,12 +33,19 @@ inline void dispatch_sync_main(dispatch_block_t block) { } // namespace @interface AtomApplication () { + int _AXEnhancedUserInterfaceRequests; + BOOL _voiceOverEnabled; + BOOL _sonomaAccessibilityRefinementsAreActive; base::ObserverList::Unchecked observers_; } +// Enables/disables screen reader support on changes to VoiceOver status. +- (void)voiceOverStateChanged:(BOOL)voiceOverEnabled; @end @implementation AtomApplication { + std::unique_ptr + _scoped_accessibility_mode_voiceover; std::unique_ptr _scoped_accessibility_mode_general; } @@ -45,6 +54,37 @@ + (AtomApplication*)sharedApplication { return (AtomApplication*)[super sharedApplication]; } +- (void)finishLaunching { + [super finishLaunching]; + + _sonomaAccessibilityRefinementsAreActive = + base::mac::MacOSVersion() >= 14'00'00 && + base::FeatureList::IsEnabled( + features::kSonomaAccessibilityActivationRefinements); +} + +- (void)observeValueForKeyPath:(NSString*)keyPath + ofObject:(id)object + change:(NSDictionary*)change + context:(void*)context { + if ([keyPath isEqualToString:@"voiceOverEnabled"] && + context == content::BrowserAccessibilityState::GetInstance()) { + NSNumber* newValueNumber = [change objectForKey:NSKeyValueChangeNewKey]; + DCHECK([newValueNumber isKindOfClass:[NSNumber class]]); + + if ([newValueNumber isKindOfClass:[NSNumber class]]) { + [self voiceOverStateChanged:[newValueNumber boolValue]]; + } + + return; + } + + [super observeValueForKeyPath:keyPath + ofObject:object + change:change + context:context]; +} + - (void)willPowerOff:(NSNotification*)notify { userStoppedShutdown_ = shouldShutdown_ && !shouldShutdown_.Run(); } @@ -214,14 +254,7 @@ - (id)accessibilityAttributeValue:(NSString*)attribute { - (void)accessibilitySetValue:(id)value forAttribute:(NSString*)attribute { bool is_manual_ax = [attribute isEqualToString:@"AXManualAccessibility"]; if ([attribute isEqualToString:@"AXEnhancedUserInterface"] || is_manual_ax) { - if (![value boolValue]) { - _scoped_accessibility_mode_general.reset(); - } else if (!_scoped_accessibility_mode_general) { - _scoped_accessibility_mode_general = - content::BrowserAccessibilityState::GetInstance() - ->CreateScopedModeForProcess(ui::kAXModeComplete); - } - + [self enableScreenReaderCompleteModeAfterDelay:[value boolValue]]; electron::Browser::Get()->OnAccessibilitySupportChanged(); // Don't call the superclass function for AXManualAccessibility, @@ -241,8 +274,11 @@ - (NSAccessibilityRole)accessibilityRole { // recommends turning on a11y when an AT accesses the 'accessibilityRole' // property. This function is accessed frequently, so we only change the // accessibility state when accessibility is already disabled. - if (!_scoped_accessibility_mode_general) { - ui::AXMode target_mode = ui::kAXModeBasic; + if (!_scoped_accessibility_mode_general && + !_scoped_accessibility_mode_voiceover) { + ui::AXMode target_mode = _sonomaAccessibilityRefinementsAreActive + ? ui::AXMode::kNativeAPIs + : ui::kAXModeBasic; _scoped_accessibility_mode_general = content::BrowserAccessibilityState::GetInstance() ->CreateScopedModeForProcess(target_mode | @@ -252,6 +288,82 @@ - (NSAccessibilityRole)accessibilityRole { return [super accessibilityRole]; } +- (void)enableScreenReaderCompleteMode:(BOOL)enable { + if (enable) { + if (!_scoped_accessibility_mode_voiceover) { + _scoped_accessibility_mode_voiceover = + content::BrowserAccessibilityState::GetInstance() + ->CreateScopedModeForProcess(ui::kAXModeComplete | + ui::AXMode::kFromPlatform | + ui::AXMode::kScreenReader); + } + } else { + _scoped_accessibility_mode_voiceover.reset(); + } +} + +// We need to call enableScreenReaderCompleteMode:YES from performSelector:... +// but there's no way to supply a BOOL as a parameter, so we have this +// explicit enable... helper method. +- (void)enableScreenReaderCompleteMode { + _AXEnhancedUserInterfaceRequests = 0; + [self enableScreenReaderCompleteMode:YES]; +} + +- (void)voiceOverStateChanged:(BOOL)voiceOverEnabled { + _voiceOverEnabled = voiceOverEnabled; + + [self enableScreenReaderCompleteMode:voiceOverEnabled]; +} + +// Enables or disables screen reader support for non-VoiceOver assistive +// technology (AT), possibly after a delay. +// +// Now that we directly monitor VoiceOver status, we no longer watch for +// changes to AXEnhancedUserInterface for that signal from VO. However, other +// AT can set a value for AXEnhancedUserInterface, so we can't ignore it. +// Unfortunately, as of macOS Sonoma, we sometimes see spurious changes to +// AXEnhancedUserInterface (quick on and off). We debounce by waiting for these +// changes to settle down before updating the screen reader state. +- (void)enableScreenReaderCompleteModeAfterDelay:(BOOL)enable { + // If VoiceOver is already explicitly enabled, ignore requests from other AT. + if (_voiceOverEnabled) { + return; + } + + // If this is a request to disable screen reader support, and we haven't seen + // a corresponding enable request, go ahead and disable. + if (!enable && _AXEnhancedUserInterfaceRequests == 0) { + [self enableScreenReaderCompleteMode:NO]; + return; + } + + // Use a counter to track requests for changes to the screen reader state. + if (enable) { + _AXEnhancedUserInterfaceRequests++; + } else { + _AXEnhancedUserInterfaceRequests--; + } + + DCHECK_GE(_AXEnhancedUserInterfaceRequests, 0); + + // _AXEnhancedUserInterfaceRequests > 0 means we want to enable screen + // reader support, but we'll delay that action until there are no more state + // change requests within a two-second window. Cancel any pending + // performSelector:..., and schedule a new one to restart the countdown. + [NSObject cancelPreviousPerformRequestsWithTarget:self + selector:@selector + (enableScreenReaderCompleteMode) + object:nil]; + + if (_AXEnhancedUserInterfaceRequests > 0) { + const float kTwoSecondDelay = 2.0; + [self performSelector:@selector(enableScreenReaderCompleteMode) + withObject:nil + afterDelay:kTwoSecondDelay]; + } +} + - (void)orderFrontStandardAboutPanel:(id)sender { electron::Browser::Get()->ShowAboutPanel(); } From c78be7617657805363b24a1ed3913247d8b2c54f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 21 May 2025 11:44:36 +0200 Subject: [PATCH 060/186] refactor: make `NativeWindow::has_client_frame_` const (#47180) * refactor: make NativeWindow::has_client_frame_ const Co-authored-by: Charles Kerr * refactor: make NativeWindow::has_client_frame_ const but not constexpr Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window.cc | 27 ++++++++++++++++----------- shell/browser/native_window.h | 7 +++++-- 2 files changed, 21 insertions(+), 13 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 2b1c9b6a37942..8423aa48f8e67 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -127,17 +127,6 @@ NativeWindow::NativeWindow(const gin_helper::Dictionary& options, if (parent) options.Get("modal", &is_modal_); -#if defined(USE_OZONE) - // Ozone X11 likes to prefer custom frames, but we don't need them unless - // on Wayland. - if (base::FeatureList::IsEnabled(features::kWaylandWindowDecorations) && - !ui::OzonePlatform::GetInstance() - ->GetPlatformRuntimeProperties() - .supports_server_side_window_decorations) { - has_client_frame_ = true; - } -#endif - WindowList::AddWindow(this); } @@ -829,6 +818,22 @@ bool NativeWindow::IsTranslucent() const { return false; } +// static +bool NativeWindow::PlatformHasClientFrame() { +#if defined(USE_OZONE) + // Ozone X11 likes to prefer custom frames, + // but we don't need them unless on Wayland. + static const bool has_client_frame = + base::FeatureList::IsEnabled(features::kWaylandWindowDecorations) && + !ui::OzonePlatform::GetInstance() + ->GetPlatformRuntimeProperties() + .supports_server_side_window_decorations; + return has_client_frame; +#else + return false; +#endif +} + // static void NativeWindowRelay::CreateForWebContents( content::WebContents* web_contents, diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index dd67759959701..ae453dae7d564 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -398,7 +398,8 @@ class NativeWindow : public base::SupportsUserData, bool has_frame() const { return has_frame_; } - bool has_client_frame() const { return has_client_frame_; } + [[nodiscard]] bool has_client_frame() const { return has_client_frame_; } + bool transparent() const { return transparent_; } bool enable_larger_than_screen() const { return enable_larger_than_screen_; } @@ -475,6 +476,8 @@ class NativeWindow : public base::SupportsUserData, std::list child_windows_; private: + static bool PlatformHasClientFrame(); + std::unique_ptr widget_; static inline int32_t next_id_ = 0; @@ -493,7 +496,7 @@ class NativeWindow : public base::SupportsUserData, // Whether window has standard frame, but it's drawn by Electron (the client // application) instead of the OS. Currently only has meaning on Linux for // Wayland hosts. - bool has_client_frame_ = false; + const bool has_client_frame_ = PlatformHasClientFrame(); // Whether window is transparent. bool transparent_ = false; From 28c5f7026f81148492e0796e996422f0c49c287f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 21 May 2025 15:32:52 -0500 Subject: [PATCH 061/186] refactor: make `NativeWindow::transparent_` const (#47198) * refactor: use in-class member initialization for NativeWindow::widget_ Co-authored-by: Charles Kerr * refactor: make NativeWindow::transparent_ const refactor: make NativeWindow::enable_larger_than_screen_ const Co-authored-by: Charles Kerr * chore: make linter happy after rebase Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window.cc | 7 ++++--- shell/browser/native_window.h | 21 ++++++++++++--------- 2 files changed, 16 insertions(+), 12 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 8423aa48f8e67..19db0ef56d76e 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -97,10 +97,11 @@ gfx::Size GetExpandedWindowSize(const NativeWindow* window, gfx::Size size) { NativeWindow::NativeWindow(const gin_helper::Dictionary& options, NativeWindow* parent) - : widget_(std::make_unique()), parent_(parent) { + : transparent_{options.ValueOrDefault(options::kTransparent, false)}, + enable_larger_than_screen_{ + options.ValueOrDefault(options::kEnableLargerThanScreen, false)}, + parent_{parent} { options.Get(options::kFrame, &has_frame_); - options.Get(options::kTransparent, &transparent_); - options.Get(options::kEnableLargerThanScreen, &enable_larger_than_screen_); options.Get(options::kTitleBarStyle, &title_bar_style_); #if BUILDFLAG(IS_WIN) options.Get(options::kBackgroundMaterial, &background_material_); diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index ae453dae7d564..f2a8334a951ac 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -400,8 +400,11 @@ class NativeWindow : public base::SupportsUserData, [[nodiscard]] bool has_client_frame() const { return has_client_frame_; } - bool transparent() const { return transparent_; } - bool enable_larger_than_screen() const { return enable_larger_than_screen_; } + [[nodiscard]] bool transparent() const { return transparent_; } + + [[nodiscard]] bool enable_larger_than_screen() const { + return enable_larger_than_screen_; + } NativeWindow* parent() const { return parent_; } bool is_modal() const { return is_modal_; } @@ -478,11 +481,17 @@ class NativeWindow : public base::SupportsUserData, private: static bool PlatformHasClientFrame(); - std::unique_ptr widget_; + std::unique_ptr widget_ = std::make_unique(); static inline int32_t next_id_ = 0; const int32_t window_id_ = ++next_id_; + // Whether window is transparent. + const bool transparent_; + + // Whether window can be resized larger than screen. + const bool enable_larger_than_screen_; + // The content view, weak ref. raw_ptr content_view_ = nullptr; @@ -498,12 +507,6 @@ class NativeWindow : public base::SupportsUserData, // Wayland hosts. const bool has_client_frame_ = PlatformHasClientFrame(); - // Whether window is transparent. - bool transparent_ = false; - - // Whether window can be resized larger than screen. - bool enable_larger_than_screen_ = false; - // The windows has been closed. bool is_closed_ = false; From 63052c45a1d40358517ede5360c6236152ecb09e Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 21 May 2025 15:49:18 -0500 Subject: [PATCH 062/186] refactor: prefer `base::circular_deque` over `std::deque` (#47192) * refactor: use base::circular_deque in ResolveProxyHelper Co-authored-by: Charles Kerr * refactor: use base::circular_deque in GetExtraCrashKeys() refactor: reduce visibility of kMaxCrashKeyValueSize This change is to match Chromium's usage advice from base/containers/README.md: `base:circular_deque` is preferred over `std::deque` to provide consistent performance across platforms. Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/net/resolve_proxy_helper.h | 4 ++-- shell/common/crash_keys.cc | 20 +++++++++----------- 2 files changed, 11 insertions(+), 13 deletions(-) diff --git a/shell/browser/net/resolve_proxy_helper.h b/shell/browser/net/resolve_proxy_helper.h index 20c998be26cfd..8ea5b7ccb3dc9 100644 --- a/shell/browser/net/resolve_proxy_helper.h +++ b/shell/browser/net/resolve_proxy_helper.h @@ -5,10 +5,10 @@ #ifndef ELECTRON_SHELL_BROWSER_NET_RESOLVE_PROXY_HELPER_H_ #define ELECTRON_SHELL_BROWSER_NET_RESOLVE_PROXY_HELPER_H_ -#include #include #include +#include "base/containers/circular_deque.h" #include "base/memory/raw_ptr.h" #include "base/memory/ref_counted.h" #include "mojo/public/cpp/bindings/receiver.h" @@ -66,7 +66,7 @@ class ResolveProxyHelper // Self-reference. Owned as long as there's an outstanding proxy lookup. scoped_refptr owned_self_; - std::deque pending_requests_; + base::circular_deque pending_requests_; // Receiver for the currently in-progress request, if any. mojo::Receiver receiver_{this}; diff --git a/shell/common/crash_keys.cc b/shell/common/crash_keys.cc index 3066ac5f01c82..a9232caf0b39b 100644 --- a/shell/common/crash_keys.cc +++ b/shell/common/crash_keys.cc @@ -5,11 +5,11 @@ #include "shell/common/crash_keys.h" #include -#include #include #include #include "base/command_line.h" +#include "base/containers/circular_deque.h" #include "base/environment.h" #include "base/no_destructor.h" #include "base/strings/strcat.h" @@ -28,19 +28,17 @@ namespace electron::crash_keys { namespace { -constexpr size_t kMaxCrashKeyValueSize = 20320; -static_assert(kMaxCrashKeyValueSize < crashpad::Annotation::kValueMaxSize, - "max crash key value length above what crashpad supports"); - -using ExtraCrashKeys = - std::deque>; -ExtraCrashKeys& GetExtraCrashKeys() { - static base::NoDestructor extra_keys; +auto& GetExtraCrashKeys() { + constexpr size_t kMaxCrashKeyValueSize = 20320; + static_assert(kMaxCrashKeyValueSize < crashpad::Annotation::kValueMaxSize, + "max crash key value length above what crashpad supports"); + using CrashKeyString = crash_reporter::CrashKeyString; + static base::NoDestructor> extra_keys; return *extra_keys; } -std::deque& GetExtraCrashKeyNames() { - static base::NoDestructor> crash_key_names; +auto& GetExtraCrashKeyNames() { + static base::NoDestructor> crash_key_names; return *crash_key_names; } From e53a7c7c00d4b981ccb5db870edc72b567067ac0 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 22 May 2025 00:01:17 -0500 Subject: [PATCH 063/186] fix: remove extra 'suspend'/'resume' handling from `powerMonitor` (#47188) fix: remove extra 'suspend'/'resume' handling from powerMonitor Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .../api/electron_api_power_monitor_mac.mm | 23 ------------------- .../api/electron_api_power_monitor_win.cc | 12 ---------- 2 files changed, 35 deletions(-) diff --git a/shell/browser/api/electron_api_power_monitor_mac.mm b/shell/browser/api/electron_api_power_monitor_mac.mm index 347d0d17d7bc2..76801e71c0abb 100644 --- a/shell/browser/api/electron_api_power_monitor_mac.mm +++ b/shell/browser/api/electron_api_power_monitor_mac.mm @@ -34,17 +34,6 @@ - (id)init { selector:@selector(onScreenUnlocked:) name:@"com.apple.screenIsUnlocked" object:nil]; - // A notification that the workspace posts before the machine goes to sleep. - [distributed_center addObserver:self - selector:@selector(isSuspending:) - name:NSWorkspaceWillSleepNotification - object:nil]; - // A notification that the workspace posts when the machine wakes from - // sleep. - [distributed_center addObserver:self - selector:@selector(isResuming:) - name:NSWorkspaceDidWakeNotification - object:nil]; NSNotificationCenter* shared_center = [[NSWorkspace sharedWorkspace] notificationCenter]; @@ -73,18 +62,6 @@ - (void)addEmitter:(electron::api::PowerMonitor*)monitor_ { self->emitters.push_back(monitor_); } -- (void)isSuspending:(NSNotification*)notify { - for (auto* emitter : self->emitters) { - emitter->Emit("suspend"); - } -} - -- (void)isResuming:(NSNotification*)notify { - for (auto* emitter : self->emitters) { - emitter->Emit("resume"); - } -} - - (void)onScreenLocked:(NSNotification*)notification { for (auto* emitter : self->emitters) { emitter->Emit("lock-screen"); diff --git a/shell/browser/api/electron_api_power_monitor_win.cc b/shell/browser/api/electron_api_power_monitor_win.cc index 7668234bb3ef4..40da9224527c2 100644 --- a/shell/browser/api/electron_api_power_monitor_win.cc +++ b/shell/browser/api/electron_api_power_monitor_win.cc @@ -88,18 +88,6 @@ LRESULT CALLBACK PowerMonitor::WndProc(HWND hwnd, base::Unretained(this))); } } - } else if (message == WM_POWERBROADCAST) { - if (wparam == PBT_APMRESUMEAUTOMATIC) { - content::GetUIThreadTaskRunner({})->PostTask( - FROM_HERE, - base::BindOnce([](PowerMonitor* pm) { pm->Emit("resume"); }, - base::Unretained(this))); - } else if (wparam == PBT_APMSUSPEND) { - content::GetUIThreadTaskRunner({})->PostTask( - FROM_HERE, - base::BindOnce([](PowerMonitor* pm) { pm->Emit("suspend"); }, - base::Unretained(this))); - } } return ::DefWindowProc(hwnd, message, wparam, lparam); } From 6a16fc3144617ce3ec19a237b212bc062792a1e6 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 22 May 2025 12:37:27 +0200 Subject: [PATCH 064/186] build(dev-deps): update @electron/lint-roller and markdownlint-cli2 (#47145) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- .github/workflows/archaeologist-dig.yml | 2 +- .../pipeline-segment-electron-build.yml | 2 +- .../pipeline-segment-electron-test.yml | 2 +- .markdownlint-cli2.jsonc | 3 +- package.json | 4 +- yarn.lock | 459 +++++++++--------- 6 files changed, 245 insertions(+), 227 deletions(-) diff --git a/.github/workflows/archaeologist-dig.yml b/.github/workflows/archaeologist-dig.yml index 06595ad342c8b..4be9246226ce8 100644 --- a/.github/workflows/archaeologist-dig.yml +++ b/.github/workflows/archaeologist-dig.yml @@ -15,7 +15,7 @@ jobs: - name: Setup Node.js/npm uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 with: - node-version: 20.11.x + node-version: 20.19.x - name: Setting Up Dig Site run: | echo "remote: ${{ github.event.pull_request.head.repo.clone_url }}" diff --git a/.github/workflows/pipeline-segment-electron-build.yml b/.github/workflows/pipeline-segment-electron-build.yml index 2b62c9bf7dbee..ac7d2e78c939f 100644 --- a/.github/workflows/pipeline-segment-electron-build.yml +++ b/.github/workflows/pipeline-segment-electron-build.yml @@ -104,7 +104,7 @@ jobs: if: ${{ inputs.target-platform == 'macos' }} uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 with: - node-version: 20.11.x + node-version: 20.19.x cache: yarn cache-dependency-path: src/electron/yarn.lock - name: Install Dependencies diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index 2336664fca8be..17cf3f2398b98 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -81,7 +81,7 @@ jobs: if: ${{ inputs.target-platform == 'win' }} uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 with: - node-version: 20.11.x + node-version: 20.19.x - name: Add TCC permissions on macOS if: ${{ inputs.target-platform == 'macos' }} run: | diff --git a/.markdownlint-cli2.jsonc b/.markdownlint-cli2.jsonc index aa44ae70b8780..11be56cea63f2 100644 --- a/.markdownlint-cli2.jsonc +++ b/.markdownlint-cli2.jsonc @@ -1,6 +1,7 @@ { "config": { "extends": "@electron/lint-roller/configs/markdownlint.json", + "descriptive-link-text": false, "link-image-style": { "autolink": false, "shortcut": false @@ -26,6 +27,6 @@ "no-newline-in-links": true }, "customRules": [ - "@electron/lint-roller/markdownlint-rules/" + "./node_modules/@electron/lint-roller/markdownlint-rules/index.mjs" ] } diff --git a/package.json b/package.json index d27cc1b4dd847..709d9147ed438 100644 --- a/package.json +++ b/package.json @@ -9,7 +9,7 @@ "@electron/docs-parser": "^2.0.0", "@electron/fiddle-core": "^1.3.4", "@electron/github-app-auth": "^2.2.1", - "@electron/lint-roller": "^2.4.0", + "@electron/lint-roller": "^3.0.0", "@electron/typescript-definitions": "^9.1.2", "@octokit/rest": "^20.0.2", "@primer/octicons": "^10.0.0", @@ -40,7 +40,7 @@ "got": "^11.8.5", "husky": "^8.0.1", "lint-staged": "^10.2.11", - "markdownlint-cli2": "^0.13.0", + "markdownlint-cli2": "^0.18.0", "minimist": "^1.2.8", "null-loader": "^4.0.1", "pre-flight": "^2.0.0", diff --git a/yarn.lock b/yarn.lock index cb940d319816e..67d472fe02555 100644 --- a/yarn.lock +++ b/yarn.lock @@ -263,26 +263,23 @@ "@octokit/auth-app" "^4.0.13" "@octokit/rest" "^19.0.11" -"@electron/lint-roller@^2.4.0": - version "2.4.0" - resolved "https://registry.yarnpkg.com/@electron/lint-roller/-/lint-roller-2.4.0.tgz#67ab5911400ec1e6a842153acc59613a9522d233" - integrity sha512-U1FDBpNxVbu9TlL8O0F9mmaEimINtdr6RB6gGNVm1aBqOvLs579w0k4aqyYqDIV20HHcuWh/287sll6ou8Pfcw== +"@electron/lint-roller@^3.0.0": + version "3.0.0" + resolved "https://registry.yarnpkg.com/@electron/lint-roller/-/lint-roller-3.0.0.tgz#1c1604f9fe87ace82142d8bd25b5c5f0d1e08003" + integrity sha512-YdbWKivSZj+J0yjJhzACU6yXuah0VQMcyijKOaVxX6qG5J/df75oCt/jyuOpRr0HRtz62DaHphEnzGRhTFx9FA== dependencies: "@dsanders11/vscode-markdown-languageservice" "^0.3.0" ajv "^8.16.0" - balanced-match "^2.0.0" - glob "^8.1.0" + balanced-match "^3.0.1" + glob "^10.4.5" hast-util-from-html "^2.0.1" - markdown-it "^13.0.1" - markdownlint-cli "^0.40.0" + markdown-it "^14.1.0" mdast-util-from-markdown "^1.3.0" - minimist "^1.2.8" - rimraf "^4.4.1" standard "^17.0.0" unist-util-visit "^4.1.2" vscode-languageserver "^8.1.0" vscode-languageserver-textdocument "^1.0.8" - vscode-uri "^3.0.7" + vscode-uri "^3.0.8" yaml "^2.4.5" "@electron/typescript-definitions@^9.1.2": @@ -924,6 +921,11 @@ dependencies: "@types/node" "*" +"@types/katex@^0.16.0": + version "0.16.7" + resolved "https://registry.yarnpkg.com/@types/katex/-/katex-0.16.7.tgz#03ab680ab4fa4fbc6cb46ecf987ecad5d8019868" + integrity sha512-HMwFiRujE5PjrgwHQ25+bsLJgowjGjm5Z8FVSf0N6PwgJrwxH0QxzHYDcKsTfV3wva0vzrpqMTJS2jXPr5BMEQ== + "@types/keyv@*": version "3.1.4" resolved "https://registry.yarnpkg.com/@types/keyv/-/keyv-3.1.4.tgz#3ccdb1c6751b0c7e52300bcdacd5bcbf8faa75b6" @@ -1624,10 +1626,10 @@ balanced-match@^1.0.0: resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee" integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== -balanced-match@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-2.0.0.tgz#dc70f920d78db8b858535795867bf48f820633d9" - integrity sha512-1ugUSr8BHXRnK23KfuYS+gVMC3LB8QGH9W1iGtDPsNWoQbgtXSExkBu2aDR4epiGWZOjZsj6lDl/N/AqqTC3UA== +balanced-match@^3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-3.0.1.tgz#e854b098724b15076384266497392a271f4a26a0" + integrity sha512-vjtV3hiLqYDNRoiAv0zC4QaGAMPomEoq83PRmYIofPswwZurCeWR5LByXm7SyoL0Zh5+2z0+HC7jG8gSZJUh0w== base64-js@^1.3.1: version "1.5.1" @@ -1669,7 +1671,7 @@ brace-expansion@^2.0.1: dependencies: balanced-match "^1.0.0" -braces@^3.0.2, braces@^3.0.3, braces@~3.0.2: +braces@^3.0.3, braces@~3.0.2: version "3.0.3" resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.3.tgz#490332f40919452272d55a8480adc0c441358789" integrity sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA== @@ -1824,6 +1826,11 @@ character-entities-legacy@^2.0.0: resolved "https://registry.yarnpkg.com/character-entities-legacy/-/character-entities-legacy-2.0.0.tgz#57f4d00974c696e8f74e9f493e7fcb75b44d7ee7" integrity sha512-YwaEtEvWLpFa6Wh3uVLrvirA/ahr9fki/NUd/Bd4OR6EdJ8D22hovYQEOUCBfQfcqnC4IAMGMsHXY1eXgL4ZZA== +character-entities-legacy@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz#76bc83a90738901d7bc223a9e93759fdd560125b" + integrity sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ== + character-entities@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/character-entities/-/character-entities-2.0.0.tgz#508355fcc8c73893e0909efc1a44d28da2b6fdf3" @@ -1990,10 +1997,10 @@ commander@^5.0.0, commander@^5.1.0: resolved "https://registry.yarnpkg.com/commander/-/commander-5.1.0.tgz#46abbd1652f8e059bddaef99bbdcb2ad9cf179ae" integrity sha512-P0CysNDQ7rtVw4QIQtm+MRxV66vKFSvlsQvGYXZWR3qFU0jlMKHZZZgw8e+8DSah4UDKMqnknRDQz+xuQXQ/Zg== -commander@~12.0.0: - version "12.0.0" - resolved "https://registry.yarnpkg.com/commander/-/commander-12.0.0.tgz#b929db6df8546080adfd004ab215ed48cf6f2592" - integrity sha512-MwVNWlYjDTtOjX5PiD7o5pK0UrFU/OYgcJfjjK4RaHZETNtjJqrZa9Y9ds88+A+f+d5lv+561eZ+yCKoS3gbAA== +commander@^8.3.0: + version "8.3.0" + resolved "https://registry.yarnpkg.com/commander/-/commander-8.3.0.tgz#4837ea1b2da67b9c616a67afbb0fafee567bca66" + integrity sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww== compress-brotli@^1.3.8: version "1.3.8" @@ -2115,11 +2122,6 @@ deep-eql@^5.0.1: resolved "https://registry.yarnpkg.com/deep-eql/-/deep-eql-5.0.2.tgz#4b756d8d770a9257300825d52a2c2cff99c3a341" integrity sha512-h5k/5U50IJJFpzfL6nO9jaaumfjO/f2NjK/oYB2Djzm4p9L+3T9qWpZqZ2hAbLPuuYq9wrU08WQyBTL5GbPk5Q== -deep-extend@^0.6.0: - version "0.6.0" - resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.6.0.tgz#c4fa7c95404a17a9c3e8ca7e1537312b736330ac" - integrity sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA== - deep-is@^0.1.3: version "0.1.3" resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.3.tgz#b369d6fb5dbc13eecf524f91b070feedc357cf34" @@ -2293,11 +2295,6 @@ entities@^4.4.0: resolved "https://registry.yarnpkg.com/entities/-/entities-4.5.0.tgz#5d268ea5e7113ec74c4d033b79ea5a35a488fb48" integrity sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw== -entities@~3.0.1: - version "3.0.1" - resolved "https://registry.yarnpkg.com/entities/-/entities-3.0.1.tgz#2b887ca62585e96db3903482d336c1006c3001d4" - integrity sha512-WiyBqoomrwMdFG1e0kqvASYfnlb0lp8M5o5Fw2OFq1hNZxxcNk8Ik0Xm7LxzBhuidnZB/UtBqVCgUz3kBOP51Q== - env-paths@^2.2.0, env-paths@^2.2.1: version "2.2.1" resolved "https://registry.yarnpkg.com/env-paths/-/env-paths-2.2.1.tgz#420399d416ce1fbe9bc0a07c62fa68d67fd0f8f2" @@ -2939,6 +2936,17 @@ fast-glob@^3.3.2: merge2 "^1.3.0" micromatch "^4.0.4" +fast-glob@^3.3.3: + version "3.3.3" + resolved "https://registry.yarnpkg.com/fast-glob/-/fast-glob-3.3.3.tgz#d06d585ce8dba90a16b0505c543c3ccfb3aeb818" + integrity sha512-7MptL8U0cqcFdzIzwOTHoilX9x5BrNqye7Z/LuC7kCMRio1EMSyqRK3BEAUD7sXRq4iT4AzTVuZdhgQ2TCvYLg== + dependencies: + "@nodelib/fs.stat" "^2.0.2" + "@nodelib/fs.walk" "^1.2.3" + glob-parent "^5.1.2" + merge2 "^1.3.0" + micromatch "^4.0.8" + fast-json-stable-stringify@^2.0.0: version "2.1.0" resolved "https://registry.yarnpkg.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz#874bf69c6f404c2b5d99c481341399fd55892633" @@ -3172,11 +3180,6 @@ get-stdin@^8.0.0: resolved "https://registry.yarnpkg.com/get-stdin/-/get-stdin-8.0.0.tgz#cbad6a73feb75f6eeb22ba9e01f89aa28aa97a53" integrity sha512-sY22aA6xchAzprjyqmSEQv4UbAAzRN0L2dQB0NlN5acTTK9Don6nhoc3eAbUnpZiCANAMfd/+40kVdKfFygohg== -get-stdin@~9.0.0: - version "9.0.0" - resolved "https://registry.yarnpkg.com/get-stdin/-/get-stdin-9.0.0.tgz#3983ff82e03d56f1b2ea0d3e60325f39d703a575" - integrity sha512-dVKBjfWisLAicarI2Sf+JuBE/DghV4UzNAVe9yhEJuzeREd3JhOTE9cUaJTeSa77fsbQUK3pcOpJfM59+VKZaA== - get-stream@^5.0.0, get-stream@^5.1.0: version "5.2.0" resolved "https://registry.yarnpkg.com/get-stream/-/get-stream-5.2.0.tgz#4966a1795ee5ace65e706c4b7beb71257d6e22d3" @@ -3234,7 +3237,7 @@ glob-to-regexp@^0.4.1: resolved "https://registry.yarnpkg.com/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz#c75297087c851b9a578bd217dd59a92f59fe546e" integrity sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw== -glob@^10.0.0, glob@^10.2.2: +glob@^10.0.0, glob@^10.2.2, glob@^10.4.5: version "10.4.5" resolved "https://registry.yarnpkg.com/glob/-/glob-10.4.5.tgz#f4d9f0b90ffdbab09c9d77f5f29b4262517b0956" integrity sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg== @@ -3258,17 +3261,6 @@ glob@^7.0.0, glob@^7.1.3, glob@^7.1.6: once "^1.3.0" path-is-absolute "^1.0.0" -glob@^8.1.0: - version "8.1.0" - resolved "https://registry.yarnpkg.com/glob/-/glob-8.1.0.tgz#d388f656593ef708ee3e34640fdfb99a9fd1c33e" - integrity sha512-r8hpEjiQEYlF2QU0df3dS+nxxSIreXQS1qRhMJM0Q5NDdR386C7jb7Hwwod8Fgiuex+k0GFjgft18yvxm5XoCQ== - dependencies: - fs.realpath "^1.0.0" - inflight "^1.0.4" - inherits "2" - minimatch "^5.0.1" - once "^1.3.0" - glob@^9.2.0: version "9.3.5" resolved "https://registry.yarnpkg.com/glob/-/glob-9.3.5.tgz#ca2ed8ca452781a3009685607fdf025a899dfe21" @@ -3279,17 +3271,6 @@ glob@^9.2.0: minipass "^4.2.4" path-scurry "^1.6.1" -glob@~10.3.12: - version "10.3.12" - resolved "https://registry.yarnpkg.com/glob/-/glob-10.3.12.tgz#3a65c363c2e9998d220338e88a5f6ac97302960b" - integrity sha512-TCNv8vJ+xz4QiqTpfOJA7HvYv+tNIRHKfUWw/q+v2jdgN4ebz+KY9tGx5J4rHP0o84mNP+ApH66HRX8us3Khqg== - dependencies: - foreground-child "^3.1.0" - jackspeak "^2.3.6" - minimatch "^9.0.1" - minipass "^7.0.4" - path-scurry "^1.10.2" - global-agent@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/global-agent/-/global-agent-3.0.0.tgz#ae7cd31bd3583b93c5a16437a1afe27cc33a1ab6" @@ -3328,17 +3309,17 @@ globalthis@^1.0.1, globalthis@^1.0.3: dependencies: define-properties "^1.1.3" -globby@14.0.1: - version "14.0.1" - resolved "https://registry.yarnpkg.com/globby/-/globby-14.0.1.tgz#a1b44841aa7f4c6d8af2bc39951109d77301959b" - integrity sha512-jOMLD2Z7MAhyG8aJpNOpmziMOP4rPLcc95oQPKXBazW82z+CEgPFBQvEpRUa1KeIMUJo4Wsm+q6uzO/Q/4BksQ== +globby@14.1.0: + version "14.1.0" + resolved "https://registry.yarnpkg.com/globby/-/globby-14.1.0.tgz#138b78e77cf5a8d794e327b15dce80bf1fb0a73e" + integrity sha512-0Ia46fDOaT7k4og1PDW4YbodWWr3scS2vAr2lTbsplOt2WkKp0vQbkI9wKis/T5LV/dqPjO3bpS/z6GTJB82LA== dependencies: "@sindresorhus/merge-streams" "^2.1.0" - fast-glob "^3.3.2" - ignore "^5.2.4" - path-type "^5.0.0" + fast-glob "^3.3.3" + ignore "^7.0.3" + path-type "^6.0.0" slash "^5.1.0" - unicorn-magic "^0.1.0" + unicorn-magic "^0.3.0" gopd@^1.0.1: version "1.0.1" @@ -3556,7 +3537,7 @@ ieee754@^1.2.1: resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.2.1.tgz#8eb7a10a63fff25d15a57b001586d177d1b0d352" integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA== -ignore@^5.0.0, ignore@^5.1.1, ignore@^5.2.0, ignore@^5.2.4, ignore@~5.3.1: +ignore@^5.0.0, ignore@^5.1.1, ignore@^5.2.0, ignore@^5.2.4: version "5.3.1" resolved "https://registry.yarnpkg.com/ignore/-/ignore-5.3.1.tgz#5073e554cd42c5b33b394375f538b8593e34d4ef" integrity sha512-5Fytz/IraMjqpwfd34ke28PTVMjZjJG2MPn5t7OE4eUCUNf8BAa7b5WUS9/Qvr6mwOQS7Mk6vdsMno5he+T8Xw== @@ -3566,6 +3547,11 @@ ignore@^5.3.1: resolved "https://registry.yarnpkg.com/ignore/-/ignore-5.3.2.tgz#3cd40e729f3643fd87cb04e50bf0eb722bc596f5" integrity sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g== +ignore@^7.0.3: + version "7.0.4" + resolved "https://registry.yarnpkg.com/ignore/-/ignore-7.0.4.tgz#a12c70d0f2607c5bf508fb65a40c75f037d7a078" + integrity sha512-gJzzk+PQNznz8ysRrC0aOkBNVRBDtE1n53IqyqEf3PXrYwomFs5q4pGMizBMJF+ykh03insJ27hB8gSrD2Hn8A== + import-fresh@^3.1.0, import-fresh@^3.2.1: version "3.3.0" resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-3.3.0.tgz#37162c25fcb9ebaa2e6e53d5b4d88ce17d9e0c2b" @@ -3615,11 +3601,6 @@ ini@^4.1.2, ini@^4.1.3: resolved "https://registry.yarnpkg.com/ini/-/ini-4.1.3.tgz#4c359675a6071a46985eb39b14e4a2c0ec98a795" integrity sha512-X7rqawQBvfdjS10YU1y1YVreA3SsLrW9dX2CewP2EbBJM4ypVNLDkO5y04gejPwKIY9lR+7r9gn3rFPt/kmWFg== -ini@~4.1.0: - version "4.1.2" - resolved "https://registry.yarnpkg.com/ini/-/ini-4.1.2.tgz#7f646dbd9caea595e61f88ef60bfff8b01f8130a" - integrity sha512-AMB1mvwR1pyBFY/nSevUX6y8nJWS63/SzUKD3JyQn97s4xgIdgQPT75IRouIiBAN4yLQBUShNYVW0+UG25daCw== - internal-slot@^1.0.3, internal-slot@^1.0.5: version "1.0.5" resolved "https://registry.yarnpkg.com/internal-slot/-/internal-slot-1.0.5.tgz#f2a2ee21f668f8627a4667f309dc0f4fb6674986" @@ -3958,15 +3939,6 @@ isobject@^3.0.1: resolved "https://registry.yarnpkg.com/isobject/-/isobject-3.0.1.tgz#4e431e92b11a9731636aa1f9c8d1ccbcfdab78df" integrity sha1-TkMekrEalzFjaqH5yNHMvP2reN8= -jackspeak@^2.3.6: - version "2.3.6" - resolved "https://registry.yarnpkg.com/jackspeak/-/jackspeak-2.3.6.tgz#647ecc472238aee4b06ac0e461acc21a8c505ca8" - integrity sha512-N3yCS/NegsOBokc8GAdM8UcmfsKiSS8cipheD/nivzr700H+nsMOxJjQnvwOcRYVuFkdH0wGUvW2WbXGmrZGbQ== - dependencies: - "@isaacs/cliui" "^8.0.2" - optionalDependencies: - "@pkgjs/parseargs" "^0.11.0" - jackspeak@^3.1.2: version "3.4.3" resolved "https://registry.yarnpkg.com/jackspeak/-/jackspeak-3.4.3.tgz#8833a9d89ab4acde6188942bd1c53b6390ed5a8a" @@ -4067,10 +4039,10 @@ json5@^2.0.0, json5@^2.1.2: resolved "https://registry.yarnpkg.com/json5/-/json5-2.2.3.tgz#78cd6f1a19bdc12b73db5ad0c61efd66c1e29283" integrity sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg== -jsonc-parser@3.2.1, jsonc-parser@~3.2.1: - version "3.2.1" - resolved "https://registry.yarnpkg.com/jsonc-parser/-/jsonc-parser-3.2.1.tgz#031904571ccf929d7670ee8c547545081cb37f1a" - integrity sha512-AilxAyFOAcK5wA1+LeaySVBrHsGQvUFCDWXKpZjzaL0PqW+xfBOttn8GNtWKFWqneyMZj41MWF9Kl6iPWLwgOA== +jsonc-parser@3.3.1: + version "3.3.1" + resolved "https://registry.yarnpkg.com/jsonc-parser/-/jsonc-parser-3.3.1.tgz#f2a524b4f7fd11e3d791e559977ad60b98b798b4" + integrity sha512-HUgH65KyejrUFPvHFPbqOY0rsFip3Bo5wb4ngvdi1EpCYWUQDC5V+Y7mZws+DLkr4M//zQJoanu1SP+87Dv1oQ== jsonfile@^4.0.0: version "4.0.0" @@ -4088,11 +4060,6 @@ jsonfile@^6.0.1: optionalDependencies: graceful-fs "^4.1.6" -jsonpointer@5.0.1: - version "5.0.1" - resolved "https://registry.yarnpkg.com/jsonpointer/-/jsonpointer-5.0.1.tgz#2110e0af0900fd37467b5907ecd13a7884a1b559" - integrity sha512-p/nXbhSEcu3pZRdkW1OfJhpsVtW1gd4Wa1fnQc9YLiTfAjn0312eMKimbdIQzuZl9aa9xUGaRlP9T/CJE/ditQ== - jsonwebtoken@^9.0.0: version "9.0.0" resolved "https://registry.yarnpkg.com/jsonwebtoken/-/jsonwebtoken-9.0.0.tgz#d0faf9ba1cc3a56255fe49c0961a67e520c1926d" @@ -4128,6 +4095,13 @@ jws@^3.2.2: jwa "^1.4.1" safe-buffer "^5.0.1" +katex@^0.16.0: + version "0.16.22" + resolved "https://registry.yarnpkg.com/katex/-/katex-0.16.22.tgz#d2b3d66464b1e6d69e6463b28a86ced5a02c5ccd" + integrity sha512-XCHRdUw4lf3SKBaJe4EvgqIuWwkPSo9XoeO8GjQW94Bp7TWv9hNhzZjZ+OH9yf1UmLygb7DIT5GSFQiyt16zYg== + dependencies: + commander "^8.3.0" + keyv@^4.0.0: version "4.3.1" resolved "https://registry.yarnpkg.com/keyv/-/keyv-4.3.1.tgz#7970672f137d987945821b1a07b524ce5a4edd27" @@ -4164,13 +4138,6 @@ lines-and-columns@^2.0.3: resolved "https://registry.yarnpkg.com/lines-and-columns/-/lines-and-columns-2.0.4.tgz#d00318855905d2660d8c0822e3f5a4715855fc42" integrity sha512-wM1+Z03eypVAVUCE7QdSqpVIvelbOakn1M0bPDoA4SGWPx3sNDVUiMo3L6To6WWGClB7VyXnhQ4Sn7gxiJbE6A== -linkify-it@^4.0.1: - version "4.0.1" - resolved "https://registry.yarnpkg.com/linkify-it/-/linkify-it-4.0.1.tgz#01f1d5e508190d06669982ba31a7d9f56a5751ec" - integrity sha512-C7bfi1UZmoj8+PQx22XyeXCuBlokoyWQL5pWSP+EI6nzRylyThouddufc2c1NDIcP9k5agmN9fLpA7VNJfIiqw== - dependencies: - uc.micro "^1.0.1" - linkify-it@^5.0.0: version "5.0.0" resolved "https://registry.yarnpkg.com/linkify-it/-/linkify-it-5.0.0.tgz#9ef238bfa6dc70bd8e7f9572b52d369af569b421" @@ -4385,63 +4352,37 @@ markdown-it@14.1.0, markdown-it@^14.1.0: punycode.js "^2.3.1" uc.micro "^2.1.0" -markdown-it@^13.0.1: - version "13.0.1" - resolved "https://registry.yarnpkg.com/markdown-it/-/markdown-it-13.0.1.tgz#c6ecc431cacf1a5da531423fc6a42807814af430" - integrity sha512-lTlxriVoy2criHP0JKRhO2VDG9c2ypWCsT237eDiLqi09rmbKoUetyGHq2uOIRoRS//kfoJckS0eUzzkDR+k2Q== - dependencies: - argparse "^2.0.1" - entities "~3.0.1" - linkify-it "^4.0.1" - mdurl "^1.0.1" - uc.micro "^1.0.5" - -markdownlint-cli2-formatter-default@0.0.4: - version "0.0.4" - resolved "https://registry.yarnpkg.com/markdownlint-cli2-formatter-default/-/markdownlint-cli2-formatter-default-0.0.4.tgz#81e26b0a50409c0357c6f0d38d8246946b236fab" - integrity sha512-xm2rM0E+sWgjpPn1EesPXx5hIyrN2ddUnUwnbCsD/ONxYtw3PX6LydvdH6dciWAoFDpwzbHM1TO7uHfcMd6IYg== +markdownlint-cli2-formatter-default@0.0.5: + version "0.0.5" + resolved "https://registry.yarnpkg.com/markdownlint-cli2-formatter-default/-/markdownlint-cli2-formatter-default-0.0.5.tgz#b8fde4e127f9a9c0596e6d45eed352dd0aa0ff98" + integrity sha512-4XKTwQ5m1+Txo2kuQ3Jgpo/KmnG+X90dWt4acufg6HVGadTUG5hzHF/wssp9b5MBYOMCnZ9RMPaU//uHsszF8Q== -markdownlint-cli2@^0.13.0: - version "0.13.0" - resolved "https://registry.yarnpkg.com/markdownlint-cli2/-/markdownlint-cli2-0.13.0.tgz#691cab01994295b4b8c87aa0485c0b1e0f792289" - integrity sha512-Pg4nF7HlopU97ZXtrcVISWp3bdsuc5M0zXyLp2/sJv2zEMlInrau0ZKK482fQURzVezJzWBpNmu4u6vGAhij+g== +markdownlint-cli2@^0.18.0: + version "0.18.0" + resolved "https://registry.yarnpkg.com/markdownlint-cli2/-/markdownlint-cli2-0.18.0.tgz#eb8007f8f276399197c65966d3428e777a9ecbf3" + integrity sha512-gHvff1KxBxTqaN1F5cTxRSxBipx+Qkki430tyg0wPxty67iQNZzxREZkXy8ltbj7ObMz1eYD4aspnYXfV0sHAw== dependencies: - globby "14.0.1" + globby "14.1.0" js-yaml "4.1.0" - jsonc-parser "3.2.1" - markdownlint "0.34.0" - markdownlint-cli2-formatter-default "0.0.4" - micromatch "4.0.5" - -markdownlint-cli@^0.40.0: - version "0.40.0" - resolved "https://registry.yarnpkg.com/markdownlint-cli/-/markdownlint-cli-0.40.0.tgz#57678cabd543c654d2ea88f752e9ac058b31c207" - integrity sha512-JXhI3dRQcaqwiFYpPz6VJ7aKYheD53GmTz9y4D/d0F1MbZDGOp9pqKlbOfUX/pHP/iAoeiE4wYRmk8/kjLakxA== - dependencies: - commander "~12.0.0" - get-stdin "~9.0.0" - glob "~10.3.12" - ignore "~5.3.1" - js-yaml "^4.1.0" - jsonc-parser "~3.2.1" - jsonpointer "5.0.1" - markdownlint "~0.34.0" - minimatch "~9.0.4" - run-con "~1.3.2" - toml "~3.0.0" - -markdownlint-micromark@0.1.9: - version "0.1.9" - resolved "https://registry.yarnpkg.com/markdownlint-micromark/-/markdownlint-micromark-0.1.9.tgz#4876996b60d4dceb3a02f4eee2d3a366eb9569fa" - integrity sha512-5hVs/DzAFa8XqYosbEAEg6ok6MF2smDj89ztn9pKkCtdKHVdPQuGMH7frFfYL9mLkvfFe4pTyAMffLbjf3/EyA== - -markdownlint@0.34.0, markdownlint@~0.34.0: - version "0.34.0" - resolved "https://registry.yarnpkg.com/markdownlint/-/markdownlint-0.34.0.tgz#bbc2047c952d1644269009a69ba227ed597b23fa" - integrity sha512-qwGyuyKwjkEMOJ10XN6OTKNOVYvOIi35RNvDLNxTof5s8UmyGHlCdpngRHoRGNvQVGuxO3BJ7uNSgdeX166WXw== - dependencies: + jsonc-parser "3.3.1" markdown-it "14.1.0" - markdownlint-micromark "0.1.9" + markdownlint "0.38.0" + markdownlint-cli2-formatter-default "0.0.5" + micromatch "4.0.8" + +markdownlint@0.38.0: + version "0.38.0" + resolved "https://registry.yarnpkg.com/markdownlint/-/markdownlint-0.38.0.tgz#862ca9d08f3a28f4149bd388ac369bb95865534e" + integrity sha512-xaSxkaU7wY/0852zGApM8LdlIfGCW8ETZ0Rr62IQtAnUMlMuifsg09vWJcNYeL4f0anvr8Vo4ZQar8jGpV0btQ== + dependencies: + micromark "4.0.2" + micromark-core-commonmark "2.0.3" + micromark-extension-directive "4.0.0" + micromark-extension-gfm-autolink-literal "2.1.0" + micromark-extension-gfm-footnote "2.1.0" + micromark-extension-gfm-table "2.1.1" + micromark-extension-math "3.1.0" + micromark-util-types "2.0.2" matcher-collection@^1.0.0: version "1.1.2" @@ -4542,11 +4483,6 @@ mdast-util-to-string@^4.0.0: dependencies: "@types/mdast" "^4.0.0" -mdurl@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/mdurl/-/mdurl-1.0.1.tgz#fe85b2ec75a59037f2adfec100fd6c601761152e" - integrity sha1-/oWy7HWlkDfyrf7BAP1sYBdhFS4= - mdurl@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/mdurl/-/mdurl-2.0.0.tgz#80676ec0433025dd3e17ee983d0fe8de5a2237e0" @@ -4570,6 +4506,28 @@ merge2@^1.3.0: resolved "https://registry.yarnpkg.com/merge2/-/merge2-1.4.1.tgz#4368892f885e907455a6fd7dc55c0c9d404990ae" integrity sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg== +micromark-core-commonmark@2.0.3: + version "2.0.3" + resolved "https://registry.yarnpkg.com/micromark-core-commonmark/-/micromark-core-commonmark-2.0.3.tgz#c691630e485021a68cf28dbc2b2ca27ebf678cd4" + integrity sha512-RDBrHEMSxVFLg6xvnXmb1Ayr2WzLAWjeSATAoxwKYJV94TeNavgoIdA0a9ytzDSVzBy2YKFK+emCPOEibLeCrg== + dependencies: + decode-named-character-reference "^1.0.0" + devlop "^1.0.0" + micromark-factory-destination "^2.0.0" + micromark-factory-label "^2.0.0" + micromark-factory-space "^2.0.0" + micromark-factory-title "^2.0.0" + micromark-factory-whitespace "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-chunked "^2.0.0" + micromark-util-classify-character "^2.0.0" + micromark-util-html-tag-name "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-resolve-all "^2.0.0" + micromark-util-subtokenize "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + micromark-core-commonmark@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/micromark-core-commonmark/-/micromark-core-commonmark-1.0.0.tgz#b767fa7687c205c224175bf067796360a3830350" @@ -4613,6 +4571,67 @@ micromark-core-commonmark@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" +micromark-extension-directive@4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/micromark-extension-directive/-/micromark-extension-directive-4.0.0.tgz#af389e33fe0654c15f8466b73a0f5af598d00368" + integrity sha512-/C2nqVmXXmiseSSuCdItCMho7ybwwop6RrrRPk0KbOHW21JKoCldC+8rFOaundDoRBUWBnJJcxeA/Kvi34WQXg== + dependencies: + devlop "^1.0.0" + micromark-factory-space "^2.0.0" + micromark-factory-whitespace "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + parse-entities "^4.0.0" + +micromark-extension-gfm-autolink-literal@2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/micromark-extension-gfm-autolink-literal/-/micromark-extension-gfm-autolink-literal-2.1.0.tgz#6286aee9686c4462c1e3552a9d505feddceeb935" + integrity sha512-oOg7knzhicgQ3t4QCjCWgTmfNhvQbDDnJeVu9v81r7NltNCVmhPy1fJRX27pISafdjL+SVc4d3l48Gb6pbRypw== + dependencies: + micromark-util-character "^2.0.0" + micromark-util-sanitize-uri "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm-footnote@2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/micromark-extension-gfm-footnote/-/micromark-extension-gfm-footnote-2.1.0.tgz#4dab56d4e398b9853f6fe4efac4fc9361f3e0750" + integrity sha512-/yPhxI1ntnDNsiHtzLKYnE3vf9JZ6cAisqVDauhp4CEHxlb4uoOTxOCJ+9s51bIB8U1N1FJ1RXOKTIlD5B/gqw== + dependencies: + devlop "^1.0.0" + micromark-core-commonmark "^2.0.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-sanitize-uri "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-gfm-table@2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/micromark-extension-gfm-table/-/micromark-extension-gfm-table-2.1.1.tgz#fac70bcbf51fe65f5f44033118d39be8a9b5940b" + integrity sha512-t2OU/dXXioARrC6yWfJ4hqB7rct14e8f7m0cbI5hUmDyyIlwv5vEtooptH8INkbLzOatzKuVbQmAYcbWoyz6Dg== + dependencies: + devlop "^1.0.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + +micromark-extension-math@3.1.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/micromark-extension-math/-/micromark-extension-math-3.1.0.tgz#c42ee3b1dd5a9a03584e83dd8f08e3de510212c1" + integrity sha512-lvEqd+fHjATVs+2v/8kg9i5Q0AP2k85H0WUOwpIVvUML8BapsMvh1XAogmQjOCsLpoKRCVQqEkQBB3NhVBcsOg== + dependencies: + "@types/katex" "^0.16.0" + devlop "^1.0.0" + katex "^0.16.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + micromark-factory-destination@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/micromark-factory-destination/-/micromark-factory-destination-1.0.0.tgz#fef1cb59ad4997c496f887b6977aa3034a5a277e" @@ -4899,6 +4918,11 @@ micromark-util-symbol@^2.0.0: resolved "https://registry.yarnpkg.com/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz#12225c8f95edf8b17254e47080ce0862d5db8044" integrity sha512-8JZt9ElZ5kyTnO94muPxIGS8oyElRJaiJO8EzV6ZSyGQ1Is8xwl4Q45qU5UOg+bGH4AikWziz0iN4sFLWs8PGw== +micromark-util-types@2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/micromark-util-types/-/micromark-util-types-2.0.2.tgz#f00225f5f5a0ebc3254f96c36b6605c4b393908e" + integrity sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA== + micromark-util-types@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/micromark-util-types/-/micromark-util-types-1.0.0.tgz#0ebdfaea3fa7c15fc82b1e06ea1ef0152d0fb2f0" @@ -4909,6 +4933,29 @@ micromark-util-types@^2.0.0: resolved "https://registry.yarnpkg.com/micromark-util-types/-/micromark-util-types-2.0.0.tgz#63b4b7ffeb35d3ecf50d1ca20e68fc7caa36d95e" integrity sha512-oNh6S2WMHWRZrmutsRmDDfkzKtxF+bc2VxLC9dvtrDIRFln627VsFP6fLMgTryGDljgLPjkrzQSDcPrjPyDJ5w== +micromark@4.0.2: + version "4.0.2" + resolved "https://registry.yarnpkg.com/micromark/-/micromark-4.0.2.tgz#91395a3e1884a198e62116e33c9c568e39936fdb" + integrity sha512-zpe98Q6kvavpCr1NPVSCMebCKfD7CA2NqZ+rykeNhONIJBpc1tFKt9hucLGwha3jNTNI8lHpctWJWoimVF4PfA== + dependencies: + "@types/debug" "^4.0.0" + debug "^4.0.0" + decode-named-character-reference "^1.0.0" + devlop "^1.0.0" + micromark-core-commonmark "^2.0.0" + micromark-factory-space "^2.0.0" + micromark-util-character "^2.0.0" + micromark-util-chunked "^2.0.0" + micromark-util-combine-extensions "^2.0.0" + micromark-util-decode-numeric-character-reference "^2.0.0" + micromark-util-encode "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-resolve-all "^2.0.0" + micromark-util-sanitize-uri "^2.0.0" + micromark-util-subtokenize "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + micromark@^3.0.0: version "3.0.3" resolved "https://registry.yarnpkg.com/micromark/-/micromark-3.0.3.tgz#4c9f76fce8ba68eddf8730bb4fee2041d699d5b7" @@ -4954,15 +5001,7 @@ micromark@^4.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromatch@4.0.5: - version "4.0.5" - resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.5.tgz#bc8999a7cbbf77cdc89f132f6e467051b49090c6" - integrity sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA== - dependencies: - braces "^3.0.2" - picomatch "^2.3.1" - -micromatch@^4.0.0, micromatch@^4.0.2, micromatch@^4.0.4: +micromatch@4.0.8, micromatch@^4.0.0, micromatch@^4.0.2, micromatch@^4.0.4, micromatch@^4.0.8: version "4.0.8" resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.8.tgz#d66fa18f3a47076789320b9b1af32bd86d9fa202" integrity sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA== @@ -5014,13 +5053,6 @@ minimatch@^3.0.2, minimatch@^3.0.4, minimatch@^3.0.5, minimatch@^3.1.2: dependencies: brace-expansion "^1.1.7" -minimatch@^5.0.1: - version "5.1.1" - resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.1.1.tgz#6c9dffcf9927ff2a31e74b5af11adf8b9604b022" - integrity sha512-362NP+zlprccbEt/SkxKfRMHnNY85V74mVnpUpNyr3F35covl09Kec7/sEFLt3RA4oXmewtoaanoIf67SE5Y5g== - dependencies: - brace-expansion "^2.0.1" - minimatch@^8.0.2: version "8.0.4" resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-8.0.4.tgz#847c1b25c014d4e9a7f68aaf63dedd668a626229" @@ -5035,13 +5067,6 @@ minimatch@^9.0.0, minimatch@^9.0.4: dependencies: brace-expansion "^2.0.1" -minimatch@^9.0.1, minimatch@~9.0.4: - version "9.0.4" - resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-9.0.4.tgz#8e49c731d1749cbec05050ee5145147b32496a51" - integrity sha512-KqWh+VchfxcMNRAJjj2tnsSJdNbHsVgnkBhTNrW7AjVo6OvLtxw8zfT9oLw1JSohlFzJ8jCoTgaoXvJ+kHt6fw== - dependencies: - brace-expansion "^2.0.1" - minimatch@~3.0.4: version "3.0.8" resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.8.tgz#5e6a59bd11e2ab0de1cfb843eb2d82e546c321c1" @@ -5081,7 +5106,7 @@ minipass@^5.0.0: resolved "https://registry.yarnpkg.com/minipass/-/minipass-6.0.2.tgz#542844b6c4ce95b202c0995b0a471f1229de4c81" integrity sha512-MzWSV5nYVT7mVyWCwn2o7JH13w2TBRmmSqSRCKzTw+lmft9X4z+3wjvs06Tzijo5z4W/kahUCDpRXTF+ZrmF/w== -"minipass@^5.0.0 || ^6.0.2 || ^7.0.0", minipass@^7.0.4: +"minipass@^5.0.0 || ^6.0.2 || ^7.0.0": version "7.1.0" resolved "https://registry.yarnpkg.com/minipass/-/minipass-7.1.0.tgz#b545f84af94e567386770159302ca113469c80b8" integrity sha512-oGZRv2OT1lO2UF1zUcwdTb3wqUwI0kBGTgt/T7OdSj6M6N5m3o5uPf0AIW6lVxGGoiWUR7e2AwTE+xiwK8WQig== @@ -5471,6 +5496,19 @@ parse-entities@^3.0.0: is-decimal "^2.0.0" is-hexadecimal "^2.0.0" +parse-entities@^4.0.0: + version "4.0.2" + resolved "https://registry.yarnpkg.com/parse-entities/-/parse-entities-4.0.2.tgz#61d46f5ed28e4ee62e9ddc43d6b010188443f159" + integrity sha512-GG2AQYWoLgL877gQIKeRPGO1xF9+eG1ujIb5soS5gPvLQ1y2o8FL90w2QWNdf9I361Mpp7726c+lj3U0qK1uGw== + dependencies: + "@types/unist" "^2.0.0" + character-entities-legacy "^3.0.0" + character-reference-invalid "^2.0.0" + decode-named-character-reference "^1.0.0" + is-alphanumerical "^2.0.0" + is-decimal "^2.0.0" + is-hexadecimal "^2.0.0" + parse-gitignore@^0.4.0: version "0.4.0" resolved "https://registry.yarnpkg.com/parse-gitignore/-/parse-gitignore-0.4.0.tgz#abf702e4b900524fff7902b683862857b63f93fe" @@ -5545,14 +5583,6 @@ path-parse@^1.0.6, path-parse@^1.0.7: resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735" integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw== -path-scurry@^1.10.2: - version "1.10.2" - resolved "https://registry.yarnpkg.com/path-scurry/-/path-scurry-1.10.2.tgz#8f6357eb1239d5fa1da8b9f70e9c080675458ba7" - integrity sha512-7xTavNy5RQXnsjANvVvMkEjvloOinkAjv/Z6Ildz9v2RinZ4SBKTWFOVRbaF8p0vpHnyjV/UwNDdKuUv6M5qcA== - dependencies: - lru-cache "^10.2.0" - minipass "^5.0.0 || ^6.0.2 || ^7.0.0" - path-scurry@^1.11.1: version "1.11.1" resolved "https://registry.yarnpkg.com/path-scurry/-/path-scurry-1.11.1.tgz#7960a668888594a0720b12a911d1a742ab9f11d2" @@ -5574,10 +5604,10 @@ path-type@^4.0.0: resolved "https://registry.yarnpkg.com/path-type/-/path-type-4.0.0.tgz#84ed01c0a7ba380afe09d90a8c180dcd9d03043b" integrity sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw== -path-type@^5.0.0: - version "5.0.0" - resolved "https://registry.yarnpkg.com/path-type/-/path-type-5.0.0.tgz#14b01ed7aea7ddf9c7c3f46181d4d04f9c785bb8" - integrity sha512-5HviZNaZcfqP95rwpv+1HDgUamezbqdSYTyzjTvwtJSnIH+3vnbmWsItli8OFEndS984VT55M3jduxZbX351gg== +path-type@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/path-type/-/path-type-6.0.0.tgz#2f1bb6791a91ce99194caede5d6c5920ed81eb51" + integrity sha512-Vj7sf++t5pBD637NSfkxpHSMfWaeig5+DKWLhcqIYx6mWQz5hdJTGDVMQiJcw1ZYkhs7AazKDGpRVji1LJCZUQ== pathval@^2.0.0: version "2.0.0" @@ -6556,16 +6586,6 @@ roarr@^2.15.3: semver-compare "^1.0.0" sprintf-js "^1.1.2" -run-con@~1.3.2: - version "1.3.2" - resolved "https://registry.yarnpkg.com/run-con/-/run-con-1.3.2.tgz#755860a10ce326a96b509485fcea50b4d03754e8" - integrity sha512-CcfE+mYiTcKEzg0IqS08+efdnH0oJ3zV0wSUFBNrMHMuxCtXvBCLzCJHatwuXDcu/RlhjTziTo/a1ruQik6/Yg== - dependencies: - deep-extend "^0.6.0" - ini "~4.1.0" - minimist "^1.2.8" - strip-json-comments "~3.1.1" - run-parallel@^1.1.9: version "1.1.9" resolved "https://registry.yarnpkg.com/run-parallel/-/run-parallel-1.1.9.tgz#c9dd3a7cf9f4b2c4b6244e173a6ed866e61dd679" @@ -7042,7 +7062,14 @@ stringify-object@^3.3.0: is-obj "^1.0.1" is-regexp "^1.0.0" -"strip-ansi-cjs@npm:strip-ansi@^6.0.1", strip-ansi@^6.0.0, strip-ansi@^6.0.1: +"strip-ansi-cjs@npm:strip-ansi@^6.0.1": + version "6.0.1" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" + integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== + dependencies: + ansi-regex "^5.0.1" + +strip-ansi@^6.0.0, strip-ansi@^6.0.1: version "6.0.1" resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== @@ -7073,7 +7100,7 @@ strip-indent@^3.0.0: dependencies: min-indent "^1.0.0" -strip-json-comments@^3.1.1, strip-json-comments@~3.1.1: +strip-json-comments@^3.1.1: version "3.1.1" resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== @@ -7229,11 +7256,6 @@ to-regex-range@^5.0.1: dependencies: is-number "^7.0.0" -toml@~3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/toml/-/toml-3.0.0.tgz#342160f1af1904ec9d204d03a5d61222d762c5ee" - integrity sha512-y/mWCZinnvxjTKYhJ+pYxwD0mRLVvOtdS2Awbgxln6iEnt4rk0yBxeSBHkGJcPucRiG0e55mwWp+g/05rsrd6w== - tr46@~0.0.3: version "0.0.3" resolved "https://registry.yarnpkg.com/tr46/-/tr46-0.0.3.tgz#8184fd347dac9cdc185992f3a6622e14b9d9ab6a" @@ -7414,11 +7436,6 @@ typescript@^5.6.2: resolved "https://registry.yarnpkg.com/typescript/-/typescript-5.6.2.tgz#d1de67b6bef77c41823f822df8f0b3bcff60a5a0" integrity sha512-NW8ByodCSNCwZeghjN3o+JX5OFH0Ojg6sadjEKY4huZ52TqbJTJnDo5+Tw98lSy63NZvi4n+ez5m2u5d4PkZyw== -uc.micro@^1.0.1, uc.micro@^1.0.5: - version "1.0.6" - resolved "https://registry.yarnpkg.com/uc.micro/-/uc.micro-1.0.6.tgz#9c411a802a409a91fc6cf74081baba34b24499ac" - integrity sha512-8Y75pvTYkLJW2hWQHXxoqRgV7qb9B+9vFEtidML+7koHUFapnVJAZ6cKs+Qjz5Aw3aZWHMC6u0wJE3At+nSGwA== - uc.micro@^2.0.0, uc.micro@^2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/uc.micro/-/uc.micro-2.1.0.tgz#f8d3f7d0ec4c3dea35a7e3c8efa4cb8b45c9e7ee" @@ -7439,10 +7456,10 @@ undici-types@~6.19.2: resolved "https://registry.yarnpkg.com/undici-types/-/undici-types-6.19.8.tgz#35111c9d1437ab83a7cdc0abae2f26d88eda0a02" integrity sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw== -unicorn-magic@^0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/unicorn-magic/-/unicorn-magic-0.1.0.tgz#1bb9a51c823aaf9d73a8bfcd3d1a23dde94b0ce4" - integrity sha512-lRfVq8fE8gz6QMBuDM6a+LO3IAzTi05H6gCVaUpir2E1Rwpo4ZUog45KpNXKC/Mn3Yb9UDuHumeFTo9iV/D9FQ== +unicorn-magic@^0.3.0: + version "0.3.0" + resolved "https://registry.yarnpkg.com/unicorn-magic/-/unicorn-magic-0.3.0.tgz#4efd45c85a69e0dd576d25532fbfa22aa5c8a104" + integrity sha512-+QBBXBCvifc56fsbuxZQ6Sic3wqqc3WWaqxs58gvJrcOuN83HGTCwz3oS5phzU9LthRNE9VrJCFCLUgHeeFnfA== unified-args@^11.0.0: version "11.0.1" @@ -7809,10 +7826,10 @@ vscode-uri@^3.0.3: resolved "https://registry.yarnpkg.com/vscode-uri/-/vscode-uri-3.0.6.tgz#5e6e2e1a4170543af30151b561a41f71db1d6f91" integrity sha512-fmL7V1eiDBFRRnu+gfRWTzyPpNIHJTc4mWnFkwBUmO9U3KPgJAmTx7oxi2bl/Rh6HLdU7+4C9wlj0k2E4AdKFQ== -vscode-uri@^3.0.7: - version "3.0.7" - resolved "https://registry.yarnpkg.com/vscode-uri/-/vscode-uri-3.0.7.tgz#6d19fef387ee6b46c479e5fb00870e15e58c1eb8" - integrity sha512-eOpPHogvorZRobNqJGhapa0JdwaxpjVvyBp0QIUMRMSf8ZAlqOdEquKuRmw9Qwu0qXtJIWqFtMkmvJjUZmMjVA== +vscode-uri@^3.0.8: + version "3.1.0" + resolved "https://registry.yarnpkg.com/vscode-uri/-/vscode-uri-3.1.0.tgz#dd09ec5a66a38b5c3fffc774015713496d14e09c" + integrity sha512-/BpdSx+yCQGnCvecbyXdxHDkuk55/G3xwnC0GqY4gmQ3j+A+g8kzzgB4Nk/SINjqn6+waqw3EgbVF2QKExkRxQ== walk-sync@^0.3.2: version "0.3.4" From 3e07a0e9a33e94dfb8435113db1f3841cae90c02 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 22 May 2025 11:16:37 -0400 Subject: [PATCH 065/186] build: fix depot tool pathing on Windows (#47205) build: properly set depot_tools pathing for Windows Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- .github/actions/install-build-tools/action.yml | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/.github/actions/install-build-tools/action.yml b/.github/actions/install-build-tools/action.yml index 5890e46e45d50..12cffbc835519 100644 --- a/.github/actions/install-build-tools/action.yml +++ b/.github/actions/install-build-tools/action.yml @@ -15,12 +15,16 @@ runs: fi export BUILD_TOOLS_SHA=6e8526315ea3b4828882497e532b8340e64e053c npm i -g @electron/build-tools + # Update depot_tools to ensure python e d update_depot_tools e auto-update disable + # Disable further updates of depot_tools e d auto-update disable if [ "$(expr substr $(uname -s) 1 10)" == "MSYS_NT-10" ]; then e d cipd.bat --version cp "C:\Python311\python.exe" "C:\Python311\python3.exe" - fi - echo "$HOME/.electron_build_tools/third_party/depot_tools" >> $GITHUB_PATH - echo "$HOME/.electron_build_tools/third_party/depot_tools/python-bin" >> $GITHUB_PATH + echo "C:\Users\ContainerAdministrator\.electron_build_tools\third_party\depot_tools" >> $GITHUB_PATH + else + echo "$HOME/.electron_build_tools/third_party/depot_tools" >> $GITHUB_PATH + echo "$HOME/.electron_build_tools/third_party/depot_tools/python-bin" >> $GITHUB_PATH + fi \ No newline at end of file From 6e7271ff7efbd226f5e2c473c5a0f748a9df760a Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 22 May 2025 10:30:16 -0700 Subject: [PATCH 066/186] ci: add problem matcher for clang output (#47220) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- .github/actions/build-electron/action.yml | 6 ++++++ .github/problem-matchers/clang.json | 18 ++++++++++++++++++ 2 files changed, 24 insertions(+) create mode 100644 .github/problem-matchers/clang.json diff --git a/.github/actions/build-electron/action.yml b/.github/actions/build-electron/action.yml index 58a416e01f404..350866638b46d 100644 --- a/.github/actions/build-electron/action.yml +++ b/.github/actions/build-electron/action.yml @@ -38,6 +38,9 @@ runs: run: | GN_APPENDED_ARGS="$GN_EXTRA_ARGS target_cpu=\"x64\" v8_snapshot_toolchain=\"//build/toolchain/mac:clang_x64\"" echo "GN_EXTRA_ARGS=$GN_APPENDED_ARGS" >> $GITHUB_ENV + - name: Add Clang problem matcher + shell: bash + run: echo "::add-matcher::src/electron/.github/problem-matchers/clang.json" - name: Build Electron ${{ inputs.step-suffix }} shell: bash run: | @@ -199,6 +202,9 @@ runs: e build --target electron:libcxx_headers_zip -j $NUMBER_OF_NINJA_PROCESSES e build --target electron:libcxxabi_headers_zip -j $NUMBER_OF_NINJA_PROCESSES e build --target electron:libcxx_objects_zip -j $NUMBER_OF_NINJA_PROCESSES + - name: Remove Clang problem matcher + shell: bash + run: echo "::remove-matcher owner=clang::" - name: Generate TypeScript Definitions ${{ inputs.step-suffix }} if: ${{ inputs.is-release == 'true' }} shell: bash diff --git a/.github/problem-matchers/clang.json b/.github/problem-matchers/clang.json new file mode 100644 index 0000000000000..35cf775305bd5 --- /dev/null +++ b/.github/problem-matchers/clang.json @@ -0,0 +1,18 @@ +{ + "problemMatcher": [ + { + "owner": "clang", + "fromPath": "src/out/Default/args.gn", + "pattern": [ + { + "regexp": "^(.+)[(:](\\d+)[:,](\\d+)\\)?:\\s+(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "column": 3, + "severity": 4, + "message": 5 + } + ] + } + ] +} From b39305af61b573ee397ea1308ae46270637ba392 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 22 May 2025 17:31:08 -0400 Subject: [PATCH 067/186] ci: add problem matcher for patch conflict output (#47225) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- .github/actions/checkout/action.yml | 9 +++++++- .github/problem-matchers/patch-conflict.json | 24 ++++++++++++++++++++ 2 files changed, 32 insertions(+), 1 deletion(-) create mode 100644 .github/problem-matchers/patch-conflict.json diff --git a/.github/actions/checkout/action.yml b/.github/actions/checkout/action.yml index 205eefde25816..b4f6ca7f2126f 100644 --- a/.github/actions/checkout/action.yml +++ b/.github/actions/checkout/action.yml @@ -80,6 +80,9 @@ runs: else echo "The cross mount cache has $freespace_human free space - continuing" fi + - name: Add patch conflict problem matcher + shell: bash + run: echo "::add-matcher::src/electron/.github/problem-matchers/patch-conflict.json" - name: Gclient Sync if: steps.check-cache.outputs.cache_exists == 'false' shell: bash @@ -128,7 +131,11 @@ runs: echo "No changes to patches detected" fi fi - + - name: Remove patch conflict problem matcher + shell: bash + run: | + echo "::remove-matcher owner=merge-conflict::" + echo "::remove-matcher owner=patch-conflict::" # delete all .git directories under src/ except for # third_party/angle/ and third_party/dawn/ because of build time generation of files # gen/angle/commit.h depends on third_party/angle/.git/HEAD diff --git a/.github/problem-matchers/patch-conflict.json b/.github/problem-matchers/patch-conflict.json new file mode 100644 index 0000000000000..e8324448cbbfa --- /dev/null +++ b/.github/problem-matchers/patch-conflict.json @@ -0,0 +1,24 @@ +{ + "problemMatcher": [ + { + "owner": "merge-conflict", + "pattern": [ + { + "regexp": "^CONFLICT\\s\\(\\S+\\): (Merge conflict in \\S+)$", + "message": 1 + } + ] + }, + { + "owner": "patch-conflict", + "pattern": [ + { + "regexp": "^error: (patch failed: (\\S+):(\\d+))$", + "message": 1, + "file": 2, + "line": 3 + } + ] + } + ] +} From c0149676fb94acbb0c9f98d870b1aeb030c0e83a Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sun, 25 May 2025 07:56:50 -0500 Subject: [PATCH 068/186] refactor: use `base::fixed_flat_set` in `NativeWindowViews::SetAlwaysOnTop()` (#47237) refactor: use base::fixed_flat_set in NativeWindowViews::SetAlwaysOnTop() Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window_views.cc | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 008e3f821cfcb..b90133927aee5 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -20,7 +20,7 @@ #include #include -#include "base/containers/contains.h" +#include "base/containers/fixed_flat_set.h" #include "base/memory/raw_ref.h" #include "base/numerics/ranges.h" #include "base/strings/utf_string_conversions.h" @@ -1103,9 +1103,9 @@ void NativeWindowViews::SetAlwaysOnTop(ui::ZOrderLevel z_order, if (z_order != ui::ZOrderLevel::kNormal) { // On macOS the window is placed behind the Dock for the following levels. // Re-use the same names on Windows to make it easier for the user. - static const std::vector levels = { - "floating", "torn-off-menu", "modal-panel", "main-menu", "status"}; - behind_task_bar_ = base::Contains(levels, level); + static constexpr auto levels = base::MakeFixedFlatSet( + {"floating", "torn-off-menu", "modal-panel", "main-menu", "status"}); + behind_task_bar_ = levels.contains(level); } #endif MoveBehindTaskBarIfNeeded(); From 584fa31adc4a405e1d5cc41bcf030c8d3a6fd774 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 26 May 2025 09:45:48 +0200 Subject: [PATCH 069/186] chore: update @electron/lint-roller to 3.1.1 (#47257) * chore: update @electron/lint-roller to 3.1.1 Co-authored-by: David Sanders * docs: fix broken link in breaking-changes.md Co-authored-by: David Sanders * chore: fix for Node.js versions without require(esm) Co-authored-by: David Sanders --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- docs/breaking-changes.md | 2 +- package.json | 2 +- script/lint.js | 3 +- yarn.lock | 328 +++------------------------------------ 4 files changed, 27 insertions(+), 308 deletions(-) diff --git a/docs/breaking-changes.md b/docs/breaking-changes.md index d8e753eb99e52..3a88ed3aee4f9 100644 --- a/docs/breaking-changes.md +++ b/docs/breaking-changes.md @@ -141,7 +141,7 @@ On Linux, the required portal version for file dialogs has been reverted to 3 from 4. Using the `defaultPath` option of the Dialog API is not supported when using portal file chooser dialogs unless the portal backend is version 4 or higher. The `--xdg-portal-required-version` -[command-line switch](/api/command-line-switches.md#--xdg-portal-required-versionversion) +[command-line switch](api/command-line-switches.md#--xdg-portal-required-versionversion) can be used to force a required version for your application. See [#44426](https://github.com/electron/electron/pull/44426) for more details. diff --git a/package.json b/package.json index 709d9147ed438..d2bfd9bfa718f 100644 --- a/package.json +++ b/package.json @@ -9,7 +9,7 @@ "@electron/docs-parser": "^2.0.0", "@electron/fiddle-core": "^1.3.4", "@electron/github-app-auth": "^2.2.1", - "@electron/lint-roller": "^3.0.0", + "@electron/lint-roller": "^3.1.1", "@electron/typescript-definitions": "^9.1.2", "@octokit/rest": "^20.0.2", "@primer/octicons": "^10.0.0", diff --git a/script/lint.js b/script/lint.js index 06f0b7ac305cf..63459f47ef173 100755 --- a/script/lint.js +++ b/script/lint.js @@ -1,7 +1,5 @@ #!/usr/bin/env node -const { getCodeBlocks } = require('@electron/lint-roller/dist/lib/markdown'); - const { GitProcess } = require('dugite'); const { ESLint } = require('eslint'); const minimist = require('minimist'); @@ -281,6 +279,7 @@ const LINTERS = [{ ignoreRoots: ['.git', 'node_modules', 'spec/node_modules'], test: filename => filename.endsWith('.md'), run: async (opts, filenames) => { + const { getCodeBlocks } = await import('@electron/lint-roller/dist/lib/markdown.js'); let errors = false; // Run markdownlint on all Markdown files diff --git a/yarn.lock b/yarn.lock index 67d472fe02555..ad0ed30e207f1 100644 --- a/yarn.lock +++ b/yarn.lock @@ -263,10 +263,10 @@ "@octokit/auth-app" "^4.0.13" "@octokit/rest" "^19.0.11" -"@electron/lint-roller@^3.0.0": - version "3.0.0" - resolved "https://registry.yarnpkg.com/@electron/lint-roller/-/lint-roller-3.0.0.tgz#1c1604f9fe87ace82142d8bd25b5c5f0d1e08003" - integrity sha512-YdbWKivSZj+J0yjJhzACU6yXuah0VQMcyijKOaVxX6qG5J/df75oCt/jyuOpRr0HRtz62DaHphEnzGRhTFx9FA== +"@electron/lint-roller@^3.1.1": + version "3.1.1" + resolved "https://registry.yarnpkg.com/@electron/lint-roller/-/lint-roller-3.1.1.tgz#a301f1f84ef836e7800c655fa3b5efcda82f95b0" + integrity sha512-s30rM5ksvVuks7bsTKxQALmqY/8/KxJieGWs3QKru2nL4UJlN5PTTbxXh42qCqQ1LRTfE/cZ5CDjF9nomc3mYw== dependencies: "@dsanders11/vscode-markdown-languageservice" "^0.3.0" ajv "^8.16.0" @@ -274,9 +274,9 @@ glob "^10.4.5" hast-util-from-html "^2.0.1" markdown-it "^14.1.0" - mdast-util-from-markdown "^1.3.0" + mdast-util-from-markdown "^2.0.2" standard "^17.0.0" - unist-util-visit "^4.1.2" + unist-util-visit "^5.0.0" vscode-languageserver "^8.1.0" vscode-languageserver-textdocument "^1.0.8" vscode-uri "^3.0.8" @@ -946,13 +946,6 @@ "@types/linkify-it" "^5" "@types/mdurl" "^2" -"@types/mdast@^3.0.0": - version "3.0.7" - resolved "https://registry.yarnpkg.com/@types/mdast/-/mdast-3.0.7.tgz#cba63d0cc11eb1605cea5c0ad76e02684394166b" - integrity sha512-YwR7OK8aPmaBvMMUi+pZXBNoW2unbVbfok4YRqGMJBe1dpDlzpRkJrYEYmvjxgs5JhuQmKfDexrN98u941Zasg== - dependencies: - "@types/unist" "*" - "@types/mdast@^4.0.0": version "4.0.4" resolved "https://registry.yarnpkg.com/@types/mdast/-/mdast-4.0.4.tgz#7ccf72edd2f1aa7dd3437e180c64373585804dd6" @@ -1821,11 +1814,6 @@ chalk@^5.0.0, chalk@^5.3.0: resolved "https://registry.yarnpkg.com/chalk/-/chalk-5.3.0.tgz#67c20a7ebef70e7f3970a01f90fa210cb6860385" integrity sha512-dLitG79d+GV1Nb/VYcCDFivJeK1hiukt9QjRNVOsUtTy1rR1YJsmpGGTZ3qJos+uw7WmWF4wUwBd9jxjocFC2w== -character-entities-legacy@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/character-entities-legacy/-/character-entities-legacy-2.0.0.tgz#57f4d00974c696e8f74e9f493e7fcb75b44d7ee7" - integrity sha512-YwaEtEvWLpFa6Wh3uVLrvirA/ahr9fki/NUd/Bd4OR6EdJ8D22hovYQEOUCBfQfcqnC4IAMGMsHXY1eXgL4ZZA== - character-entities-legacy@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz#76bc83a90738901d7bc223a9e93759fdd560125b" @@ -2185,11 +2173,6 @@ diff@^3.1.0: resolved "https://registry.yarnpkg.com/diff/-/diff-3.5.0.tgz#800c0dd1e0a8bfbc95835c202ad220fe317e5a12" integrity sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA== -diff@^5.0.0: - version "5.1.0" - resolved "https://registry.yarnpkg.com/diff/-/diff-5.1.0.tgz#bc52d298c5ea8df9194800224445ed43ffc87e40" - integrity sha512-D+mk+qE8VC/PAUrlAU34N+VfXev0ghe5ywmpqrawphmVZc1bEfn56uo9qpyGp1p4xpzOHkSW4ztBd6L7Xx4ACw== - doctrine@^2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-2.1.0.tgz#5cd01fc101621b42c4cd7f5d1a66243716d3f39d" @@ -4115,11 +4098,6 @@ kind-of@^6.0.2: resolved "https://registry.yarnpkg.com/kind-of/-/kind-of-6.0.3.tgz#07c05034a6c349fa06e24fa35aa76db4580ce4dd" integrity sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw== -kleur@^4.0.3: - version "4.1.5" - resolved "https://registry.yarnpkg.com/kleur/-/kleur-4.1.5.tgz#95106101795f7050c6c650f350c683febddb1780" - integrity sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ== - levn@^0.4.1: version "0.4.1" resolved "https://registry.yarnpkg.com/levn/-/levn-0.4.1.tgz#ae4562c007473b932a6200d403268dd2fffc6ade" @@ -4403,24 +4381,6 @@ mdast-comment-marker@^1.0.0: resolved "https://registry.yarnpkg.com/mdast-comment-marker/-/mdast-comment-marker-1.1.1.tgz#9c9c18e1ed57feafc1965d92b028f37c3c8da70d" integrity sha512-TWZDaUtPLwKX1pzDIY48MkSUQRDwX/HqbTB4m3iYdL/zosi/Z6Xqfdv0C0hNVKvzrPjZENrpWDt4p4odeVO0Iw== -mdast-util-from-markdown@^1.3.0: - version "1.3.0" - resolved "https://registry.yarnpkg.com/mdast-util-from-markdown/-/mdast-util-from-markdown-1.3.0.tgz#0214124154f26154a2b3f9d401155509be45e894" - integrity sha512-HN3W1gRIuN/ZW295c7zi7g9lVBllMgZE40RxCX37wrTPWXCWtpvOZdfnuK+1WNpvZje6XuJeI3Wnb4TJEUem+g== - dependencies: - "@types/mdast" "^3.0.0" - "@types/unist" "^2.0.0" - decode-named-character-reference "^1.0.0" - mdast-util-to-string "^3.1.0" - micromark "^3.0.0" - micromark-util-decode-numeric-character-reference "^1.0.0" - micromark-util-decode-string "^1.0.0" - micromark-util-normalize-identifier "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - unist-util-stringify-position "^3.0.0" - uvu "^0.5.0" - mdast-util-from-markdown@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.1.tgz#32a6e8f512b416e1f51eb817fc64bd867ebcd9cc" @@ -4439,6 +4399,24 @@ mdast-util-from-markdown@^2.0.0: micromark-util-types "^2.0.0" unist-util-stringify-position "^4.0.0" +mdast-util-from-markdown@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/mdast-util-from-markdown/-/mdast-util-from-markdown-2.0.2.tgz#4850390ca7cf17413a9b9a0fbefcd1bc0eb4160a" + integrity sha512-uZhTV/8NBuw0WHkPTrCqDOl0zVe1BIng5ZtHoDk49ME1qqcjYmmLmOf0gELgcRMxN4w2iuIeVso5/6QymSrgmA== + dependencies: + "@types/mdast" "^4.0.0" + "@types/unist" "^3.0.0" + decode-named-character-reference "^1.0.0" + devlop "^1.0.0" + mdast-util-to-string "^4.0.0" + micromark "^4.0.0" + micromark-util-decode-numeric-character-reference "^2.0.0" + micromark-util-decode-string "^2.0.0" + micromark-util-normalize-identifier "^2.0.0" + micromark-util-symbol "^2.0.0" + micromark-util-types "^2.0.0" + unist-util-stringify-position "^4.0.0" + mdast-util-heading-style@^1.0.2: version "1.0.5" resolved "https://registry.yarnpkg.com/mdast-util-heading-style/-/mdast-util-heading-style-1.0.5.tgz#81b2e60d76754198687db0e8f044e42376db0426" @@ -4471,11 +4449,6 @@ mdast-util-to-string@^1.0.2: resolved "https://registry.yarnpkg.com/mdast-util-to-string/-/mdast-util-to-string-1.0.6.tgz#7d85421021343b33de1552fc71cb8e5b4ae7536d" integrity sha512-868pp48gUPmZIhfKrLbaDneuzGiw3OTDjHc5M1kAepR2CWBJ+HpEsm252K4aXdiP5coVZaJPOqGtVU6Po8xnXg== -mdast-util-to-string@^3.1.0: - version "3.1.0" - resolved "https://registry.yarnpkg.com/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz#56c506d065fbf769515235e577b5a261552d56e9" - integrity sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA== - mdast-util-to-string@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/mdast-util-to-string/-/mdast-util-to-string-4.0.0.tgz#7a5121475556a04e7eddeb67b264aae79d312814" @@ -4528,27 +4501,6 @@ micromark-core-commonmark@2.0.3: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-core-commonmark@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-core-commonmark/-/micromark-core-commonmark-1.0.0.tgz#b767fa7687c205c224175bf067796360a3830350" - integrity sha512-y9g7zymcKRBHM/aNBekstvs/Grpf+y4OEBULUTYvGZcusnp+JeOxmilJY4GMpo2/xY7iHQL9fjz5pD9pSAud9A== - dependencies: - micromark-factory-destination "^1.0.0" - micromark-factory-label "^1.0.0" - micromark-factory-space "^1.0.0" - micromark-factory-title "^1.0.0" - micromark-factory-whitespace "^1.0.0" - micromark-util-character "^1.0.0" - micromark-util-chunked "^1.0.0" - micromark-util-classify-character "^1.0.0" - micromark-util-html-tag-name "^1.0.0" - micromark-util-normalize-identifier "^1.0.0" - micromark-util-resolve-all "^1.0.0" - micromark-util-subtokenize "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - parse-entities "^3.0.0" - micromark-core-commonmark@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/micromark-core-commonmark/-/micromark-core-commonmark-2.0.1.tgz#9a45510557d068605c6e9a80f282b2bb8581e43d" @@ -4632,15 +4584,6 @@ micromark-extension-math@3.1.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-factory-destination@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-factory-destination/-/micromark-factory-destination-1.0.0.tgz#fef1cb59ad4997c496f887b6977aa3034a5a277e" - integrity sha512-eUBA7Rs1/xtTVun9TmV3gjfPz2wEwgK5R5xcbIM5ZYAtvGF6JkyaDsj0agx8urXnO31tEO6Ug83iVH3tdedLnw== - dependencies: - micromark-util-character "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - micromark-factory-destination@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-factory-destination/-/micromark-factory-destination-2.0.0.tgz#857c94debd2c873cba34e0445ab26b74f6a6ec07" @@ -4650,15 +4593,6 @@ micromark-factory-destination@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-factory-label@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-factory-label/-/micromark-factory-label-1.0.0.tgz#b316ec479b474232973ff13b49b576f84a6f2cbb" - integrity sha512-XWEucVZb+qBCe2jmlOnWr6sWSY6NHx+wtpgYFsm4G+dufOf6tTQRRo0bdO7XSlGPu5fyjpJenth6Ksnc5Mwfww== - dependencies: - micromark-util-character "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - micromark-factory-label@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-factory-label/-/micromark-factory-label-2.0.0.tgz#17c5c2e66ce39ad6f4fc4cbf40d972f9096f726a" @@ -4669,14 +4603,6 @@ micromark-factory-label@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-factory-space@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-factory-space/-/micromark-factory-space-1.0.0.tgz#cebff49968f2b9616c0fcb239e96685cb9497633" - integrity sha512-qUmqs4kj9a5yBnk3JMLyjtWYN6Mzfcx8uJfi5XAveBniDevmZasdGBba5b4QsvRcAkmvGo5ACmSUmyGiKTLZew== - dependencies: - micromark-util-character "^1.0.0" - micromark-util-types "^1.0.0" - micromark-factory-space@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-factory-space/-/micromark-factory-space-2.0.0.tgz#5e7afd5929c23b96566d0e1ae018ae4fcf81d030" @@ -4685,16 +4611,6 @@ micromark-factory-space@^2.0.0: micromark-util-character "^2.0.0" micromark-util-types "^2.0.0" -micromark-factory-title@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-factory-title/-/micromark-factory-title-1.0.0.tgz#708f7a8044f34a898c0efdb4f55e4da66b537273" - integrity sha512-flvC7Gx0dWVWorXuBl09Cr3wB5FTuYec8pMGVySIp2ZlqTcIjN/lFohZcP0EG//krTptm34kozHk7aK/CleCfA== - dependencies: - micromark-factory-space "^1.0.0" - micromark-util-character "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - micromark-factory-title@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-factory-title/-/micromark-factory-title-2.0.0.tgz#726140fc77892af524705d689e1cf06c8a83ea95" @@ -4705,16 +4621,6 @@ micromark-factory-title@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-factory-whitespace@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-factory-whitespace/-/micromark-factory-whitespace-1.0.0.tgz#e991e043ad376c1ba52f4e49858ce0794678621c" - integrity sha512-Qx7uEyahU1lt1RnsECBiuEbfr9INjQTGa6Err+gF3g0Tx4YEviPbqqGKNv/NrBaE7dVHdn1bVZKM/n5I/Bak7A== - dependencies: - micromark-factory-space "^1.0.0" - micromark-util-character "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - micromark-factory-whitespace@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-factory-whitespace/-/micromark-factory-whitespace-2.0.0.tgz#9e92eb0f5468083381f923d9653632b3cfb5f763" @@ -4725,14 +4631,6 @@ micromark-factory-whitespace@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-util-character@^1.0.0: - version "1.1.0" - resolved "https://registry.yarnpkg.com/micromark-util-character/-/micromark-util-character-1.1.0.tgz#d97c54d5742a0d9611a68ca0cd4124331f264d86" - integrity sha512-agJ5B3unGNJ9rJvADMJ5ZiYjBRyDpzKAOk01Kpi1TKhlT1APx3XZk6eN7RtSz1erbWHC2L8T3xLZ81wdtGRZzg== - dependencies: - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - micromark-util-character@^2.0.0: version "2.1.0" resolved "https://registry.yarnpkg.com/micromark-util-character/-/micromark-util-character-2.1.0.tgz#31320ace16b4644316f6bf057531689c71e2aee1" @@ -4741,13 +4639,6 @@ micromark-util-character@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-util-chunked@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-chunked/-/micromark-util-chunked-1.0.0.tgz#5b40d83f3d53b84c4c6bce30ed4257e9a4c79d06" - integrity sha512-5e8xTis5tEZKgesfbQMKRCyzvffRRUX+lK/y+DvsMFdabAicPkkZV6gO+FEWi9RfuKKoxxPwNL+dFF0SMImc1g== - dependencies: - micromark-util-symbol "^1.0.0" - micromark-util-chunked@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-chunked/-/micromark-util-chunked-2.0.0.tgz#e51f4db85fb203a79dbfef23fd41b2f03dc2ef89" @@ -4755,15 +4646,6 @@ micromark-util-chunked@^2.0.0: dependencies: micromark-util-symbol "^2.0.0" -micromark-util-classify-character@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-classify-character/-/micromark-util-classify-character-1.0.0.tgz#cbd7b447cb79ee6997dd274a46fc4eb806460a20" - integrity sha512-F8oW2KKrQRb3vS5ud5HIqBVkCqQi224Nm55o5wYLzY/9PwHGXC01tr3d7+TqHHz6zrKQ72Okwtvm/xQm6OVNZA== - dependencies: - micromark-util-character "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - micromark-util-classify-character@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-classify-character/-/micromark-util-classify-character-2.0.0.tgz#8c7537c20d0750b12df31f86e976d1d951165f34" @@ -4773,14 +4655,6 @@ micromark-util-classify-character@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-util-combine-extensions@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-combine-extensions/-/micromark-util-combine-extensions-1.0.0.tgz#91418e1e74fb893e3628b8d496085639124ff3d5" - integrity sha512-J8H058vFBdo/6+AsjHp2NF7AJ02SZtWaVUjsayNFeAiydTxUwViQPxN0Hf8dp4FmCQi0UUFovFsEyRSUmFH3MA== - dependencies: - micromark-util-chunked "^1.0.0" - micromark-util-types "^1.0.0" - micromark-util-combine-extensions@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-combine-extensions/-/micromark-util-combine-extensions-2.0.0.tgz#75d6ab65c58b7403616db8d6b31315013bfb7ee5" @@ -4789,13 +4663,6 @@ micromark-util-combine-extensions@^2.0.0: micromark-util-chunked "^2.0.0" micromark-util-types "^2.0.0" -micromark-util-decode-numeric-character-reference@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-1.0.0.tgz#dcc85f13b5bd93ff8d2868c3dba28039d490b946" - integrity sha512-OzO9AI5VUtrTD7KSdagf4MWgHMtET17Ua1fIpXTpuhclCqD8egFWo85GxSGvxgkGS74bEahvtM0WP0HjvV0e4w== - dependencies: - micromark-util-symbol "^1.0.0" - micromark-util-decode-numeric-character-reference@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-2.0.1.tgz#2698bbb38f2a9ba6310e359f99fcb2b35a0d2bd5" @@ -4803,16 +4670,6 @@ micromark-util-decode-numeric-character-reference@^2.0.0: dependencies: micromark-util-symbol "^2.0.0" -micromark-util-decode-string@^1.0.0: - version "1.0.2" - resolved "https://registry.yarnpkg.com/micromark-util-decode-string/-/micromark-util-decode-string-1.0.2.tgz#942252ab7a76dec2dbf089cc32505ee2bc3acf02" - integrity sha512-DLT5Ho02qr6QWVNYbRZ3RYOSSWWFuH3tJexd3dgN1odEuPNxCngTCXJum7+ViRAd9BbdxCvMToPOD/IvVhzG6Q== - dependencies: - decode-named-character-reference "^1.0.0" - micromark-util-character "^1.0.0" - micromark-util-decode-numeric-character-reference "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-decode-string@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-decode-string/-/micromark-util-decode-string-2.0.0.tgz#7dfa3a63c45aecaa17824e656bcdb01f9737154a" @@ -4823,33 +4680,16 @@ micromark-util-decode-string@^2.0.0: micromark-util-decode-numeric-character-reference "^2.0.0" micromark-util-symbol "^2.0.0" -micromark-util-encode@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-encode/-/micromark-util-encode-1.0.0.tgz#c409ecf751a28aa9564b599db35640fccec4c068" - integrity sha512-cJpFVM768h6zkd8qJ1LNRrITfY4gwFt+tziPcIf71Ui8yFzY9wG3snZQqiWVq93PG4Sw6YOtcNiKJfVIs9qfGg== - micromark-util-encode@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-encode/-/micromark-util-encode-2.0.0.tgz#0921ac7953dc3f1fd281e3d1932decfdb9382ab1" integrity sha512-pS+ROfCXAGLWCOc8egcBvT0kf27GoWMqtdarNfDcjb6YLuV5cM3ioG45Ys2qOVqeqSbjaKg72vU+Wby3eddPsA== -micromark-util-html-tag-name@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-html-tag-name/-/micromark-util-html-tag-name-1.0.0.tgz#75737e92fef50af0c6212bd309bc5cb8dbd489ed" - integrity sha512-NenEKIshW2ZI/ERv9HtFNsrn3llSPZtY337LID/24WeLqMzeZhBEE6BQ0vS2ZBjshm5n40chKtJ3qjAbVV8S0g== - micromark-util-html-tag-name@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-html-tag-name/-/micromark-util-html-tag-name-2.0.0.tgz#ae34b01cbe063363847670284c6255bb12138ec4" integrity sha512-xNn4Pqkj2puRhKdKTm8t1YHC/BAjx6CEwRFXntTaRf/x16aqka6ouVoutm+QdkISTlT7e2zU7U4ZdlDLJd2Mcw== -micromark-util-normalize-identifier@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-1.0.0.tgz#4a3539cb8db954bbec5203952bfe8cedadae7828" - integrity sha512-yg+zrL14bBTFrQ7n35CmByWUTFsgst5JhA4gJYoty4Dqzj4Z4Fr/DHekSS5aLfH9bdlfnSvKAWsAgJhIbogyBg== - dependencies: - micromark-util-symbol "^1.0.0" - micromark-util-normalize-identifier@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-2.0.0.tgz#91f9a4e65fe66cc80c53b35b0254ad67aa431d8b" @@ -4857,13 +4697,6 @@ micromark-util-normalize-identifier@^2.0.0: dependencies: micromark-util-symbol "^2.0.0" -micromark-util-resolve-all@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-resolve-all/-/micromark-util-resolve-all-1.0.0.tgz#a7c363f49a0162e931960c44f3127ab58f031d88" - integrity sha512-CB/AGk98u50k42kvgaMM94wzBqozSzDDaonKU7P7jwQIuH2RU0TeBqGYJz2WY1UdihhjweivStrJ2JdkdEmcfw== - dependencies: - micromark-util-types "^1.0.0" - micromark-util-resolve-all@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-resolve-all/-/micromark-util-resolve-all-2.0.0.tgz#189656e7e1a53d0c86a38a652b284a252389f364" @@ -4871,15 +4704,6 @@ micromark-util-resolve-all@^2.0.0: dependencies: micromark-util-types "^2.0.0" -micromark-util-sanitize-uri@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-1.0.0.tgz#27dc875397cd15102274c6c6da5585d34d4f12b2" - integrity sha512-cCxvBKlmac4rxCGx6ejlIviRaMKZc0fWm5HdCHEeDWRSkn44l6NdYVRyU+0nT1XC72EQJMZV8IPHF+jTr56lAg== - dependencies: - micromark-util-character "^1.0.0" - micromark-util-encode "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-sanitize-uri@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-2.0.0.tgz#ec8fbf0258e9e6d8f13d9e4770f9be64342673de" @@ -4889,15 +4713,6 @@ micromark-util-sanitize-uri@^2.0.0: micromark-util-encode "^2.0.0" micromark-util-symbol "^2.0.0" -micromark-util-subtokenize@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-subtokenize/-/micromark-util-subtokenize-1.0.0.tgz#6f006fa719af92776c75a264daaede0fb3943c6a" - integrity sha512-EsnG2qscmcN5XhkqQBZni/4oQbLFjz9yk3ZM/P8a3YUjwV6+6On2wehr1ALx0MxK3+XXXLTzuBKHDFeDFYRdgQ== - dependencies: - micromark-util-chunked "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - micromark-util-subtokenize@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/micromark-util-subtokenize/-/micromark-util-subtokenize-2.0.1.tgz#76129c49ac65da6e479c09d0ec4b5f29ec6eace5" @@ -4908,11 +4723,6 @@ micromark-util-subtokenize@^2.0.0: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark-util-symbol@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-symbol/-/micromark-util-symbol-1.0.0.tgz#91cdbcc9b2a827c0129a177d36241bcd3ccaa34d" - integrity sha512-NZA01jHRNCt4KlOROn8/bGi6vvpEmlXld7EHcRH+aYWUfL3Wc8JLUNNlqUMKa0hhz6GrpUWsHtzPmKof57v0gQ== - micromark-util-symbol@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-symbol/-/micromark-util-symbol-2.0.0.tgz#12225c8f95edf8b17254e47080ce0862d5db8044" @@ -4923,11 +4733,6 @@ micromark-util-types@2.0.2: resolved "https://registry.yarnpkg.com/micromark-util-types/-/micromark-util-types-2.0.2.tgz#f00225f5f5a0ebc3254f96c36b6605c4b393908e" integrity sha512-Yw0ECSpJoViF1qTU4DC6NwtC4aWGt1EkzaQB8KPPyCRR8z9TWeV0HbEFGTO+ZY1wB22zmxnJqhPyTpOVCpeHTA== -micromark-util-types@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/micromark-util-types/-/micromark-util-types-1.0.0.tgz#0ebdfaea3fa7c15fc82b1e06ea1ef0152d0fb2f0" - integrity sha512-psf1WAaP1B77WpW4mBGDkTr+3RsPuDAgsvlP47GJzbH1jmjH8xjOx7Z6kp84L8oqHmy5pYO3Ev46odosZV+3AA== - micromark-util-types@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/micromark-util-types/-/micromark-util-types-2.0.0.tgz#63b4b7ffeb35d3ecf50d1ca20e68fc7caa36d95e" @@ -4956,28 +4761,6 @@ micromark@4.0.2: micromark-util-symbol "^2.0.0" micromark-util-types "^2.0.0" -micromark@^3.0.0: - version "3.0.3" - resolved "https://registry.yarnpkg.com/micromark/-/micromark-3.0.3.tgz#4c9f76fce8ba68eddf8730bb4fee2041d699d5b7" - integrity sha512-fWuHx+JKV4zA8WfCFor2DWP9XmsZkIiyWRGofr7P7IGfpRIlb7/C5wwusGsNyr1D8HI5arghZDG1Ikc0FBwS5Q== - dependencies: - "@types/debug" "^4.0.0" - debug "^4.0.0" - micromark-core-commonmark "^1.0.0" - micromark-factory-space "^1.0.0" - micromark-util-character "^1.0.0" - micromark-util-chunked "^1.0.0" - micromark-util-combine-extensions "^1.0.0" - micromark-util-decode-numeric-character-reference "^1.0.0" - micromark-util-encode "^1.0.0" - micromark-util-normalize-identifier "^1.0.0" - micromark-util-resolve-all "^1.0.0" - micromark-util-sanitize-uri "^1.0.0" - micromark-util-subtokenize "^1.0.0" - micromark-util-symbol "^1.0.0" - micromark-util-types "^1.0.0" - parse-entities "^3.0.0" - micromark@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/micromark/-/micromark-4.0.0.tgz#84746a249ebd904d9658cfabc1e8e5f32cbc6249" @@ -5136,11 +4919,6 @@ mkdirp@^1.0.3: resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-1.0.4.tgz#3eb5ed62622756d79a5f0e2a221dfebad75c2f7e" integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== -mri@^1.1.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/mri/-/mri-1.2.0.tgz#6721480fec2a11a4889861115a48b6cbe7cc8f0b" - integrity sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA== - ms@^2.1.1, ms@^2.1.3: version "2.1.3" resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2" @@ -5484,18 +5262,6 @@ parent-module@^1.0.0: dependencies: callsites "^3.0.0" -parse-entities@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/parse-entities/-/parse-entities-3.0.0.tgz#9ed6d6569b6cfc95ade058d683ddef239dad60dc" - integrity sha512-AJlcIFDNPEP33KyJLguv0xJc83BNvjxwpuUIcetyXUsLpVXAUCePJ5kIoYtEN2R1ac0cYaRu/vk9dVFkewHQhQ== - dependencies: - character-entities "^2.0.0" - character-entities-legacy "^2.0.0" - character-reference-invalid "^2.0.0" - is-alphanumerical "^2.0.0" - is-decimal "^2.0.0" - is-hexadecimal "^2.0.0" - parse-entities@^4.0.0: version "4.0.2" resolved "https://registry.yarnpkg.com/parse-entities/-/parse-entities-4.0.2.tgz#61d46f5ed28e4ee62e9ddc43d6b010188443f159" @@ -6598,13 +6364,6 @@ rxjs@^6.5.5: dependencies: tslib "^1.9.0" -sade@^1.7.3: - version "1.8.1" - resolved "https://registry.yarnpkg.com/sade/-/sade-1.8.1.tgz#0a78e81d658d394887be57d2a409bf703a3b2701" - integrity sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A== - dependencies: - mri "^1.1.0" - safe-array-concat@^1.1.2: version "1.1.2" resolved "https://registry.yarnpkg.com/safe-array-concat/-/safe-array-concat-1.1.2.tgz#81d77ee0c4e8b863635227c721278dd524c20edb" @@ -7553,11 +7312,6 @@ unist-util-is@^4.0.0: resolved "https://registry.yarnpkg.com/unist-util-is/-/unist-util-is-4.1.0.tgz#976e5f462a7a5de73d94b706bac1b90671b57797" integrity sha512-ZOQSsnce92GrxSqlnEEseX0gi7GH9zTJZ0p9dtu87WRb/37mMPO2Ilx1s/t9vBHrFhbgweUwb+t7cIn5dxPhZg== -unist-util-is@^5.0.0: - version "5.1.1" - resolved "https://registry.yarnpkg.com/unist-util-is/-/unist-util-is-5.1.1.tgz#e8aece0b102fa9bc097b0fef8f870c496d4a6236" - integrity sha512-F5CZ68eYzuSvJjGhCLPL3cYx45IxkqXSetCcRgUXtbcm50X2L9oOWQlfUfDdAf+6Pd27YDblBfdtmsThXmwpbQ== - unist-util-is@^6.0.0: version "6.0.0" resolved "https://registry.yarnpkg.com/unist-util-is/-/unist-util-is-6.0.0.tgz#b775956486aff107a9ded971d996c173374be424" @@ -7577,13 +7331,6 @@ unist-util-stringify-position@^2.0.0: dependencies: "@types/unist" "^2.0.2" -unist-util-stringify-position@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/unist-util-stringify-position/-/unist-util-stringify-position-3.0.0.tgz#d517d2883d74d0daa0b565adc3d10a02b4a8cde9" - integrity sha512-SdfAl8fsDclywZpfMDTVDxA2V7LjtRDTOFd44wUJamgl6OlVngsqWjxvermMYf60elWHbxhuRCZml7AnuXCaSA== - dependencies: - "@types/unist" "^2.0.0" - unist-util-stringify-position@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/unist-util-stringify-position/-/unist-util-stringify-position-4.0.0.tgz#449c6e21a880e0855bf5aabadeb3a740314abac2" @@ -7599,14 +7346,6 @@ unist-util-visit-parents@^3.0.0: "@types/unist" "^2.0.0" unist-util-is "^4.0.0" -unist-util-visit-parents@^5.1.1: - version "5.1.1" - resolved "https://registry.yarnpkg.com/unist-util-visit-parents/-/unist-util-visit-parents-5.1.1.tgz#868f353e6fce6bf8fa875b251b0f4fec3be709bb" - integrity sha512-gks4baapT/kNRaWxuGkl5BIhoanZo7sC/cUT/JToSRNL1dYoXRFl75d++NkjYk4TAu2uv2Px+l8guMajogeuiw== - dependencies: - "@types/unist" "^2.0.0" - unist-util-is "^5.0.0" - unist-util-visit-parents@^6.0.0: version "6.0.1" resolved "https://registry.yarnpkg.com/unist-util-visit-parents/-/unist-util-visit-parents-6.0.1.tgz#4d5f85755c3b8f0dc69e21eca5d6d82d22162815" @@ -7624,15 +7363,6 @@ unist-util-visit@^2.0.0: unist-util-is "^4.0.0" unist-util-visit-parents "^3.0.0" -unist-util-visit@^4.1.2: - version "4.1.2" - resolved "https://registry.yarnpkg.com/unist-util-visit/-/unist-util-visit-4.1.2.tgz#125a42d1eb876283715a3cb5cceaa531828c72e2" - integrity sha512-MSd8OUGISqHdVvfY9TPhyK2VdUrPgxkUtWSuMHF6XAAFuL4LokseigBnZtPnJMu+FbynTkFNnFlyjxpVKujMRg== - dependencies: - "@types/unist" "^2.0.0" - unist-util-is "^5.0.0" - unist-util-visit-parents "^5.1.1" - unist-util-visit@^5.0.0: version "5.0.0" resolved "https://registry.yarnpkg.com/unist-util-visit/-/unist-util-visit-5.0.0.tgz#a7de1f31f72ffd3519ea71814cccf5fd6a9217d6" @@ -7698,16 +7428,6 @@ util-deprecate@^1.0.1, util-deprecate@~1.0.1: resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8= -uvu@^0.5.0: - version "0.5.6" - resolved "https://registry.yarnpkg.com/uvu/-/uvu-0.5.6.tgz#2754ca20bcb0bb59b64e9985e84d2e81058502df" - integrity sha512-+g8ENReyr8YsOc6fv/NVJs2vFdHBnBNdfE49rshrTzDWOlUx4Gq7KOS2GD8eqhy2j+Ejq29+SbKH8yjkAqXqoA== - dependencies: - dequal "^2.0.0" - diff "^5.0.0" - kleur "^4.0.3" - sade "^1.7.3" - validate-npm-package-license@^3.0.1, validate-npm-package-license@^3.0.4: version "3.0.4" resolved "https://registry.yarnpkg.com/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz#fc91f6b9c7ba15c857f4cb2c5defeec39d4f410a" From 65b9accc80a984f9055e25618fc14e2ed71c327f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 26 May 2025 10:06:40 +0200 Subject: [PATCH 070/186] build: migrate to new chromium git auth (#47255) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- .github/actions/checkout/action.yml | 4 +- .../actions/set-chromium-cookie/action.yml | 58 ------------------- .../set-chromium-git-helper/action.yml | 41 +++++++++++++ .github/workflows/build.yml | 10 ++-- .github/workflows/linux-publish.yml | 3 +- .github/workflows/macos-publish.yml | 3 +- .github/workflows/pipeline-electron-lint.yml | 7 ++- .../pipeline-segment-electron-build.yml | 8 +-- .../pipeline-segment-electron-gn-check.yml | 4 +- .../pipeline-segment-electron-test.yml | 8 +-- .../pipeline-segment-node-nan-test.yml | 11 ++-- .github/workflows/windows-publish.yml | 3 +- 12 files changed, 75 insertions(+), 85 deletions(-) delete mode 100644 .github/actions/set-chromium-cookie/action.yml create mode 100644 .github/actions/set-chromium-git-helper/action.yml diff --git a/.github/actions/checkout/action.yml b/.github/actions/checkout/action.yml index b4f6ca7f2126f..7cfbd542c1b60 100644 --- a/.github/actions/checkout/action.yml +++ b/.github/actions/checkout/action.yml @@ -20,8 +20,8 @@ runs: echo "GIT_CACHE_PATH=$(pwd)/git-cache" >> $GITHUB_ENV - name: Install Dependencies uses: ./src/electron/.github/actions/install-dependencies - - name: Set Chromium Git Cookie - uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Set Chromium Git Helper + uses: ./src/electron/.github/actions/set-chromium-git-helper - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Generate DEPS Hash diff --git a/.github/actions/set-chromium-cookie/action.yml b/.github/actions/set-chromium-cookie/action.yml deleted file mode 100644 index 2011655e29b59..0000000000000 --- a/.github/actions/set-chromium-cookie/action.yml +++ /dev/null @@ -1,58 +0,0 @@ -name: 'Set Chromium Git Cookie' -description: 'Sets an authenticated cookie from Chromium to allow for a higher request limit' -runs: - using: "composite" - steps: - - name: Set the git cookie from chromium.googlesource.com (Unix) - if: ${{ runner.os != 'Windows' }} - shell: bash - run: | - if [[ -z "${{ env.CHROMIUM_GIT_COOKIE }}" ]]; then - echo "CHROMIUM_GIT_COOKIE is not set - cannot authenticate." - exit 0 - fi - - eval 'set +o history' 2>/dev/null || setopt HIST_IGNORE_SPACE 2>/dev/null - touch ~/.gitcookies - chmod 0600 ~/.gitcookies - - git config --global http.cookiefile ~/.gitcookies - - tr , \\t <<\__END__ >>~/.gitcookies - ${{ env.CHROMIUM_GIT_COOKIE }} - __END__ - eval 'set -o history' 2>/dev/null || unsetopt HIST_IGNORE_SPACE 2>/dev/null - - RESPONSE=$(curl -s -b ~/.gitcookies https://chromium-review.googlesource.com/a/accounts/self) - if [[ $RESPONSE == ")]}'"* ]]; then - # Extract account email for verification - EMAIL=$(echo "$RESPONSE" | tail -c +5 | jq -r '.email // "No email found"') - echo "Cookie authentication successful - authenticated as: $EMAIL" - else - echo "Cookie authentication failed - ensure CHROMIUM_GIT_COOKIE is set correctly" - echo $RESPONSE - fi - - name: Set the git cookie from chromium.googlesource.com (Windows) - if: ${{ runner.os == 'Windows' }} - shell: cmd - run: | - if "%CHROMIUM_GIT_COOKIE_WINDOWS_STRING%"=="" ( - echo CHROMIUM_GIT_COOKIE_WINDOWS_STRING is not set - cannot authenticate. - exit /b 0 - ) - - git config --global http.cookiefile "%USERPROFILE%\.gitcookies" - powershell -noprofile -nologo -command Write-Output "${{ env.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }}" >>"%USERPROFILE%\.gitcookies" - - curl -s -b "%USERPROFILE%\.gitcookies" https://chromium-review.googlesource.com/a/accounts/self > response.txt - - findstr /B /C:")]}'" response.txt > nul - if %ERRORLEVEL% EQU 0 ( - echo Cookie authentication successful - powershell -NoProfile -Command "& {$content = Get-Content -Raw response.txt; $content = $content.Substring(4); try { $json = ConvertFrom-Json $content; if($json.email) { Write-Host 'Authenticated as:' $json.email } else { Write-Host 'No email found in response' } } catch { Write-Host 'Error parsing JSON:' $_ }}" - ) else ( - echo Cookie authentication failed - ensure CHROMIUM_GIT_COOKIE_WINDOWS_STRING is set correctly - type response.txt - ) - - del response.txt diff --git a/.github/actions/set-chromium-git-helper/action.yml b/.github/actions/set-chromium-git-helper/action.yml new file mode 100644 index 0000000000000..bdc0ceb303d25 --- /dev/null +++ b/.github/actions/set-chromium-git-helper/action.yml @@ -0,0 +1,41 @@ +name: 'Set Chromium Git Helper' +description: 'Sets Chromium Git Helper to allow for a higher request limit' +runs: + using: "composite" + steps: + - name: Save the chromium git credentials to a file + shell: bash + run: | + if [[ -z "${{ env.CHROMIUM_GIT_AUTH }}" ]]; then + echo "CHROMIUM_GIT_AUTH is not set - cannot authenticate." + exit 0 + fi + if [[ "${{ runner.os }}" != "Windows" ]]; then + cd $HOME + fi + echo "${{ env.CHROMIUM_GIT_AUTH }}" > .chromium_git_auth + + - name: Set the chromium git helper to use auth from a file + shell: bash + run: | + if [[ "${{ runner.os }}" == "Windows" ]]; then + if [[ ! -f "/c/actions-runner/_work/electron/electron/.chromium_git_auth" ]]; then + echo "File /c/actions-runner/_work/electron/electron/.chromium_git_auth does not exist - cannot authenticate." + exit 0 + fi + else + if [[ ! -f "$HOME/.chromium_git_auth" ]]; then + echo "File $HOME/.chromium_git_auth does not exist - cannot authenticate." + exit 0 + fi + fi + if [[ -z "${{ env.CHROMIUM_GIT_USER }}" ]]; then + echo "CHROMIUM_GIT_USER is not set - cannot authenticate." + exit 0 + fi + git config --global credential.https://chromium.googlesource.com.username "${{ env.CHROMIUM_GIT_USER }}" + if [[ "${{ runner.os }}" == "Windows" ]]; then + git config --global credential.https://chromium.googlesource.com.helper '!f() { test "$1" = get && echo "password=$(cat /c/actions-runner/_work/electron/electron/.chromium_git_auth)"; }; f' + else + git config --global credential.https://chromium.googlesource.com.helper '!f() { test "$1" = get && echo "password=$(cat $HOME/.chromium_git_auth)"; }; f' + fi diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index bf578ebe26100..ace3bae71f5a4 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -100,7 +100,8 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_mac=True --custom-var=host_os=mac' outputs: build-image-sha: ${{ needs.setup.outputs.build-image-sha }} @@ -128,7 +129,8 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_arm=True --custom-var=checkout_arm64=True' PATCH_UP_APP_CREDS: ${{ secrets.PATCH_UP_APP_CREDS }} outputs: @@ -154,8 +156,8 @@ jobs: - /mnt/win-cache:/mnt/win-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} - CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_win=True' TARGET_OS: 'win' ELECTRON_DEPOT_TOOLS_WIN_TOOLCHAIN: '1' diff --git a/.github/workflows/linux-publish.yml b/.github/workflows/linux-publish.yml index 8cadd26d23bcc..a003a15fc1184 100644 --- a/.github/workflows/linux-publish.yml +++ b/.github/workflows/linux-publish.yml @@ -27,7 +27,8 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_arm=True --custom-var=checkout_arm64=True' steps: - name: Checkout Electron diff --git a/.github/workflows/macos-publish.yml b/.github/workflows/macos-publish.yml index c7241b6a3bb00..3e4654445092a 100644 --- a/.github/workflows/macos-publish.yml +++ b/.github/workflows/macos-publish.yml @@ -28,7 +28,8 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_mac=True --custom-var=host_os=mac' steps: - name: Checkout Electron diff --git a/.github/workflows/pipeline-electron-lint.yml b/.github/workflows/pipeline-electron-lint.yml index acbf2a6510945..88445a478a5c0 100644 --- a/.github/workflows/pipeline-electron-lint.yml +++ b/.github/workflows/pipeline-electron-lint.yml @@ -13,7 +13,8 @@ concurrency: cancel-in-progress: ${{ github.ref_protected != true }} env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} jobs: lint: @@ -30,8 +31,8 @@ jobs: ref: ${{ github.event.pull_request.head.sha }} - name: Install Dependencies uses: ./src/electron/.github/actions/install-dependencies - - name: Set Chromium Git Cookie - uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Set Chromium Git Helper + uses: ./src/electron/.github/actions/set-chromium-git-helper - name: Setup third_party Depot Tools shell: bash run: | diff --git a/.github/workflows/pipeline-segment-electron-build.yml b/.github/workflows/pipeline-segment-electron-build.yml index ac7d2e78c939f..520511f28a7ef 100644 --- a/.github/workflows/pipeline-segment-electron-build.yml +++ b/.github/workflows/pipeline-segment-electron-build.yml @@ -65,8 +65,8 @@ concurrency: cancel-in-progress: ${{ github.ref_protected != true }} env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} - CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} ELECTRON_ARTIFACTS_BLOB_STORAGE: ${{ secrets.ELECTRON_ARTIFACTS_BLOB_STORAGE }} ELECTRON_RBE_JWT: ${{ secrets.ELECTRON_RBE_JWT }} SUDOWOODO_EXCHANGE_URL: ${{ secrets.SUDOWOODO_EXCHANGE_URL }} @@ -127,8 +127,8 @@ jobs: GN_EXTRA_ARGS='is_asan=true' fi echo "GN_EXTRA_ARGS=$GN_EXTRA_ARGS" >> $GITHUB_ENV - - name: Set Chromium Git Cookie - uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Set Chromium Git Helper + uses: ./src/electron/.github/actions/set-chromium-git-helper - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Generate DEPS Hash diff --git a/.github/workflows/pipeline-segment-electron-gn-check.yml b/.github/workflows/pipeline-segment-electron-gn-check.yml index 48fe703078145..9e74404070b13 100644 --- a/.github/workflows/pipeline-segment-electron-gn-check.yml +++ b/.github/workflows/pipeline-segment-electron-gn-check.yml @@ -66,8 +66,8 @@ jobs: - name: Check disk space after freeing up space if: ${{ inputs.target-platform == 'macos' }} run: df -h - - name: Set Chromium Git Cookie - uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Set Chromium Git Helper + uses: ./src/electron/.github/actions/set-chromium-git-helper - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Enable windows toolchain diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index 17cf3f2398b98..5040ebb1ac046 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -36,8 +36,8 @@ permissions: pull-requests: read env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} - CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} ELECTRON_OUT_DIR: Default ELECTRON_RBE_JWT: ${{ secrets.ELECTRON_RBE_JWT }} @@ -126,8 +126,8 @@ jobs: ref: ${{ github.event.pull_request.head.sha }} - name: Install Dependencies uses: ./src/electron/.github/actions/install-dependencies - - name: Set Chromium Git Cookie - uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Set Chromium Git Helper + uses: ./src/electron/.github/actions/set-chromium-git-helper - name: Get Depot Tools timeout-minutes: 5 run: | diff --git a/.github/workflows/pipeline-segment-node-nan-test.yml b/.github/workflows/pipeline-segment-node-nan-test.yml index 7b5e71c3cd347..d7375886850aa 100644 --- a/.github/workflows/pipeline-segment-node-nan-test.yml +++ b/.github/workflows/pipeline-segment-node-nan-test.yml @@ -31,7 +31,8 @@ concurrency: cancel-in-progress: ${{ github.ref_protected != true }} env: - CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} ELECTRON_OUT_DIR: Default ELECTRON_RBE_JWT: ${{ secrets.ELECTRON_RBE_JWT }} @@ -51,8 +52,8 @@ jobs: path: src/electron fetch-depth: 0 ref: ${{ github.event.pull_request.head.sha }} - - name: Set Chromium Git Cookie - uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Set Chromium Git Helper + uses: ./src/electron/.github/actions/set-chromium-git-helper - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Init Build Tools @@ -105,8 +106,8 @@ jobs: path: src/electron fetch-depth: 0 ref: ${{ github.event.pull_request.head.sha }} - - name: Set Chromium Git Cookie - uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Set Chromium Git Helper + uses: ./src/electron/.github/actions/set-chromium-git-helper - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Init Build Tools diff --git a/.github/workflows/windows-publish.yml b/.github/workflows/windows-publish.yml index e8b7c6172fdd8..c0acf202f6d30 100644 --- a/.github/workflows/windows-publish.yml +++ b/.github/workflows/windows-publish.yml @@ -28,7 +28,8 @@ jobs: - /mnt/win-cache:/mnt/win-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} + CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} + CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_win=True' TARGET_OS: 'win' ELECTRON_DEPOT_TOOLS_WIN_TOOLCHAIN: '1' From 7dd024a9dcba969702584830686282e5d3e5a893 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 26 May 2025 20:32:45 -0700 Subject: [PATCH 071/186] chore: debug crash on DevTools SetOwnerWindow (#47263) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/api/electron_api_web_contents.cc | 5 ++++- shell/browser/ui/inspectable_web_contents.cc | 2 ++ shell/browser/ui/inspectable_web_contents.h | 3 +++ 3 files changed, 9 insertions(+), 1 deletion(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index 1b764296d5dc3..b984d57f865bd 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -2152,8 +2152,11 @@ void WebContents::DevToolsOpened() { // Inherit owner window in devtools when it doesn't have one. auto* devtools = inspectable_web_contents_->GetDevToolsWebContents(); bool has_window = devtools->GetUserData(NativeWindowRelay::UserDataKey()); - if (owner_window() && !has_window) + if (owner_window_ && !has_window) { + DCHECK(!owner_window_.WasInvalidated()); + DCHECK_EQ(handle->owner_window(), nullptr); handle->SetOwnerWindow(devtools, owner_window()); + } Emit("devtools-opened"); } diff --git a/shell/browser/ui/inspectable_web_contents.cc b/shell/browser/ui/inspectable_web_contents.cc index 60d481a9d5caa..e80d6a6d7662d 100644 --- a/shell/browser/ui/inspectable_web_contents.cc +++ b/shell/browser/ui/inspectable_web_contents.cc @@ -530,6 +530,8 @@ void InspectableWebContents::CloseWindow() { } void InspectableWebContents::LoadCompleted() { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + frontend_loaded_ = true; if (managed_devtools_web_contents_) view_->ShowDevTools(activate_); diff --git a/shell/browser/ui/inspectable_web_contents.h b/shell/browser/ui/inspectable_web_contents.h index 012f613895e3a..87fe41aaad7fc 100644 --- a/shell/browser/ui/inspectable_web_contents.h +++ b/shell/browser/ui/inspectable_web_contents.h @@ -15,6 +15,7 @@ #include "base/containers/unique_ptr_adapters.h" #include "base/memory/raw_ptr.h" #include "base/memory/weak_ptr.h" +#include "base/sequence_checker.h" #include "chrome/browser/devtools/devtools_embedder_message_dispatcher.h" #include "content/public/browser/devtools_agent_host.h" #include "content/public/browser/devtools_frontend_host.h" @@ -271,6 +272,8 @@ class InspectableWebContents // use, which guarantees that this set must not be persisted. base::flat_set synced_setting_names_; + SEQUENCE_CHECKER(sequence_checker_); + base::WeakPtrFactory weak_factory_{this}; }; From f9b86609a90d43ecac6f4cc39e1758706036ab96 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 27 May 2025 14:24:48 +0200 Subject: [PATCH 072/186] fix: titlebar showing in content protected window (#47266) Closes https://github.com/electron/electron/issues/47152. Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .../electron_desktop_window_tree_host_win.cc | 26 +++++++++++++++++-- .../electron_desktop_window_tree_host_win.h | 3 +++ 2 files changed, 27 insertions(+), 2 deletions(-) diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc index 641aaf5b753ca..38111744620cd 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc @@ -143,11 +143,33 @@ bool ElectronDesktopWindowTreeHostWin::HandleMouseEvent(ui::MouseEvent* event) { void ElectronDesktopWindowTreeHostWin::HandleVisibilityChanged(bool visible) { if (native_window_view_->widget()) native_window_view_->widget()->OnNativeWidgetVisibilityChanged(visible); + + if (visible) + UpdateAllowScreenshots(); } void ElectronDesktopWindowTreeHostWin::SetAllowScreenshots(bool allow) { - ::SetWindowDisplayAffinity(GetAcceleratedWidget(), - allow ? WDA_NONE : WDA_EXCLUDEFROMCAPTURE); + if (allow_screenshots_ == allow) + return; + + allow_screenshots_ = allow; + + // If the window is not visible, do not set the window display affinity + // because `SetWindowDisplayAffinity` will attempt to compose the window, + if (!IsVisible()) + return; + + UpdateAllowScreenshots(); +} + +void ElectronDesktopWindowTreeHostWin::UpdateAllowScreenshots() { + bool allowed = views::DesktopWindowTreeHostWin::AreScreenshotsAllowed(); + if (allowed == allow_screenshots_) + return; + + ::SetWindowDisplayAffinity( + GetAcceleratedWidget(), + allow_screenshots_ ? WDA_NONE : WDA_EXCLUDEFROMCAPTURE); } void ElectronDesktopWindowTreeHostWin::OnNativeThemeUpdated( diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.h b/shell/browser/ui/win/electron_desktop_window_tree_host_win.h index 4776d66593067..4cab017bef0b1 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.h +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.h @@ -51,8 +51,11 @@ class ElectronDesktopWindowTreeHostWin : public views::DesktopWindowTreeHostWin, bool ShouldWindowContentsBeTransparent() const override; private: + void UpdateAllowScreenshots(); + raw_ptr native_window_view_; // weak ref std::optional force_should_paint_as_active_; + bool allow_screenshots_ = true; bool widget_init_done_ = false; }; From 47e0baf21d991d9ff7b6c49dbb958cf457c36c92 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 27 May 2025 11:17:32 -0400 Subject: [PATCH 073/186] fix: regression with directory selection in macOS dialogs (#47277) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: deepak1556 --- shell/browser/ui/file_dialog_mac.mm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/shell/browser/ui/file_dialog_mac.mm b/shell/browser/ui/file_dialog_mac.mm index 06adfb5f5f8f4..c3967ef0d3c8d 100644 --- a/shell/browser/ui/file_dialog_mac.mm +++ b/shell/browser/ui/file_dialog_mac.mm @@ -321,7 +321,7 @@ void ReadDialogPathsWithBookmarks(NSOpenPanel* dialog, BOOL is_package_as_directory = [[NSWorkspace sharedWorkspace] isFilePackageAtPath:path] && [dialog treatsFilePackagesAsDirectories]; - if (!exists || !is_directory || !is_package_as_directory) + if (!exists || !(is_directory || is_package_as_directory)) continue; } From c2e8d71683c71e5095f7ee9373dcfa1689896b98 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 30 May 2025 11:00:37 +0200 Subject: [PATCH 074/186] ci: add a problem matcher for ESLint output (#47305) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- .github/problem-matchers/eslint-stylish.json | 22 ++++++++++++++++++++ .github/workflows/pipeline-electron-lint.yml | 3 +++ 2 files changed, 25 insertions(+) create mode 100644 .github/problem-matchers/eslint-stylish.json diff --git a/.github/problem-matchers/eslint-stylish.json b/.github/problem-matchers/eslint-stylish.json new file mode 100644 index 0000000000000..a98afcfb11b94 --- /dev/null +++ b/.github/problem-matchers/eslint-stylish.json @@ -0,0 +1,22 @@ +{ + "problemMatcher": [ + { + "owner": "eslint-stylish", + "pattern": [ + { + "regexp": "^\\s*([^\\s].*)$", + "file": 1 + }, + { + "regexp": "^\\s+(\\d+):(\\d+)\\s+(error|warning|info)\\s+(.*)\\s\\s+(.*)$", + "line": 1, + "column": 2, + "severity": 3, + "message": 4, + "code": 5, + "loop": true + } + ] + } + ] +} diff --git a/.github/workflows/pipeline-electron-lint.yml b/.github/workflows/pipeline-electron-lint.yml index 88445a478a5c0..a49ce67b62f85 100644 --- a/.github/workflows/pipeline-electron-lint.yml +++ b/.github/workflows/pipeline-electron-lint.yml @@ -62,6 +62,9 @@ jobs: curl -sL "https://chromium.googlesource.com/chromium/src/+/${chromium_revision}/buildtools/DEPS?format=TEXT" | base64 -d > src/buildtools/DEPS gclient sync --spec="solutions=[{'name':'src/buildtools','url':None,'deps_file':'DEPS','custom_vars':{'process_deps':True},'managed':False}]" + - name: Add ESLint problem matcher + shell: bash + run: echo "::add-matcher::src/electron/.github/problem-matchers/eslint-stylish.json" - name: Run Lint shell: bash run: | From ab78c8a295826358aa64ec48b226d83a160e682a Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 30 May 2025 13:48:13 +0200 Subject: [PATCH 075/186] docs: add documentation for `ImageView` (#47297) * docs: Add documentation for ImageView * docs: Add ImageView main process module list in README.md * test: Add some basic tests for ImageView * test: Fill out Window embedding tests to better reflect how someone might use an ImageView * docs: Add notes about using ImageView as a splash screen * docs: Update ImageView example to show a more complete splash screen example * docs: Remove view resizing logic since the ImageView automatically gets resized --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Will Anderson --- docs/README.md | 1 + docs/api/image-view.md | 61 ++++++++++++++++++++++++++ filenames.auto.gni | 1 + spec/api-image-view-spec.ts | 86 +++++++++++++++++++++++++++++++++++++ 4 files changed, 149 insertions(+) create mode 100644 docs/api/image-view.md create mode 100644 spec/api-image-view-spec.ts diff --git a/docs/README.md b/docs/README.md index 01663cc017769..02d5d1331ca29 100644 --- a/docs/README.md +++ b/docs/README.md @@ -113,6 +113,7 @@ These individual tutorials expand on topics discussed in the guide above. * [dialog](api/dialog.md) * [globalShortcut](api/global-shortcut.md) * [inAppPurchase](api/in-app-purchase.md) +* [ImageView](api/image-view.md) * [ipcMain](api/ipc-main.md) * [Menu](api/menu.md) * [MenuItem](api/menu-item.md) diff --git a/docs/api/image-view.md b/docs/api/image-view.md new file mode 100644 index 0000000000000..854de3054601a --- /dev/null +++ b/docs/api/image-view.md @@ -0,0 +1,61 @@ +# ImageView + +> A View that displays an image. + +Process: [Main](../glossary.md#main-process) + +This module cannot be used until the `ready` event of the `app` +module is emitted. + +Useful for showing splash screens that will be swapped for `WebContentsView`s +when the content finishes loading. + +Note that `ImageView` is experimental and may be changed or removed in the future. + +```js +const { BaseWindow, ImageView, nativeImage, WebContentsView } = require('electron') +const path = require('node:path') + +const win = new BaseWindow({ width: 800, height: 600 }) + +// Create a "splash screen" image to display while the WebContentsView loads +const splashView = new ImageView() +const splashImage = nativeImage.createFromPath(path.join(__dirname, 'loading.png')) +splashView.setImage(splashImage) +win.setContentView(splashView) + +const webContentsView = new WebContentsView() +webContentsView.webContents.once('did-finish-load', () => { + // Now that the WebContentsView has loaded, swap out the "splash screen" ImageView + win.setContentView(webContentsView) +}) +webContentsView.webContents.loadURL('https://electronjs.org') +``` + +## Class: ImageView extends `View` + +> A View that displays an image. + +Process: [Main](../glossary.md#main-process) + +`ImageView` inherits from [`View`](view.md). + +`ImageView` is an [EventEmitter][event-emitter]. + +### `new ImageView()` _Experimental_ + +Creates an ImageView. + +### Instance Methods + +The following methods are available on instances of the `ImageView` class, in +addition to those inherited from [View](view.md): + +#### `image.setImage(image)` _Experimental_ + +* `image` NativeImage + +Sets the image for this `ImageView`. Note that only image formats supported by +`NativeImage` can be used with an `ImageView`. + +[event-emitter]: https://nodejs.org/api/events.html#events_class_eventemitter diff --git a/filenames.auto.gni b/filenames.auto.gni index df963e2c831b6..ecdc659fd06a4 100644 --- a/filenames.auto.gni +++ b/filenames.auto.gni @@ -25,6 +25,7 @@ auto_filenames = { "docs/api/extensions-api.md", "docs/api/extensions.md", "docs/api/global-shortcut.md", + "docs/api/image-view.md", "docs/api/in-app-purchase.md", "docs/api/incoming-message.md", "docs/api/ipc-main-service-worker.md", diff --git a/spec/api-image-view-spec.ts b/spec/api-image-view-spec.ts new file mode 100644 index 0000000000000..45f7bfdb96c24 --- /dev/null +++ b/spec/api-image-view-spec.ts @@ -0,0 +1,86 @@ +import { nativeImage } from 'electron/common'; +import { BaseWindow, BrowserWindow, ImageView } from 'electron/main'; + +import { expect } from 'chai'; + +import * as path from 'node:path'; + +import { closeAllWindows } from './lib/window-helpers'; + +describe('ImageView', () => { + afterEach(async () => { + await closeAllWindows(); + }); + + it('can be instantiated with no arguments', () => { + // eslint-disable-next-line no-new + new ImageView(); + }); + + it('can set an empty NativeImage', () => { + const view = new ImageView(); + const image = nativeImage.createEmpty(); + view.setImage(image); + }); + + it('can set a NativeImage', () => { + const view = new ImageView(); + const image = nativeImage.createFromPath(path.join(__dirname, 'fixtures', 'assets', 'logo.png')); + view.setImage(image); + }); + + it('can change its NativeImage', () => { + const view = new ImageView(); + const image1 = nativeImage.createFromPath(path.join(__dirname, 'fixtures', 'assets', 'logo.png')); + const image2 = nativeImage.createFromPath(path.join(__dirname, 'fixtures', 'assets', 'capybara.png')); + view.setImage(image1); + view.setImage(image2); + }); + + it('can be embedded in a BaseWindow', () => { + const w = new BaseWindow({ show: false }); + const view = new ImageView(); + const image = nativeImage.createFromPath(path.join(__dirname, 'fixtures', 'assets', 'capybara.png')); + view.setImage(image); + w.setContentView(view); + w.setContentSize(image.getSize().width, image.getSize().height); + view.setBounds({ + x: 0, + y: 0, + width: image.getSize().width, + height: image.getSize().height + }); + }); + + it('can be embedded in a BrowserWindow', () => { + const w = new BrowserWindow({ show: false }); + const image = nativeImage.createFromPath(path.join(__dirname, 'fixtures', 'assets', 'logo.png')); + const view = new ImageView(); + view.setImage(image); + w.contentView.addChildView(view); + w.setContentSize(image.getSize().width, image.getSize().height); + view.setBounds({ + x: 0, + y: 0, + width: image.getSize().width, + height: image.getSize().height + }); + + expect(w.contentView.children).to.include(view); + }); + + it('can be removed from a BrowserWindow', async () => { + const w = new BrowserWindow({ show: false }); + const image = nativeImage.createFromPath(path.join(__dirname, 'fixtures', 'assets', 'logo.png')); + const view = new ImageView(); + view.setImage(image); + + w.contentView.addChildView(view); + expect(w.contentView.children).to.include(view); + + await w.loadFile(path.join(__dirname, 'fixtures', 'api', 'blank.html')); + + w.contentView.removeChildView(view); + expect(w.contentView.children).to.not.include(view); + }); +}); From 91c153ed0bfd0da91fc3a759f07a42218b9ac25d Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 30 May 2025 10:46:12 -0400 Subject: [PATCH 076/186] fix: Squirrel.Mac crash when zip extraction fails (#47302) * fix: Squirrel.Mac crash when zip extraction process fails to launch Co-authored-by: Niklas Wenzel * chore: add end-to-end test Co-authored-by: Niklas Wenzel --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Niklas Wenzel --- patches/squirrel.mac/.patches | 1 + ...ss_to_extract_zip_cannot_be_launched.patch | 30 +++++++++++++ spec/api-autoupdater-darwin-spec.ts | 45 +++++++++++++++++++ .../auto-update/sandbox/block-ditto.sb | 5 +++ 4 files changed, 81 insertions(+) create mode 100644 patches/squirrel.mac/fix_crash_when_process_to_extract_zip_cannot_be_launched.patch create mode 100644 spec/fixtures/auto-update/sandbox/block-ditto.sb diff --git a/patches/squirrel.mac/.patches b/patches/squirrel.mac/.patches index a86478c8892a4..4b47e7da493ea 100644 --- a/patches/squirrel.mac/.patches +++ b/patches/squirrel.mac/.patches @@ -7,3 +7,4 @@ fix_abort_installation_attempt_at_the_final_mile_if_the_app_is.patch feat_add_ability_to_prevent_version_downgrades.patch refactor_use_non-deprecated_nskeyedarchiver_apis.patch chore_turn_off_launchapplicationaturl_deprecation_errors_in_squirrel.patch +fix_crash_when_process_to_extract_zip_cannot_be_launched.patch diff --git a/patches/squirrel.mac/fix_crash_when_process_to_extract_zip_cannot_be_launched.patch b/patches/squirrel.mac/fix_crash_when_process_to_extract_zip_cannot_be_launched.patch new file mode 100644 index 0000000000000..a9438c7b068c8 --- /dev/null +++ b/patches/squirrel.mac/fix_crash_when_process_to_extract_zip_cannot_be_launched.patch @@ -0,0 +1,30 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Niklas Wenzel +Date: Tue, 27 May 2025 02:03:54 +0200 +Subject: fix: crash when process to extract zip cannot be launched + +Fixes https://github.com/electron/electron/issues/47270 + +diff --git a/Squirrel/SQRLZipArchiver.m b/Squirrel/SQRLZipArchiver.m +index 68f5dac8e553638f41306956df9d38eeda18f8f2..a9cd676df63e19edf9e20473d27b85591c7cb49e 100644 +--- a/Squirrel/SQRLZipArchiver.m ++++ b/Squirrel/SQRLZipArchiver.m +@@ -153,7 +153,17 @@ - (RACSignal *)launchWithArguments:(NSArray *)arguments { + setNameWithFormat:@"-launchWithArguments: %@", arguments]; + + self.dittoTask.arguments = arguments; +- [self.dittoTask launch]; ++ ++ NSError *launchError = nil; ++ ++ if (![self.dittoTask launchAndReturnError:&launchError]) { ++ NSMutableDictionary *userInfo = [NSMutableDictionary dictionary]; ++ userInfo[NSLocalizedDescriptionKey] = launchError.localizedDescription; ++ ++ NSLog(@"Starting ditto task failed with error: %@", launchError.localizedDescription); ++ ++ return [RACSignal error:[NSError errorWithDomain:SQRLZipArchiverErrorDomain code:SQRLZipArchiverShellTaskFailed userInfo:userInfo]]; ++ } + + return signal; + } diff --git a/spec/api-autoupdater-darwin-spec.ts b/spec/api-autoupdater-darwin-spec.ts index 24925c503c5b9..24709ef21b91d 100644 --- a/spec/api-autoupdater-darwin-spec.ts +++ b/spec/api-autoupdater-darwin-spec.ts @@ -42,6 +42,16 @@ ifdescribe(shouldRunCodesignTests)('autoUpdater behavior', function () { return cp.spawn(path.resolve(appPath, 'Contents/MacOS/Electron'), args); }; + const launchAppSandboxed = (appPath: string, profilePath: string, args: string[] = []) => { + return spawn('/usr/bin/sandbox-exec', [ + '-f', + profilePath, + path.resolve(appPath, 'Contents/MacOS/Electron'), + ...args, + '--no-sandbox' + ]); + }; + const getRunningShipIts = async (appPath: string) => { const processes = await psList(); const activeShipIts = processes.filter(p => p.cmd?.includes('Squirrel.framework/Resources/ShipIt com.github.Electron.ShipIt') && p.cmd!.startsWith(appPath)); @@ -740,6 +750,41 @@ ifdescribe(shouldRunCodesignTests)('autoUpdater behavior', function () { }); }); + it('should hit the download endpoint when an update is available and fail when the zip extraction process fails to launch', async () => { + await withUpdatableApp({ + nextVersion: '2.0.0', + startFixture: 'update', + endFixture: 'update' + }, async (appPath, updateZipPath) => { + server.get('/update-file', (req, res) => { + res.download(updateZipPath); + }); + server.get('/update-check', (req, res) => { + res.json({ + url: `http://localhost:${port}/update-file`, + name: 'My Release Name', + notes: 'Theses are some release notes innit', + pub_date: (new Date()).toString() + }); + }); + const launchResult = await launchAppSandboxed( + appPath, + path.resolve(__dirname, 'fixtures/auto-update/sandbox/block-ditto.sb'), + [`http://localhost:${port}/update-check`] + ); + logOnError(launchResult, () => { + expect(launchResult).to.have.property('code', 1); + expect(launchResult.out).to.include('Starting ditto task failed with error:'); + expect(launchResult.out).to.include('SQRLZipArchiverErrorDomain'); + expect(requests).to.have.lengthOf(2); + expect(requests[0]).to.have.property('url', '/update-check'); + expect(requests[1]).to.have.property('url', '/update-file'); + expect(requests[0].header('user-agent')).to.include('Electron/'); + expect(requests[1].header('user-agent')).to.include('Electron/'); + }); + }); + }); + it('should hit the download endpoint when an update is available and update successfully when the zip is provided with JSON update mode', async () => { await withUpdatableApp({ nextVersion: '2.0.0', diff --git a/spec/fixtures/auto-update/sandbox/block-ditto.sb b/spec/fixtures/auto-update/sandbox/block-ditto.sb new file mode 100644 index 0000000000000..79194bdbd03ac --- /dev/null +++ b/spec/fixtures/auto-update/sandbox/block-ditto.sb @@ -0,0 +1,5 @@ +(version 1) +(allow default) +(deny process-exec + (literal "/usr/bin/ditto") +) From 95212a539be3941697315cd3512ba8a5fbcd8a04 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 3 Jun 2025 10:53:54 +0200 Subject: [PATCH 077/186] docs: correct 'select-bluetooth-device' requirement (#47336) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- docs/api/web-contents.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/docs/api/web-contents.md b/docs/api/web-contents.md index 3e89f5e6f7abc..85d2ee83406eb 100644 --- a/docs/api/web-contents.md +++ b/docs/api/web-contents.md @@ -839,9 +839,10 @@ Emitted when a bluetooth device needs to be selected when a call to the `deviceId` of the device to be selected. Passing an empty string to `callback` will cancel the request. -If an event listener is not added for this event, or if `event.preventDefault` -is not called when handling this event, the first available device will be -automatically selected. +If no event listener is added for this event, all bluetooth requests will be cancelled. + +If `event.preventDefault` is not called when handling this event, the first available +device will be automatically selected. Due to the nature of bluetooth, scanning for devices when `navigator.bluetooth.requestDevice` is called may take time and will cause From ca22facaafe863c8944c97bef8ad55acfd15ede0 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 3 Jun 2025 17:06:30 -0400 Subject: [PATCH 078/186] chore: bump chromium to 138.0.7190.0 (37-x-y) (#47349) * chore: bump chromium in DEPS to 138.0.7180.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * 6546797: Add a metric for the overall success of the "safe storage" item retrieval. Refs https://chromium-review.googlesource.com/c/chromium/src/+/6546797 Co-authored-by: David Sanders * 6548078: extensions: Fix TODO in ScriptInjectionTracker for desktop Android Refs https://chromium-review.googlesource.com/c/chromium/src/+/6548078 Co-authored-by: David Sanders * 6544950: Revert "FSA: Only normalize the hardcoded rules once during initialization" Refs https://chromium-review.googlesource.com/c/chromium/src/+/6544950 Co-authored-by: David Sanders * chore: bump chromium in DEPS to 138.0.7181.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: update patches Co-authored-by: David Sanders * fix: correctly clamp HSL shift values between 0 and 1 Co-authored-by: David Sanders * chore: bump DEPS to 138.0.7183.0 Co-authored-by: Keeley Hammond * 6553142: Remove SelectFileDialogLinuxKde | https://chromium-review.googlesource.com/c/chromium/src/+/6553142 Co-authored-by: Keeley Hammond * chore: update patches Co-authored-by: Keeley Hammond * chore: bump chromium in DEPS to 138.0.7184.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: bump chromium in DEPS to 138.0.7186.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: bump chromium in DEPS to 138.0.7190.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> * chore: update patches Co-authored-by: Keeley Hammond * 6547778: Remove some superfluous //ui/gfx includes from //chrome headers | https://chromium-review.googlesource.com/c/chromium/src/+/6547778 Co-authored-by: Keeley Hammond * 6556022: Reland FSA: Only normalize the hardcoded rules once during initialization | https://chromium-review.googlesource.com/c/chromium/src/+/6556022 Co-authored-by: Keeley Hammond * fix: remove pdf_extension_util::AddAdditionalData https://chromium-review.googlesource.com/c/chromium/src/+/4099130 This was removed 2 years ago in Chrome. Co-authored-by: Samuel Maddock * fix: provide BrowserContext to pdf_extension_util::AddAdditionalData https://chromium-review.googlesource.com/c/chromium/src/+/6558173 Co-authored-by: Samuel Maddock * fixup! 6556022: Reland FSA: Only normalize the hardcoded rules once during initialization | https://chromium-review.googlesource.com/c/chromium/src/+/6556022 Co-authored-by: Samuel Maddock * fix: pass in navigation throttle registry https://chromium-review.googlesource.com/c/chromium/src/+/6536175 Co-authored-by: Samuel Maddock * fixup! 6556022: Reland "FSA: Only normalize the hardcoded rules once during initialization" | https://chromium-review.googlesource.com/c/chromium/src/+/6556022 This partially reverts commit 20d709dd15ba0ff332e24ee314149d642dc5d47c. Co-authored-by: Keeley Hammond * 6545984: corner-shape: render dashed & dotted borders Refs https://chromium-review.googlesource.com/c/chromium/src/+/6545984 Co-authored-by: Samuel Maddock * Update corner smoothing expected images Co-authored-by: clavin * Apply "future" revert commit to fix windows build > Reason for revert: Multiple eng reporting that this is causing build failures due to too-long pathnames, with no immediate feasible workaround This issue also affects our CI builds. Problematic CL in current roll: 6494836: [webgl] Add stub WebGL[2]RenderingContextWebGPU | https://chromium-review.googlesource.com/c/chromium/src/+/6494836 "Future" revert CL: 6565622: Revert "[webgl] Add stub WebGL[2]RenderingContextWebGPU" | https://chromium-review.googlesource.com/c/chromium/src/+/6565622 This patch should automatically disappear when we roll the revert. Co-authored-by: clavin * 6533919: win: don't add WS_CAPTION style to popup windows https://chromium-review.googlesource.com/c/chromium/src/+/6533919 This mirrors the change made earlier to the code ours is based on: 6374074: [headless] Provide headless aware window metrics on Windows | https://chromium-review.googlesource.com/c/chromium/src/+/6374074 Co-authored-by: clavin * chore: update patches --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: David Sanders Co-authored-by: Keeley Hammond Co-authored-by: Samuel Maddock Co-authored-by: clavin Co-authored-by: John Kleinschmidt --- DEPS | 2 +- patches/chromium/.patches | 1 + ...adjust_accessibility_ui_for_electron.patch | 26 +- ..._windows_to_have_different_web_prefs.patch | 8 +- .../build_add_electron_tracing_category.patch | 2 +- ..._depend_on_packed_resource_integrity.patch | 14 +- patches/chromium/build_gn.patch | 2 +- .../build_libc_as_static_library.patch | 2 +- patches/chromium/can_create_window.patch | 20 +- ...hore_add_electron_deps_to_gitignores.patch | 4 +- ...ther_in_electron_views_and_delegates.patch | 2 +- ..._introduce_blocking_api_for_electron.patch | 6 +- ...fy_chromium_handling_of_mouse_events.patch | 12 +- .../chromium/chore_partial_revert_of.patch | 4 +- ...screationoverridden_with_full_params.patch | 26 +- ..._is_test_on_script_injection_tracker.patch | 15 +- patches/chromium/disable_hidden.patch | 4 +- .../chromium/enable_reset_aspect_ratio.patch | 8 +- ...xpose_setuseragent_on_networkcontext.patch | 4 +- ...d_data_parameter_to_processsingleton.patch | 13 +- ...ing_dialog_features_to_shell_dialogs.patch | 103 +- ...t_allow_code_cache_in_custom_schemes.patch | 2 +- ...sharingpicker_on_supported_platforms.patch | 2 +- ...e_launch_options_for_service_process.patch | 6 +- ...moothing_css_rule_and_blink_painting.patch | 24 +- ...screen_rendering_with_viz_compositor.patch | 4 +- ...same_application_can_use_safestorage.patch | 14 +- ..._raw_response_headers_from_urlloader.patch | 18 +- ...ivate_background_material_on_windows.patch | 8 +- .../fix_aspect_ratio_with_max_size.patch | 4 +- ...ding_non-standard_schemes_in_iframes.patch | 6 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ...x_remove_caption-removing_style_call.patch | 4 +- ...original_resize_performance_on_macos.patch | 4 +- ...from_localframe_requestexecutescript.patch | 4 +- patches/chromium/frame_host_manager.patch | 4 +- .../chromium/gritsettings_resource_ids.patch | 2 +- ...sync_with_host_os_mac_on_linux_in_ci.patch | 2 +- ..._avoid_private_macos_api_usage.patch.patch | 40 +- ...emote_certificate_verification_logic.patch | 10 +- .../chromium/notification_provenance.patch | 6 +- ...utofill_colors_to_the_color_pipeline.patch | 6 +- patches/chromium/printing.patch | 4 +- patches/chromium/process_singleton.patch | 6 +- ...r_changes_to_the_webcontentsobserver.patch | 12 +- ..._expose_file_system_access_blocklist.patch | 8 +- ...efactor_unfilter_unresponsive_events.patch | 4 +- ...ean_up_stale_macwebcontentsocclusion.patch | 8 +- ..._stub_webgl_2_renderingcontextwebgpu.patch | 4219 +++++++++++++++++ patches/chromium/scroll_bounce_flag.patch | 4 +- .../support_mixed_sandbox_with_zygote.patch | 4 +- patches/chromium/web_contents.patch | 8 +- patches/chromium/webview_fullscreen.patch | 10 +- .../worker_context_will_destroy.patch | 10 +- ...feat_add_hook_to_notify_script_ready.patch | 10 +- ...i_to_allow_electron_to_set_dock_side.patch | 2 +- shell/browser/electron_browser_client.cc | 9 +- shell/browser/electron_navigation_throttle.cc | 4 +- shell/browser/electron_navigation_throttle.h | 3 +- .../resources_private_api.cc | 2 +- ...on_component_extension_resource_manager.cc | 1 - shell/browser/ui/views/win_frame_view.cc | 4 +- .../api/electron_api_native_image_mac.mm | 2 +- .../corner-smoothing/shape/expected-false.png | Bin 125457 -> 133445 bytes .../corner-smoothing/shape/expected-true.png | Bin 117286 -> 135835 bytes 65 files changed, 4461 insertions(+), 325 deletions(-) create mode 100644 patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch diff --git a/DEPS b/DEPS index ac72ef0228819..c844729724ca5 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7178.0', + '138.0.7190.0', 'node_version': 'v22.15.1', 'nan_version': diff --git a/patches/chromium/.patches b/patches/chromium/.patches index e49e542bf3caa..6cd66748b9cc4 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -143,3 +143,4 @@ fix_enable_wrap_iter_in_string_view_and_array.patch fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch +revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch diff --git a/patches/chromium/adjust_accessibility_ui_for_electron.patch b/patches/chromium/adjust_accessibility_ui_for_electron.patch index 13cd0e0b16c03..894fd5344d31b 100644 --- a/patches/chromium/adjust_accessibility_ui_for_electron.patch +++ b/patches/chromium/adjust_accessibility_ui_for_electron.patch @@ -10,7 +10,7 @@ usage of BrowserList and Browser as we subclass related methods and use our WindowList. diff --git a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc -index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49c4515aa4 100644 +index afd58dd8c32582c17a3a9508f0755ac894022a40..7034cb00d27e2c6ca06d89ae59365934762a402b 100644 --- a/chrome/browser/ui/webui/accessibility/accessibility_ui.cc +++ b/chrome/browser/ui/webui/accessibility/accessibility_ui.cc @@ -48,6 +48,7 @@ @@ -20,8 +20,8 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 +#include "electron/shell/browser/electron_browser_context.h" #include "ui/accessibility/accessibility_features.h" #include "ui/accessibility/ax_updates_and_events.h" - #include "ui/accessibility/platform/ax_platform_node.h" -@@ -169,7 +170,7 @@ base::Value::Dict BuildTargetDescriptor(content::RenderViewHost* rvh) { + #include "ui/accessibility/platform/ax_platform.h" +@@ -174,7 +175,7 @@ base::Value::Dict BuildTargetDescriptor(content::RenderViewHost* rvh) { rvh->GetRoutingID(), accessibility_mode); } @@ -30,7 +30,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 base::Value::Dict BuildTargetDescriptor(Browser* browser) { base::Value::Dict target_data; target_data.Set(kSessionIdField, browser->session_id().id()); -@@ -193,7 +194,7 @@ void HandleAccessibilityRequestCallback( +@@ -198,7 +199,7 @@ void HandleAccessibilityRequestCallback( auto& browser_accessibility_state = *content::BrowserAccessibilityState::GetInstance(); base::Value::Dict data; @@ -39,8 +39,8 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 ui::AXMode mode = browser_accessibility_state.GetAccessibilityMode(); bool native = mode.has_mode(ui::AXMode::kNativeAPIs); bool web = mode.has_mode(ui::AXMode::kWebContents); -@@ -246,7 +247,7 @@ void HandleAccessibilityRequestCallback( - initial_process_mode.has_mode(ui::AXMode::kHTML))); +@@ -259,7 +260,7 @@ void HandleAccessibilityRequestCallback( + data.Set(kIsScreenReaderActive, is_screen_reader_active); std::string pref_api_type = - pref->GetString(prefs::kShownAccessibilityApiType); @@ -48,7 +48,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 bool pref_api_type_supported = false; std::vector supported_api_types = -@@ -314,11 +315,11 @@ void HandleAccessibilityRequestCallback( +@@ -327,11 +328,11 @@ void HandleAccessibilityRequestCallback( data.Set(kPagesField, std::move(page_list)); base::Value::List browser_list; @@ -62,7 +62,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 data.Set(kBrowsersField, std::move(browser_list)); std::string json_string; -@@ -792,7 +793,8 @@ void AccessibilityUIMessageHandler::SetGlobalString( +@@ -805,7 +806,8 @@ void AccessibilityUIMessageHandler::SetGlobalString( const std::string value = CheckJSValue(data.FindString(kValueField)); if (string_name == kApiTypeField) { @@ -72,7 +72,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 pref->SetString(prefs::kShownAccessibilityApiType, value); } } -@@ -846,7 +848,8 @@ void AccessibilityUIMessageHandler::RequestWebContentsTree( +@@ -859,7 +861,8 @@ void AccessibilityUIMessageHandler::RequestWebContentsTree( AXPropertyFilter::ALLOW_EMPTY); AddPropertyFilters(property_filters, deny, AXPropertyFilter::DENY); @@ -82,7 +82,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 ui::AXApiType::Type api_type = ui::AXApiType::From(pref->GetString(prefs::kShownAccessibilityApiType)); std::string accessibility_contents = -@@ -873,6 +876,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( +@@ -886,6 +889,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( AXPropertyFilter::ALLOW_EMPTY); AddPropertyFilters(property_filters, deny, AXPropertyFilter::DENY); @@ -90,7 +90,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 for (Browser* browser : *BrowserList::GetInstance()) { if (browser->session_id().id() == session_id) { base::Value::Dict result = BuildTargetDescriptor(browser); -@@ -885,6 +889,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( +@@ -898,6 +902,7 @@ void AccessibilityUIMessageHandler::RequestNativeUITree( return; } } @@ -98,7 +98,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 #endif // !BUILDFLAG(IS_ANDROID) // No browser with the specified |session_id| was found. base::Value::Dict result; -@@ -928,11 +933,13 @@ void AccessibilityUIMessageHandler::StopRecording( +@@ -941,11 +946,13 @@ void AccessibilityUIMessageHandler::StopRecording( } ui::AXApiType::Type AccessibilityUIMessageHandler::GetRecordingApiType() { @@ -115,7 +115,7 @@ index 476b993aa130a1e7d2bc61993b27044d674425bc..3c5dfca61be10f2fd4126a8ba5bcfa49 // Check to see if it is in the supported types list. if (std::find(supported_types.begin(), supported_types.end(), api_type) == supported_types.end()) { -@@ -1002,8 +1009,11 @@ void AccessibilityUIMessageHandler::RequestAccessibilityEvents( +@@ -1015,8 +1022,11 @@ void AccessibilityUIMessageHandler::RequestAccessibilityEvents( // static void AccessibilityUIMessageHandler::RegisterProfilePrefs( user_prefs::PrefRegistrySyncable* registry) { diff --git a/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch b/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch index 426dc24c4eb0a..912663a418587 100644 --- a/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch +++ b/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch @@ -8,7 +8,7 @@ WebPreferences of in-process child windows, rather than relying on process-level command line switches, as before. diff --git a/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc b/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc -index 9fe216ae76191985751c5aff735cb38ba747a5cb..274dbe4fe45f5ca03e4f93fa1ef94f22ca3559ed 100644 +index b3e72c9d198a350a164d4abc37fcb19024f43c57..909ac417f24c0e104cba286b6420d8c820784d31 100644 --- a/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc +++ b/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc @@ -149,6 +149,19 @@ bool StructTraitsaccelerated_video_decode_enabled = data.accelerated_video_decode_enabled(); diff --git a/third_party/blink/public/common/web_preferences/web_preferences.h b/third_party/blink/public/common/web_preferences/web_preferences.h -index 2d9ef567d7aba3d78ecb0637fc7a31cbaaba564b..9c6c5e3b2668bdfa3ec1f5f0482bc1294bfed9b0 100644 +index 1ee685e777e27a56da50d38ae7710abb240699a1..7f0ed7e9b0c4c0077eaa733e81ebc421f0ddd02a 100644 --- a/third_party/blink/public/common/web_preferences/web_preferences.h +++ b/third_party/blink/public/common/web_preferences/web_preferences.h @@ -9,6 +9,7 @@ @@ -65,7 +65,7 @@ index 2d9ef567d7aba3d78ecb0637fc7a31cbaaba564b..9c6c5e3b2668bdfa3ec1f5f0482bc129 // chrome, except for the cases where it would require lots of extra work for // the embedder to use the same default value. diff --git a/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h b/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h -index 86e4152b85d85ed3c620458567509e0eaa2ad5d8..6f39bf14c42278dc8ada95902868608bd6a6f171 100644 +index 36a5fb0b42be57e9602c0709b6abb55385f48666..306838bbf7c6d5cddd95e09d703e41d1deac21ab 100644 --- a/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h +++ b/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h @@ -8,6 +8,7 @@ @@ -130,7 +130,7 @@ index 86e4152b85d85ed3c620458567509e0eaa2ad5d8..6f39bf14c42278dc8ada95902868608b return r.cookie_enabled; } diff --git a/third_party/blink/public/mojom/webpreferences/web_preferences.mojom b/third_party/blink/public/mojom/webpreferences/web_preferences.mojom -index 41d33c9ecebf615162dc8a9fa1653d32bdaa8d66..6891f25242b83c113a26c2919663a33da8a9b2d7 100644 +index 9de5f6dafc754b6ee8d894ccd9747a18b8c8efde..dbdf9f48beaa7b5dcc528906d7bfec66c2ebb89f 100644 --- a/third_party/blink/public/mojom/webpreferences/web_preferences.mojom +++ b/third_party/blink/public/mojom/webpreferences/web_preferences.mojom @@ -8,9 +8,11 @@ import "third_party/blink/public/mojom/css/preferred_color_scheme.mojom"; diff --git a/patches/chromium/build_add_electron_tracing_category.patch b/patches/chromium/build_add_electron_tracing_category.patch index c8b228545b265..374dbbf156f70 100644 --- a/patches/chromium/build_add_electron_tracing_category.patch +++ b/patches/chromium/build_add_electron_tracing_category.patch @@ -8,7 +8,7 @@ categories in use are known / declared. This patch is required for us to introduce a new Electron category for Electron-specific tracing. diff --git a/base/trace_event/builtin_categories.h b/base/trace_event/builtin_categories.h -index d4c70f285fa6798798558974d7d79604dd388909..31f396bb437b7089930c05e6b1067bc156155be1 100644 +index e149fca0c6c38eb3898735cb38e41443af61b6d8..24ab0a9b37299e62176167507215351ecc54092b 100644 --- a/base/trace_event/builtin_categories.h +++ b/base/trace_event/builtin_categories.h @@ -102,6 +102,7 @@ PERFETTO_DEFINE_CATEGORIES_IN_NAMESPACE_WITH_ATTRS( diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index d82d630d019c2..000d9a91df9fb 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -33,10 +33,10 @@ index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff6 "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index 186cbeb02aa7b4e5b22800ece7cbc4791777356a..7137860ba1423a5ff36b85952790c5b25d6adf9d 100644 +index 74d78554a4816e76cbf800762386444520c32906..c89251393bdd9439aa768e3d516516dfc4b18824 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4674,7 +4674,7 @@ static_library("browser") { +@@ -4681,7 +4681,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,10 +46,10 @@ index 186cbeb02aa7b4e5b22800ece7cbc4791777356a..7137860ba1423a5ff36b85952790c5b2 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 4a299a91dccd83f5e9595bdab2317c6ed9b26920..16f2e321030d61ee2cbab91c15fc93da3cf735b5 100644 +index 9dc89f62b8cc049955d8faa4dcbd4904776580ee..cd3b00e4c2a22819e8bd4844cfa5048403f9a70a 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7209,9 +7209,12 @@ test("unit_tests") { +@@ -7216,9 +7216,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index 4a299a91dccd83f5e9595bdab2317c6ed9b26920..16f2e321030d61ee2cbab91c15fc93da "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8180,6 +8183,10 @@ test("unit_tests") { +@@ -8182,6 +8185,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,8 +74,8 @@ index 4a299a91dccd83f5e9595bdab2317c6ed9b26920..16f2e321030d61ee2cbab91c15fc93da sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8235,7 +8242,6 @@ test("unit_tests") { - # Non-android deps for "unit_tests" target. +@@ -8239,7 +8246,6 @@ test("unit_tests") { + # TODO(crbug.com/417513088): Maybe merge with the non-android `deps` declaration above? deps += [ "../browser/screen_ai:screen_ai_install_state", - "//chrome:packed_resources_integrity_header", diff --git a/patches/chromium/build_gn.patch b/patches/chromium/build_gn.patch index 2a059f803d50e..fd519adbff7a2 100644 --- a/patches/chromium/build_gn.patch +++ b/patches/chromium/build_gn.patch @@ -7,7 +7,7 @@ These are variables we add to the root BUILDCONFIG so that they're available everywhere, without having to import("//electron/.../flags.gni"). diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn -index c3a3bf4970783804bc76ee4e71bb8233b5f215a8..78c72710b411e05ca0b6f01811076599fa66fc15 100644 +index 32cbfa5cfee7f9a2f2d9e696fb54ee753dda4f6c..cc9d083a598aa1e07bf60bc961c5ddcd730921bf 100644 --- a/build/config/BUILDCONFIG.gn +++ b/build/config/BUILDCONFIG.gn @@ -123,6 +123,9 @@ if (current_os == "") { diff --git a/patches/chromium/build_libc_as_static_library.patch b/patches/chromium/build_libc_as_static_library.patch index 1b7d654c50d52..1851ebc6154c3 100644 --- a/patches/chromium/build_libc_as_static_library.patch +++ b/patches/chromium/build_libc_as_static_library.patch @@ -7,7 +7,7 @@ Build libc++ as static library to compile and pass nan tests diff --git a/buildtools/third_party/libc++/BUILD.gn b/buildtools/third_party/libc++/BUILD.gn -index 2b4c153a67fda5effaac8d2932a985d87539fe69..c0c310ecbf74b8c1649bcd23ebe1c142c088fc9f 100644 +index 73c197f3cecd7ff34e97326cbf615e7c78919a54..1e93e7ce444cd5c31ddeac86fb1549c648a9a5c0 100644 --- a/buildtools/third_party/libc++/BUILD.gn +++ b/buildtools/third_party/libc++/BUILD.gn @@ -298,6 +298,7 @@ target(libcxx_target_type, "libc++") { diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index c808d727ab876..97d4048b611d7 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,10 +9,10 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index db20a849f0e093a940587f94d777b7941882443d..e87536a31d03d8030b26781b9345fa7478d24afd 100644 +index 4c1785b8b7dcc2e0543b12bc4c765c8f0c833451..be73611db5328c76982ecca3caf5eccc30aac45e 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -9711,6 +9711,7 @@ void RenderFrameHostImpl::CreateNewWindow( +@@ -9718,6 +9718,7 @@ void RenderFrameHostImpl::CreateNewWindow( last_committed_origin_, params->window_container_type, params->target_url, params->referrer.To(), params->frame_name, params->disposition, *params->features, @@ -21,10 +21,10 @@ index db20a849f0e093a940587f94d777b7941882443d..e87536a31d03d8030b26781b9345fa74 &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index af97a08179fd92e71daff17ca75cf4c6c06be1cc..65a3b57c38419c15b071e67852789b48533fe53a 100644 +index 8bd0e1d60f6f1af48b106f25d8e8951423eb05ed..c0ef22f3872e96be15867428aff1006b8a14a1df 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5155,6 +5155,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5308,6 +5308,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( // Sets the newly created WebContents WindowOpenDisposition. new_contents_impl->original_window_open_disposition_ = params.disposition; @@ -37,7 +37,7 @@ index af97a08179fd92e71daff17ca75cf4c6c06be1cc..65a3b57c38419c15b071e67852789b48 // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5196,12 +5202,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5349,12 +5355,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -66,7 +66,7 @@ index 09f1899c9b044a05b2e40c291f17fdf1f9f2fcac..89643bf7059d4fc0d6de6116ffe0fdac // Operation result when the renderer asks the browser to create a new window. diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc -index e8a1b16cbe8aeb9c185de622250b73c402d56228..38a9b7ae1548f86ae700acc41565f340ed4dbff5 100644 +index eb036b92b42d794cabd71f4c6314962df8988bbb..0ec4e4f41d261f60cb8e963ca1d715b765e7c47d 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc @@ -842,6 +842,8 @@ bool ContentBrowserClient::CanCreateWindow( @@ -79,7 +79,7 @@ index e8a1b16cbe8aeb9c185de622250b73c402d56228..38a9b7ae1548f86ae700acc41565f340 bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 9061895e64ce94700692b0b990f22a32b5e0e353..bd3cccc408c61f4c4e408fd5d093d6aa1ef0e201 100644 +index 8c53f1aab26cf78ae0526ae51c1738019f1c0b90..0a74c5a3bee425c5c1af33ef27791a6d852baa6e 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -200,6 +200,7 @@ class NetworkService; @@ -90,7 +90,7 @@ index 9061895e64ce94700692b0b990f22a32b5e0e353..bd3cccc408c61f4c4e408fd5d093d6aa } // namespace network namespace sandbox { -@@ -1404,6 +1405,8 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -1403,6 +1404,8 @@ class CONTENT_EXPORT ContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -210,10 +210,10 @@ index 82e9d3dfb5f7da76d89fe15ae61d379fa46e177d..fd035512099a54dff6cc951a2226c23a } // namespace blink diff --git a/third_party/blink/renderer/core/frame/local_dom_window.cc b/third_party/blink/renderer/core/frame/local_dom_window.cc -index 6de4ad918b8c1d2a3dfb977ed80ea232dbbee9c1..f983903112efd76c8bd73656a0de5e54026e6d1b 100644 +index 382daacf9b2ea77c4d8814fa375ecbbd830cce50..4728a4b7c064fc902317115637b6e64f068b25a8 100644 --- a/third_party/blink/renderer/core/frame/local_dom_window.cc +++ b/third_party/blink/renderer/core/frame/local_dom_window.cc -@@ -2280,6 +2280,8 @@ DOMWindow* LocalDOMWindow::open(v8::Isolate* isolate, +@@ -2293,6 +2293,8 @@ DOMWindow* LocalDOMWindow::open(v8::Isolate* isolate, WebWindowFeatures window_features = GetWindowFeaturesFromString(features, entered_window); diff --git a/patches/chromium/chore_add_electron_deps_to_gitignores.patch b/patches/chromium/chore_add_electron_deps_to_gitignores.patch index 029afcacac7a2..495a6c703fffb 100644 --- a/patches/chromium/chore_add_electron_deps_to_gitignores.patch +++ b/patches/chromium/chore_add_electron_deps_to_gitignores.patch @@ -6,10 +6,10 @@ Subject: chore: add electron deps to gitignores Makes things like "git status" quicker when developing electron locally diff --git a/.gitignore b/.gitignore -index 0a0f0118d5c1a5a2f3ad28b068bebb849eba7246..5ca6d03b709ef119ccd6482b2f305f8a3aeb7438 100644 +index 469572522566fa57f04bc66ade675eea2048b0df..852d842df3801564cfe8dd7c4ffb84a7b3af8fc1 100644 --- a/.gitignore +++ b/.gitignore -@@ -217,6 +217,7 @@ vs-chromium-project.txt +@@ -220,6 +220,7 @@ vs-chromium-project.txt /data /delegate_execute /device/serial/device_serial_mojo.xml diff --git a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch index 393e2d4ba08bc..598f8cdb6a2fe 100644 --- a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch +++ b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch @@ -10,7 +10,7 @@ Subject: chore: "grandfather in" Electron Views and Delegates 6448510: Lock further access to View::set_owned_by_client(). | https://chromium-review.googlesource.com/c/chromium/src/+/6448510 diff --git a/ui/views/view.h b/ui/views/view.h -index ae7eab37f12ba80ec423d229cf048021e9ba6765..507a75dc7947295db221b01356fa57baf3cf03e4 100644 +index 0dbbd7979ad79a7a74681222fcf36a315f0634ce..b04e77440c1273c5b866ea329e62ac07fdcf5404 100644 --- a/ui/views/view.h +++ b/ui/views/view.h @@ -82,6 +82,19 @@ class ArcNotificationContentView; diff --git a/patches/chromium/chore_introduce_blocking_api_for_electron.patch b/patches/chromium/chore_introduce_blocking_api_for_electron.patch index 0fbdb80214b08..cb012a2a811bd 100644 --- a/patches/chromium/chore_introduce_blocking_api_for_electron.patch +++ b/patches/chromium/chore_introduce_blocking_api_for_electron.patch @@ -7,7 +7,7 @@ This patch comes after Chromium removed the ScopedAllowIO API in favor of explicitly adding ScopedAllowBlocking calls as friends. diff --git a/base/threading/thread_restrictions.h b/base/threading/thread_restrictions.h -index b1abcfaab58df4555d3a26481915d64ef5458e17..f2f43454c1c124da9983998564837ebf3589aefd 100644 +index 20d867b5d56cd6d961004b19bd3e69ee306dd816..07db0c05df4ce028017e70e6f593235516aa556e 100644 --- a/base/threading/thread_restrictions.h +++ b/base/threading/thread_restrictions.h @@ -132,6 +132,7 @@ class KeyStorageLinux; @@ -28,7 +28,7 @@ index b1abcfaab58df4555d3a26481915d64ef5458e17..f2f43454c1c124da9983998564837ebf namespace enterprise_connectors { class LinuxKeyRotationCommand; } // namespace enterprise_connectors -@@ -577,6 +581,7 @@ class BASE_EXPORT ScopedAllowBlocking { +@@ -578,6 +582,7 @@ class BASE_EXPORT ScopedAllowBlocking { friend class ::DesktopNotificationBalloon; friend class ::FirefoxProfileLock; friend class ::GaiaConfig; @@ -36,7 +36,7 @@ index b1abcfaab58df4555d3a26481915d64ef5458e17..f2f43454c1c124da9983998564837ebf friend class ::ProfileImpl; friend class ::ScopedAllowBlockingForProfile; friend class ::StartupTabProviderImpl; -@@ -615,6 +620,7 @@ class BASE_EXPORT ScopedAllowBlocking { +@@ -616,6 +621,7 @@ class BASE_EXPORT ScopedAllowBlocking { friend class cronet::CronetPrefsManager; friend class crypto::ScopedAllowBlockingForNSS; // http://crbug.com/59847 friend class drive::FakeDriveService; diff --git a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch index afe116bc3ed65..8dc23c774a1d4 100644 --- a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch +++ b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch @@ -34,10 +34,10 @@ index 39b5a8fdd165efd74b00256552b51b5413107958..bfc4ef4f50efff4a77f2aef64335bb7e class ScrollEvent; diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index 5f9612ff000c1544f572bab0cbc9982dc4e647ce..2ce65548dd1283adb4c095e37198e08a8a13635c 100644 +index 3c273b08e3a0cb1a249334b06244bb6b89fde27f..20fcbe09d9fe9104cbe791e03b02f8e2e5064c2d 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -@@ -1415,6 +1415,10 @@ void DesktopWindowTreeHostWin::HandleHeadlessWindowBoundsChanged( +@@ -1382,6 +1382,10 @@ void DesktopWindowTreeHostWin::HandleHeadlessWindowBoundsChanged( window()->SetProperty(aura::client::kHeadlessBoundsKey, bounds); } @@ -61,10 +61,10 @@ index dab595aacaeca4f6f735fd04004c27a4949278d2..177134d439866db9dbbde657ff358a76 Widget* GetWidget(); const Widget* GetWidget() const; diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 9747e945b2ebfc113ffd12839c28a98fcccf2872..6f2e2702d3b982fe7e8d258f303c8055d3d37df8 100644 +index 418dc47b6d4df097e8f0cfd61de8485af2a8d2c2..8c13b9db078e690240eca0a48a7c546dcdac3c11 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -3167,15 +3167,19 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3171,15 +3171,19 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, } // We must let Windows handle the caption buttons if it's drawing them, or // they won't work. @@ -86,7 +86,7 @@ index 9747e945b2ebfc113ffd12839c28a98fcccf2872..6f2e2702d3b982fe7e8d258f303c8055 return 0; } } -@@ -3198,6 +3202,7 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3202,6 +3206,7 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, // handle alt-space, or in the frame itself. is_right_mouse_pressed_on_caption_ = false; ReleaseCapture(); @@ -94,7 +94,7 @@ index 9747e945b2ebfc113ffd12839c28a98fcccf2872..6f2e2702d3b982fe7e8d258f303c8055 // |point| is in window coordinates, but WM_NCHITTEST and TrackPopupMenu() // expect screen coordinates. POINT screen_point = CR_POINT_INITIALIZER_FROM_LPARAM(l_param); -@@ -3205,7 +3210,17 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3209,7 +3214,17 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, w_param = static_cast(SendMessage( hwnd(), WM_NCHITTEST, 0, MAKELPARAM(screen_point.x, screen_point.y))); if (w_param == HTCAPTION || w_param == HTSYSMENU) { diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 28fd072806d30..290f57a3ca584 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index acb6b6257ccb13aae284d9b02baada14fe9ee0cc..9269ef00d1c0ce0606a39533b839e061ba448d7e 100644 +index 29185fc4c426652d192870c8a11aaa981a08ebf8..de2e8163c6ae5a1a01a79413d3d44b7c11ede311 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5071,7 +5071,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5224,7 +5224,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index 21d7bbf36b361..2014d114c1799 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -80,10 +80,10 @@ index b6582b4013d9682d32bd524b4053b443a4df00f8..afcbce72e0f247b4d5a637b27c9f25d9 content::WebContents* source, const content::OpenURLParams& params, diff --git a/chrome/browser/ui/browser.cc b/chrome/browser/ui/browser.cc -index 1bea3ad5b3c9960a7b1193e232b0c1f5c847e79d..0f416f0eeadca6bc7cc559d8879c694b7ccf62e6 100644 +index 875c7a37c48ce50b5439a51df5e505e1bbcd5155..035432c70a6b65a2520f130e0db8a91f20e92770 100644 --- a/chrome/browser/ui/browser.cc +++ b/chrome/browser/ui/browser.cc -@@ -2406,8 +2406,7 @@ bool Browser::IsWebContentsCreationOverridden( +@@ -2392,8 +2392,7 @@ bool Browser::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -93,7 +93,7 @@ index 1bea3ad5b3c9960a7b1193e232b0c1f5c847e79d..0f416f0eeadca6bc7cc559d8879c694b if (IsActorCoordinatorActingOnTab( profile(), content::WebContents::FromRenderFrameHost(opener))) { // If an ActorCoordinator is acting on the opener, prevent it from creating -@@ -2419,7 +2418,7 @@ bool Browser::IsWebContentsCreationOverridden( +@@ -2405,7 +2404,7 @@ bool Browser::IsWebContentsCreationOverridden( return (window_container_type == content::mojom::WindowContainerType::BACKGROUND && ShouldCreateBackgroundContents(source_site_instance, opener_url, @@ -103,10 +103,10 @@ index 1bea3ad5b3c9960a7b1193e232b0c1f5c847e79d..0f416f0eeadca6bc7cc559d8879c694b WebContents* Browser::CreateCustomWebContents( diff --git a/chrome/browser/ui/browser.h b/chrome/browser/ui/browser.h -index 5d3ab970d01b20bef2c715ab8bc65187814b0008..6efef3f3e9c7005fae59a404929d80bebe965f02 100644 +index 9dfba94b0aaa3f27f363bd50b489cae9e0e3cda6..3867e5d5741103ee0b65533dae4b80906b393f59 100644 --- a/chrome/browser/ui/browser.h +++ b/chrome/browser/ui/browser.h -@@ -1041,8 +1041,7 @@ class Browser : public TabStripModelObserver, +@@ -1037,8 +1037,7 @@ class Browser : public TabStripModelObserver, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -159,10 +159,10 @@ index 1c30afe192809d85ced6af595347353ec3cb5364..af48bb2755c33f6c372be6b51048b3cf } content::WebContents* CreateCustomWebContents( diff --git a/components/embedder_support/android/delegate/web_contents_delegate_android.cc b/components/embedder_support/android/delegate/web_contents_delegate_android.cc -index 37260552fcc42edcac08422bdf6cb9f0f4b09c39..461fb20c1093cf2de06f9bb6f41f80ab0017b6a1 100644 +index 807f43c164015e9372623b6ca9db1293640a530f..5e1875cde93f27e3d0324c84b94f076b33123495 100644 --- a/components/embedder_support/android/delegate/web_contents_delegate_android.cc +++ b/components/embedder_support/android/delegate/web_contents_delegate_android.cc -@@ -190,14 +190,13 @@ bool WebContentsDelegateAndroid::IsWebContentsCreationOverridden( +@@ -199,14 +199,13 @@ bool WebContentsDelegateAndroid::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -180,10 +180,10 @@ index 37260552fcc42edcac08422bdf6cb9f0f4b09c39..461fb20c1093cf2de06f9bb6f41f80ab java_gurl); } diff --git a/components/embedder_support/android/delegate/web_contents_delegate_android.h b/components/embedder_support/android/delegate/web_contents_delegate_android.h -index 996b3d453b375fec2a823a0dd0d3122ba626b5f2..5a5c6ed67f698fdd914e79df528e2ca391e056b7 100644 +index 7a8cdc28f87399e494a58490cdc4ac0dd4b06520..0c2a83b44f6909b5b3a6303715e1611d039711bb 100644 --- a/components/embedder_support/android/delegate/web_contents_delegate_android.h +++ b/components/embedder_support/android/delegate/web_contents_delegate_android.h -@@ -83,8 +83,7 @@ class WebContentsDelegateAndroid : public content::WebContentsDelegate { +@@ -84,8 +84,7 @@ class WebContentsDelegateAndroid : public content::WebContentsDelegate { content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -222,10 +222,10 @@ index b969f1d97b7e3396119b579cfbe61e19ff7d2dd4..b8d6169652da28266a514938b45b39c5 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index fcb7a38577a7b597be09b73cea9308b7112fee2a..3435a1d0ce5c8025b5a2005ebb4066e306579a69 100644 +index 6eaa7d566058fdcc9ebfa10f0420c3a234cb0483..bbbc07e36e6de11169f8317c64558b8c4d1699d5 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5034,8 +5034,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5187,8 +5187,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( if (delegate_ && delegate_->IsWebContentsCreationOverridden( opener, source_site_instance, params.window_container_type, @@ -356,10 +356,10 @@ index 7eeffdfbda9611806c6f260f0c68f6d84689cb7e..5d8f6d132068d7fabaa52bc61354c71a content::RenderFrameHost* opener, content::SiteInstance* source_site_instance, diff --git a/fuchsia_web/webengine/browser/frame_impl.cc b/fuchsia_web/webengine/browser/frame_impl.cc -index c61784e1d0717063e5aefd05d7c09358bae5b8c5..b987c5660942e94f89ff19cc55e032e4cb693863 100644 +index bd09d0f34a1610d64a1438b618ef5b3786315e91..4b2a979db1e00bc0d7f3b1b54570c305070acccc 100644 --- a/fuchsia_web/webengine/browser/frame_impl.cc +++ b/fuchsia_web/webengine/browser/frame_impl.cc -@@ -579,8 +579,7 @@ bool FrameImpl::IsWebContentsCreationOverridden( +@@ -581,8 +581,7 @@ bool FrameImpl::IsWebContentsCreationOverridden( content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, diff --git a/patches/chromium/chore_remove_check_is_test_on_script_injection_tracker.patch b/patches/chromium/chore_remove_check_is_test_on_script_injection_tracker.patch index 31dfe317fe9ae..b1832a7542bd3 100644 --- a/patches/chromium/chore_remove_check_is_test_on_script_injection_tracker.patch +++ b/patches/chromium/chore_remove_check_is_test_on_script_injection_tracker.patch @@ -9,15 +9,14 @@ Electron when a session is non persistent we do not initialize the ExtensionSystem, so this check is not relevant for Electron. diff --git a/extensions/browser/script_injection_tracker.cc b/extensions/browser/script_injection_tracker.cc -index 172f02dbe9bb22425f8d45119b6d8466c949ba36..063015e14053f75544e6700c9251d6ecae95389c 100644 +index 8f590b9ebd02969f0c5d9f617852954a69f51afd..91c4a61525173d2cd95a8c2c626c1be5a84b003f 100644 --- a/extensions/browser/script_injection_tracker.cc +++ b/extensions/browser/script_injection_tracker.cc -@@ -178,7 +178,7 @@ std::vector GetLoadedDynamicScripts( +@@ -176,7 +176,6 @@ std::vector GetLoadedDynamicScripts( + UserScriptManager* manager = + ExtensionSystem::Get(process.GetBrowserContext())->user_script_manager(); if (!manager) { - // TODO(crbug.com/412829476): Remove this guard once we enable - // UserScriptManager on desktop Android. --#if BUILDFLAG(ENABLE_EXTENSIONS) -+#if 0 - CHECK_IS_TEST(); - #endif +- CHECK_IS_TEST(); return std::vector(); + } + diff --git a/patches/chromium/disable_hidden.patch b/patches/chromium/disable_hidden.patch index b5aff925031b1..7c6ef540c4a15 100644 --- a/patches/chromium/disable_hidden.patch +++ b/patches/chromium/disable_hidden.patch @@ -6,10 +6,10 @@ Subject: disable_hidden.patch Electron uses this to disable background throttling for hidden windows. diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 43174a968fa1394d8c995adda338c15cace4e7be..a1cec61f882c38efa611401da69de123c99c9e7f 100644 +index 8173547224997a68c2878d6dfb26b1cb436353c6..6a60a4b0275e1832216b092c29bc867f4727ca22 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -834,6 +834,10 @@ void RenderWidgetHostImpl::WasHidden() { +@@ -833,6 +833,10 @@ void RenderWidgetHostImpl::WasHidden() { return; } diff --git a/patches/chromium/enable_reset_aspect_ratio.patch b/patches/chromium/enable_reset_aspect_ratio.patch index 5954ee90821d7..e62d786bec980 100644 --- a/patches/chromium/enable_reset_aspect_ratio.patch +++ b/patches/chromium/enable_reset_aspect_ratio.patch @@ -6,10 +6,10 @@ Subject: feat: enable setting aspect ratio to 0 Make SetAspectRatio accept 0 as valid input, which would reset to null. diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index 6240e33c74a0a487affb3ec7e01d6a662d3950b7..5f9612ff000c1544f572bab0cbc9982dc4e647ce 100644 +index f754ca0c3bc3ba9e7ff2f3f883b29c15be2b410a..3c273b08e3a0cb1a249334b06244bb6b89fde27f 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -@@ -664,7 +664,7 @@ void DesktopWindowTreeHostWin::SetOpacity(float opacity) { +@@ -631,7 +631,7 @@ void DesktopWindowTreeHostWin::SetOpacity(float opacity) { void DesktopWindowTreeHostWin::SetAspectRatio( const gfx::SizeF& aspect_ratio, const gfx::Size& excluded_margin) { @@ -19,10 +19,10 @@ index 6240e33c74a0a487affb3ec7e01d6a662d3950b7..5f9612ff000c1544f572bab0cbc9982d excluded_margin); } diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 9a42a64f52ccbab2cab6119c91b69ab44eeeb9e5..2cd46f4692c84cffff0775bbb67d3585f24e900d 100644 +index cb66f6e84abd95080a2051b39d86b1838a6df9bb..c38b58ed16b14ff765f24d0bb8bdf34b8de3a901 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -992,8 +992,11 @@ void HWNDMessageHandler::SetFullscreen(bool fullscreen, +@@ -993,8 +993,11 @@ void HWNDMessageHandler::SetFullscreen(bool fullscreen, void HWNDMessageHandler::SetAspectRatio(float aspect_ratio, const gfx::Size& excluded_margin) { diff --git a/patches/chromium/expose_setuseragent_on_networkcontext.patch b/patches/chromium/expose_setuseragent_on_networkcontext.patch index 53dc349f59ad2..d0e5af5f54773 100644 --- a/patches/chromium/expose_setuseragent_on_networkcontext.patch +++ b/patches/chromium/expose_setuseragent_on_networkcontext.patch @@ -33,10 +33,10 @@ index 0ab8187b0db8ae6db46d81738f653a2bc4c566f6..de3d55e85c22317f7f9375eb94d0d5d4 } // namespace net diff --git a/services/network/network_context.cc b/services/network/network_context.cc -index 7d65c373ac4f1f538085a44ca0b11ddce89b1e62..8d3a7ca4c955a0e5004e3e2a8435591cfbfe2f16 100644 +index 02853bf6552d49986b782785d3ab5a61ec0d3734..5934676556e25e51d580e063aeb0afde2a3f2a97 100644 --- a/services/network/network_context.cc +++ b/services/network/network_context.cc -@@ -1838,6 +1838,13 @@ void NetworkContext::SetNetworkConditions( +@@ -1837,6 +1837,13 @@ void NetworkContext::SetNetworkConditions( std::move(network_conditions)); } diff --git a/patches/chromium/feat_add_data_parameter_to_processsingleton.patch b/patches/chromium/feat_add_data_parameter_to_processsingleton.patch index cd0f620c67470..738ddbf939ea3 100644 --- a/patches/chromium/feat_add_data_parameter_to_processsingleton.patch +++ b/patches/chromium/feat_add_data_parameter_to_processsingleton.patch @@ -13,19 +13,20 @@ app.requestSingleInstanceLock API so that users can pass in a JSON object for the second instance to send to the first instance. diff --git a/chrome/browser/process_singleton.h b/chrome/browser/process_singleton.h -index 085b00fbb3ff95cdcde2a46760ab449808b4c1a9..22d5c994a6944ce7ea725ee045d9801126c32dd4 100644 +index 2748dd196fe1f56357348a204e24f0b8a28b97dd..5800dd00b47c657d9e6766f3fc5a30654cffffa6 100644 --- a/chrome/browser/process_singleton.h +++ b/chrome/browser/process_singleton.h -@@ -18,6 +18,8 @@ +@@ -18,7 +18,8 @@ #include "base/functional/callback.h" #include "base/memory/scoped_refptr.h" #include "base/process/process.h" +- +#include "base/containers/span.h" +#include "base/memory/raw_span.h" - #include "ui/gfx/native_widget_types.h" - #if BUILDFLAG(IS_POSIX) && !BUILDFLAG(IS_ANDROID) -@@ -100,21 +102,24 @@ class ProcessSingleton { + #include "base/files/scoped_temp_dir.h" + #endif +@@ -99,21 +100,24 @@ class ProcessSingleton { // should handle it (i.e., because the current process is shutting down). using NotificationCallback = base::RepeatingCallback results); -+ -+ // Common function for OnSelectSingleFolderDialogResponse and -+ // OnSelectMultiFileDialogResponse. -+ void SelectMultiFileDialogHelper( -+ bool allow_folder, -+ gfx::AcceleratedWidget parent, -+ std::unique_ptr results); -+ - void OnSelectSingleFolderDialogResponse( - gfx::AcceleratedWidget parent, - std::unique_ptr results); -+ void OnSelectMultiFolderDialogResponse( -+ gfx::AcceleratedWidget parent, -+ std::unique_ptr results); - - // Should be either DESKTOP_ENVIRONMENT_KDE3, KDE4, KDE5, or KDE6. - base::nix::DesktopEnvironment desktop_; -@@ -468,6 +479,7 @@ void SelectFileDialogLinuxKde::CreateSelectFolderDialog( - int title_message_id = (type == SELECT_UPLOAD_FOLDER) - ? IDS_SELECT_UPLOAD_FOLDER_DIALOG_TITLE - : IDS_SELECT_FOLDER_DIALOG_TITLE; -+ bool multiple_selection = allow_multiple_selection(); - pipe_task_runner_->PostTaskAndReplyWithResult( - FROM_HERE, - base::BindOnce( -@@ -475,10 +487,12 @@ void SelectFileDialogLinuxKde::CreateSelectFolderDialog( - KDialogParams( - "--getexistingdirectory", GetTitle(title, title_message_id), - default_path.empty() ? *last_opened_path() : default_path, parent, -- false, false)), -+ false, multiple_selection)), - base::BindOnce( -- &SelectFileDialogLinuxKde::OnSelectSingleFolderDialogResponse, this, -- parent)); -+ multiple_selection -+ ? &SelectFileDialogLinuxKde::OnSelectMultiFolderDialogResponse -+ : &SelectFileDialogLinuxKde::OnSelectSingleFolderDialogResponse, -+ this, parent)); - } - - void SelectFileDialogLinuxKde::CreateFileOpenDialog( -@@ -568,7 +582,8 @@ void SelectFileDialogLinuxKde::OnSelectSingleFolderDialogResponse( - SelectSingleFileHelper(true, std::move(results)); - } - --void SelectFileDialogLinuxKde::OnSelectMultiFileDialogResponse( -+void SelectFileDialogLinuxKde::SelectMultiFileDialogHelper( -+ bool allow_folder, - gfx::AcceleratedWidget parent, - std::unique_ptr results) { - DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); -@@ -586,7 +601,7 @@ void SelectFileDialogLinuxKde::OnSelectMultiFileDialogResponse( - base::SplitStringPiece(results->output, "\n", base::KEEP_WHITESPACE, - base::SPLIT_WANT_NONEMPTY)) { - base::FilePath path(line); -- if (CallDirectoryExistsOnUIThread(path)) -+ if (!allow_folder && CallDirectoryExistsOnUIThread(path)) - continue; - filenames_fp.push_back(path); - } -@@ -598,4 +613,16 @@ void SelectFileDialogLinuxKde::OnSelectMultiFileDialogResponse( - MultiFilesSelected(filenames_fp); - } - -+void SelectFileDialogLinuxKde::OnSelectMultiFolderDialogResponse( -+ gfx::AcceleratedWidget parent, -+ std::unique_ptr results) { -+ SelectMultiFileDialogHelper(true, parent, std::move(results)); -+} -+ -+void SelectFileDialogLinuxKde::OnSelectMultiFileDialogResponse( -+ gfx::AcceleratedWidget parent, -+ std::unique_ptr results) { -+ SelectMultiFileDialogHelper(false, parent, std::move(results)); -+} -+ } // namespace ui diff --git a/ui/shell_dialogs/select_file_dialog_linux_portal.cc b/ui/shell_dialogs/select_file_dialog_linux_portal.cc index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db84e8dff6 100644 diff --git a/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch b/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch index a7845a1f9938d..e798bf875ad4d 100644 --- a/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch +++ b/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch @@ -411,7 +411,7 @@ index cf71655553cf510e1309ac47bdd5ddab08e52672..0a02d17d06e080f40bf12bb2e48f51ad std::vector extension_schemes; // Registers a URL scheme with a predefined default custom handler. diff --git a/url/url_util.cc b/url/url_util.cc -index 67c4c5f3ce124e111fb7a70e16386120cf24d9b8..d9876cd58ff28ea1af87596691cd836b815825dd 100644 +index e09d63ee585919842b2b92f9a53b85f67da90531..9e844e2ac9da41dd711497412d03e9b313726162 100644 --- a/url/url_util.cc +++ b/url/url_util.cc @@ -135,6 +135,9 @@ struct SchemeRegistry { diff --git a/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch b/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch index 972a59652bdc6..e72bf218b2d44 100644 --- a/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch +++ b/patches/chromium/feat_allow_usage_of_sccontentsharingpicker_on_supported_platforms.patch @@ -356,7 +356,7 @@ index 23b19cc8405293aa44c4f2c20f715f8443fcd151..21c0c84dc6e3128b641fac682e3069a0 kMaxNumberOfBuffers, std::move(receiver), std::move(receiver_on_io_thread)), diff --git a/content/public/browser/desktop_media_id.h b/content/public/browser/desktop_media_id.h -index 415156d403a59bf426cf4561a9d58ecdb27524b4..78aa7b2359c684d5305bf6352751dfbb7ca00d29 100644 +index 294b5f79955ba72976f8ba127fd19556c81e322c..27553e51b281575c5cb7a4ba4dab06d19704388e 100644 --- a/content/public/browser/desktop_media_id.h +++ b/content/public/browser/desktop_media_id.h @@ -27,6 +27,8 @@ struct CONTENT_EXPORT DesktopMediaID { diff --git a/patches/chromium/feat_configure_launch_options_for_service_process.patch b/patches/chromium/feat_configure_launch_options_for_service_process.patch index cef5d94f3f627..a5c061551451e 100644 --- a/patches/chromium/feat_configure_launch_options_for_service_process.patch +++ b/patches/chromium/feat_configure_launch_options_for_service_process.patch @@ -19,7 +19,7 @@ to STDOUT_FILENO/STD_OUTPUT_HANDLE and STDERR_FILENO/STD_ERROR_HANDLE allowing t parent process to read from the pipe. diff --git a/content/browser/child_process_launcher.h b/content/browser/child_process_launcher.h -index 4c3d9917baee848b673d2895a54d96528ef14286..a3735de9aa88cef41be61fe742d8beb85de96a6e 100644 +index 2f85aeb4f51c0d126214616027c9c4cec710e263..26d35b53bcc41807452bcc68b484781d491b7a23 100644 --- a/content/browser/child_process_launcher.h +++ b/content/browser/child_process_launcher.h @@ -33,6 +33,7 @@ @@ -30,7 +30,7 @@ index 4c3d9917baee848b673d2895a54d96528ef14286..a3735de9aa88cef41be61fe742d8beb8 #endif #if BUILDFLAG(IS_POSIX) -@@ -193,7 +194,10 @@ struct ChildProcessLauncherFileData { +@@ -192,7 +193,10 @@ struct ChildProcessLauncherFileData { delete; ~ChildProcessLauncherFileData(); @@ -42,7 +42,7 @@ index 4c3d9917baee848b673d2895a54d96528ef14286..a3735de9aa88cef41be61fe742d8beb8 // Files opened by the browser and passed as corresponding file descriptors // in the child process. If a FilePath is provided, the file will be opened // and the descriptor cached for future process launches. If a ScopedFD is -@@ -208,6 +212,15 @@ struct ChildProcessLauncherFileData { +@@ -207,6 +211,15 @@ struct ChildProcessLauncherFileData { std::map> files_to_preload; #endif diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index 9653ef7b69b90..e51dc822db4b5 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -75,7 +75,7 @@ index f8361faf6151210d65a597562c533aaa0a5235df..328238c34a9381fbbeb5970af3de721c // used for canvas noising. uint64 canvas_noise_token = 0; diff --git a/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom b/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom -index 32e70a4fa70ac2fc41d95813590fe9a7120eecde..54d292d737748302fa0369b73d876d84f1fec1d4 100644 +index 8e1737f9d205c511ae8e4103278a2650166f3915..ced3d02fdf338e3e2a07e93a4d22b2f9398c2267 100644 --- a/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom +++ b/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom @@ -48,6 +48,7 @@ enum CSSSampleId { @@ -112,10 +112,10 @@ index 6e991652d242795e292cea4c94cff59aaea078fa..b6834c78575520bb6e584dd2ce3333ac 'internal-forced-visited-'): internal_visited_order = 0 diff --git a/third_party/blink/renderer/core/css/css_properties.json5 b/third_party/blink/renderer/core/css/css_properties.json5 -index 5bacbf438f37363e8a6c2f61ff8eff0dae781aaa..e16363cbff7a4af50656f64f7f69ecfa15081245 100644 +index 63fff5e26a00d65818e5a05ae4f3285162521574..23cbe424b6c9de4f66cf1c2ce91682bf706d6f90 100644 --- a/third_party/blink/renderer/core/css/css_properties.json5 +++ b/third_party/blink/renderer/core/css/css_properties.json5 -@@ -8810,6 +8810,24 @@ +@@ -8824,6 +8824,24 @@ property_methods: ["ParseShorthand", "CSSValueFromComputedStyleInternal"], }, @@ -141,10 +141,10 @@ index 5bacbf438f37363e8a6c2f61ff8eff0dae781aaa..e16363cbff7a4af50656f64f7f69ecfa { name: "-internal-visited-color", diff --git a/third_party/blink/renderer/core/css/css_property_equality.cc b/third_party/blink/renderer/core/css/css_property_equality.cc -index 936bd39e77a5a181a94a48129e38efc9c8c82847..75d332ef497018e4c863a47d4491d25da365206a 100644 +index 11c153b01a111efed101ae53d2148b7f523a66f5..7a3547a2aa70ef7699bf9022a15199d499e8a802 100644 --- a/third_party/blink/renderer/core/css/css_property_equality.cc +++ b/third_party/blink/renderer/core/css/css_property_equality.cc -@@ -346,6 +346,8 @@ bool CSSPropertyEquality::PropertiesEqual(const PropertyHandle& property, +@@ -348,6 +348,8 @@ bool CSSPropertyEquality::PropertiesEqual(const PropertyHandle& property, return a.DominantBaseline() == b.DominantBaseline(); case CSSPropertyID::kDynamicRangeLimit: return a.GetDynamicRangeLimit() == b.GetDynamicRangeLimit(); @@ -154,10 +154,10 @@ index 936bd39e77a5a181a94a48129e38efc9c8c82847..75d332ef497018e4c863a47d4491d25d return a.EmptyCells() == b.EmptyCells(); case CSSPropertyID::kFill: diff --git a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -index aa12ac9e27c55870269dd780e868b5eaee5acaab..1a06511ee56717df547817813eb80c3db1fa01df 100644 +index db463eb084f96e661a271be0646d6dbc84913ee2..336564df6f1266d6f186a56efd1836cfba951c72 100644 --- a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -@@ -12086,5 +12086,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( +@@ -12143,5 +12143,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( CSSValueID::kNone>(stream); } @@ -184,10 +184,10 @@ index aa12ac9e27c55870269dd780e868b5eaee5acaab..1a06511ee56717df547817813eb80c3d } // namespace css_longhand } // namespace blink diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -index 56429f6e0da31c28aef86b1b5a5e538207b42706..33c6a8ff7cf6ffff2952b5a8b9389eb04ee6946d 100644 +index ae5470212b28d47f8b79799d1ef52757fcd5cbae..667ba05f2595048bcadab0b394c52540f8bceaf1 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -@@ -3900,4 +3900,12 @@ PositionArea StyleBuilderConverter::ConvertPositionArea( +@@ -3913,4 +3913,12 @@ PositionArea StyleBuilderConverter::ConvertPositionArea( return PositionArea(span[0], span[1], span[2], span[3]); } @@ -307,7 +307,7 @@ index 2c2f4f405074e5baa4a26f255283404f86b40e21..ebeb7d6988ee9e6a4e78cb82fc01fdad ContouredRect PixelSnappedContouredBorderInternal( diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn -index 3788f76b50f6a1776baef2131033a62875e101b9..f3e2226021d1de6a5cb787538ca6c0f18f208670 100644 +index b63dfc16103a6882ffb4dd81a20408092aaed3ab..d56e6f0a527ddc8adccb5fec3adb66fd2f5c99bd 100644 --- a/third_party/blink/renderer/platform/BUILD.gn +++ b/third_party/blink/renderer/platform/BUILD.gn @@ -1658,6 +1658,8 @@ component("platform") { @@ -320,7 +320,7 @@ index 3788f76b50f6a1776baef2131033a62875e101b9..f3e2226021d1de6a5cb787538ca6c0f1 sources -= blink_platform_avx_files diff --git a/third_party/blink/renderer/platform/geometry/contoured_rect.h b/third_party/blink/renderer/platform/geometry/contoured_rect.h -index 88e78f1d8050c73ae6a8929f23e636ef7a383404..17b63c5ecdcd8feb17b76a13392595c737c316b7 100644 +index 54d3ae85eaed0699714728bcb8ff0c817f6b5e86..3014d286ecbef8b9a90f007527cce5141110eaf6 100644 --- a/third_party/blink/renderer/platform/geometry/contoured_rect.h +++ b/third_party/blink/renderer/platform/geometry/contoured_rect.h @@ -47,19 +47,29 @@ class PLATFORM_EXPORT ContouredRect { @@ -373,7 +373,7 @@ index 88e78f1d8050c73ae6a8929f23e636ef7a383404..17b63c5ecdcd8feb17b76a13392595c7 // A Corner is a axis-aligned quad, with the points ordered (start, outer, diff --git a/third_party/blink/renderer/platform/geometry/path_builder.cc b/third_party/blink/renderer/platform/geometry/path_builder.cc -index b17bc9760b97b1e72783ae174ffa0f69ca830462..226b546694524e3848ea849059df74970403690e 100644 +index 414b73e219a7f4e499414cf120c5b8ebd0ae3a63..2093364a27e89fa10fe9a6921453d2d8285e445e 100644 --- a/third_party/blink/renderer/platform/geometry/path_builder.cc +++ b/third_party/blink/renderer/platform/geometry/path_builder.cc @@ -4,6 +4,7 @@ diff --git a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch index 23a4d1bc337f5..107aa4007339f 100644 --- a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch +++ b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch @@ -564,10 +564,10 @@ index 399fba1a3d4e601dc2cdd5f1f4def8b7fd7a3011..8bcbe0d26c80323155d536c0d3a177a1 gpu::SyncPointManager* GetSyncPointManager() override; gpu::Scheduler* GetGpuScheduler() override; diff --git a/content/browser/compositor/viz_process_transport_factory.cc b/content/browser/compositor/viz_process_transport_factory.cc -index 8e2ddfa9337b5ba952a186a85bce78d39a62e8bd..efb54a95b2ad76546eafa1907064a298961b1a4d 100644 +index 130067b91baa360a7234fecfe6342c8239d587b5..d701328102f9a53e12b1b2e2a86265910692ca59 100644 --- a/content/browser/compositor/viz_process_transport_factory.cc +++ b/content/browser/compositor/viz_process_transport_factory.cc -@@ -389,8 +389,14 @@ void VizProcessTransportFactory::OnEstablishedGpuChannel( +@@ -387,8 +387,14 @@ void VizProcessTransportFactory::OnEstablishedGpuChannel( mojo::AssociatedRemote display_private; root_params->display_private = display_private.BindNewEndpointAndPassReceiver(); diff --git a/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch b/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch index 9a8fc18059786..0668d63d121fc 100644 --- a/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch +++ b/patches/chromium/feat_ensure_mas_builds_of_the_same_application_can_use_safestorage.patch @@ -12,10 +12,10 @@ We attempt to migrate the safe storage key from the old account, if that migrati Existing apps that aren't built for the app store should be unimpacted, there is one edge case where a user uses BOTH an AppStore and a darwin build of the same app only one will keep it's access to the safestorage key as during the migration we delete the old account. This is an acceptable edge case as no one should be actively using two versions of the same app. diff --git a/components/os_crypt/sync/keychain_password_mac.mm b/components/os_crypt/sync/keychain_password_mac.mm -index 3d388a85aaf52acdcc2b7aaea56f5a24b2435bff..7a0d28cbf1651e76a4356f1193b502d27e7a8ed4 100644 +index 77409051c67a5a7bd3826a7063666954a38a86f0..397c5a17f0dc4d662f6413234ddc430b680fb0b3 100644 --- a/components/os_crypt/sync/keychain_password_mac.mm +++ b/components/os_crypt/sync/keychain_password_mac.mm -@@ -25,6 +25,12 @@ +@@ -26,6 +26,12 @@ using KeychainNameContainerType = const base::NoDestructor; #endif @@ -28,10 +28,10 @@ index 3d388a85aaf52acdcc2b7aaea56f5a24b2435bff..7a0d28cbf1651e76a4356f1193b502d2 namespace { // These two strings ARE indeed user facing. But they are used to access -@@ -79,10 +85,47 @@ - KeychainPassword::~KeychainPassword() = default; +@@ -95,11 +101,49 @@ + uma_result); + }; - std::string KeychainPassword::GetPassword() const { + const std::string account_name_suffix = kAccountNameSuffix; + const std::string suffixed_account_name = GetAccountName() + account_name_suffix; auto password = @@ -43,7 +43,7 @@ index 3d388a85aaf52acdcc2b7aaea56f5a24b2435bff..7a0d28cbf1651e76a4356f1193b502d2 + } + + // If the error was anything other than "it does not exist" we should error out here -+ // This normally means the account exists but we were deniged access to it ++ // This normally means the account exists but we were denied access to it + if (password.error() != errSecItemNotFound) { + OSSTATUS_LOG(ERROR, password.error()) << "Keychain lookup for suffixed key failed"; + return std::string(); @@ -57,6 +57,8 @@ index 3d388a85aaf52acdcc2b7aaea56f5a24b2435bff..7a0d28cbf1651e76a4356f1193b502d2 + item_ref.InitializeInto()); if (password.has_value()) { + uma_result = FindGenericPasswordResult::kPasswordFound; ++ + // If we found the legacy account name we should copy it over to + // the new suffixed account + OSStatus error = keychain_->AddGenericPassword( diff --git a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch index 9394103e1aeb9..47c34fd73b1da 100644 --- a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch +++ b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch @@ -17,7 +17,7 @@ headers, moving forward we should find a way in upstream to provide access to these headers for loader clients created on the browser process. diff --git a/services/network/public/cpp/resource_request.cc b/services/network/public/cpp/resource_request.cc -index 28355f4c6c3cbbe60e827246e88107ce7374104a..4183f448dc40f0fbe1fabadf58f09eeb84c9f684 100644 +index 0becf4f37532fb7acfdf4d516a72f7048e98c550..0a267234eff1684fe2e6231584ccd1b5c9ed03e3 100644 --- a/services/network/public/cpp/resource_request.cc +++ b/services/network/public/cpp/resource_request.cc @@ -178,6 +178,7 @@ ResourceRequest::TrustedParams& ResourceRequest::TrustedParams::operator=( @@ -37,10 +37,10 @@ index 28355f4c6c3cbbe60e827246e88107ce7374104a..4183f448dc40f0fbe1fabadf58f09eeb allow_cookies_from_browser == other.allow_cookies_from_browser && include_request_cookies_with_response == diff --git a/services/network/public/cpp/resource_request.h b/services/network/public/cpp/resource_request.h -index 8634c50fbede68bf5497ed50e258eecac594b4d4..c6f06966f0f58e5087e1f62537eecffc95cd1962 100644 +index df29c7cb739a488684c0c50bc5343df101911a31..86b5576c9c10e5544347117e4f6b09d7692caffa 100644 --- a/services/network/public/cpp/resource_request.h +++ b/services/network/public/cpp/resource_request.h -@@ -77,6 +77,7 @@ struct COMPONENT_EXPORT(NETWORK_CPP_BASE) ResourceRequest { +@@ -78,6 +78,7 @@ struct COMPONENT_EXPORT(NETWORK_CPP_BASE) ResourceRequest { bool has_user_activation = false; bool allow_cookies_from_browser = false; bool include_request_cookies_with_response = false; @@ -49,10 +49,10 @@ index 8634c50fbede68bf5497ed50e258eecac594b4d4..c6f06966f0f58e5087e1f62537eecffc mojo::PendingRemote trust_token_observer; mojo::PendingRemote diff --git a/services/network/public/cpp/url_request_mojom_traits.cc b/services/network/public/cpp/url_request_mojom_traits.cc -index e67d4d6f11cb68cfc7f6f1dad60285cbaf905e76..e8e35f02b4a9c5662cd8b2cbb7dbb30e31efd4f3 100644 +index 1fbe54bda8198423b42cb5eba291d7346a76873c..71b58ec4e11317a4da1c89d9407ab439ff1629c3 100644 --- a/services/network/public/cpp/url_request_mojom_traits.cc +++ b/services/network/public/cpp/url_request_mojom_traits.cc -@@ -49,6 +49,7 @@ bool StructTraitsallow_cookies_from_browser = data.allow_cookies_from_browser(); out->include_request_cookies_with_response = data.include_request_cookies_with_response(); @@ -61,10 +61,10 @@ index e67d4d6f11cb68cfc7f6f1dad60285cbaf905e76..e8e35f02b4a9c5662cd8b2cbb7dbb30e mojo::PendingRemote>(); out->trust_token_observer = data.TakeTrustTokenObserver< diff --git a/services/network/public/cpp/url_request_mojom_traits.h b/services/network/public/cpp/url_request_mojom_traits.h -index 91628c93c415d8293ac989bdf9135cf2c8c59557..a51f9ca3f06ada3232c52b2b3e39a4433860bf2a 100644 +index 1d6f7cb0347c2d1156052f43b82f22130c4750aa..ef6625a9148107772f94d2f62478914fc84d6b89 100644 --- a/services/network/public/cpp/url_request_mojom_traits.h +++ b/services/network/public/cpp/url_request_mojom_traits.h -@@ -71,6 +71,10 @@ struct COMPONENT_EXPORT(NETWORK_CPP_BASE) +@@ -72,6 +72,10 @@ struct COMPONENT_EXPORT(NETWORK_CPP_BASE) const network::ResourceRequest::TrustedParams& trusted_params) { return trusted_params.include_request_cookies_with_response; } @@ -76,10 +76,10 @@ index 91628c93c415d8293ac989bdf9135cf2c8c59557..a51f9ca3f06ada3232c52b2b3e39a443 cookie_observer( const network::ResourceRequest::TrustedParams& trusted_params) { diff --git a/services/network/public/mojom/url_request.mojom b/services/network/public/mojom/url_request.mojom -index e4ebfcfbbd56e284dcb88918a779abccc467a4af..f22dc2c544c676e3c0bd318f21cba11205ed8386 100644 +index 392d697a8d1573815bf08e37b1bcc5c0c7493116..cf9915b9322487734b27a1776e721440035d7ad7 100644 --- a/services/network/public/mojom/url_request.mojom +++ b/services/network/public/mojom/url_request.mojom -@@ -86,6 +86,9 @@ struct TrustedUrlRequestParams { +@@ -87,6 +87,9 @@ struct TrustedUrlRequestParams { // client which should not be able to see them. bool include_request_cookies_with_response = false; diff --git a/patches/chromium/fix_activate_background_material_on_windows.patch b/patches/chromium/fix_activate_background_material_on_windows.patch index 5cc74422f369b..5dfab7478972f 100644 --- a/patches/chromium/fix_activate_background_material_on_windows.patch +++ b/patches/chromium/fix_activate_background_material_on_windows.patch @@ -14,10 +14,10 @@ This patch likely can't be upstreamed as-is, as Chromium doesn't have this use case in mind currently. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 88f658aeb32a3181e3a0cd45fbd2aacad95116aa..cef61dcf3ab89f06cba16f309e800dbab5a7cc05 100644 +index 30399c8a81819a57f07702a97f85e3edd7df9d69..1559eb26fb86ac6172509785afff1e0bbd226ee7 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -936,13 +936,13 @@ void HWNDMessageHandler::FrameTypeChanged() { +@@ -937,13 +937,13 @@ void HWNDMessageHandler::FrameTypeChanged() { void HWNDMessageHandler::PaintAsActiveChanged() { if (!delegate_->HasNonClientView() || !delegate_->CanActivate() || @@ -33,7 +33,7 @@ index 88f658aeb32a3181e3a0cd45fbd2aacad95116aa..cef61dcf3ab89f06cba16f309e800dba } void HWNDMessageHandler::SetWindowIcons(const gfx::ImageSkia& window_icon, -@@ -1728,7 +1728,7 @@ void HWNDMessageHandler::OnActivateApp(BOOL active, DWORD thread_id) { +@@ -1732,7 +1732,7 @@ void HWNDMessageHandler::OnActivateApp(BOOL active, DWORD thread_id) { if (delegate_->HasNonClientView() && !active && thread_id != GetCurrentThreadId()) { // Update the native frame if it is rendering the non-client area. @@ -42,7 +42,7 @@ index 88f658aeb32a3181e3a0cd45fbd2aacad95116aa..cef61dcf3ab89f06cba16f309e800dba DefWindowProcWithRedrawLock(WM_NCACTIVATE, FALSE, 0); } } -@@ -2336,17 +2336,18 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message, +@@ -2340,17 +2340,18 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message, delegate_->SchedulePaint(); } diff --git a/patches/chromium/fix_aspect_ratio_with_max_size.patch b/patches/chromium/fix_aspect_ratio_with_max_size.patch index 7cef957d01da0..aea35450aad2d 100644 --- a/patches/chromium/fix_aspect_ratio_with_max_size.patch +++ b/patches/chromium/fix_aspect_ratio_with_max_size.patch @@ -11,10 +11,10 @@ enlarge window above dimensions set during creation of the BrowserWindow. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 2cd46f4692c84cffff0775bbb67d3585f24e900d..9747e945b2ebfc113ffd12839c28a98fcccf2872 100644 +index c38b58ed16b14ff765f24d0bb8bdf34b8de3a901..418dc47b6d4df097e8f0cfd61de8485af2a8d2c2 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -3771,15 +3771,30 @@ void HWNDMessageHandler::SizeWindowToAspectRatio(UINT param, +@@ -3775,15 +3775,30 @@ void HWNDMessageHandler::SizeWindowToAspectRatio(UINT param, delegate_->GetMinMaxSize(&min_window_size, &max_window_size); min_window_size = delegate_->DIPToScreenSize(min_window_size); max_window_size = delegate_->DIPToScreenSize(max_window_size); diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index 134d0ea09aa42..e9594ef50b2e2 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -28,10 +28,10 @@ The patch should be removed in favor of either: Upstream bug https://bugs.chromium.org/p/chromium/issues/detail?id=1081397. diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc -index e35fc05100fd582669a021574fcd0a01e72d2302..fec6fb5ff81b362fc299b36b447c1141911ccb56 100644 +index deb3de267fb5e6a326985fa7943e5a66217888f8..ad53374b86efe1db1e2c2e06056cd3b50696ad9b 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc -@@ -11080,6 +11080,11 @@ url::Origin NavigationRequest::GetOriginForURLLoaderFactoryUnchecked() { +@@ -11158,6 +11158,11 @@ url::Origin NavigationRequest::GetOriginForURLLoaderFactoryUnchecked() { target_rph_id); } @@ -44,7 +44,7 @@ index e35fc05100fd582669a021574fcd0a01e72d2302..fec6fb5ff81b362fc299b36b447c1141 // origin of |common_params.url| and/or |common_params.initiator_origin|. url::Origin resolved_origin = url::Origin::Resolve( diff --git a/third_party/blink/renderer/core/loader/document_loader.cc b/third_party/blink/renderer/core/loader/document_loader.cc -index 59e909f5b9b3b9e2cb648359d3a0b4db2f1671b7..297aa66d55a62557deafe1d723809d68f898095c 100644 +index 094f7359e5d3b701676daa6c26fa6f8dee9d4a29..ac23e8b6e5b16670e942bf4801d97296176e2a00 100644 --- a/third_party/blink/renderer/core/loader/document_loader.cc +++ b/third_party/blink/renderer/core/loader/document_loader.cc @@ -2332,6 +2332,10 @@ Frame* DocumentLoader::CalculateOwnerFrame() { diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 3a0c0cd608ae0..0a09c111672c8 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index fc4af3a293fd807780f39b0cddc7605031620879..acb6b6257ccb13aae284d9b02baada14fe9ee0cc 100644 +index 97df851aa73d1bf8d8c8001646b63cbb43cd9a92..29185fc4c426652d192870c8a11aaa981a08ebf8 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10009,7 +10009,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -10162,7 +10162,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_remove_caption-removing_style_call.patch b/patches/chromium/fix_remove_caption-removing_style_call.patch index cf72a25a5708b..9ec10741fd494 100644 --- a/patches/chromium/fix_remove_caption-removing_style_call.patch +++ b/patches/chromium/fix_remove_caption-removing_style_call.patch @@ -18,10 +18,10 @@ or resizing, but Electron does not seem to run into that issue for opaque frameless windows even with that block commented out. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 6f2e2702d3b982fe7e8d258f303c8055d3d37df8..88f658aeb32a3181e3a0cd45fbd2aacad95116aa 100644 +index 8c13b9db078e690240eca0a48a7c546dcdac3c11..30399c8a81819a57f07702a97f85e3edd7df9d69 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -1796,7 +1796,23 @@ LRESULT HWNDMessageHandler::OnCreate(CREATESTRUCT* create_struct) { +@@ -1800,7 +1800,23 @@ LRESULT HWNDMessageHandler::OnCreate(CREATESTRUCT* create_struct) { SendMessage(hwnd(), WM_CHANGEUISTATE, MAKELPARAM(UIS_CLEAR, UISF_HIDEFOCUS), 0); diff --git a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch index 6cc351a49ae9c..280c1093565ae 100644 --- a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch +++ b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch @@ -11,10 +11,10 @@ This patch should be upstreamed as a conditional revert of the logic in desktop vs mobile runtimes. i.e. restore the old logic only on desktop platforms diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 583b7cf8c0e484d53a0b93b86e65f28ba5359906..31cedc79b9763bee5cc69066f5d4afa6f4ec7e39 100644 +index 6a939edf24643207b26c9cc155ccca661b06f937..c33beb8be5535ad0951013ef0617fb881fe9fac4 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2135,9 +2135,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { +@@ -2134,9 +2134,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { void RenderWidgetHostImpl::NotifyScreenInfoChanged() { // The resize message (which may not happen immediately) will carry with it // the screen info as well as the new size (if the screen has changed scale diff --git a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch index 832e684a9a2c5..25a3c6fd18ae0 100644 --- a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch +++ b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch @@ -203,7 +203,7 @@ index fa65331f40b90d812b71a489fd560e9359152d2b..390714d631dc88ef92d59ef9618a5706 const mojom::blink::UserActivationOption user_activation_option_; const mojom::blink::LoadEventBlockingOption blocking_option_; diff --git a/third_party/blink/renderer/core/frame/web_frame_test.cc b/third_party/blink/renderer/core/frame/web_frame_test.cc -index 5e12b61ba14cd1afb07b71ff15e73e905da0addc..685a2ebb6694c173471d0450149321254da652ec 100644 +index c9af87ce934e52d530dc30d0969a22e5b1747810..e89b768983e8b6882bf0bdc92d2a9a48714283c9 100644 --- a/third_party/blink/renderer/core/frame/web_frame_test.cc +++ b/third_party/blink/renderer/core/frame/web_frame_test.cc @@ -298,6 +298,7 @@ void ExecuteScriptsInMainWorld( @@ -215,7 +215,7 @@ index 5e12b61ba14cd1afb07b71ff15e73e905da0addc..685a2ebb6694c173471d045014932125 mojom::blink::WantResultOption::kWantResult, wait_for_promise); } diff --git a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc -index b9adaba2543608f91815ca5e1aca443da5813d9d..966210be0d0b2d89c0b24ea12686ebe0289087a1 100644 +index 0c34345a9a6d79f9ef8b8a108842d5b2c6d1434f..f4b05b74303e258738c07f6f1c8320cb5fae5652 100644 --- a/third_party/blink/renderer/core/frame/web_local_frame_impl.cc +++ b/third_party/blink/renderer/core/frame/web_local_frame_impl.cc @@ -1111,14 +1111,15 @@ void WebLocalFrameImpl::RequestExecuteScript( diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index f775fad1e681e..1fb5372d75642 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -20,10 +20,10 @@ index 39eae72b5f9f05fc9dda3b6b3a51b4d1d2bf7fcf..cd95bbd34218cb3181b887832a84893c } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index bd3cccc408c61f4c4e408fd5d093d6aa1ef0e201..4f65dbc23f3039a0144745cd3cdefeff657b6b3e 100644 +index 0a74c5a3bee425c5c1af33ef27791a6d852baa6e..2a657027c39370d7ea839576afe547ad6da6c5a7 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h -@@ -342,6 +342,11 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -341,6 +341,11 @@ class CONTENT_EXPORT ContentBrowserClient { virtual ~ContentBrowserClient() = default; diff --git a/patches/chromium/gritsettings_resource_ids.patch b/patches/chromium/gritsettings_resource_ids.patch index fd588f74de93c..6e31d7bb7ed72 100644 --- a/patches/chromium/gritsettings_resource_ids.patch +++ b/patches/chromium/gritsettings_resource_ids.patch @@ -6,7 +6,7 @@ Subject: gritsettings_resource_ids.patch Add electron resources file to the list of resource ids generation. diff --git a/tools/gritsettings/resource_ids.spec b/tools/gritsettings/resource_ids.spec -index 78d72ec8ed37f4a551ff091038e6741e3f0b9efb..1c9de5cc18ab8656e7a91d5ce3f5a5424b7d8739 100644 +index 6d02cc4f84fc2de0404f006f6895919f6aa21cb4..92882f52b2ba1898608b2eb38702f37dd8cfb8cd 100644 --- a/tools/gritsettings/resource_ids.spec +++ b/tools/gritsettings/resource_ids.spec @@ -1524,6 +1524,11 @@ diff --git a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch index f52c337c296b2..ec2984e8d3252 100644 --- a/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch +++ b/patches/chromium/hack_to_allow_gclient_sync_with_host_os_mac_on_linux_in_ci.patch @@ -11,7 +11,7 @@ If removing this patch causes no sync failures, it's safe to delete :+1: Ref https://chromium-review.googlesource.com/c/chromium/src/+/2953903 diff --git a/tools/clang/scripts/update.py b/tools/clang/scripts/update.py -index 420c106a5f6fbbcfc77f2409e6272689ec71cf87..dad329cec5786323a981e150129c97357122c617 100755 +index 316567b6ea69aad254f6acfe78c07ee8c9d31627..0c0ef515ec1d2429b9325dfff16893a4171e9da4 100755 --- a/tools/clang/scripts/update.py +++ b/tools/clang/scripts/update.py @@ -307,6 +307,8 @@ def GetDefaultHostOs(): diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 4210fad044947..7e3094d85141e 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,10 +35,10 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index 01c19144731d186d857dda72c3ac002a9ae2e911..14faff7dd8f32437f849011df222a37744f379d5 100644 +index 275f4e0ece8c5bd8cee239c61fdb965eef524650..4726c37e6fc70133af5e2152ec4d0774f2ddfcaa 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn -@@ -1046,6 +1046,7 @@ component("base") { +@@ -1048,6 +1048,7 @@ component("base") { "//build:ios_buildflags", "//build/config/compiler:compiler_buildflags", "//third_party/modp_b64", @@ -208,7 +208,7 @@ index ff1e356ff696d3830d02644969c36a71fdf32ff6..b39c716c52524b95f2d3417a98e60c0c sources += [ "os_crypt_win.cc" ] deps += [ "//components/version_info" ] diff --git a/components/os_crypt/sync/keychain_password_mac.mm b/components/os_crypt/sync/keychain_password_mac.mm -index 6b936d228cf71d33025769430afbe6fe322ed186..3d388a85aaf52acdcc2b7aaea56f5a24b2435bff 100644 +index 6567e6f2d3b1dc859408666dd3c15c4a9e1238b0..77409051c67a5a7bd3826a7063666954a38a86f0 100644 --- a/components/os_crypt/sync/keychain_password_mac.mm +++ b/components/os_crypt/sync/keychain_password_mac.mm @@ -15,6 +15,7 @@ @@ -216,9 +216,9 @@ index 6b936d228cf71d33025769430afbe6fe322ed186..3d388a85aaf52acdcc2b7aaea56f5a24 #include "build/branding_buildflags.h" #include "crypto/apple_keychain.h" +#include "electron/mas.h" + #include "third_party/abseil-cpp/absl/cleanup/cleanup.h" using crypto::AppleKeychain; - diff --git a/components/remote_cocoa/app_shim/BUILD.gn b/components/remote_cocoa/app_shim/BUILD.gn index ad40ddbbcb0fcfa070833ea6c0d01432bbb67768..df632da340c132f469f4f35738514763437e67fc 100644 --- a/components/remote_cocoa/app_shim/BUILD.gn @@ -582,7 +582,7 @@ index d83f420d25e2c108ad400ebecae02b1ac327c058..77852c5c315ac09dddb7227adf3b840e return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 1006244a7ed861fdd58bfb3af926a69af2061322..4074a0429ce78963d4406f957c96382333d760ed 100644 +index 3f6fb6a8653f1d087cf28396361fc77d98668db9..0603b350939376c6e3499de7f19980b7cd274735 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn @@ -342,6 +342,7 @@ source_set("browser") { @@ -715,10 +715,10 @@ index da0e8c7260391805fa6950125c797565a2812521..8e8b093cd142326010445e9b2aae7c20 defines = [] diff --git a/content/renderer/BUILD.gn b/content/renderer/BUILD.gn -index 7424d33cc34ca44b1949260215b2f0a44a2d393e..80e284ca761069e5d544b5a056b13df32d509d00 100644 +index b8fd955057ebdbf910c81f5d79d7a7ca47601ac7..aa232a7d02f353d83fd2862416b0c3b8ebbccc52 100644 --- a/content/renderer/BUILD.gn +++ b/content/renderer/BUILD.gn -@@ -327,6 +327,7 @@ target(link_target_type, "renderer") { +@@ -321,6 +321,7 @@ target(link_target_type, "renderer") { "//ui/surface", "//url", "//v8", @@ -797,10 +797,10 @@ index a1068589ad844518038ee7bc15a3de9bc5cba525..1ff781c49f086ec8015c7d3c44567dbe } // namespace content diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn -index 5544ddc8faae9cc4a75c812227a94df4ad4f5e53..d6fa2a588fec9895101dc4c308eb84b015a908aa 100644 +index 1403a31f878228d835772bffd9b37eea3b742599..5a013396c0990cb3f49a659d4398e9cbe64e0283 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn -@@ -664,6 +664,7 @@ static_library("test_support") { +@@ -665,6 +665,7 @@ static_library("test_support") { "//url", "//url/mojom:url_mojom_gurl", "//v8", @@ -808,7 +808,7 @@ index 5544ddc8faae9cc4a75c812227a94df4ad4f5e53..d6fa2a588fec9895101dc4c308eb84b0 ] data_deps = [ -@@ -1120,6 +1121,7 @@ static_library("browsertest_support") { +@@ -1121,6 +1122,7 @@ static_library("browsertest_support") { } configs += [ "//v8:external_startup_data" ] @@ -816,7 +816,7 @@ index 5544ddc8faae9cc4a75c812227a94df4ad4f5e53..d6fa2a588fec9895101dc4c308eb84b0 } mojom("content_test_mojo_bindings") { -@@ -1963,6 +1965,7 @@ test("content_browsertests") { +@@ -1964,6 +1966,7 @@ test("content_browsertests") { "//ui/shell_dialogs", "//ui/snapshot", "//ui/webui:test_support", @@ -824,7 +824,7 @@ index 5544ddc8faae9cc4a75c812227a94df4ad4f5e53..d6fa2a588fec9895101dc4c308eb84b0 ] if (!(is_chromeos && target_cpu == "arm64" && current_cpu == "arm")) { -@@ -3293,6 +3296,7 @@ test("content_unittests") { +@@ -3297,6 +3300,7 @@ test("content_unittests") { "//ui/shell_dialogs:shell_dialogs", "//ui/webui:test_support", "//url", @@ -903,7 +903,7 @@ index 6431af67ab634cf23729b9102c189b2181cfd2cf..22040e1bfb96d810a2d8e62e44e4afbc base::WeakPtr diff --git a/gpu/ipc/service/BUILD.gn b/gpu/ipc/service/BUILD.gn -index 2ef64102137f543ec8c4d88bd6718264d1c52691..7e2c450a44b4bddf7cb3e2d3482ec04c5b750e02 100644 +index 237bff815a69c786a9ae31437c6df1c933e4963b..215c9affd67ebddc81415eefc12ee5727ab07aee 100644 --- a/gpu/ipc/service/BUILD.gn +++ b/gpu/ipc/service/BUILD.gn @@ -131,6 +131,7 @@ component("service") { @@ -937,10 +937,10 @@ index f89dbdfb0c4e8e31d387d1ce2e5304277ac4df26..7b75bfeba59345d63f4ac81153697941 namespace ui { diff --git a/media/audio/BUILD.gn b/media/audio/BUILD.gn -index 4f663e28aa078bd2e692a79d06dbdde055287f3c..8588214d7f30384cc37aaf0062c941a854d4bba5 100644 +index 6192d8fdc48be430b2d2eac0e1c97c88df11e196..b2aa0735896f58155667546d05937bd96a0dcfca 100644 --- a/media/audio/BUILD.gn +++ b/media/audio/BUILD.gn -@@ -198,6 +198,7 @@ source_set("audio") { +@@ -202,6 +202,7 @@ source_set("audio") { "CoreMedia.framework", ] weak_frameworks = [ "ScreenCaptureKit.framework" ] # macOS 13.0 @@ -1436,7 +1436,7 @@ index eb81a70e4d5d5cd3e6ae9b45f8cd1c795ea76c51..9921ccb10d3455600eddd85f77f10228 } // namespace sandbox diff --git a/third_party/blink/renderer/core/BUILD.gn b/third_party/blink/renderer/core/BUILD.gn -index 1b5e616ebd3c610739a9dcf3fd6694f1e442d783..8449d7eb65687fa82db0f23c7627807ef26e34f3 100644 +index bae0728aa1b2d8416e815862fd5d4aceb165ee44..a1a653bb5ec345f07027d1911071792510c5da6f 100644 --- a/third_party/blink/renderer/core/BUILD.gn +++ b/third_party/blink/renderer/core/BUILD.gn @@ -414,6 +414,7 @@ component("core") { @@ -1584,10 +1584,10 @@ index dcf493d62990018040a3f84b6f875af737bd2214..3d1c4dcc9ee0bbfdac15f40d9c74e9f3 void DisplayCALayerTree::GotIOSurfaceFrame( diff --git a/ui/accessibility/platform/BUILD.gn b/ui/accessibility/platform/BUILD.gn -index 349a50ce687d5594296ce3c302938424be2e739b..0c5313b8f31a97747ae28f2c188e0fb591e5cc36 100644 +index 09b5f1a0165cacb9826cdb1ffb8ab4645cddfdf4..713678ce99b9d3bd46d1ef662a9fe1e7e8fc43ab 100644 --- a/ui/accessibility/platform/BUILD.gn +++ b/ui/accessibility/platform/BUILD.gn -@@ -296,6 +296,7 @@ component("platform") { +@@ -297,6 +297,7 @@ component("platform") { "AppKit.framework", "Foundation.framework", ] @@ -1678,7 +1678,7 @@ index 6846060ef9622d8fc8d1d6c8da16e2f1b785e6bd..05c22db87e882b246bd7034e027cf149 // Accessible object if (AXElementWrapper::IsValidElement(value)) { diff --git a/ui/base/BUILD.gn b/ui/base/BUILD.gn -index d2bd63f57da9b3ff84ebe36053ec18978d86c9f3..a6261be96e00548af7eba8a5fc7461586b9dbf53 100644 +index b5456d6483b35efd929aa772be65b68bc03aabc4..2d1bd535d66c2fab0209e5adc957d827d9182737 100644 --- a/ui/base/BUILD.gn +++ b/ui/base/BUILD.gn @@ -365,6 +365,13 @@ component("base") { @@ -1848,7 +1848,7 @@ index 033ebc0036bcd373b011ca829d255e8c83701a6d..ad06707f31872c58217d2d034f050c55 // Query the display's refresh rate. if (@available(macos 12.0, *)) { diff --git a/ui/gfx/BUILD.gn b/ui/gfx/BUILD.gn -index af66f53bbec8e3cf9b1e2e69e602173725958706..381498a4d51b32a30a206d9ec3878d9ab3109386 100644 +index 073269d426f55591e2daeff32782d957624d11d4..c6fe49958fd3e0b556352fda5cc35b9455792002 100644 --- a/ui/gfx/BUILD.gn +++ b/ui/gfx/BUILD.gn @@ -337,6 +337,12 @@ component("gfx") { diff --git a/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch b/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch index 44c72ea13f4a3..0bf84dae055e3 100644 --- a/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch +++ b/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch @@ -7,10 +7,10 @@ This adds a callback from the network service that's used to implement session.setCertificateVerifyCallback. diff --git a/services/network/network_context.cc b/services/network/network_context.cc -index 3c261f50a966bd9d472671c9d9c74cfa843355a6..7d65c373ac4f1f538085a44ca0b11ddce89b1e62 100644 +index 0339a3733272095428d5717c6df9fce8d16062c3..02853bf6552d49986b782785d3ab5a61ec0d3734 100644 --- a/services/network/network_context.cc +++ b/services/network/network_context.cc -@@ -165,6 +165,11 @@ +@@ -164,6 +164,11 @@ #include "services/network/web_transport.h" #include "url/gurl.h" @@ -22,7 +22,7 @@ index 3c261f50a966bd9d472671c9d9c74cfa843355a6..7d65c373ac4f1f538085a44ca0b11ddc #if BUILDFLAG(IS_CT_SUPPORTED) // gn check does not account for BUILDFLAG(). So, for iOS builds, it will // complain about a missing dependency on the target exposing this header. Add a -@@ -604,6 +609,99 @@ void RecordHSTSPreconnectUpgradeReason(HSTSRedirectUpgradeReason reason) { +@@ -603,6 +608,99 @@ void RecordHSTSPreconnectUpgradeReason(HSTSRedirectUpgradeReason reason) { } // namespace @@ -122,7 +122,7 @@ index 3c261f50a966bd9d472671c9d9c74cfa843355a6..7d65c373ac4f1f538085a44ca0b11ddc constexpr uint32_t NetworkContext::kMaxOutstandingRequestsPerProcess; NetworkContext::NetworkContextHttpAuthPreferences:: -@@ -1007,6 +1105,13 @@ void NetworkContext::SetClient( +@@ -1006,6 +1104,13 @@ void NetworkContext::SetClient( client_.Bind(std::move(client)); } @@ -136,7 +136,7 @@ index 3c261f50a966bd9d472671c9d9c74cfa843355a6..7d65c373ac4f1f538085a44ca0b11ddc void NetworkContext::CreateURLLoaderFactory( mojo::PendingReceiver receiver, mojom::URLLoaderFactoryParamsPtr params) { -@@ -2612,6 +2717,10 @@ URLRequestContextOwner NetworkContext::MakeURLRequestContext( +@@ -2611,6 +2716,10 @@ URLRequestContextOwner NetworkContext::MakeURLRequestContext( cert_verifier = std::make_unique( std::make_unique( std::move(cert_verifier))); diff --git a/patches/chromium/notification_provenance.patch b/patches/chromium/notification_provenance.patch index 71e3f12bbf422..7266481311147 100644 --- a/patches/chromium/notification_provenance.patch +++ b/patches/chromium/notification_provenance.patch @@ -133,10 +133,10 @@ index 5be62a3fb27e37f3c1db6b811172f6dfebe18f61..34349f9832fe4b9a3d48db613a789afb const GURL& document_url, const WeakDocumentPtr& weak_document_ptr, diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index 2dcb080a4bd9b2cd6a9f8f8ae41305dfd4400066..332f611678e53c0ea56c8baea71ca123d8cc0a95 100644 +index 9fd362b58903930c3fcb053d561cf8d8c815ce15..c97471d75ab2d11cfe71f34d8d11b27edb5c0fce 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc -@@ -2217,7 +2217,7 @@ void RenderProcessHostImpl::CreateNotificationService( +@@ -2225,7 +2225,7 @@ void RenderProcessHostImpl::CreateNotificationService( case RenderProcessHost::NotificationServiceCreatorType::kSharedWorker: case RenderProcessHost::NotificationServiceCreatorType::kDedicatedWorker: { storage_partition_impl_->GetPlatformNotificationContext()->CreateService( @@ -145,7 +145,7 @@ index 2dcb080a4bd9b2cd6a9f8f8ae41305dfd4400066..332f611678e53c0ea56c8baea71ca123 creator_type, std::move(receiver)); break; } -@@ -2225,7 +2225,7 @@ void RenderProcessHostImpl::CreateNotificationService( +@@ -2233,7 +2233,7 @@ void RenderProcessHostImpl::CreateNotificationService( CHECK(rfh); storage_partition_impl_->GetPlatformNotificationContext()->CreateService( diff --git a/patches/chromium/port_autofill_colors_to_the_color_pipeline.patch b/patches/chromium/port_autofill_colors_to_the_color_pipeline.patch index f14b4d040f86c..e12a23881ff92 100644 --- a/patches/chromium/port_autofill_colors_to_the_color_pipeline.patch +++ b/patches/chromium/port_autofill_colors_to_the_color_pipeline.patch @@ -8,10 +8,10 @@ needed in chromium but our autofill implementation uses them. This patch can be our autofill implementation to work like Chromium's. diff --git a/ui/color/color_id.h b/ui/color/color_id.h -index 56ac73d6a9b8c00039bbbfc660e423bc14152e19..72a08ab14653136308ace4f4ee6e83773060dae5 100644 +index 4093391163580e262ef2ab7634e3d5937dbbacee..122f32030f5d07a737c3b76c587098efefe6b48a 100644 --- a/ui/color/color_id.h +++ b/ui/color/color_id.h -@@ -410,6 +410,10 @@ +@@ -431,6 +431,10 @@ E_CPONLY(kColorRadioButtonForegroundUnchecked) \ E_CPONLY(kColorRadioButtonForegroundDisabled) \ E_CPONLY(kColorRadioButtonForegroundChecked) \ @@ -22,7 +22,7 @@ index 56ac73d6a9b8c00039bbbfc660e423bc14152e19..72a08ab14653136308ace4f4ee6e8377 E_CPONLY(kColorSegmentedButtonBorder) \ E_CPONLY(kColorSegmentedButtonFocus) \ E_CPONLY(kColorSegmentedButtonForegroundChecked) \ -@@ -518,6 +522,7 @@ +@@ -539,6 +543,7 @@ E_CPONLY(kColorTreeNodeForeground) \ E_CPONLY(kColorTreeNodeForegroundSelectedFocused) \ E_CPONLY(kColorTreeNodeForegroundSelectedUnfocused) \ diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index bc230aa4e5d52..91855d62b57b0 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -881,10 +881,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 4074a0429ce78963d4406f957c96382333d760ed..c8f1114cb5cd892c80500da5ec4828cf5ad77dc9 100644 +index 0603b350939376c6e3499de7f19980b7cd274735..4adc2b7d4a244d60c9523feb9e4b24f7c0e634a7 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3161,8 +3161,9 @@ source_set("browser") { +@@ -3167,8 +3167,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/process_singleton.patch b/patches/chromium/process_singleton.patch index 6ddc3cd2745f2..a145cb11c0cc5 100644 --- a/patches/chromium/process_singleton.patch +++ b/patches/chromium/process_singleton.patch @@ -18,10 +18,10 @@ This patch adds a few changes to the Chromium code: admin permissions. diff --git a/chrome/browser/process_singleton.h b/chrome/browser/process_singleton.h -index 4d446aa9ecfa14ffb1f65a2f45af6aaded122890..085b00fbb3ff95cdcde2a46760ab449808b4c1a9 100644 +index c19313c0b58baf0597a99d52ed7fcdb7faacc934..2748dd196fe1f56357348a204e24f0b8a28b97dd 100644 --- a/chrome/browser/process_singleton.h +++ b/chrome/browser/process_singleton.h -@@ -102,12 +102,19 @@ class ProcessSingleton { +@@ -101,12 +101,19 @@ class ProcessSingleton { base::RepeatingCallback; @@ -41,7 +41,7 @@ index 4d446aa9ecfa14ffb1f65a2f45af6aaded122890..085b00fbb3ff95cdcde2a46760ab4498 ~ProcessSingleton(); // Notify another process, if available. Otherwise sets ourselves as the -@@ -176,6 +183,8 @@ class ProcessSingleton { +@@ -175,6 +182,8 @@ class ProcessSingleton { #if BUILDFLAG(IS_WIN) bool EscapeVirtualization(const base::FilePath& user_data_dir); diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 451366d54d284..5136b1de11cc5 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -30,10 +30,10 @@ index a54a0dedf8ef1cfffa4e80a4707debed0e83d277..e66e71fdbabb40a5307b12cd8965e773 // RenderWidgetHost on the primary main frame, and false otherwise. virtual bool IsWidgetForPrimaryMainFrame(RenderWidgetHostImpl*); diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index a1cec61f882c38efa611401da69de123c99c9e7f..583b7cf8c0e484d53a0b93b86e65f28ba5359906 100644 +index 6a60a4b0275e1832216b092c29bc867f4727ca22..6a939edf24643207b26c9cc155ccca661b06f937 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2069,6 +2069,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { +@@ -2068,6 +2068,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { if (view_) { view_->UpdateCursor(cursor); } @@ -44,10 +44,10 @@ index a1cec61f882c38efa611401da69de123c99c9e7f..583b7cf8c0e484d53a0b93b86e65f28b void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 65a3b57c38419c15b071e67852789b48533fe53a..fcb7a38577a7b597be09b73cea9308b7112fee2a 100644 +index c0ef22f3872e96be15867428aff1006b8a14a1df..6eaa7d566058fdcc9ebfa10f0420c3a234cb0483 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5907,6 +5907,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -6060,6 +6060,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,10 +60,10 @@ index 65a3b57c38419c15b071e67852789b48533fe53a..fcb7a38577a7b597be09b73cea9308b7 RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index de9650b781ccb250fd5f59aaea8dc6e09d7816ef..09ae0904e236336058bbf1fe9c4d211ddbe146a4 100644 +index bb00cc84d8880911c1b170a0b7084a8d9cd4bbdb..e8db4afa0c4f1061fe1609745cbac815f52b4a28 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h -@@ -1186,6 +1186,7 @@ class CONTENT_EXPORT WebContentsImpl +@@ -1189,6 +1189,7 @@ class CONTENT_EXPORT WebContentsImpl void SendScreenRects() override; void SendActiveState(bool active) override; TextInputManager* GetTextInputManager() override; diff --git a/patches/chromium/refactor_expose_file_system_access_blocklist.patch b/patches/chromium/refactor_expose_file_system_access_blocklist.patch index 2e7293355ab49..20dba82debd12 100644 --- a/patches/chromium/refactor_expose_file_system_access_blocklist.patch +++ b/patches/chromium/refactor_expose_file_system_access_blocklist.patch @@ -269,7 +269,7 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca void ChromeFileSystemAccessPermissionContext::SetOriginExtendedPermissionByUser( diff --git a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h -index 5e1aa12c6337e8d0dee9f24d7ec233a894763053..e1e6a8163be4c95031a464481f55357af253cfb2 100644 +index f647100981fd98d8511d07a6d7e100910e38a0f2..14e1b3c8ec78429f5a845f54cc973e7c77ea8bc4 100644 --- a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h +++ b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h @@ -9,10 +9,13 @@ @@ -294,9 +294,9 @@ index 5e1aa12c6337e8d0dee9f24d7ec233a894763053..e1e6a8163be4c95031a464481f55357a #include "components/enterprise/buildflags/buildflags.h" #include "components/permissions/features.h" #include "components/permissions/object_permission_context_base.h" -@@ -399,6 +403,183 @@ class ChromeFileSystemAccessPermissionContext - // This is needed when updating path with ScopedPathOverride. - void ResetBlockPathsForTesting(); +@@ -403,6 +407,183 @@ class ChromeFileSystemAccessPermissionContext + return is_block_path_rules_init_complete_; + } + // Sentinel used to indicate that no PathService key is specified for a path in + // the struct below. diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index 676ea456832bd..e9dd22401d93b 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 9269ef00d1c0ce0606a39533b839e061ba448d7e..7c4851fb5f9e28ab77837755993d375e91a0dcac 100644 +index de2e8163c6ae5a1a01a79413d3d44b7c11ede311..e1692192bfa25f9949dd3f2fa2b61fc5dcef2e26 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10146,25 +10146,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10299,25 +10299,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch index b7b7f6aae4eb9..e0e67b527d258 100644 --- a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch +++ b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch @@ -233,10 +233,10 @@ index 7c99a9512e6f65713fe8483cef7b7c9b494b4491..8fb6cf252961c9773d1a6a09d47bec6a } diff --git a/content/common/features.cc b/content/common/features.cc -index 8dcb54b4c48cde0d11e682cc23dacbec9c4814df..c55f4d02691ec3b2255c47e89491fa76d8b996ea 100644 +index 8c02eee693930e68cc734bbaba9a1fdb403cf8c1..aa3084feb5aa8c6a771016b38f0adcfa39bed9b2 100644 --- a/content/common/features.cc +++ b/content/common/features.cc -@@ -308,6 +308,14 @@ BASE_FEATURE(kIOSurfaceCapturer, +@@ -315,6 +315,14 @@ BASE_FEATURE(kIOSurfaceCapturer, base::FEATURE_ENABLED_BY_DEFAULT); #endif @@ -252,10 +252,10 @@ index 8dcb54b4c48cde0d11e682cc23dacbec9c4814df..c55f4d02691ec3b2255c47e89491fa76 // invalidated upon notifications sent by base::SystemMonitor. If disabled, the // cache is considered invalid on every enumeration request. diff --git a/content/common/features.h b/content/common/features.h -index 6ffc0e6c10c190b410c9f7269a6146447a38c800..bba9eb2e3291539a4565b306f4c2c687b7d27541 100644 +index 032df239241bb73a19f1f3e1c0683764c40e96eb..56d00c458e0702de4830d849aa0639336823112a 100644 --- a/content/common/features.h +++ b/content/common/features.h -@@ -101,6 +101,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); +@@ -102,6 +102,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); #if BUILDFLAG(IS_MAC) CONTENT_EXPORT BASE_DECLARE_FEATURE(kIOSurfaceCapturer); #endif diff --git a/patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch b/patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch new file mode 100644 index 0000000000000..965070769efd2 --- /dev/null +++ b/patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch @@ -0,0 +1,4219 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Colin Blundell +Date: Mon, 19 May 2025 23:49:13 -0700 +Subject: Revert "[webgl] Add stub WebGL[2]RenderingContextWebGPU" + +This reverts commit e530c1578622adea59ae2ac3a586ae090681422b. + +Reason for revert: Multiple eng reporting that this is causing build failures due to too-long pathnames, with no immediate feasible workaround + +Bug: 414506479 +Original change's description: +> [webgl] Add stub WebGL[2]RenderingContextWebGPU +> +> These implementations of the WebGL IDL are meant to be implemented with +> ANGLE running on top of the WebGPU using dawn::wire, the same way that +> WebGPU's JS bindings are implemented. If successful, this would allow +> reducing the GPU process attack surface as it wouldn't need to support +> the GLES command buffer anymore. +> +> Binary-Size: Required initial increase to add WebGLOnWebGPU. +> Fuchsia-Binary-Size: Increase is temporary, will be more than compensated by linking ANGLE statically (-400kb). +> Bug: 414506479 +> Change-Id: I63d88a06d0d91e9842b48414d335df99522bba8d +> Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6494836 +> Reviewed-by: Brandon Jones +> Commit-Queue: Corentin Wallez +> Reviewed-by: Colin Blundell +> Cr-Commit-Position: refs/heads/main@{#1462154} + +Bug: 414506479 +No-Presubmit: true +No-Tree-Checks: true +No-Try: true +Change-Id: I0d4f94e9ceabd770250390d6f4ffe844a4ad00cb +Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6565622 +Auto-Submit: Colin Blundell +Commit-Queue: Rubber Stamper +Bot-Commit: Rubber Stamper +Cr-Commit-Position: refs/heads/main@{#1462590} + +diff --git a/third_party/blink/renderer/bindings/generated_in_modules.gni b/third_party/blink/renderer/bindings/generated_in_modules.gni +index b42efe786712f81b5b86ff90f62a7ee486c16c9a..c8177157631aeb7a0d8c65c57ac6da5b74da8b1f 100644 +--- a/third_party/blink/renderer/bindings/generated_in_modules.gni ++++ b/third_party/blink/renderer/bindings/generated_in_modules.gni +@@ -2986,8 +2986,6 @@ generated_interface_sources_in_modules = [ + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_web_transport_error.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context.h", +- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context_webgpu.cc", +- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context_webgpu.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_active_info.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_active_info.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_blend_func_extended.cc", +@@ -3046,8 +3044,6 @@ generated_interface_sources_in_modules = [ + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_renderbuffer.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context.h", +- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context_webgpu.cc", +- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context_webgpu.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_sampler.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_sampler.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_shader.cc", +@@ -3282,8 +3278,8 @@ generated_union_sources_in_modules = [ + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_boolean_mediatrackconstraints.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasfilter_string.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasfilter_string.h", +- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.cc", +- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h", ++ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webglrenderingcontext.cc", ++ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webglrenderingcontext.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_client_messageport_serviceworker.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_client_messageport_serviceworker.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_constraindomstringparameters_string_stringsequence.cc", +@@ -3310,8 +3306,8 @@ generated_union_sources_in_modules = [ + "$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_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.cc", +- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h", ++ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webglrenderingcontext.cc", ++ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webglrenderingcontext.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuextent3ddict_unsignedlongenforcerangesequence.cc", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuextent3ddict_unsignedlongenforcerangesequence.h", + "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuorigin2ddict_unsignedlongenforcerangesequence.cc", +diff --git a/third_party/blink/renderer/bindings/idl_in_modules.gni b/third_party/blink/renderer/bindings/idl_in_modules.gni +index e48d158c150ab1a0bc9ed309310171e12c6de22e..e378f59cd4a6a7d3482fbb7b43e207d9f14ffb45 100644 +--- a/third_party/blink/renderer/bindings/idl_in_modules.gni ++++ b/third_party/blink/renderer/bindings/idl_in_modules.gni +@@ -997,7 +997,6 @@ static_idl_files_in_modules = [ + "//third_party/blink/renderer/modules/webgl/ovr_multiview_2.idl", + "//third_party/blink/renderer/modules/webgl/webgl2_rendering_context.idl", + "//third_party/blink/renderer/modules/webgl/webgl2_rendering_context_base.idl", +- "//third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl", + "//third_party/blink/renderer/modules/webgl/webgl_active_info.idl", + "//third_party/blink/renderer/modules/webgl/webgl_blend_func_extended.idl", + "//third_party/blink/renderer/modules/webgl/webgl_buffer.idl", +@@ -1030,7 +1029,6 @@ static_idl_files_in_modules = [ + "//third_party/blink/renderer/modules/webgl/webgl_renderbuffer.idl", + "//third_party/blink/renderer/modules/webgl/webgl_rendering_context.idl", + "//third_party/blink/renderer/modules/webgl/webgl_rendering_context_base.idl", +- "//third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl", + "//third_party/blink/renderer/modules/webgl/webgl_sampler.idl", + "//third_party/blink/renderer/modules/webgl/webgl_shader.idl", + "//third_party/blink/renderer/modules/webgl/webgl_shader_pixel_local_storage.idl", +diff --git a/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h b/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h +index 23dea4bb35b90c20dc6d7de9cc5c8356cbcde2f2..392b7a1c1574045d5118be10fd50068cc419afb3 100644 +--- a/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h ++++ b/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h +@@ -80,9 +80,9 @@ class ImageBitmap; + class ScriptState; + class StaticBitmapImage; + using V8RenderingContext = class +- V8UnionCanvasRenderingContext2DOrGPUCanvasContextOrImageBitmapRenderingContextOrWebGL2RenderingContextOrWebGL2RenderingContextWebGPUOrWebGLRenderingContextOrWebGLRenderingContextWebGPU; ++ V8UnionCanvasRenderingContext2DOrGPUCanvasContextOrImageBitmapRenderingContextOrWebGL2RenderingContextOrWebGLRenderingContext; + using V8OffscreenRenderingContext = class +- V8UnionGPUCanvasContextOrImageBitmapRenderingContextOrOffscreenCanvasRenderingContext2DOrWebGL2RenderingContextOrWebGL2RenderingContextWebGPUOrWebGLRenderingContextOrWebGLRenderingContextWebGPU; ++ V8UnionGPUCanvasContextOrImageBitmapRenderingContextOrOffscreenCanvasRenderingContext2DOrWebGL2RenderingContextOrWebGLRenderingContext; + class WebGraphicsContext3DVideoFramePool; + + class CORE_EXPORT CanvasRenderingContext +diff --git a/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl b/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl +index 261e9ad46901da85ea2d72c8f6b8e12b23641b94..70d0c26f00fc947af54d8ac8388a68c15d3b43dd 100644 +--- a/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl ++++ b/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl +@@ -7,8 +7,6 @@ + typedef (CanvasRenderingContext2D or + WebGLRenderingContext or + WebGL2RenderingContext or +- WebGLRenderingContextWebGPU or +- WebGL2RenderingContextWebGPU or + ImageBitmapRenderingContext or + GPUCanvasContext) RenderingContext; + +diff --git a/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h b/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h +index aa7114367cfefe7871fcf6eb69bc1ac96739bf37..cfa8ac671aa20c8631c2524bd970da21bdf57c06 100644 +--- a/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h ++++ b/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h +@@ -8,6 +8,6 @@ + // This is just a forwarding header to avoid including an enormous filename in + // each file that needs the declaration of the union that is used for + // RenderingContext. +-#include "third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h" ++#include "third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webglrenderingcontext.h" + + #endif // THIRD_PARTY_BLINK_RENDERER_MODULES_CANVAS_HTMLCANVAS_V8_RENDERING_CONTEXT_H_ +diff --git a/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl b/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl +index a15d8d671f7504c9e771e607485413728479423b..f88b06ce555b0a49ac40a93ce52cb49a5bf8c6e6 100644 +--- a/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl ++++ b/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl +@@ -7,8 +7,6 @@ + typedef (OffscreenCanvasRenderingContext2D or + WebGLRenderingContext or + WebGL2RenderingContext or +- WebGLRenderingContextWebGPU or +- WebGL2RenderingContextWebGPU or + ImageBitmapRenderingContext or + GPUCanvasContext) OffscreenRenderingContext; + enum OffscreenRenderingContextType { "2d", "webgl", "webgl2", "bitmaprenderer", "webgpu" }; +diff --git a/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h b/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h +index 3742d1e586615165f3bfdddbbd054e13a45e244d..b44bacfe4240240b0f65bdafd1ae8bc37182bdc7 100644 +--- a/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h ++++ b/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h +@@ -8,6 +8,6 @@ + // This is just a forwarding header to avoid including an enormous filename in + // each file that needs the declaration of the union that is used for + // OffscreenRenderingContext. +-#include "third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h" ++#include "third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webglrenderingcontext.h" + + #endif // THIRD_PARTY_BLINK_RENDERER_MODULES_CANVAS_OFFSCREENCANVAS_V8_OFFSCREEN_RENDERING_CONTEXT_H_ +diff --git a/third_party/blink/renderer/modules/webgl/BUILD.gn b/third_party/blink/renderer/modules/webgl/BUILD.gn +index 5c1ff9afbfea45aba7b1fa68234fc1c35914aa95..08d7b3f52c5c2cd6d1199396b2ce1775f2289798 100644 +--- a/third_party/blink/renderer/modules/webgl/BUILD.gn ++++ b/third_party/blink/renderer/modules/webgl/BUILD.gn +@@ -79,8 +79,6 @@ blink_modules_sources("webgl") { + "webgl2_rendering_context.h", + "webgl2_rendering_context_base.cc", + "webgl2_rendering_context_base.h", +- "webgl2_rendering_context_webgpu.cc", +- "webgl2_rendering_context_webgpu.h", + "webgl_active_info.h", + "webgl_blend_func_extended.cc", + "webgl_blend_func_extended.h", +@@ -153,10 +151,6 @@ blink_modules_sources("webgl") { + "webgl_rendering_context.h", + "webgl_rendering_context_base.cc", + "webgl_rendering_context_base.h", +- "webgl_rendering_context_webgpu.cc", +- "webgl_rendering_context_webgpu.h", +- "webgl_rendering_context_webgpu_base.cc", +- "webgl_rendering_context_webgpu_base.h", + "webgl_sampler.cc", + "webgl_sampler.h", + "webgl_shader.cc", +diff --git a/third_party/blink/renderer/modules/webgl/DEPS b/third_party/blink/renderer/modules/webgl/DEPS +index b0efa5dd316811a166016c144c048e15130586a3..ec20717bde034b51a30a949efee2e24db9bac499 100644 +--- a/third_party/blink/renderer/modules/webgl/DEPS ++++ b/third_party/blink/renderer/modules/webgl/DEPS +@@ -1,5 +1,4 @@ + include_rules = [ +- "+base/notimplemented.h", + "+device/vr/buildflags/buildflags.h", + "+device/vr/public/mojom/vr_service.mojom-blink.h", + "+device/vr/public/mojom/vr_service.mojom-blink-forward.h", +diff --git a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.cc b/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.cc +deleted file mode 100644 +index 290b5d688cbe44bb17ea73e388393f618c9e42c4..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.cc ++++ /dev/null +@@ -1,29 +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 "third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h" +- +-#include "base/notimplemented.h" +-#include "third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h" +-#include "third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h" +- +-namespace blink { +- +-WebGL2RenderingContextWebGPU::WebGL2RenderingContextWebGPU( +- CanvasRenderingContextHost* host, +- const CanvasContextCreationAttributesCore& requested_attributes) +- : WebGLRenderingContextWebGPUBase(host, +- requested_attributes, +- CanvasRenderingAPI::kWebgl2) {} +- +-V8RenderingContext* WebGL2RenderingContextWebGPU::AsV8RenderingContext() { +- return MakeGarbageCollected(this); +-} +- +-V8OffscreenRenderingContext* +-WebGL2RenderingContextWebGPU::AsV8OffscreenRenderingContext() { +- return MakeGarbageCollected(this); +-} +- +-} // namespace blink +diff --git a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h b/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h +deleted file mode 100644 +index db83b4ac9d3138dc82a2522adc22ded58f7d1627..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h ++++ /dev/null +@@ -1,28 +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 THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL2_RENDERING_CONTEXT_WEBGPU_H_ +-#define THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL2_RENDERING_CONTEXT_WEBGPU_H_ +- +-#include "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h" +- +-namespace blink { +- +-class WebGL2RenderingContextWebGPU final +- : public WebGLRenderingContextWebGPUBase { +- DEFINE_WRAPPERTYPEINFO(); +- +- public: +- WebGL2RenderingContextWebGPU( +- CanvasRenderingContextHost* host, +- const CanvasContextCreationAttributesCore& requested_attributes); +- +- // CanvasRenderingContext implementation +- V8RenderingContext* AsV8RenderingContext() final; +- V8OffscreenRenderingContext* AsV8OffscreenRenderingContext() final; +-}; +- +-} // namespace blink +- +-#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL2_RENDERING_CONTEXT_WEBGPU_H_ +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 +deleted file mode 100644 +index ac76ded5b53871030a6b7496fa3b24d79f27b56d..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl ++++ /dev/null +@@ -1,13 +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. +- +-// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7 +- +-[ +- ActiveScriptWrappable, +- Exposed=(Window,Worker), +- RuntimeEnabled=WebGLOnWebGPU +-] interface WebGL2RenderingContextWebGPU { }; +-WebGL2RenderingContextWebGPU includes WebGLRenderingContextBase; +-WebGL2RenderingContextWebGPU includes WebGL2RenderingContextBase; +diff --git a/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc b/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc +index 8a983f1720d94391f641be229c8fcac0fb07d148..048feec570e2bcdac3c57ac14094ba28635b112f 100644 +--- a/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc ++++ b/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc +@@ -4,15 +4,11 @@ + + #include "third_party/blink/renderer/modules/webgl/webgl_context_factory.h" + +-#include "base/notimplemented.h" + #include "third_party/blink/renderer/core/html/canvas/canvas_context_creation_attributes_core.h" + #include "third_party/blink/renderer/core/html/canvas/html_canvas_element.h" + #include "third_party/blink/renderer/modules/webgl/webgl2_rendering_context.h" +-#include "third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h" + #include "third_party/blink/renderer/modules/webgl/webgl_context_event.h" + #include "third_party/blink/renderer/modules/webgl/webgl_rendering_context.h" +-#include "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h" +-#include "third_party/blink/renderer/platform/runtime_enabled_features.h" + + namespace blink { + +@@ -32,11 +28,7 @@ WebGLContextFactory::WebGLContextFactory(bool is_webgl2) + CanvasRenderingContext* WebGLContextFactory::Create( + CanvasRenderingContextHost* host, + const CanvasContextCreationAttributesCore& attrs) { +- if (RuntimeEnabledFeatures::WebGLOnWebGPUEnabled()) { +- return CreateInternalWebGPU(host, attrs); +- } else { +- return CreateInternal(host, attrs); +- } ++ return CreateInternal(host, attrs); + } + + CanvasRenderingContext* WebGLContextFactory::CreateInternal( +@@ -106,16 +98,6 @@ CanvasRenderingContext* WebGLContextFactory::CreateInternal( + } + } + +-CanvasRenderingContext* WebGLContextFactory::CreateInternalWebGPU( +- CanvasRenderingContextHost* host, +- const CanvasContextCreationAttributesCore& attrs) { +- if (is_webgl2_) { +- return MakeGarbageCollected(host, attrs); +- } else { +- return MakeGarbageCollected(host, attrs); +- } +-} +- + CanvasRenderingContext::CanvasRenderingAPI + WebGLContextFactory::GetRenderingAPI() const { + if (is_webgl2_) { +diff --git a/third_party/blink/renderer/modules/webgl/webgl_context_factory.h b/third_party/blink/renderer/modules/webgl/webgl_context_factory.h +index e58bbe3f6eec6e64a89d08e7e83d63d9b0841a04..df24c7085def9fc934a835635c10ebf7382ba528 100644 +--- a/third_party/blink/renderer/modules/webgl/webgl_context_factory.h ++++ b/third_party/blink/renderer/modules/webgl/webgl_context_factory.h +@@ -39,9 +39,6 @@ class WebGLContextFactory : public CanvasRenderingContextFactory { + CanvasRenderingContext* CreateInternal( + CanvasRenderingContextHost*, + const CanvasContextCreationAttributesCore&); +- CanvasRenderingContext* CreateInternalWebGPU( +- CanvasRenderingContextHost*, +- const CanvasContextCreationAttributesCore&); + + const char* GetContextName() const; + Platform::ContextType GetContextType() const; +diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.cc b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.cc +deleted file mode 100644 +index ead39056f29ff7080c66d983489b090ad4b1ce8d..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.cc ++++ /dev/null +@@ -1,29 +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 "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h" +- +-#include "base/notimplemented.h" +-#include "third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h" +-#include "third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h" +- +-namespace blink { +- +-WebGLRenderingContextWebGPU::WebGLRenderingContextWebGPU( +- CanvasRenderingContextHost* host, +- const CanvasContextCreationAttributesCore& requested_attributes) +- : WebGLRenderingContextWebGPUBase(host, +- requested_attributes, +- CanvasRenderingAPI::kWebgl) {} +- +-V8RenderingContext* WebGLRenderingContextWebGPU::AsV8RenderingContext() { +- return MakeGarbageCollected(this); +-} +- +-V8OffscreenRenderingContext* +-WebGLRenderingContextWebGPU::AsV8OffscreenRenderingContext() { +- return MakeGarbageCollected(this); +-} +- +-} // namespace blink +diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h +deleted file mode 100644 +index d0f3d1c34212165549eacf89b8d62ad611c0e168..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h ++++ /dev/null +@@ -1,28 +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 THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_H_ +-#define THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_H_ +- +-#include "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h" +- +-namespace blink { +- +-class WebGLRenderingContextWebGPU final +- : public WebGLRenderingContextWebGPUBase { +- DEFINE_WRAPPERTYPEINFO(); +- +- public: +- WebGLRenderingContextWebGPU( +- CanvasRenderingContextHost* host, +- const CanvasContextCreationAttributesCore& requested_attributes); +- +- // CanvasRenderingContext implementation +- V8RenderingContext* AsV8RenderingContext() final; +- V8OffscreenRenderingContext* AsV8OffscreenRenderingContext() final; +-}; +- +-} // namespace blink +- +-#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_H_ +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 +deleted file mode 100644 +index 2f4c23c68dc658cd8f91a72948b78f1f39c92578..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl ++++ /dev/null +@@ -1,16 +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. +- +-// https://www.khronos.org/registry/webgl/specs/latest/1.0/#WebGLRenderingContext +- +-[ +- ActiveScriptWrappable, +- Exposed=(Window,Worker), +- RuntimeEnabled=WebGLOnWebGPU +-] interface WebGLRenderingContextWebGPU { +- +- [RuntimeEnabled=WebGLDrawingBufferStorage] const GLenum RGB8 = 0x8051; +- [RuntimeEnabled=WebGLDrawingBufferStorage] const GLenum RGBA8 = 0x8058; +-}; +-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 +deleted file mode 100644 +index 18d26cfe4faea0937d6f6c0c35424b29acc43786..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.cc ++++ /dev/null +@@ -1,2475 +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 "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h" +- +-#include "base/notimplemented.h" +- +-namespace blink { +- +-WebGLRenderingContextWebGPUBase::WebGLRenderingContextWebGPUBase( +- CanvasRenderingContextHost* host, +- const CanvasContextCreationAttributesCore& requested_attributes, +- CanvasRenderingAPI api) +- : WebGLContextObjectSupport( +- host->GetTopExecutionContext()->GetTaskRunner(TaskType::kWebGL), +- /* is_webgl2 */ api == CanvasRenderingAPI::kWebgl2), +- CanvasRenderingContext(host, requested_attributes, api) {} +- +-WebGLRenderingContextWebGPUBase::~WebGLRenderingContextWebGPUBase() {} +- +-// **************************************************************************** +-// Start of WebGLRenderingContextBase's IDL methods +-// **************************************************************************** +- +-V8UnionHTMLCanvasElementOrOffscreenCanvas* +-WebGLRenderingContextWebGPUBase::getHTMLOrOffscreenCanvas() const { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-int WebGLRenderingContextWebGPUBase::drawingBufferWidth() const { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-int WebGLRenderingContextWebGPUBase::drawingBufferHeight() const { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-GLenum WebGLRenderingContextWebGPUBase::drawingBufferFormat() const { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-V8PredefinedColorSpace +-WebGLRenderingContextWebGPUBase::drawingBufferColorSpace() const { +- NOTIMPLEMENTED(); +- return V8PredefinedColorSpace(V8PredefinedColorSpace::Enum::kSRGB); +-} +- +-void WebGLRenderingContextWebGPUBase::setDrawingBufferColorSpace( +- const V8PredefinedColorSpace& color_space, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-V8PredefinedColorSpace WebGLRenderingContextWebGPUBase::unpackColorSpace() +- const { +- NOTIMPLEMENTED(); +- return V8PredefinedColorSpace(V8PredefinedColorSpace::Enum::kSRGB); +-} +- +-void WebGLRenderingContextWebGPUBase::setUnpackColorSpace( +- const V8PredefinedColorSpace& color_space, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::activeTexture(GLenum texture) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::attachShader(WebGLProgram*, +- WebGLShader*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bindAttribLocation(WebGLProgram*, +- GLuint index, +- const String& name) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bindBuffer(GLenum target, +- WebGLBuffer* buffer) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bindFramebuffer(GLenum target, +- WebGLFramebuffer*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bindRenderbuffer(GLenum target, +- WebGLRenderbuffer*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bindTexture(GLenum target, +- WebGLTexture*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::blendColor(GLfloat red, +- GLfloat green, +- GLfloat blue, +- GLfloat alpha) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::blendEquation(GLenum mode) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::blendEquationSeparate(GLenum mode_rgb, +- GLenum mode_alpha) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::blendFunc(GLenum sfactor, +- GLenum dfactor) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::blendFuncSeparate(GLenum src_rgb, +- GLenum dst_rgb, +- GLenum src_alpha, +- GLenum dst_alpha) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bufferData(GLenum target, +- int64_t size, +- GLenum usage) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bufferData(GLenum target, +- DOMArrayBufferBase* data, +- GLenum usage) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bufferData( +- GLenum target, +- MaybeShared data, +- GLenum usage) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bufferSubData( +- GLenum target, +- int64_t offset, +- base::span data) { +- NOTIMPLEMENTED(); +-} +- +-GLenum WebGLRenderingContextWebGPUBase::checkFramebufferStatus(GLenum target) { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-void WebGLRenderingContextWebGPUBase::clear(GLbitfield mask) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::clearColor(GLfloat red, +- GLfloat green, +- GLfloat blue, +- GLfloat alpha) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::clearDepth(GLfloat) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::clearStencil(GLint) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::colorMask(GLboolean red, +- GLboolean green, +- GLboolean blue, +- GLboolean alpha) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compileShader(WebGLShader*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexImage2D( +- GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- MaybeShared data) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexSubImage2D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- MaybeShared data) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::copyTexImage2D(GLenum target, +- GLint level, +- GLenum internalformat, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLint border) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::copyTexSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-WebGLBuffer* WebGLRenderingContextWebGPUBase::createBuffer() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-WebGLFramebuffer* WebGLRenderingContextWebGPUBase::createFramebuffer() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-WebGLProgram* WebGLRenderingContextWebGPUBase::createProgram() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-WebGLRenderbuffer* WebGLRenderingContextWebGPUBase::createRenderbuffer() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-WebGLShader* WebGLRenderingContextWebGPUBase::createShader(GLenum type) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-WebGLTexture* WebGLRenderingContextWebGPUBase::createTexture() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::cullFace(GLenum mode) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::deleteBuffer(WebGLBuffer*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::deleteFramebuffer(WebGLFramebuffer*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::deleteProgram(WebGLProgram*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::deleteRenderbuffer(WebGLRenderbuffer*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::deleteShader(WebGLShader*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::deleteTexture(WebGLTexture*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::depthFunc(GLenum) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::depthMask(GLboolean) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::depthRange(GLfloat z_near, +- GLfloat z_far) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::detachShader(WebGLProgram*, +- WebGLShader*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::disable(GLenum cap) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::disableVertexAttribArray(GLuint index) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::drawArrays(GLenum mode, +- GLint first, +- GLsizei count) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::drawElements(GLenum mode, +- GLsizei count, +- GLenum type, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::enable(GLenum cap) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::enableVertexAttribArray(GLuint index) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::finish() { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::flush() { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::framebufferRenderbuffer( +- GLenum target, +- GLenum attachment, +- GLenum renderbuffertarget, +- WebGLRenderbuffer*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::framebufferTexture2D(GLenum target, +- GLenum attachment, +- GLenum textarget, +- WebGLTexture*, +- GLint level) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::frontFace(GLenum mode) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::generateMipmap(GLenum target) { +- NOTIMPLEMENTED(); +-} +- +-WebGLActiveInfo* WebGLRenderingContextWebGPUBase::getActiveAttrib( +- WebGLProgram*, +- GLuint index) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-WebGLActiveInfo* WebGLRenderingContextWebGPUBase::getActiveUniform( +- WebGLProgram*, +- GLuint index) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-std::optional>> +-WebGLRenderingContextWebGPUBase::getAttachedShaders(WebGLProgram*) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-GLint WebGLRenderingContextWebGPUBase::getAttribLocation(WebGLProgram*, +- const String& name) { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getBufferParameter(ScriptState*, +- GLenum target, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-WebGLContextAttributes* WebGLRenderingContextWebGPUBase::getContextAttributes() +- const { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-GLenum WebGLRenderingContextWebGPUBase::getError() { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-ScriptObject WebGLRenderingContextWebGPUBase::getExtension(ScriptState*, +- const String& name) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getFramebufferAttachmentParameter( +- ScriptState*, +- GLenum target, +- GLenum attachment, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getParameter(ScriptState*, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getProgramParameter(ScriptState*, +- WebGLProgram*, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-String WebGLRenderingContextWebGPUBase::getProgramInfoLog(WebGLProgram*) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getRenderbufferParameter( +- ScriptState*, +- GLenum target, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getShaderParameter(ScriptState*, +- WebGLShader*, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-String WebGLRenderingContextWebGPUBase::getShaderInfoLog(WebGLShader*) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-WebGLShaderPrecisionFormat* +-WebGLRenderingContextWebGPUBase::getShaderPrecisionFormat( +- GLenum shader_type, +- GLenum precision_type) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-String WebGLRenderingContextWebGPUBase::getShaderSource(WebGLShader*) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-std::optional> +-WebGLRenderingContextWebGPUBase::getSupportedExtensions() { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getTexParameter(ScriptState*, +- GLenum target, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getUniform( +- ScriptState*, +- WebGLProgram*, +- const WebGLUniformLocation*) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-WebGLUniformLocation* WebGLRenderingContextWebGPUBase::getUniformLocation( +- WebGLProgram*, +- const String&) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getVertexAttrib(ScriptState*, +- GLuint index, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-int64_t WebGLRenderingContextWebGPUBase::getVertexAttribOffset(GLuint index, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-void WebGLRenderingContextWebGPUBase::hint(GLenum target, GLenum mode) { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::isBuffer(WebGLBuffer*) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::isEnabled(GLenum cap) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::isFramebuffer(WebGLFramebuffer*) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::isProgram(WebGLProgram*) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::isRenderbuffer(WebGLRenderbuffer*) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::isShader(WebGLShader*) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::isTexture(WebGLTexture*) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-void WebGLRenderingContextWebGPUBase::lineWidth(GLfloat) { +- NOTIMPLEMENTED(); +-} +-void WebGLRenderingContextWebGPUBase::linkProgram(WebGLProgram*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::pixelStorei(GLenum pname, GLint param) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::polygonOffset(GLfloat factor, +- GLfloat units) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::readPixels( +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared pixels) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::renderbufferStorage(GLenum target, +- GLenum internalformat, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::sampleCoverage(GLfloat value, +- GLboolean invert) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::scissor(GLint x, +- GLint y, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::shaderSource(WebGLShader*, +- const String&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::stencilFunc(GLenum func, +- GLint ref, +- GLuint mask) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::stencilFuncSeparate(GLenum face, +- GLenum func, +- GLint ref, +- GLuint mask) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::stencilMask(GLuint) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::stencilMaskSeparate(GLenum face, +- GLuint mask) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::stencilOp(GLenum fail, +- GLenum zfail, +- GLenum zpass) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::stencilOpSeparate(GLenum face, +- GLenum fail, +- GLenum zfail, +- GLenum zpass) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texParameterf(GLenum target, +- GLenum pname, +- GLfloat param) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texParameteri(GLenum target, +- GLenum pname, +- GLint param) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D( +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- ImageData*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- HTMLImageElement*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- HTMLVideoElement*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- VideoFrame*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- ImageBitmap*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- ImageData*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- HTMLImageElement*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +-void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- HTMLVideoElement*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- VideoFrame*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- ImageBitmap*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1f(const WebGLUniformLocation*, +- GLfloat x) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1fv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1i(const WebGLUniformLocation*, +- GLint x) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1iv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2f(const WebGLUniformLocation*, +- GLfloat x, +- GLfloat y) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2fv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2i(const WebGLUniformLocation*, +- GLint x, +- GLint y) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2iv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3f(const WebGLUniformLocation*, +- GLfloat x, +- GLfloat y, +- GLfloat z) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3fv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3i(const WebGLUniformLocation*, +- GLint x, +- GLint y, +- GLint z) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3iv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4f(const WebGLUniformLocation*, +- GLfloat x, +- GLfloat y, +- GLfloat z, +- GLfloat w) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4fv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4i(const WebGLUniformLocation*, +- GLint x, +- GLint y, +- GLint z, +- GLint w) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4iv(const WebGLUniformLocation*, +- base::span) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix2fv( +- const WebGLUniformLocation*, +- GLboolean transpose, +- base::span value) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix3fv( +- const WebGLUniformLocation*, +- GLboolean transpose, +- base::span value) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix4fv( +- const WebGLUniformLocation*, +- GLboolean transpose, +- base::span value) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::useProgram(WebGLProgram*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::validateProgram(WebGLProgram*) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib1f(GLuint index, GLfloat x) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib1fv( +- GLuint index, +- base::span values) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib2f(GLuint index, +- GLfloat x, +- GLfloat y) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib2fv( +- GLuint index, +- base::span values) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib3f(GLuint index, +- GLfloat x, +- GLfloat y, +- GLfloat z) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib3fv( +- GLuint index, +- base::span values) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib4f(GLuint index, +- GLfloat x, +- GLfloat y, +- GLfloat z, +- GLfloat w) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttrib4fv( +- GLuint index, +- base::span values) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttribPointer(GLuint index, +- GLint size, +- GLenum type, +- GLboolean normalized, +- GLsizei stride, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::viewport(GLint x, +- GLint y, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::drawingBufferStorage(GLenum sizedformat, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::commit() { +- NOTIMPLEMENTED(); +-} +- +-ScriptPromise WebGLRenderingContextWebGPUBase::makeXRCompatible( +- ScriptState*, +- ExceptionState&) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-// **************************************************************************** +-// End of WebGLRenderingContextBase's IDL methods +-// **************************************************************************** +- +-// ************************************************************************** +-// Start of WebGL2RenderingContextBase's IDL methods +-// ************************************************************************** +- +-void WebGLRenderingContextWebGPUBase::bufferData( +- GLenum target, +- MaybeShared srcData, +- GLenum usage, +- int64_t srcOffset, +- GLuint length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bufferSubData( +- GLenum target, +- int64_t offset, +- MaybeShared srcData, +- int64_t srcOffset, +- GLuint length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::copyBufferSubData(GLenum readTarget, +- GLenum writeTarget, +- int64_t readOffset, +- int64_t writeOffset, +- int64_t size) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::getBufferSubData( +- GLenum target, +- int64_t srcByteOffset, +- MaybeShared dstData, +- int64_t dstOffset, +- GLuint length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::blitFramebuffer(GLint src_x0, +- GLint src_y0, +- GLint src_x1, +- GLint src_y1, +- GLint dst_x0, +- GLint dst_y0, +- GLint dst_x1, +- GLint dst_y1, +- GLbitfield mask, +- GLenum filter) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::framebufferTextureLayer( +- GLenum target, +- GLenum attachment, +- WebGLTexture* texture, +- GLint level, +- GLint layer) { +- NOTIMPLEMENTED(); +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getInternalformatParameter( +- ScriptState* script_state, +- GLenum target, +- GLenum internalformat, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-void WebGLRenderingContextWebGPUBase::invalidateFramebuffer( +- GLenum target, +- const Vector& attachments) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::invalidateSubFramebuffer( +- GLenum target, +- const Vector& attachments, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::readBuffer(GLenum mode) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::renderbufferStorageMultisample( +- GLenum target, +- GLsizei samples, +- GLenum internalformat, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- ImageData* pixels) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* canvas, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D( +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage2D( +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared data, +- int64_t src_offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texElement2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- Element* element, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- ImageData* pixels) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* canvas, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage2D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- int64_t src_offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texStorage2D(GLenum target, +- GLsizei levels, +- GLenum internalformat, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texStorage3D(GLenum target, +- GLsizei levels, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- ImageData* pixels) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* canvas, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D( +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D( +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared pixels) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texImage3D( +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- GLuint src_offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- ImageData* pixels) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* context_host, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D( +- ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- MaybeShared pixels) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::texSubImage3D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- GLuint src_offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::copyTexSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexImage2D( +- GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexSubImage2D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexImage3D( +- GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexSubImage3D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexImage2D( +- GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLsizei image_size, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexSubImage2D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLsizei image_size, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexImage3D( +- GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLsizei image_size, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::compressedTexSubImage3D( +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLsizei image_size, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-GLint WebGLRenderingContextWebGPUBase::getFragDataLocation( +- WebGLProgram* program, +- const String& name) { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1ui( +- const WebGLUniformLocation* location, +- GLuint v0) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2ui( +- const WebGLUniformLocation* location, +- GLuint v0, +- GLuint v1) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3ui( +- const WebGLUniformLocation* location, +- GLuint v0, +- GLuint v1, +- GLuint v2) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4ui( +- const WebGLUniformLocation* location, +- GLuint v0, +- GLuint v1, +- GLuint v2, +- GLuint v3) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1fv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2fv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3fv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4fv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1iv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2iv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3iv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4iv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform1uiv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform2uiv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform3uiv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniform4uiv( +- const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix2fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix3fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix4fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix2x3fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix3x2fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix2x4fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix4x2fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix3x4fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::uniformMatrix4x3fv( +- const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttribI4i(GLuint index, +- GLint x, +- GLint y, +- GLint z, +- GLint w) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttribI4iv( +- GLuint index, +- base::span v) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttribI4ui(GLuint index, +- GLuint x, +- GLuint y, +- GLuint z, +- GLuint w) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttribI4uiv( +- GLuint index, +- base::span v) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttribIPointer(GLuint index, +- GLint size, +- GLenum type, +- GLsizei stride, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::vertexAttribDivisor(GLuint index, +- GLuint divisor) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::drawArraysInstanced( +- GLenum mode, +- GLint first, +- GLsizei count, +- GLsizei instance_count) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::drawElementsInstanced( +- GLenum mode, +- GLsizei count, +- GLenum type, +- int64_t offset, +- GLsizei instance_count) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::drawRangeElements(GLenum mode, +- GLuint start, +- GLuint end, +- GLsizei count, +- GLenum type, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::drawBuffers( +- const Vector& buffers) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::clearBufferiv( +- GLenum buffer, +- GLint drawbuffer, +- base::span value, +- GLuint src_offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::clearBufferuiv( +- GLenum buffer, +- GLint drawbuffer, +- base::span value, +- GLuint src_offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::clearBufferfv( +- GLenum buffer, +- GLint drawbuffer, +- base::span value, +- GLuint src_offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::clearBufferfi(GLenum buffer, +- GLint drawbuffer, +- GLfloat depth, +- GLint stencil) { +- NOTIMPLEMENTED(); +-} +- +-WebGLQuery* WebGLRenderingContextWebGPUBase::createQuery() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::deleteQuery(WebGLQuery* query) { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::isQuery(WebGLQuery* query) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-void WebGLRenderingContextWebGPUBase::beginQuery(GLenum target, +- WebGLQuery* query) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::endQuery(GLenum target) { +- NOTIMPLEMENTED(); +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getQuery(ScriptState* script_state, +- GLenum target, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getQueryParameter( +- ScriptState* script_state, +- WebGLQuery* query, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-WebGLSampler* WebGLRenderingContextWebGPUBase::createSampler() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::deleteSampler(WebGLSampler* sampler) { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::isSampler(WebGLSampler* sampler) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-void WebGLRenderingContextWebGPUBase::bindSampler(GLuint unit, +- WebGLSampler* sampler) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::samplerParameteri(WebGLSampler* sampler, +- GLenum pname, +- GLint param) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::samplerParameterf(WebGLSampler* sampler, +- GLenum pname, +- GLfloat param) { +- NOTIMPLEMENTED(); +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getSamplerParameter( +- ScriptState* script_state, +- WebGLSampler* sampler, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-WebGLSync* WebGLRenderingContextWebGPUBase::fenceSync(GLenum condition, +- GLbitfield flags) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-bool WebGLRenderingContextWebGPUBase::isSync(WebGLSync* sync) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-void WebGLRenderingContextWebGPUBase::deleteSync(WebGLSync* sync) { +- NOTIMPLEMENTED(); +-} +- +-GLenum WebGLRenderingContextWebGPUBase::clientWaitSync(WebGLSync* sync, +- GLbitfield flags, +- GLuint64 timeout) { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-void WebGLRenderingContextWebGPUBase::waitSync(WebGLSync* sync, +- GLbitfield flags, +- GLint64 timeout) { +- NOTIMPLEMENTED(); +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getSyncParameter( +- ScriptState* script_state, +- WebGLSync* sync, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-WebGLTransformFeedback* +-WebGLRenderingContextWebGPUBase::createTransformFeedback() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::deleteTransformFeedback( +- WebGLTransformFeedback* feedback) { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::isTransformFeedback( +- WebGLTransformFeedback* feedback) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-void WebGLRenderingContextWebGPUBase::bindTransformFeedback( +- GLenum target, +- WebGLTransformFeedback* feedback) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::beginTransformFeedback( +- GLenum primitive_mode) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::endTransformFeedback() { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::transformFeedbackVaryings( +- WebGLProgram* program, +- const Vector& varyings, +- GLenum buffer_mode) { +- NOTIMPLEMENTED(); +-} +- +-WebGLActiveInfo* WebGLRenderingContextWebGPUBase::getTransformFeedbackVarying( +- WebGLProgram* program, +- GLuint index) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::pauseTransformFeedback() { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::resumeTransformFeedback() { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bindBufferBase(GLenum target, +- GLuint index, +- WebGLBuffer* buffer) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::bindBufferRange(GLenum target, +- GLuint index, +- WebGLBuffer* buffer, +- int64_t offset, +- int64_t size) { +- NOTIMPLEMENTED(); +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getIndexedParameter( +- ScriptState* script_state, +- GLenum target, +- GLuint index) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-std::optional> +-WebGLRenderingContextWebGPUBase::getUniformIndices( +- WebGLProgram* program, +- const Vector& uniform_names) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getActiveUniforms( +- ScriptState* script_state, +- WebGLProgram* program, +- const Vector& uniform_indices, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-GLuint WebGLRenderingContextWebGPUBase::getUniformBlockIndex( +- WebGLProgram* program, +- const String& uniform_block_name) { +- NOTIMPLEMENTED(); +- return 0; +-} +- +-ScriptValue WebGLRenderingContextWebGPUBase::getActiveUniformBlockParameter( +- ScriptState* script_state, +- WebGLProgram* program, +- GLuint uniform_block_index, +- GLenum pname) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-String WebGLRenderingContextWebGPUBase::getActiveUniformBlockName( +- WebGLProgram* program, +- GLuint uniform_block_index) { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-void WebGLRenderingContextWebGPUBase::uniformBlockBinding( +- WebGLProgram* program, +- GLuint uniform_block_index, +- GLuint uniform_block_binding) { +- NOTIMPLEMENTED(); +-} +- +-WebGLVertexArrayObject* WebGLRenderingContextWebGPUBase::createVertexArray() { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::deleteVertexArray( +- WebGLVertexArrayObject* vertex_array) { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::isVertexArray( +- WebGLVertexArrayObject* vertex_array) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-void WebGLRenderingContextWebGPUBase::bindVertexArray( +- WebGLVertexArrayObject* vertex_array) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::readPixels(GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::readPixels( +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- int64_t offset) { +- NOTIMPLEMENTED(); +-} +- +-// ************************************************************************** +-// End of WebGL2RenderingContextBase's IDL methods +-// ************************************************************************** +- +-// **************************************************************************** +-// Start of CanvasRenderingContext implementation +-// **************************************************************************** +-SkAlphaType WebGLRenderingContextWebGPUBase::GetAlphaType() const { +- NOTIMPLEMENTED(); +- return SkAlphaType::kUnknown_SkAlphaType; +-} +- +-viz::SharedImageFormat WebGLRenderingContextWebGPUBase::GetSharedImageFormat() +- const { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-gfx::ColorSpace WebGLRenderingContextWebGPUBase::GetColorSpace() const { +- NOTIMPLEMENTED(); +- return {}; +-} +- +-bool WebGLRenderingContextWebGPUBase::isContextLost() const { +- NOTIMPLEMENTED(); +- return false; +-} +- +-scoped_refptr WebGLRenderingContextWebGPUBase::GetImage( +- FlushReason) { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::SetHdrMetadata( +- const gfx::HDRMetadata& hdr_metadata) { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::IsComposited() const { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::IsPaintable() const { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::UsingSwapChain() const { +- NOTIMPLEMENTED(); +- return false; +-} +- +-void WebGLRenderingContextWebGPUBase::PageVisibilityChanged() { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::PaintRenderingResultsToCanvas( +- SourceDrawingBuffer) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-bool WebGLRenderingContextWebGPUBase::CopyRenderingResultsToVideoFrame( +- WebGraphicsContext3DVideoFramePool*, +- SourceDrawingBuffer, +- const gfx::ColorSpace&, +- VideoFrameCopyCompletedCallback) { +- NOTIMPLEMENTED(); +- return false; +-} +- +-cc::Layer* WebGLRenderingContextWebGPUBase::CcLayer() const { +- NOTIMPLEMENTED(); +- return nullptr; +-} +- +-void WebGLRenderingContextWebGPUBase::Stop() { +- NOTIMPLEMENTED(); +-} +- +-void WebGLRenderingContextWebGPUBase::FinalizeFrame(FlushReason) { +- NOTIMPLEMENTED(); +-} +- +-bool WebGLRenderingContextWebGPUBase::PushFrame() { +- NOTIMPLEMENTED(); +- return false; +-} +- +-// **************************************************************************** +-// End of CanvasRenderingContext implementation +-// **************************************************************************** +- +-void WebGLRenderingContextWebGPUBase::Trace(Visitor* visitor) const { +- WebGLContextObjectSupport::Trace(visitor); +- CanvasRenderingContext::Trace(visitor); +-} +-} // 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 +deleted file mode 100644 +index 10df703f34e8357a08f3d891e4b7291e247e3adc..0000000000000000000000000000000000000000 +--- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h ++++ /dev/null +@@ -1,1285 +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 THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_BASE_H_ +-#define THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_BASE_H_ +- +-#include "third_party/blink/renderer/bindings/core/v8/script_promise_resolver.h" +-#include "third_party/blink/renderer/bindings/core/v8/script_value.h" +-#include "third_party/blink/renderer/bindings/core/v8/v8_predefined_color_space.h" +-#include "third_party/blink/renderer/bindings/modules/v8/v8_webgl_context_attributes.h" +-#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/wtf/text/wtf_string.h" +- +-namespace blink { +- +-class ExceptionState; +-class HTMLImageElement; +-class HTMLVideoElement; +-class ImageBitmap; +-class ImageData; +-class ScriptState; +-class V8PredefinedColorSpace; +-class V8UnionHTMLCanvasElementOrOffscreenCanvas; +-class VideoFrame; +-class WebGLActiveInfo; +-class WebGLBuffer; +-class WebGLFramebuffer; +-class WebGLProgram; +-class WebGLQuery; +-class WebGLRenderbuffer; +-class WebGLSampler; +-class WebGLShader; +-class WebGLShaderPrecisionFormat; +-class WebGLSync; +-class WebGLTexture; +-class WebGLTransformFeedback; +-class WebGLUniformLocation; +-class WebGLVertexArrayObject; +- +-class MODULES_EXPORT WebGLRenderingContextWebGPUBase +- : public WebGLContextObjectSupport, +- public CanvasRenderingContext { +- public: +- WebGLRenderingContextWebGPUBase( +- CanvasRenderingContextHost* host, +- const CanvasContextCreationAttributesCore& requested_attributes, +- CanvasRenderingAPI api); +- ~WebGLRenderingContextWebGPUBase() override; +- +- WebGLRenderingContextWebGPUBase(const WebGLRenderingContextWebGPUBase&) = +- delete; +- WebGLRenderingContextWebGPUBase& operator=( +- const WebGLRenderingContextWebGPUBase&) = delete; +- +- // ************************************************************************** +- // Start of WebGLRenderingContextBase's IDL methods +- // ************************************************************************** +- V8UnionHTMLCanvasElementOrOffscreenCanvas* getHTMLOrOffscreenCanvas() const; +- +- int drawingBufferWidth() const; +- int drawingBufferHeight() const; +- GLenum drawingBufferFormat() const; +- V8PredefinedColorSpace drawingBufferColorSpace() const; +- void setDrawingBufferColorSpace(const V8PredefinedColorSpace& color_space, +- ExceptionState&); +- V8PredefinedColorSpace unpackColorSpace() const; +- void setUnpackColorSpace(const V8PredefinedColorSpace& color_space, +- ExceptionState&); +- +- void activeTexture(GLenum texture); +- void attachShader(WebGLProgram*, WebGLShader*); +- +- void bindAttribLocation(WebGLProgram*, GLuint index, const String& name); +- void bindBuffer(GLenum target, WebGLBuffer* buffer); +- void bindFramebuffer(GLenum target, WebGLFramebuffer*); +- void bindRenderbuffer(GLenum target, WebGLRenderbuffer*); +- void bindTexture(GLenum target, WebGLTexture*); +- void blendColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha); +- void blendEquation(GLenum mode); +- void blendEquationSeparate(GLenum mode_rgb, GLenum mode_alpha); +- void blendFunc(GLenum sfactor, GLenum dfactor); +- void blendFuncSeparate(GLenum src_rgb, +- GLenum dst_rgb, +- GLenum src_alpha, +- GLenum dst_alpha); +- +- void bufferData(GLenum target, int64_t size, GLenum usage); +- void bufferData(GLenum target, DOMArrayBufferBase* data, GLenum usage); +- void bufferData(GLenum target, +- MaybeShared data, +- GLenum usage); +- void bufferSubData(GLenum target, +- int64_t offset, +- base::span data); +- +- GLenum checkFramebufferStatus(GLenum target); +- void clear(GLbitfield mask); +- void clearColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha); +- void clearDepth(GLfloat); +- void clearStencil(GLint); +- void colorMask(GLboolean red, +- GLboolean green, +- GLboolean blue, +- GLboolean alpha); +- void compileShader(WebGLShader*); +- +- void compressedTexImage2D(GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- MaybeShared data); +- void compressedTexSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- MaybeShared data); +- void copyTexImage2D(GLenum target, +- GLint level, +- GLenum internalformat, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLint border); +- void copyTexSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height); +- +- WebGLBuffer* createBuffer(); +- WebGLFramebuffer* createFramebuffer(); +- WebGLProgram* createProgram(); +- WebGLRenderbuffer* createRenderbuffer(); +- WebGLShader* createShader(GLenum type); +- WebGLTexture* createTexture(); +- +- void cullFace(GLenum mode); +- +- void deleteBuffer(WebGLBuffer*); +- void deleteFramebuffer(WebGLFramebuffer*); +- void deleteProgram(WebGLProgram*); +- void deleteRenderbuffer(WebGLRenderbuffer*); +- void deleteShader(WebGLShader*); +- void deleteTexture(WebGLTexture*); +- +- void depthFunc(GLenum); +- void depthMask(GLboolean); +- void depthRange(GLfloat z_near, GLfloat z_far); +- void detachShader(WebGLProgram*, WebGLShader*); +- void disable(GLenum cap); +- void disableVertexAttribArray(GLuint index); +- void drawArrays(GLenum mode, GLint first, GLsizei count); +- void drawElements(GLenum mode, GLsizei count, GLenum type, int64_t offset); +- +- void enable(GLenum cap); +- void enableVertexAttribArray(GLuint index); +- void finish(); +- void flush(); +- void framebufferRenderbuffer(GLenum target, +- GLenum attachment, +- GLenum renderbuffertarget, +- WebGLRenderbuffer*); +- void framebufferTexture2D(GLenum target, +- GLenum attachment, +- GLenum textarget, +- WebGLTexture*, +- GLint level); +- void frontFace(GLenum mode); +- void generateMipmap(GLenum target); +- +- WebGLActiveInfo* getActiveAttrib(WebGLProgram*, GLuint index); +- WebGLActiveInfo* getActiveUniform(WebGLProgram*, GLuint index); +- std::optional>> getAttachedShaders( +- WebGLProgram*); +- GLint getAttribLocation(WebGLProgram*, const String& name); +- ScriptValue getBufferParameter(ScriptState*, GLenum target, GLenum pname); +- WebGLContextAttributes* getContextAttributes() const; +- GLenum getError(); +- ScriptObject getExtension(ScriptState*, const String& name); +- ScriptValue getFramebufferAttachmentParameter(ScriptState*, +- GLenum target, +- GLenum attachment, +- GLenum pname); +- ScriptValue getParameter(ScriptState*, GLenum pname); +- ScriptValue getProgramParameter(ScriptState*, WebGLProgram*, GLenum pname); +- String getProgramInfoLog(WebGLProgram*); +- ScriptValue getRenderbufferParameter(ScriptState*, +- GLenum target, +- GLenum pname); +- ScriptValue getShaderParameter(ScriptState*, WebGLShader*, GLenum pname); +- String getShaderInfoLog(WebGLShader*); +- WebGLShaderPrecisionFormat* getShaderPrecisionFormat(GLenum shader_type, +- GLenum precision_type); +- String getShaderSource(WebGLShader*); +- std::optional> getSupportedExtensions(); +- ScriptValue getTexParameter(ScriptState*, GLenum target, GLenum pname); +- ScriptValue getUniform(ScriptState*, +- WebGLProgram*, +- const WebGLUniformLocation*); +- WebGLUniformLocation* getUniformLocation(WebGLProgram*, const String&); +- ScriptValue getVertexAttrib(ScriptState*, GLuint index, GLenum pname); +- int64_t getVertexAttribOffset(GLuint index, GLenum pname); +- +- void hint(GLenum target, GLenum mode); +- bool isBuffer(WebGLBuffer*); +- bool isEnabled(GLenum cap); +- bool isFramebuffer(WebGLFramebuffer*); +- bool isProgram(WebGLProgram*); +- bool isRenderbuffer(WebGLRenderbuffer*); +- bool isShader(WebGLShader*); +- bool isTexture(WebGLTexture*); +- +- void lineWidth(GLfloat); +- void linkProgram(WebGLProgram*); +- void pixelStorei(GLenum pname, GLint param); +- void polygonOffset(GLfloat factor, GLfloat units); +- +- void readPixels(GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared pixels); +- +- void renderbufferStorage(GLenum target, +- GLenum internalformat, +- GLsizei width, +- GLsizei height); +- +- void sampleCoverage(GLfloat value, GLboolean invert); +- void scissor(GLint x, GLint y, GLsizei width, GLsizei height); +- void shaderSource(WebGLShader*, const String&); +- void stencilFunc(GLenum func, GLint ref, GLuint mask); +- void stencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask); +- void stencilMask(GLuint); +- void stencilMaskSeparate(GLenum face, GLuint mask); +- void stencilOp(GLenum fail, GLenum zfail, GLenum zpass); +- void stencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass); +- +- void texParameterf(GLenum target, GLenum pname, GLfloat param); +- void texParameteri(GLenum target, GLenum pname, GLint param); +- +- void texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared); +- void texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- ImageData*); +- void texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- HTMLImageElement*, +- ExceptionState&); +- void texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost*, +- ExceptionState&); +- void texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- HTMLVideoElement*, +- ExceptionState&); +- void texImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- VideoFrame*, +- ExceptionState&); +- void texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- ImageBitmap*, +- ExceptionState&); +- +- void texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared); +- void texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- ImageData*); +- void texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- HTMLImageElement*, +- ExceptionState&); +- void texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost*, +- ExceptionState&); +- void texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- HTMLVideoElement*, +- ExceptionState&); +- void texSubImage2D(ScriptState*, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- VideoFrame*, +- ExceptionState&); +- void texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLenum format, +- GLenum type, +- ImageBitmap*, +- ExceptionState&); +- +- void uniform1f(const WebGLUniformLocation*, GLfloat x); +- void uniform1fv(const WebGLUniformLocation*, base::span); +- void uniform1i(const WebGLUniformLocation*, GLint x); +- void uniform1iv(const WebGLUniformLocation*, base::span); +- void uniform2f(const WebGLUniformLocation*, GLfloat x, GLfloat y); +- void uniform2fv(const WebGLUniformLocation*, base::span); +- void uniform2i(const WebGLUniformLocation*, GLint x, GLint y); +- void uniform2iv(const WebGLUniformLocation*, base::span); +- void uniform3f(const WebGLUniformLocation*, GLfloat x, GLfloat y, GLfloat z); +- void uniform3fv(const WebGLUniformLocation*, base::span); +- void uniform3i(const WebGLUniformLocation*, GLint x, GLint y, GLint z); +- void uniform3iv(const WebGLUniformLocation*, base::span); +- void uniform4f(const WebGLUniformLocation*, +- GLfloat x, +- GLfloat y, +- GLfloat z, +- GLfloat w); +- void uniform4fv(const WebGLUniformLocation*, base::span); +- void uniform4i(const WebGLUniformLocation*, +- GLint x, +- GLint y, +- GLint z, +- GLint w); +- void uniform4iv(const WebGLUniformLocation*, base::span); +- +- void uniformMatrix2fv(const WebGLUniformLocation*, +- GLboolean transpose, +- base::span value); +- void uniformMatrix3fv(const WebGLUniformLocation*, +- GLboolean transpose, +- base::span value); +- void uniformMatrix4fv(const WebGLUniformLocation*, +- GLboolean transpose, +- base::span value); +- +- void useProgram(WebGLProgram*); +- void validateProgram(WebGLProgram*); +- +- void vertexAttrib1f(GLuint index, GLfloat x); +- void vertexAttrib1fv(GLuint index, base::span values); +- void vertexAttrib2f(GLuint index, GLfloat x, GLfloat y); +- void vertexAttrib2fv(GLuint index, base::span values); +- void vertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z); +- void vertexAttrib3fv(GLuint index, base::span values); +- void vertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w); +- void vertexAttrib4fv(GLuint index, base::span values); +- void vertexAttribPointer(GLuint index, +- GLint size, +- GLenum type, +- GLboolean normalized, +- GLsizei stride, +- int64_t offset); +- +- void viewport(GLint x, GLint y, GLsizei width, GLsizei height); +- +- void drawingBufferStorage(GLenum sizedformat, GLsizei width, GLsizei height); +- +- void commit(); +- +- ScriptPromise makeXRCompatible(ScriptState*, ExceptionState&); +- // ************************************************************************** +- // End of WebGLRenderingContextBase's IDL methods +- // ************************************************************************** +- +- // ************************************************************************** +- // Start of WebGL2RenderingContextBase's IDL methods +- // ************************************************************************** +- +- /* Buffer objects */ +- void bufferData(GLenum target, +- MaybeShared srcData, +- GLenum usage, +- int64_t srcOffset, +- GLuint length); +- void bufferSubData(GLenum target, +- int64_t offset, +- MaybeShared srcData, +- int64_t srcOffset, +- GLuint length); +- void copyBufferSubData(GLenum readTarget, +- GLenum writeTarget, +- int64_t readOffset, +- int64_t writeOffset, +- int64_t size); +- void getBufferSubData(GLenum target, +- int64_t srcByteOffset, +- MaybeShared dstData, +- int64_t dstOffset, +- GLuint length); +- +- /* Framebuffer objects */ +- void blitFramebuffer(GLint src_x0, +- GLint src_y0, +- GLint src_x1, +- GLint src_y1, +- GLint dst_x0, +- GLint dst_y0, +- GLint dst_x1, +- GLint dst_y1, +- GLbitfield mask, +- GLenum filter); +- void framebufferTextureLayer(GLenum target, +- GLenum attachment, +- WebGLTexture* texture, +- GLint level, +- GLint layer); +- ScriptValue getInternalformatParameter(ScriptState* script_state, +- GLenum target, +- GLenum internalformat, +- GLenum pname); +- void invalidateFramebuffer(GLenum target, const Vector& attachments); +- void invalidateSubFramebuffer(GLenum target, +- const Vector& attachments, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height); +- void readBuffer(GLenum mode); +- +- /* Renderbuffer objects */ +- void renderbufferStorageMultisample(GLenum target, +- GLsizei samples, +- GLenum internalformat, +- GLsizei width, +- GLsizei height); +- +- /* Texture objects */ +- void texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- int64_t offset); +- void texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- ImageData* pixels); +- void texImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state); +- // Handles both OffscreenCanvas and HTMLCanvasElement +- void texImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* canvas, +- ExceptionState& exception_state); +- void texImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state); +- void texImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state); +- void texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state); +- void texImage2D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared data, +- int64_t src_offset); +- +- void texElement2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLenum format, +- GLenum type, +- Element* element, +- ExceptionState& exception_state); +- +- void texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- int64_t offset); +- void texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- ImageData* pixels); +- void texSubImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state); +- // Handles both OffscreenCanvas and HTMLCanvasElement +- void texSubImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* canvas, +- ExceptionState& exception_state); +- void texSubImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state); +- void texSubImage2D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state); +- void texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state); +- void texSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- int64_t src_offset); +- +- void texStorage2D(GLenum target, +- GLsizei levels, +- GLenum internalformat, +- GLsizei width, +- GLsizei height); +- void texStorage3D(GLenum target, +- GLsizei levels, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth); +- void texImage3D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- int64_t offset); +- void texImage3D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- ImageData* pixels); +- void texImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state); +- // Handles both OffscreenCanvas and HTMLCanvasElement +- void texImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* canvas, +- ExceptionState& exception_state); +- void texImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state); +- void texImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state); +- void texImage3D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state); +- void texImage3D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared pixels); +- void texImage3D(GLenum target, +- GLint level, +- GLint internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- GLuint src_offset); +- void texSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- int64_t offset); +- void texSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- ImageData* pixels); +- void texSubImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- HTMLImageElement* image, +- ExceptionState& exception_state); +- // Handles both OffscreenCanvas and HTMLCanvasElement +- void texSubImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- CanvasRenderingContextHost* context_host, +- ExceptionState& exception_state); +- void texSubImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- HTMLVideoElement* video, +- ExceptionState& exception_state); +- void texSubImage3D(ScriptState* script_state, +- GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- VideoFrame* frame, +- ExceptionState& exception_state); +- void texSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- ImageBitmap* bitmap, +- ExceptionState& exception_state); +- void texSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- MaybeShared pixels); +- void texSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- GLuint src_offset); +- +- void copyTexSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLint x, +- GLint y, +- GLsizei width, +- GLsizei height); +- +- void compressedTexImage2D(GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override); +- void compressedTexSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override); +- void compressedTexImage3D(GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override); +- void compressedTexSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- MaybeShared data, +- GLuint src_offset, +- GLuint src_length_override); +- void compressedTexImage2D(GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLint border, +- GLsizei image_size, +- int64_t offset); +- void compressedTexSubImage2D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLsizei image_size, +- int64_t offset); +- void compressedTexImage3D(GLenum target, +- GLint level, +- GLenum internalformat, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLint border, +- GLsizei image_size, +- int64_t offset); +- void compressedTexSubImage3D(GLenum target, +- GLint level, +- GLint xoffset, +- GLint yoffset, +- GLint zoffset, +- GLsizei width, +- GLsizei height, +- GLsizei depth, +- GLenum format, +- GLsizei image_size, +- int64_t offset); +- +- /* Programs and shaders */ +- GLint getFragDataLocation(WebGLProgram* program, const String& name); +- +- /* Uniforms and attributes */ +- void uniform1ui(const WebGLUniformLocation* location, GLuint v0); +- void uniform2ui(const WebGLUniformLocation* location, GLuint v0, GLuint v1); +- void uniform3ui(const WebGLUniformLocation* location, +- GLuint v0, +- GLuint v1, +- GLuint v2); +- void uniform4ui(const WebGLUniformLocation* location, +- GLuint v0, +- GLuint v1, +- GLuint v2, +- GLuint v3); +- void uniform1fv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform2fv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform3fv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform4fv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform1iv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform2iv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform3iv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform4iv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform1uiv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform2uiv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform3uiv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniform4uiv(const WebGLUniformLocation* location, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix2fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix3fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix4fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix2x3fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix3x2fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix2x4fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix4x2fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix3x4fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- void uniformMatrix4x3fv(const WebGLUniformLocation* location, +- GLboolean transpose, +- base::span v, +- GLuint src_offset, +- GLuint src_length); +- +- void vertexAttribI4i(GLuint index, GLint x, GLint y, GLint z, GLint w); +- void vertexAttribI4iv(GLuint index, base::span v); +- void vertexAttribI4ui(GLuint index, GLuint x, GLuint y, GLuint z, GLuint w); +- void vertexAttribI4uiv(GLuint index, base::span v); +- void vertexAttribIPointer(GLuint index, +- GLint size, +- GLenum type, +- GLsizei stride, +- int64_t offset); +- +- /* Writing to the drawing buffer */ +- void vertexAttribDivisor(GLuint index, GLuint divisor); +- void drawArraysInstanced(GLenum mode, +- GLint first, +- GLsizei count, +- GLsizei instance_count); +- void drawElementsInstanced(GLenum mode, +- GLsizei count, +- GLenum type, +- int64_t offset, +- GLsizei instance_count); +- void drawRangeElements(GLenum mode, +- GLuint start, +- GLuint end, +- GLsizei count, +- GLenum type, +- int64_t offset); +- +- /* Multiple Render Targets */ +- void drawBuffers(const Vector& buffers); +- void clearBufferiv(GLenum buffer, +- GLint drawbuffer, +- base::span value, +- GLuint src_offset); +- void clearBufferuiv(GLenum buffer, +- GLint drawbuffer, +- base::span value, +- GLuint src_offset); +- void clearBufferfv(GLenum buffer, +- GLint drawbuffer, +- base::span value, +- GLuint src_offset); +- void clearBufferfi(GLenum buffer, +- GLint drawbuffer, +- GLfloat depth, +- GLint stencil); +- +- /* Query Objects */ +- WebGLQuery* createQuery(); +- void deleteQuery(WebGLQuery* query); +- bool isQuery(WebGLQuery* query); +- void beginQuery(GLenum target, WebGLQuery* query); +- void endQuery(GLenum target); +- ScriptValue getQuery(ScriptState* script_state, GLenum target, GLenum pname); +- ScriptValue getQueryParameter(ScriptState* script_state, +- WebGLQuery* query, +- GLenum pname); +- +- /* Sampler Objects */ +- WebGLSampler* createSampler(); +- void deleteSampler(WebGLSampler* sampler); +- bool isSampler(WebGLSampler* sampler); +- void bindSampler(GLuint unit, WebGLSampler* sampler); +- void samplerParameteri(WebGLSampler* sampler, GLenum pname, GLint param); +- void samplerParameterf(WebGLSampler* sampler, GLenum pname, GLfloat param); +- ScriptValue getSamplerParameter(ScriptState* script_state, +- WebGLSampler* sampler, +- GLenum pname); +- +- /* Sync objects */ +- WebGLSync* fenceSync(GLenum condition, GLbitfield flags); +- bool isSync(WebGLSync* sync); +- void deleteSync(WebGLSync* sync); +- GLenum clientWaitSync(WebGLSync* sync, GLbitfield flags, GLuint64 timeout); +- void waitSync(WebGLSync* sync, GLbitfield flags, GLint64 timeout); +- +- ScriptValue getSyncParameter(ScriptState* script_state, +- WebGLSync* sync, +- GLenum pname); +- +- /* Transform Feedback */ +- WebGLTransformFeedback* createTransformFeedback(); +- void deleteTransformFeedback(WebGLTransformFeedback* feedback); +- bool isTransformFeedback(WebGLTransformFeedback* feedback); +- void bindTransformFeedback(GLenum target, WebGLTransformFeedback* feedback); +- void beginTransformFeedback(GLenum primitive_mode); +- void endTransformFeedback(); +- void transformFeedbackVaryings(WebGLProgram* program, +- const Vector& varyings, +- GLenum buffer_mode); +- WebGLActiveInfo* getTransformFeedbackVarying(WebGLProgram* program, +- GLuint index); +- void pauseTransformFeedback(); +- void resumeTransformFeedback(); +- +- /* Uniform Buffer Objects and Transform Feedback Buffers */ +- void bindBufferBase(GLenum target, GLuint index, WebGLBuffer* buffer); +- void bindBufferRange(GLenum target, +- GLuint index, +- WebGLBuffer* buffer, +- int64_t offset, +- int64_t size); +- ScriptValue getIndexedParameter(ScriptState* script_state, +- GLenum target, +- GLuint index); +- std::optional> getUniformIndices( +- WebGLProgram* program, +- const Vector& uniform_names); +- ScriptValue getActiveUniforms(ScriptState* script_state, +- WebGLProgram* program, +- const Vector& uniform_indices, +- GLenum pname); +- GLuint getUniformBlockIndex(WebGLProgram* program, +- const String& uniform_block_name); +- ScriptValue getActiveUniformBlockParameter(ScriptState* script_state, +- WebGLProgram* program, +- GLuint uniform_block_index, +- GLenum pname); +- String getActiveUniformBlockName(WebGLProgram* program, +- GLuint uniform_block_index); +- void uniformBlockBinding(WebGLProgram* program, +- GLuint uniform_block_index, +- GLuint uniform_block_binding); +- +- /* Vertex Array Objects */ +- WebGLVertexArrayObject* createVertexArray(); +- void deleteVertexArray(WebGLVertexArrayObject* vertex_array); +- bool isVertexArray(WebGLVertexArrayObject* vertex_array); +- void bindVertexArray(WebGLVertexArrayObject* vertex_array); +- +- /* Reading */ +- void readPixels(GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- int64_t offset); +- void readPixels(GLint x, +- GLint y, +- GLsizei width, +- GLsizei height, +- GLenum format, +- GLenum type, +- MaybeShared pixels, +- int64_t offset); +- +- // ************************************************************************** +- // End of WebGL2RenderingContextBase's IDL methods +- // ************************************************************************** +- +- // ************************************************************************** +- // Start of CanvasRenderingContext implementation +- // ************************************************************************** +- SkAlphaType GetAlphaType() const override; +- viz::SharedImageFormat GetSharedImageFormat() const override; +- gfx::ColorSpace GetColorSpace() const override; +- bool isContextLost() const override; +- scoped_refptr 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; +- bool PaintRenderingResultsToCanvas(SourceDrawingBuffer) override; +- bool CopyRenderingResultsToVideoFrame( +- WebGraphicsContext3DVideoFramePool*, +- SourceDrawingBuffer, +- const gfx::ColorSpace&, +- VideoFrameCopyCompletedCallback) override; +- +- cc::Layer* CcLayer() const override; +- void Stop() override; +- void FinalizeFrame(FlushReason) override; +- bool PushFrame() override; +- +- // ************************************************************************** +- // End of CanvasRenderingContext implementation +- // ************************************************************************** +- +- void Trace(Visitor*) const override; +- +- private: +-}; +- +-} // namespace blink +- +-#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_BASE_H_ diff --git a/patches/chromium/scroll_bounce_flag.patch b/patches/chromium/scroll_bounce_flag.patch index 903b292f474f8..80773b57b2944 100644 --- a/patches/chromium/scroll_bounce_flag.patch +++ b/patches/chromium/scroll_bounce_flag.patch @@ -6,10 +6,10 @@ Subject: scroll_bounce_flag.patch Patch to make scrollBounce option work. diff --git a/content/renderer/render_thread_impl.cc b/content/renderer/render_thread_impl.cc -index 4176c771c26f67be6bb378c7b923f848bcf7cd1b..915e6b3098cea99e2ea2fca79cfb87026c1ba758 100644 +index 790bf3bdfc48936799e690ad644feaa12b3873a3..c86c7bc7790ab4c94d3692e8e70cb9fcdef93eda 100644 --- a/content/renderer/render_thread_impl.cc +++ b/content/renderer/render_thread_impl.cc -@@ -1331,7 +1331,7 @@ bool RenderThreadImpl::IsLcdTextEnabled() { +@@ -1309,7 +1309,7 @@ bool RenderThreadImpl::IsLcdTextEnabled() { } bool RenderThreadImpl::IsElasticOverscrollEnabled() { diff --git a/patches/chromium/support_mixed_sandbox_with_zygote.patch b/patches/chromium/support_mixed_sandbox_with_zygote.patch index 516afca1eff18..27d086b643d57 100644 --- a/patches/chromium/support_mixed_sandbox_with_zygote.patch +++ b/patches/chromium/support_mixed_sandbox_with_zygote.patch @@ -22,10 +22,10 @@ However, the patch would need to be reviewed by the security team, as it does touch a security-sensitive class. diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index 332f611678e53c0ea56c8baea71ca123d8cc0a95..6a1b182868157c91742c6b652cbdfc0f4373a27a 100644 +index c97471d75ab2d11cfe71f34d8d11b27edb5c0fce..44a8635ba28722b30e34695c130f7b271978391a 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc -@@ -1825,6 +1825,10 @@ bool RenderProcessHostImpl::Init() { +@@ -1833,6 +1833,10 @@ bool RenderProcessHostImpl::Init() { std::unique_ptr sandbox_delegate = std::make_unique( *cmd_line, IsPdf(), IsJitDisabled()); diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index 3d2707a42d38d..a388d87790125 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 3435a1d0ce5c8025b5a2005ebb4066e306579a69..3d37f389e0d9685119a5776832e0e005f8bcc6ca 100644 +index bbbc07e36e6de11169f8317c64558b8c4d1699d5..0cf259360950a7063c4f9d6dc71b004706330f37 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -3941,6 +3941,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -4094,6 +4094,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index 3435a1d0ce5c8025b5a2005ebb4066e306579a69..3d37f389e0d9685119a5776832e0e005 std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -3951,6 +3958,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -4104,6 +4111,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } @@ -35,7 +35,7 @@ index 3435a1d0ce5c8025b5a2005ebb4066e306579a69..3d37f389e0d9685119a5776832e0e005 CHECK(view_.get()); diff --git a/content/public/browser/web_contents.h b/content/public/browser/web_contents.h -index 560e0056bb9b0feb7510f81a80a6365cd38676d2..5ff33943a133b45d7a48a48844f5fa9e62a1f413 100644 +index 37061d761f18ea143a8095393c42c4cf5c9eca0e..e70f25a52dbe66bf1a9bbbcb6bf56f072b23eb34 100644 --- a/content/public/browser/web_contents.h +++ b/content/public/browser/web_contents.h @@ -121,10 +121,13 @@ class BrowserPluginGuestDelegate; diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index 8014e7b2a7672..6b2997ef95156 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,10 +15,10 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index e87536a31d03d8030b26781b9345fa7478d24afd..6182d198b65fd26e594ff04bbf4dc483299d19ed 100644 +index be73611db5328c76982ecca3caf5eccc30aac45e..0c4d801b3705fb609a40b8c58d2ee7f9b690461f 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -8817,6 +8817,17 @@ void RenderFrameHostImpl::EnterFullscreen( +@@ -8824,6 +8824,17 @@ void RenderFrameHostImpl::EnterFullscreen( } } @@ -37,10 +37,10 @@ index e87536a31d03d8030b26781b9345fa7478d24afd..6182d198b65fd26e594ff04bbf4dc483 if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 3d37f389e0d9685119a5776832e0e005f8bcc6ca..fc4af3a293fd807780f39b0cddc7605031620879 100644 +index 0cf259360950a7063c4f9d6dc71b004706330f37..97df851aa73d1bf8d8c8001646b63cbb43cd9a92 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4231,21 +4231,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4384,21 +4384,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index 3d37f389e0d9685119a5776832e0e005f8bcc6ca..fc4af3a293fd807780f39b0cddc76050 } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4404,7 +4408,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4557,7 +4561,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/patches/chromium/worker_context_will_destroy.patch b/patches/chromium/worker_context_will_destroy.patch index 4cdcc4de4f9b4..1e7ac85738928 100644 --- a/patches/chromium/worker_context_will_destroy.patch +++ b/patches/chromium/worker_context_will_destroy.patch @@ -26,10 +26,10 @@ index 7a2d251ba2d13d0a34df176111e6524a27b87f55..cbbe0fbdd25a0f7859b113fdb3dcd9ce // An empty URL is returned if the URL is not overriden. virtual GURL OverrideFlashEmbedWithHTML(const GURL& url); diff --git a/content/renderer/renderer_blink_platform_impl.cc b/content/renderer/renderer_blink_platform_impl.cc -index 64655ef0370c22eb4adb995b5ca640e9756e800e..d9deae4ffb30dc3b22c2c1bc8fc53ff9c64b1183 100644 +index 45cbe16e4582ccc832e1bd809c64036b508768d9..dd11bc6ff48f72228158239ad9dda426ede9c6b8 100644 --- a/content/renderer/renderer_blink_platform_impl.cc +++ b/content/renderer/renderer_blink_platform_impl.cc -@@ -903,6 +903,12 @@ void RendererBlinkPlatformImpl::WillStopWorkerThread() { +@@ -902,6 +902,12 @@ void RendererBlinkPlatformImpl::WillStopWorkerThread() { WorkerThreadRegistry::Instance()->WillStopCurrentWorkerThread(); } @@ -43,7 +43,7 @@ index 64655ef0370c22eb4adb995b5ca640e9756e800e..d9deae4ffb30dc3b22c2c1bc8fc53ff9 const v8::Local& worker) { GetContentClient()->renderer()->DidInitializeWorkerContextOnWorkerThread( diff --git a/content/renderer/renderer_blink_platform_impl.h b/content/renderer/renderer_blink_platform_impl.h -index 206b8df48273a041ff7fd18f5d71e7e128f6da7d..549fdfb451ad72c5058cb0bc3be481aaff713769 100644 +index 2b6f49b635456283daf1b6ccf8919330dcf117c8..c05d4f3c8bc44396cc0415934d12c53e918c527f 100644 --- a/content/renderer/renderer_blink_platform_impl.h +++ b/content/renderer/renderer_blink_platform_impl.h @@ -197,6 +197,7 @@ class CONTENT_EXPORT RendererBlinkPlatformImpl : public BlinkPlatformImpl { @@ -55,10 +55,10 @@ index 206b8df48273a041ff7fd18f5d71e7e128f6da7d..549fdfb451ad72c5058cb0bc3be481aa const blink::WebSecurityOrigin& script_origin) override; blink::ProtocolHandlerSecurityLevel GetProtocolHandlerSecurityLevel( diff --git a/third_party/blink/public/platform/platform.h b/third_party/blink/public/platform/platform.h -index fa4beef133fd9bec1f1dc5fefdfbb240cec28621..7f3e3d7fa01d3d6cb7142ed1cd168268043052f7 100644 +index 54e25fb12f680eb4bbe0d51f162e227610065345..3648f1be362dc4c13071e73fed478454af7518ca 100644 --- a/third_party/blink/public/platform/platform.h +++ b/third_party/blink/public/platform/platform.h -@@ -671,6 +671,7 @@ class BLINK_PLATFORM_EXPORT Platform { +@@ -670,6 +670,7 @@ class BLINK_PLATFORM_EXPORT Platform { virtual void DidStartWorkerThread() {} virtual void WillStopWorkerThread() {} virtual void WorkerContextCreated(const v8::Local& worker) {} diff --git a/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch b/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch index 072de0abc4f48..668fbfc1ad5da 100644 --- a/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch +++ b/patches/chromium/worker_feat_add_hook_to_notify_script_ready.patch @@ -35,10 +35,10 @@ index cbbe0fbdd25a0f7859b113fdb3dcd9ce57e597d6..1345bb5008e1b4fc3a450f7e353d52ec // from the worker thread. virtual void WillDestroyWorkerContextOnWorkerThread( diff --git a/content/renderer/renderer_blink_platform_impl.cc b/content/renderer/renderer_blink_platform_impl.cc -index d9deae4ffb30dc3b22c2c1bc8fc53ff9c64b1183..3a0bb8b4d8eba3d67e444541b06326b9a3440eee 100644 +index dd11bc6ff48f72228158239ad9dda426ede9c6b8..f9438122223fcdf7249eda0a5cbaa65250eb12dc 100644 --- a/content/renderer/renderer_blink_platform_impl.cc +++ b/content/renderer/renderer_blink_platform_impl.cc -@@ -915,6 +915,12 @@ void RendererBlinkPlatformImpl::WorkerContextCreated( +@@ -914,6 +914,12 @@ void RendererBlinkPlatformImpl::WorkerContextCreated( worker); } @@ -52,7 +52,7 @@ index d9deae4ffb30dc3b22c2c1bc8fc53ff9c64b1183..3a0bb8b4d8eba3d67e444541b06326b9 const blink::WebSecurityOrigin& script_origin) { return GetContentClient()->renderer()->AllowScriptExtensionForServiceWorker( diff --git a/content/renderer/renderer_blink_platform_impl.h b/content/renderer/renderer_blink_platform_impl.h -index 549fdfb451ad72c5058cb0bc3be481aaff713769..52a575f593ef6f59fb6f0d85f12164f02541a5ab 100644 +index c05d4f3c8bc44396cc0415934d12c53e918c527f..84fff89368318b525f9e7aad6aeaf061c0cd76a1 100644 --- a/content/renderer/renderer_blink_platform_impl.h +++ b/content/renderer/renderer_blink_platform_impl.h @@ -197,6 +197,8 @@ class CONTENT_EXPORT RendererBlinkPlatformImpl : public BlinkPlatformImpl { @@ -65,10 +65,10 @@ index 549fdfb451ad72c5058cb0bc3be481aaff713769..52a575f593ef6f59fb6f0d85f12164f0 bool AllowScriptExtensionForServiceWorker( const blink::WebSecurityOrigin& script_origin) override; diff --git a/third_party/blink/public/platform/platform.h b/third_party/blink/public/platform/platform.h -index 7f3e3d7fa01d3d6cb7142ed1cd168268043052f7..00682c4fe82ec77f79a4d9e70c6e7f5788083f25 100644 +index 3648f1be362dc4c13071e73fed478454af7518ca..4c4e92cc0ec5c132418691a56c13e59c29281718 100644 --- a/third_party/blink/public/platform/platform.h +++ b/third_party/blink/public/platform/platform.h -@@ -671,6 +671,8 @@ class BLINK_PLATFORM_EXPORT Platform { +@@ -670,6 +670,8 @@ class BLINK_PLATFORM_EXPORT Platform { virtual void DidStartWorkerThread() {} virtual void WillStopWorkerThread() {} virtual void WorkerContextCreated(const v8::Local& worker) {} diff --git a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch index bff9bbb53a086..d291daafbaee7 100644 --- a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch +++ b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch @@ -10,7 +10,7 @@ to handle this without patching, but this is fairly clean for now and no longer patching legacy devtools code. diff --git a/front_end/entrypoints/main/MainImpl.ts b/front_end/entrypoints/main/MainImpl.ts -index 90dfc1abb2f03ccc4b120e16b25434023d8f47a8..d9da92c75c27bc21bc7a165c489a6e04935c41f2 100644 +index 2be25257dfc26d280733f6b55fa13da5e316ba3c..263bfe5be5becb18c73b0fc27ab1a41d455a5508 100644 --- a/front_end/entrypoints/main/MainImpl.ts +++ b/front_end/entrypoints/main/MainImpl.ts @@ -721,6 +721,8 @@ export class MainImpl { diff --git a/shell/browser/electron_browser_client.cc b/shell/browser/electron_browser_client.cc index 36e25a4bd33eb..71f10117d5e6b 100644 --- a/shell/browser/electron_browser_client.cc +++ b/shell/browser/electron_browser_client.cc @@ -954,20 +954,19 @@ bool ElectronBrowserClient::HandleExternalProtocol( void ElectronBrowserClient::CreateThrottlesForNavigation( content::NavigationThrottleRegistry& registry) { - content::NavigationHandle* handle = ®istry.GetNavigationHandle(); registry.MaybeAddThrottle( - std::make_unique(handle)); + std::make_unique(registry)); #if BUILDFLAG(ENABLE_ELECTRON_EXTENSIONS) registry.MaybeAddThrottle( - std::make_unique(handle)); + std::make_unique(registry)); #endif #if BUILDFLAG(ENABLE_PDF_VIEWER) registry.MaybeAddThrottle( - std::make_unique(handle)); + std::make_unique(registry)); registry.MaybeAddThrottle(std::make_unique( - handle, std::make_unique())); + registry, std::make_unique())); #endif } diff --git a/shell/browser/electron_navigation_throttle.cc b/shell/browser/electron_navigation_throttle.cc index 35ad181eee2b4..a124d11657f10 100644 --- a/shell/browser/electron_navigation_throttle.cc +++ b/shell/browser/electron_navigation_throttle.cc @@ -13,8 +13,8 @@ namespace electron { ElectronNavigationThrottle::ElectronNavigationThrottle( - content::NavigationHandle* navigation_handle) - : content::NavigationThrottle(navigation_handle) {} + content::NavigationThrottleRegistry& registry) + : content::NavigationThrottle(registry) {} ElectronNavigationThrottle::~ElectronNavigationThrottle() = default; diff --git a/shell/browser/electron_navigation_throttle.h b/shell/browser/electron_navigation_throttle.h index bd445a8cd1c17..36c8aff71738e 100644 --- a/shell/browser/electron_navigation_throttle.h +++ b/shell/browser/electron_navigation_throttle.h @@ -11,7 +11,8 @@ namespace electron { class ElectronNavigationThrottle : public content::NavigationThrottle { public: - explicit ElectronNavigationThrottle(content::NavigationHandle* handle); + explicit ElectronNavigationThrottle( + content::NavigationThrottleRegistry& registry); ~ElectronNavigationThrottle() override; // disable copy diff --git a/shell/browser/extensions/api/resources_private/resources_private_api.cc b/shell/browser/extensions/api/resources_private/resources_private_api.cc index c2ab5bf5f93db..61a508f409952 100644 --- a/shell/browser/extensions/api/resources_private/resources_private_api.cc +++ b/shell/browser/extensions/api/resources_private/resources_private_api.cc @@ -50,7 +50,7 @@ ExtensionFunction::ResponseAction ResourcesPrivateGetStringsFunction::Run() { #if BUILDFLAG(ENABLE_PDF_VIEWER) pdf_extension_util::AddStrings( pdf_extension_util::PdfViewerContext::kPdfViewer, &dict); - pdf_extension_util::AddAdditionalData(true, false, &dict); + pdf_extension_util::AddAdditionalData(browser_context(), &dict); #endif break; case api::resources_private::Component::kIdentity: diff --git a/shell/browser/extensions/electron_component_extension_resource_manager.cc b/shell/browser/extensions/electron_component_extension_resource_manager.cc index 0a1b2df5d61d5..da72977cfe051 100644 --- a/shell/browser/extensions/electron_component_extension_resource_manager.cc +++ b/shell/browser/extensions/electron_component_extension_resource_manager.cc @@ -31,7 +31,6 @@ ElectronComponentExtensionResourceManager:: base::Value::Dict pdf_strings; pdf_extension_util::AddStrings( pdf_extension_util::PdfViewerContext::kPdfViewer, &pdf_strings); - pdf_extension_util::AddAdditionalData(false, true, &pdf_strings); ui::TemplateReplacements pdf_viewer_replacements; ui::TemplateReplacementsFromDictionaryValue(pdf_strings, diff --git a/shell/browser/ui/views/win_frame_view.cc b/shell/browser/ui/views/win_frame_view.cc index d4afdb86fa38f..88a18703a00a9 100644 --- a/shell/browser/ui/views/win_frame_view.cc +++ b/shell/browser/ui/views/win_frame_view.cc @@ -198,8 +198,8 @@ int WinFrameView::FrameTopBorderThicknessPx(bool restored) const { // Note that this method assumes an equal resize handle thickness on all // sides of the window. // TODO(dfried): Consider having it return a gfx::Insets object instead. - return ui::GetFrameThickness( - MonitorFromWindow(HWNDForView(this), MONITOR_DEFAULTTONEAREST)); + return ui::GetFrameThicknessFromWindow(HWNDForView(this), + MONITOR_DEFAULTTONEAREST); } int WinFrameView::TitlebarMaximizedVisualHeight() const { diff --git a/shell/common/api/electron_api_native_image_mac.mm b/shell/common/api/electron_api_native_image_mac.mm index 918635e95edbb..f3e766c896fcf 100644 --- a/shell/common/api/electron_api_native_image_mac.mm +++ b/shell/common/api/electron_api_native_image_mac.mm @@ -36,7 +36,7 @@ } double safeShift(double in, double def) { - if (in >= 0 || in <= 1 || in == def) + if ((in >= 0 && in <= 1) || in == def) return in; return def; } diff --git a/spec/fixtures/api/corner-smoothing/shape/expected-false.png b/spec/fixtures/api/corner-smoothing/shape/expected-false.png index 56c135d740af762f572fcb7859d8173e927ba155..83bf09d5d3169a2765f3a82a35522237e3686fb7 100644 GIT binary patch literal 133445 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

*%X9f9GgO_!$yzglmx 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�k8<-J8cw#@iWaS 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 Du*Xdc diff --git a/spec/fixtures/api/corner-smoothing/shape/expected-true.png b/spec/fixtures/api/corner-smoothing/shape/expected-true.png index 97280d9369ce2ac3cd7c755e4c51eb4413a107eb..f26213d7b101fc664d1d95171fd36bc8a6f8fe55 100644 GIT binary patch literal 135835 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 literal 117286 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

VLQ%*^OE} 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� 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 Date: Wed, 4 Jun 2025 01:28:18 +0200 Subject: [PATCH 079/186] chore: cherry-pick 1 changes from 1-M137 (#47352) * chore: [37-x-y] cherry-pick 1 changes from 1-M137 * 7bc0a67ebfbf from v8 * chore: update patches --- patches/v8/.patches | 1 + patches/v8/cherry-pick-7bc0a67ebfbf.patch | 53 +++++++++++++++++++++++ 2 files changed, 54 insertions(+) create mode 100644 patches/v8/cherry-pick-7bc0a67ebfbf.patch diff --git a/patches/v8/.patches b/patches/v8/.patches index dc98544242e85..5fb328123db0b 100644 --- a/patches/v8/.patches +++ b/patches/v8/.patches @@ -1 +1,2 @@ chore_allow_customizing_microtask_policy_per_context.patch +cherry-pick-7bc0a67ebfbf.patch diff --git a/patches/v8/cherry-pick-7bc0a67ebfbf.patch b/patches/v8/cherry-pick-7bc0a67ebfbf.patch new file mode 100644 index 0000000000000..ff5e0b4f29805 --- /dev/null +++ b/patches/v8/cherry-pick-7bc0a67ebfbf.patch @@ -0,0 +1,53 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Leszek Swirski +Date: Tue, 27 May 2025 20:33:19 +0200 +Subject: Weaken alias analysis in store-store elimination + +Bug: 420636529 +Change-Id: I7c5a8f47960708cecbb27d811eedc7f754933deb +Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/6594051 +Reviewed-by: Shu-yu Guo +Auto-Submit: Leszek Swirski +Commit-Queue: Leszek Swirski +Cr-Commit-Position: refs/heads/main@{#100530} + +diff --git a/src/compiler/turboshaft/store-store-elimination-reducer-inl.h b/src/compiler/turboshaft/store-store-elimination-reducer-inl.h +index 45654a022fbaa67634d68d7d6e9dab7a5a50cb28..e058a41f23e29bbe4f5098608b340ccfef50bf98 100644 +--- a/src/compiler/turboshaft/store-store-elimination-reducer-inl.h ++++ b/src/compiler/turboshaft/store-store-elimination-reducer-inl.h +@@ -325,10 +325,11 @@ class RedundantStoreAnalysis { + // TODO(nicohartmann@): Use the new effect flags to distinguish heap + // access once available. + const bool is_on_heap_store = store.kind.tagged_base; +- const bool is_field_store = !store.index().valid(); ++ const bool is_fixed_offset_store = !store.index().valid(); + const uint8_t size = store.stored_rep.SizeInBytes(); +- // For now we consider only stores of fields of objects on the heap. +- if (is_on_heap_store && is_field_store) { ++ // For now we consider only stores of fixed offsets of objects on the ++ // heap. ++ if (is_on_heap_store && is_fixed_offset_store) { + bool is_eliminable_store = false; + switch (table_.GetObservability(store.base(), store.offset, size)) { + case StoreObservability::kUnobservable: +@@ -415,11 +416,16 @@ class RedundantStoreAnalysis { + // TODO(nicohartmann@): Use the new effect flags to distinguish heap + // access once available. + const bool is_on_heap_load = load.kind.tagged_base; +- const bool is_field_load = !load.index().valid(); ++ const bool is_fixed_offset_load = !load.index().valid(); + // For now we consider only loads of fields of objects on the heap. +- if (is_on_heap_load && is_field_load) { +- table_.MarkPotentiallyAliasingStoresAsObservable(load.base(), +- load.offset); ++ if (is_on_heap_load) { ++ if (is_fixed_offset_load) { ++ table_.MarkPotentiallyAliasingStoresAsObservable(load.base(), ++ load.offset); ++ } else { ++ // A dynamically indexed load might alias any fixed offset. ++ table_.MarkAllStoresAsObservable(); ++ } + } + break; + } From bdcf09861e19ae4292061cc67181635dec94aca6 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Wed, 4 Jun 2025 05:34:16 +0200 Subject: [PATCH 080/186] chore: bump node to v22.16.0 (37-x-y) (#47216) --- DEPS | 2 +- patches/node/.patches | 1 - ..._to_foreground_task_runner_signature.patch | 8 +-- patches/node/build_add_gn_build_files.patch | 25 +++++---- ...w_unbundling_of_node_js_dependencies.patch | 6 +-- .../build_compile_with_c_20_support.patch | 2 +- patches/node/build_enable_perfetto.patch | 6 +-- ...compilation_fails_if_not_using_a_new.patch | 6 +-- ...f_original-fs_and_custom_embedder_js.patch | 6 +-- ...o_use_custom_inspector_protocol_path.patch | 4 +- ...e_clang_as_default_compiler_on_macos.patch | 2 +- ...de_entrypoint_to_be_a_builtin_module.patch | 4 +- ..._node_tests_set_electron_run_as_node.patch | 11 ++-- ...cli_move_--trace-atomics-wait_to_eol.patch | 20 +++---- .../node/cli_remove_deprecated_v8_flag.patch | 8 +-- ..._values_for_variables_in_common_gypi.patch | 2 +- ...d_source_location_for_v8_task_runner.patch | 24 ++++----- ...ssert_module_in_the_renderer_process.patch | 4 +- .../node/fix_cppgc_initializing_twice.patch | 4 +- ..._do_not_resolve_electron_entrypoints.patch | 2 +- ...separent_bails_on_resource_path_exit.patch | 6 +-- ...se_readfilesync_override_for_modules.patch | 18 +++---- ...ingssl_and_openssl_incompatibilities.patch | 46 +++++++--------- .../fix_remove_fastapitypedarray_usage.patch | 18 +++---- ...rmony-import-assertions_from_node_cc.patch | 4 +- .../pass_all_globals_through_require.patch | 2 +- ...ch_cppgc_heap_on_v8_isolate_creation.patch | 52 +++++++++++-------- ..._on_wrapper-descriptor-based_cppheap.patch | 4 +- ...ted_fields_of_fastapicallbackoptions.patch | 2 +- .../node/support_v8_sandboxed_pointers.patch | 12 ++--- patches/node/zlib_fix_pointer_alignment.patch | 50 ------------------ script/node-disabled-tests.json | 2 + shell/common/node_bindings.cc | 9 ++-- shell/common/node_util.cc | 4 +- shell/common/node_util.h | 4 +- .../electron_sandboxed_renderer_client.cc | 6 +-- shell/renderer/preload_realm_context.cc | 6 +-- shell/renderer/renderer_client_base.cc | 8 +-- 38 files changed, 177 insertions(+), 223 deletions(-) delete mode 100644 patches/node/zlib_fix_pointer_alignment.patch diff --git a/DEPS b/DEPS index c844729724ca5..0b63a1984fa29 100644 --- a/DEPS +++ b/DEPS @@ -4,7 +4,7 @@ vars = { 'chromium_version': '138.0.7190.0', 'node_version': - 'v22.15.1', + 'v22.16.0', 'nan_version': 'e14bdcd1f72d62bca1d541b66da43130384ec213', 'squirrel.mac_version': diff --git a/patches/node/.patches b/patches/node/.patches index b9f8f3b2719a9..d6d0530bffd23 100644 --- a/patches/node/.patches +++ b/patches/node/.patches @@ -47,6 +47,5 @@ fix_ensure_traverseparent_bails_on_resource_path_exit.patch cli_move_--trace-atomics-wait_to_eol.patch fix_cppgc_initializing_twice.patch fix_task_starvation_in_inspector_context_test.patch -zlib_fix_pointer_alignment.patch fix_expose_readfilesync_override_for_modules.patch test_force_slow_json_stringify_path_for_overflow.patch diff --git a/patches/node/add_v8_taskpirority_to_foreground_task_runner_signature.patch b/patches/node/add_v8_taskpirority_to_foreground_task_runner_signature.patch index 43b5a271bedff..e1497804ce738 100644 --- a/patches/node/add_v8_taskpirority_to_foreground_task_runner_signature.patch +++ b/patches/node/add_v8_taskpirority_to_foreground_task_runner_signature.patch @@ -8,10 +8,10 @@ naturally upstream, and we will be able to remove this patch in a future Node.js upgrade. diff --git a/src/node_platform.cc b/src/node_platform.cc -index 65a9b79ae6ac8b7589e8f8109a709acb41d12b97..743ac069ad579a208a632ef5096ae46c8a0dfd74 100644 +index b438b3774d0aa7680fdbc6c6bf39a87893d221b2..ec355061825fb861c17fa2e6cc967b4c7b8d4586 100644 --- a/src/node_platform.cc +++ b/src/node_platform.cc -@@ -556,8 +556,8 @@ bool NodePlatform::IdleTasksEnabled(Isolate* isolate) { +@@ -687,8 +687,8 @@ bool NodePlatform::IdleTasksEnabled(Isolate* isolate) { return ForIsolate(isolate)->IdleTasksEnabled(); } @@ -23,10 +23,10 @@ index 65a9b79ae6ac8b7589e8f8109a709acb41d12b97..743ac069ad579a208a632ef5096ae46c } diff --git a/src/node_platform.h b/src/node_platform.h -index dde2d1b5687a5b52a4f09183bb4ff88d7d3e4d01..0a99f5b4b5eeb221ef3a34db7a50955c32d3c163 100644 +index a0222b4a1b074c6708e390d58d04221717069ac1..8015ca1801573c3a7c4a5db6d0f10b4016a9267c 100644 --- a/src/node_platform.h +++ b/src/node_platform.h -@@ -177,7 +177,7 @@ class NodePlatform : public MultiIsolatePlatform { +@@ -213,7 +213,7 @@ class NodePlatform : public MultiIsolatePlatform { void (*callback)(void*), void* data) override; std::shared_ptr GetForegroundTaskRunner( diff --git a/patches/node/build_add_gn_build_files.patch b/patches/node/build_add_gn_build_files.patch index d1d2ec6d8a637..6f6e1a48a0662 100644 --- a/patches/node/build_add_gn_build_files.patch +++ b/patches/node/build_add_gn_build_files.patch @@ -55,10 +55,10 @@ index a2123cc6c6d21c53fafc8934203b3720393e7b11..245a43920c7baf000ba63192a84a4c3f assert(!node_enable_inspector || node_use_openssl, diff --git a/src/node_builtins.cc b/src/node_builtins.cc -index e85860de93dd5753dd4542ecee9f0888af93898a..04eab49c368c8f86837ed2c1384bf3c63e4bde24 100644 +index defb657a62a0316224a02b68505ac1142fd89d03..d637faac88875bfa110e2b8d1f53962061d98279 100644 --- a/src/node_builtins.cc +++ b/src/node_builtins.cc -@@ -783,6 +783,7 @@ void BuiltinLoader::RegisterExternalReferences( +@@ -785,6 +785,7 @@ void BuiltinLoader::RegisterExternalReferences( registry->Register(GetNatives); RegisterExternalReferencesForInternalizedBuiltinCode(registry); @@ -67,7 +67,7 @@ index e85860de93dd5753dd4542ecee9f0888af93898a..04eab49c368c8f86837ed2c1384bf3c6 } // namespace builtins diff --git a/src/node_builtins.h b/src/node_builtins.h -index a73de23a1debfdac66873e0baccf882e383bfc36..7ac5291be093773ee7efd39e77e01bf5d5ce5247 100644 +index f9426599f2d5dc6ad061407f0c4eb2c9203a4433..302030f610965f07dd6998d282275c1bdf738009 100644 --- a/src/node_builtins.h +++ b/src/node_builtins.h @@ -74,6 +74,8 @@ using BuiltinCodeCacheMap = @@ -258,10 +258,10 @@ index 856878c33681a73d41016729dabe48b0a6a80589..91a11852d206b65485fe90fd037a0bd1 if sys.platform == 'win32': files = [ x.replace('\\', '/') for x in files ] diff --git a/unofficial.gni b/unofficial.gni -index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50ae50a3d8 100644 +index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187f3c04c5c 100644 --- a/unofficial.gni +++ b/unofficial.gni -@@ -142,32 +142,39 @@ template("node_gn_build") { +@@ -142,32 +142,42 @@ template("node_gn_build") { public_configs = [ ":node_external_config", "deps/googletest:googletest_config", @@ -296,7 +296,10 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50 "$node_v8_path:v8_libplatform", ] -+ cflags_cc = [ "-Wno-unguarded-availability-new" ] ++ cflags_cc = [ ++ "-Wno-unguarded-availability-new", ++ "-Wno-return-stack-address" ++ ] + sources = [ + "src/node_snapshot_stub.cc", @@ -304,7 +307,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50 "$target_gen_dir/node_javascript.cc", ] + gypi_values.node_sources -@@ -190,7 +197,7 @@ template("node_gn_build") { +@@ -190,7 +200,7 @@ template("node_gn_build") { } if (node_use_openssl) { deps += [ "deps/ncrypto" ] @@ -313,7 +316,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50 sources += gypi_values.node_crypto_sources } if (node_enable_inspector) { -@@ -214,6 +221,10 @@ template("node_gn_build") { +@@ -214,6 +224,10 @@ template("node_gn_build") { } } @@ -324,7 +327,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50 executable(target_name) { forward_variables_from(invoker, "*") -@@ -288,6 +299,7 @@ template("node_gn_build") { +@@ -288,6 +302,7 @@ template("node_gn_build") { } executable("node_js2c") { @@ -332,7 +335,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50 deps = [ "deps/uv", "$node_simdutf_path", -@@ -298,26 +310,75 @@ template("node_gn_build") { +@@ -298,26 +313,75 @@ template("node_gn_build") { "src/embedded_data.cc", "src/embedded_data.h", ] @@ -418,7 +421,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..672e97436d9220e8d5046b0c92025f50 outputs = [ "$target_gen_dir/node_javascript.cc" ] # Get the path to node_js2c executable of the host toolchain. -@@ -331,11 +392,11 @@ template("node_gn_build") { +@@ -331,11 +395,11 @@ template("node_gn_build") { get_label_info(":node_js2c($host_toolchain)", "name") + host_executable_suffix diff --git a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch index a38d9cc5f0074..c36f65af02e60 100644 --- a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch +++ b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch @@ -14,7 +14,7 @@ We don't need to do this for zlib, as the existing gn workflow uses the same Upstreamed at https://github.com/nodejs/node/pull/55903 diff --git a/unofficial.gni b/unofficial.gni -index 672e97436d9220e8d5046b0c92025f50ae50a3d8..a8ce18acfe333350f91b3e5f235db5f756b2e34a 100644 +index e17e4f043af6e4047ab82723ffd83187f3c04c5c..d591dfc99fdea4f830008502786ee44d863a31fc 100644 --- a/unofficial.gni +++ b/unofficial.gni @@ -155,7 +155,6 @@ template("node_gn_build") { @@ -25,7 +25,7 @@ index 672e97436d9220e8d5046b0c92025f50ae50a3d8..a8ce18acfe333350f91b3e5f235db5f7 "deps/nbytes", "deps/nghttp2", "deps/postject", -@@ -191,7 +190,17 @@ template("node_gn_build") { +@@ -194,7 +193,17 @@ template("node_gn_build") { configs -= [ "//build/config/gcc:symbol_visibility_hidden" ] configs += [ "//build/config/gcc:symbol_visibility_default" ] } @@ -44,7 +44,7 @@ index 672e97436d9220e8d5046b0c92025f50ae50a3d8..a8ce18acfe333350f91b3e5f235db5f7 if (v8_enable_i18n_support) { deps += [ "//third_party/icu" ] } -@@ -219,6 +228,19 @@ template("node_gn_build") { +@@ -222,6 +231,19 @@ template("node_gn_build") { sources += node_inspector.node_inspector_sources + node_inspector.node_inspector_generated_sources } diff --git a/patches/node/build_compile_with_c_20_support.patch b/patches/node/build_compile_with_c_20_support.patch index a21de5e73697b..10aec30f9fc6c 100644 --- a/patches/node/build_compile_with_c_20_support.patch +++ b/patches/node/build_compile_with_c_20_support.patch @@ -10,7 +10,7 @@ V8 requires C++20 support as of https://chromium-review.googlesource.com/c/v8/v8 This can be removed when Electron upgrades to a version of Node.js containing the required V8 version. diff --git a/common.gypi b/common.gypi -index 53016fc79c3d914982abeb61bf0a76181024e2bf..99b147482b636706b1372b89298f35b60ca2bb31 100644 +index f3476a91e4c3cda7cecf49e07bb594a167ac46ef..de73f6c18131f43e6fe3107c866599aa3398cf10 100644 --- a/common.gypi +++ b/common.gypi @@ -530,7 +530,7 @@ diff --git a/patches/node/build_enable_perfetto.patch b/patches/node/build_enable_perfetto.patch index 6aab4ea140fe8..f0b97e2c4acae 100644 --- a/patches/node/build_enable_perfetto.patch +++ b/patches/node/build_enable_perfetto.patch @@ -64,10 +64,10 @@ index 251f51ec454f9cba4023b8b6729241ee753aac13..1de8cac6e3953ce9cab9db03530da327 module.exports = { diff --git a/node.gyp b/node.gyp -index ec1f90b73f7d119b2c0e0207a5e36f3cec7295e9..66244b6638e34536aed397f56c6a4570a73e9b90 100644 +index ad010a8d99cf08013b7202eddce66e5b3885652d..d735b887d05ddfadec8e56dd8eae09646890aa84 100644 --- a/node.gyp +++ b/node.gyp -@@ -175,7 +175,6 @@ +@@ -176,7 +176,6 @@ 'src/timers.cc', 'src/timer_wrap.cc', 'src/tracing/agent.cc', @@ -75,7 +75,7 @@ index ec1f90b73f7d119b2c0e0207a5e36f3cec7295e9..66244b6638e34536aed397f56c6a4570 'src/tracing/node_trace_writer.cc', 'src/tracing/trace_event.cc', 'src/tracing/traced_value.cc', -@@ -303,7 +302,6 @@ +@@ -305,7 +304,6 @@ 'src/tcp_wrap.h', 'src/timers.h', 'src/tracing/agent.h', diff --git a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch index 8b09ad639398a..0527e9476f670 100644 --- a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch +++ b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch @@ -7,7 +7,7 @@ Subject: build: ensure native module compilation fails if not using a new This should not be upstreamed, it is a quality-of-life patch for downstream module builders. diff --git a/common.gypi b/common.gypi -index f2a45f0f0bbfce93e61d3696a18425af4d022a00..53016fc79c3d914982abeb61bf0a76181024e2bf 100644 +index d9c0b721fe0a629a30efb3c4e04905176ca0a7f5..f3476a91e4c3cda7cecf49e07bb594a167ac46ef 100644 --- a/common.gypi +++ b/common.gypi @@ -88,6 +88,8 @@ @@ -40,7 +40,7 @@ index f2a45f0f0bbfce93e61d3696a18425af4d022a00..53016fc79c3d914982abeb61bf0a7618 # list in v8/BUILD.gn. ['v8_enable_v8_checks == 1', { diff --git a/configure.py b/configure.py -index 95faeeef3867cbf3ca4b1857d893aa127d550a2f..b36f63a5482074f79a20709b8c4774cb6dadec52 100755 +index 932484674e5b15b765b8bfe307bdf99b49b5039f..befaa85527b9ebebad226e603586e23d04ec1e51 100755 --- a/configure.py +++ b/configure.py @@ -1698,6 +1698,7 @@ def configure_library(lib, output, pkgname=None): @@ -52,7 +52,7 @@ index 95faeeef3867cbf3ca4b1857d893aa127d550a2f..b36f63a5482074f79a20709b8c4774cb o['variables']['v8_enable_javascript_promise_hooks'] = 1 o['variables']['v8_enable_lite_mode'] = 1 if options.v8_lite_mode else 0 diff --git a/src/node.h b/src/node.h -index 8b77f7cb4d53105f42ba76d99a76a98b7a73789f..bdc77f8eb7abffa9e6c98cd254daedad3e44b981 100644 +index 835c78145956de3d8c52b6cc0581bcfef600f90b..174fd4d1af4c8cd75aec09f4548a674fd5539fb2 100644 --- a/src/node.h +++ b/src/node.h @@ -22,6 +22,12 @@ diff --git a/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch b/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch index b20f8418dab33..c4c54c21fdfe0 100644 --- a/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch +++ b/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch @@ -34,10 +34,10 @@ index 411eab8136d5957ae8a491bc38ffbdc88e59f5da..63c93b5be09692d0d4b6bfbb214b173b let kResistStopPropagation; diff --git a/src/node_builtins.cc b/src/node_builtins.cc -index 04eab49c368c8f86837ed2c1384bf3c63e4bde24..c3d2b3c90c206dd81a3d8aa6c14fdf4678a1cddd 100644 +index d637faac88875bfa110e2b8d1f53962061d98279..e0b58c4d0ac5640a677c22d710f88f1b318378d7 100644 --- a/src/node_builtins.cc +++ b/src/node_builtins.cc -@@ -34,6 +34,7 @@ using v8::Value; +@@ -35,6 +35,7 @@ using v8::Value; BuiltinLoader::BuiltinLoader() : config_(GetConfig()), code_cache_(std::make_shared()) { LoadJavaScriptSource(); @@ -46,7 +46,7 @@ index 04eab49c368c8f86837ed2c1384bf3c63e4bde24..c3d2b3c90c206dd81a3d8aa6c14fdf46 AddExternalizedBuiltin( "internal/deps/cjs-module-lexer/lexer", diff --git a/src/node_builtins.h b/src/node_builtins.h -index 7ac5291be093773ee7efd39e77e01bf5d5ce5247..c3c987d535285be84026ad0c633650bd2067d22d 100644 +index 302030f610965f07dd6998d282275c1bdf738009..35cb7766eeccc62dd2f0ce9484a2f1ec7beccc05 100644 --- a/src/node_builtins.h +++ b/src/node_builtins.h @@ -138,6 +138,7 @@ class NODE_EXTERN_PRIVATE BuiltinLoader { diff --git a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch b/patches/node/build_option_to_use_custom_inspector_protocol_path.patch index 7f4a2c213c82a..8e3aa3dbea37a 100644 --- a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch +++ b/patches/node/build_option_to_use_custom_inspector_protocol_path.patch @@ -65,10 +65,10 @@ index 3d7aa148678b2646b88fa7c32abec91791b02b82..4810d93eb971b253f7dadff7011a632f gypi_values = exec_script( "../../tools/gypi_to_gn.py", diff --git a/unofficial.gni b/unofficial.gni -index a8ce18acfe333350f91b3e5f235db5f756b2e34a..6bcc40b282543fc40f80c5c6659de658209844b8 100644 +index d591dfc99fdea4f830008502786ee44d863a31fc..9e26399482d6a1cdb843efb72c152d5cdd5e08ea 100644 --- a/unofficial.gni +++ b/unofficial.gni -@@ -211,13 +211,14 @@ template("node_gn_build") { +@@ -214,13 +214,14 @@ template("node_gn_build") { } if (node_enable_inspector) { deps += [ diff --git a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch index 7c7f11672aebd..73e7e840edf73 100644 --- a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch +++ b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch @@ -11,7 +11,7 @@ node-gyp will use the result of `process.config` that reflects the environment in which the binary got built. diff --git a/common.gypi b/common.gypi -index 99b147482b636706b1372b89298f35b60ca2bb31..5024e5fb0aee210f4986572638a523db6d26b4cc 100644 +index de73f6c18131f43e6fe3107c866599aa3398cf10..e2171e14b9e29dfc3c629f8164545d56d5e9057e 100644 --- a/common.gypi +++ b/common.gypi @@ -127,6 +127,7 @@ diff --git a/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch b/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch index d8640574d1cea..ae864ce06db1d 100644 --- a/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch +++ b/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch @@ -8,10 +8,10 @@ they use themselves as the entry point. We should try to upstream some form of this. diff --git a/lib/internal/process/pre_execution.js b/lib/internal/process/pre_execution.js -index d1c05d1717cdc825c4e48885c963c9ed65bcf51c..278665921c5160ff10b3178db27d4df319fab6b3 100644 +index 4e7be0594ca1e1ceaf1963debbce46783893ed77..a6df0672bf6ae6e9a74ebbb0e4debff63599cc99 100644 --- a/lib/internal/process/pre_execution.js +++ b/lib/internal/process/pre_execution.js -@@ -243,12 +243,14 @@ function patchProcessObject(expandArgv1) { +@@ -245,12 +245,14 @@ function patchProcessObject(expandArgv1) { // the entry point. if (expandArgv1 && process.argv[1] && process.argv[1][0] !== '-') { // Expand process.argv[1] into a full path. diff --git a/patches/node/ci_ensure_node_tests_set_electron_run_as_node.patch b/patches/node/ci_ensure_node_tests_set_electron_run_as_node.patch index ef4d76a3e8049..4890f20896718 100644 --- a/patches/node/ci_ensure_node_tests_set_electron_run_as_node.patch +++ b/patches/node/ci_ensure_node_tests_set_electron_run_as_node.patch @@ -8,15 +8,18 @@ which causes the `ELECTRON_RUN_AS_NODE` variable to be lost. This patch re-injects it. diff --git a/test/fixtures/test-runner/output/arbitrary-output-colored.js b/test/fixtures/test-runner/output/arbitrary-output-colored.js -index af23e674cb361ed81dafa22670d5633559cd1144..1dd59990cb7cdba8aecf4f499ee6b92e7cd41b30 100644 +index 444531da1df2f9bbbc19bb8a43fb6eb2d1802d1a..81b3b3e37e5664dc53bec987a2ce3a83a8da105f 100644 --- a/test/fixtures/test-runner/output/arbitrary-output-colored.js +++ b/test/fixtures/test-runner/output/arbitrary-output-colored.js -@@ -7,6 +7,6 @@ const fixtures = require('../../../common/fixtures'); +@@ -7,9 +7,9 @@ const fixtures = require('../../../common/fixtures'); (async function run() { const test = fixtures.path('test-runner/output/arbitrary-output-colored-1.js'); const reset = fixtures.path('test-runner/output/reset-color-depth.js'); - await once(spawn(process.execPath, ['-r', reset, '--test', test], { stdio: 'inherit' }), 'exit'); -- await once(spawn(process.execPath, ['-r', reset, '--test', '--test-reporter', 'tap', test], { stdio: 'inherit' }), 'exit'); + await once(spawn(process.execPath, ['-r', reset, '--test', test], { stdio: 'inherit', env: { ELECTRON_RUN_AS_NODE: 1 }}), 'exit'); -+ await once(spawn(process.execPath, ['-r', reset, '--test', '--test-reporter', 'tap', test], { stdio: 'inherit', env: { ELECTRON_RUN_AS_NODE: 1 } }), 'exit'); + await once( +- spawn(process.execPath, ['-r', reset, '--test', '--test-reporter', 'tap', test], { stdio: 'inherit' }), ++ spawn(process.execPath, ['-r', reset, '--test', '--test-reporter', 'tap', test], { stdio: 'inherit', env: { ELECTRON_RUN_AS_NODE: 1 }}), + 'exit', + ); })().then(common.mustCall()); diff --git a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch index 70ae224eebb1a..6eec17ed7bf01 100644 --- a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch +++ b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch @@ -15,10 +15,10 @@ Reviewed-By: Benjamin Gruenbaum Reviewed-By: Yagiz Nizipli diff --git a/doc/api/cli.md b/doc/api/cli.md -index 114b7bbf6b1e105fc1696ed8a064065db73ff519..ad863e52761332c3249a86af0e3d239cd0f73b03 100644 +index 121d8f2bbd2b1d93067a06a902b1e7b986bcdb49..3460ad33c6186dcc3aa3281d80b723a1cc1d50dd 100644 --- a/doc/api/cli.md +++ b/doc/api/cli.md -@@ -3313,7 +3313,6 @@ one is included in the list below. +@@ -3367,7 +3367,6 @@ one is included in the list below. * `--tls-min-v1.1` * `--tls-min-v1.2` * `--tls-min-v1.3` @@ -27,10 +27,10 @@ index 114b7bbf6b1e105fc1696ed8a064065db73ff519..ad863e52761332c3249a86af0e3d239c * `--trace-env-js-stack` * `--trace-env-native-stack` diff --git a/doc/node.1 b/doc/node.1 -index 9f534746ef9d9c1c1ee2edd6c195573a2e228600..e01fc511a1034518c0fb9bc5fa925524aecad927 100644 +index 663d123ac728f097e8a76c94cf10c53d059983d7..497f5a61182beafbaa26b945181056353674cfc3 100644 --- a/doc/node.1 +++ b/doc/node.1 -@@ -533,11 +533,6 @@ but the option is supported for compatibility with older Node.js versions. +@@ -539,11 +539,6 @@ but the option is supported for compatibility with older Node.js versions. Set default minVersion to 'TLSv1.3'. Use to disable support for TLSv1.2 in favour of TLSv1.3, which is more secure. . @@ -43,10 +43,10 @@ index 9f534746ef9d9c1c1ee2edd6c195573a2e228600..e01fc511a1034518c0fb9bc5fa925524 Print stack traces for deprecations. . diff --git a/src/node.cc b/src/node.cc -index 2f58a6fa69069dabb99b5ddb8011991b07fa5f02..9f6fa646ba6673f67f5f625e157ed850633a26da 100644 +index 6f8f6386d0db8aef1e2e0126cc9064101cbe6112..bc670a6c8b5027417cdc35e1cd94a60f63fd342d 100644 --- a/src/node.cc +++ b/src/node.cc -@@ -226,44 +226,6 @@ void Environment::WaitForInspectorFrontendByOptions() { +@@ -232,44 +232,6 @@ void Environment::WaitForInspectorFrontendByOptions() { } #endif // HAVE_INSPECTOR @@ -91,7 +91,7 @@ index 2f58a6fa69069dabb99b5ddb8011991b07fa5f02..9f6fa646ba6673f67f5f625e157ed850 void Environment::InitializeDiagnostics() { isolate_->GetHeapProfiler()->AddBuildEmbedderGraphCallback( Environment::BuildEmbedderGraph, this); -@@ -272,17 +234,6 @@ void Environment::InitializeDiagnostics() { +@@ -278,17 +240,6 @@ void Environment::InitializeDiagnostics() { } if (options_->trace_uncaught) isolate_->SetCaptureStackTraceForUncaughtExceptions(true); @@ -110,10 +110,10 @@ index 2f58a6fa69069dabb99b5ddb8011991b07fa5f02..9f6fa646ba6673f67f5f625e157ed850 isolate_->SetPromiseHook(TracePromises); } diff --git a/src/node_options.cc b/src/node_options.cc -index 54b253aa54f5cdebdb04315f9c6c2506977555c0..acf390bd456c7ddfa6987e440fb45940aec6b1ff 100644 +index a9500716f2a955fc591628a969c5fba40783a2e7..b153d2c6a771e80bcdf5ed6adbc1cd225b3bf97e 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -762,10 +762,6 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() { +@@ -770,10 +770,6 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() { "throw an exception on deprecations", &EnvironmentOptions::throw_deprecation, kAllowedInEnvvar); @@ -125,7 +125,7 @@ index 54b253aa54f5cdebdb04315f9c6c2506977555c0..acf390bd456c7ddfa6987e440fb45940 "show stack traces on deprecations", &EnvironmentOptions::trace_deprecation, diff --git a/src/node_options.h b/src/node_options.h -index 065457acfde6ba4d04ed570cc72005cfd2798fd5..150f833bb21bd6d37f652f0785a4a98f3de5f67d 100644 +index 60068b008b2e2a034c3f0c58b947a8d04d55e3b2..d821bc6a9adf28ea312a9c446f8acfc8ed586ae3 100644 --- a/src/node_options.h +++ b/src/node_options.h @@ -203,7 +203,6 @@ class EnvironmentOptions : public Options { diff --git a/patches/node/cli_remove_deprecated_v8_flag.patch b/patches/node/cli_remove_deprecated_v8_flag.patch index caff01e09ec1d..70a46ac99e195 100644 --- a/patches/node/cli_remove_deprecated_v8_flag.patch +++ b/patches/node/cli_remove_deprecated_v8_flag.patch @@ -18,10 +18,10 @@ Reviewed-By: MichaĆ«l Zasso Reviewed-By: Yagiz Nizipli diff --git a/doc/api/cli.md b/doc/api/cli.md -index 1b42c5a7f4715e56fa5bc39cd6f78a76473406f2..114b7bbf6b1e105fc1696ed8a064065db73ff519 100644 +index 6f984926a62973ba36bd3c27cc39b01f2bcac819..121d8f2bbd2b1d93067a06a902b1e7b986bcdb49 100644 --- a/doc/api/cli.md +++ b/doc/api/cli.md -@@ -3350,7 +3350,6 @@ V8 options that are allowed are: +@@ -3404,7 +3404,6 @@ V8 options that are allowed are: * `--disallow-code-generation-from-strings` * `--enable-etw-stack-walking` * `--expose-gc` @@ -30,10 +30,10 @@ index 1b42c5a7f4715e56fa5bc39cd6f78a76473406f2..114b7bbf6b1e105fc1696ed8a064065d * `--jitless` * `--max-old-space-size` diff --git a/src/node_options.cc b/src/node_options.cc -index b22fbb0a285f6f323779d6ebb2b027a3990b031e..54b253aa54f5cdebdb04315f9c6c2506977555c0 100644 +index bb1e80ece4158dfed1b8bab7dc6d00dd56505aac..a9500716f2a955fc591628a969c5fba40783a2e7 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -984,11 +984,6 @@ PerIsolateOptionsParser::PerIsolateOptionsParser( +@@ -992,11 +992,6 @@ PerIsolateOptionsParser::PerIsolateOptionsParser( "disallow eval and friends", V8Option{}, kAllowedInEnvvar); diff --git a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch index 45edf948a98da..f21f31edd6765 100644 --- a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch +++ b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch @@ -7,7 +7,7 @@ common.gypi is a file that's included in the node header bundle, despite the fact that we do not build node with gyp. diff --git a/common.gypi b/common.gypi -index 372409f4b09cc3b3be9809f697816498e5c021fe..f2a45f0f0bbfce93e61d3696a18425af4d022a00 100644 +index 393fe32765794fbc5e92690e968e3c18f0d749fa..d9c0b721fe0a629a30efb3c4e04905176ca0a7f5 100644 --- a/common.gypi +++ b/common.gypi @@ -90,6 +90,23 @@ diff --git a/patches/node/fix_add_source_location_for_v8_task_runner.patch b/patches/node/fix_add_source_location_for_v8_task_runner.patch index 35a8dba0ed365..43896b7b67e60 100644 --- a/patches/node/fix_add_source_location_for_v8_task_runner.patch +++ b/patches/node/fix_add_source_location_for_v8_task_runner.patch @@ -15,10 +15,10 @@ corresponding change. CL: https://chromium-review.googlesource.com/c/v8/v8/+/5300826 diff --git a/src/node_platform.cc b/src/node_platform.cc -index 00ca9757bc4d0cdeb03a3f32be3ef19077cb7969..65a9b79ae6ac8b7589e8f8109a709acb41d12b97 100644 +index 9c4c1e1db5fa7c0ca791e01d9be331e0957e9699..b438b3774d0aa7680fdbc6c6bf39a87893d221b2 100644 --- a/src/node_platform.cc +++ b/src/node_platform.cc -@@ -245,11 +245,13 @@ void PerIsolatePlatformData::FlushTasks(uv_async_t* handle) { +@@ -307,11 +307,13 @@ void PerIsolatePlatformData::FlushTasks(uv_async_t* handle) { platform_data->FlushForegroundTasksInternal(); } @@ -31,10 +31,10 @@ index 00ca9757bc4d0cdeb03a3f32be3ef19077cb7969..65a9b79ae6ac8b7589e8f8109a709acb -void PerIsolatePlatformData::PostTask(std::unique_ptr task) { +void PerIsolatePlatformData::PostTaskImpl(std::unique_ptr task, + const v8::SourceLocation& location) { - if (flush_tasks_ == nullptr) { - // V8 may post tasks during Isolate disposal. In that case, the only - // sensible path forward is to discard the task. -@@ -259,8 +261,10 @@ void PerIsolatePlatformData::PostTask(std::unique_ptr task) { + // The task can be posted from any V8 background worker thread, even when + // the foreground task runner is being cleaned up by Shutdown(). In that + // case, make sure we wait until the shutdown is completed (which leads +@@ -330,8 +332,10 @@ void PerIsolatePlatformData::PostTask(std::unique_ptr task) { uv_async_send(flush_tasks_); } @@ -44,10 +44,10 @@ index 00ca9757bc4d0cdeb03a3f32be3ef19077cb7969..65a9b79ae6ac8b7589e8f8109a709acb + std::unique_ptr task, + double delay_in_seconds, + const v8::SourceLocation& location) { - if (flush_tasks_ == nullptr) { - // V8 may post tasks during Isolate disposal. In that case, the only - // sensible path forward is to discard the task. -@@ -274,13 +278,15 @@ void PerIsolatePlatformData::PostDelayedTask( + if (debug_log_level_ != PlatformDebugLogLevel::kNone) { + fprintf(stderr, + "\nPerIsolatePlatformData::PostDelayedTaskImpl %p %f", +@@ -353,13 +357,15 @@ void PerIsolatePlatformData::PostDelayedTask( uv_async_send(flush_tasks_); } @@ -67,10 +67,10 @@ index 00ca9757bc4d0cdeb03a3f32be3ef19077cb7969..65a9b79ae6ac8b7589e8f8109a709acb } diff --git a/src/node_platform.h b/src/node_platform.h -index 77cb5e6e4f891c510cdaf7fd6175a1f00d9bc420..dde2d1b5687a5b52a4f09183bb4ff88d7d3e4d01 100644 +index af30ebeb0c8629ab86d1a55fd63610165abfbabf..a0222b4a1b074c6708e390d58d04221717069ac1 100644 --- a/src/node_platform.h +++ b/src/node_platform.h -@@ -59,18 +59,21 @@ class PerIsolatePlatformData : +@@ -80,18 +80,21 @@ class PerIsolatePlatformData : ~PerIsolatePlatformData() override; std::shared_ptr GetForegroundTaskRunner() override; diff --git a/patches/node/fix_assert_module_in_the_renderer_process.patch b/patches/node/fix_assert_module_in_the_renderer_process.patch index e6ab076547afe..63191d23c70b6 100644 --- a/patches/node/fix_assert_module_in_the_renderer_process.patch +++ b/patches/node/fix_assert_module_in_the_renderer_process.patch @@ -44,10 +44,10 @@ index 59b5a16f1309a5e4055bccfdb7a529045ad30402..bfdaf6211466a01b64b7942f7b16c480 let filename = call.getFileName(); const line = call.getLineNumber() - 1; diff --git a/src/node_options.cc b/src/node_options.cc -index 23cb558a22b4462f5ce4f74833d25c7f712f8139..b22fbb0a285f6f323779d6ebb2b027a3990b031e 100644 +index 8be78889e8234eb3100f309829bf7470db544dcd..bb1e80ece4158dfed1b8bab7dc6d00dd56505aac 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -1535,14 +1535,16 @@ void GetEmbedderOptions(const FunctionCallbackInfo& args) { +@@ -1557,14 +1557,16 @@ void GetEmbedderOptions(const FunctionCallbackInfo& args) { } Isolate* isolate = args.GetIsolate(); diff --git a/patches/node/fix_cppgc_initializing_twice.patch b/patches/node/fix_cppgc_initializing_twice.patch index 6ecf3b9675de9..432dce585764e 100644 --- a/patches/node/fix_cppgc_initializing_twice.patch +++ b/patches/node/fix_cppgc_initializing_twice.patch @@ -12,10 +12,10 @@ This can be removed/refactored once Node.js upgrades to a version of V8 containing the above CL. diff --git a/src/node.cc b/src/node.cc -index 9f6fa646ba6673f67f5f625e157ed850633a26da..63a462876c00588d22abdd6ed8ee41ecf6590d03 100644 +index bc670a6c8b5027417cdc35e1cd94a60f63fd342d..49a9670de72c222d6b4a681be001efb4a2651ea3 100644 --- a/src/node.cc +++ b/src/node.cc -@@ -1173,7 +1173,7 @@ InitializeOncePerProcessInternal(const std::vector& args, +@@ -1209,7 +1209,7 @@ InitializeOncePerProcessInternal(const std::vector& args, result->platform_ = per_process::v8_platform.Platform(); } diff --git a/patches/node/fix_do_not_resolve_electron_entrypoints.patch b/patches/node/fix_do_not_resolve_electron_entrypoints.patch index 68ec69cf3ee8f..679f1bf31632d 100644 --- a/patches/node/fix_do_not_resolve_electron_entrypoints.patch +++ b/patches/node/fix_do_not_resolve_electron_entrypoints.patch @@ -33,7 +33,7 @@ index 49aacb6262502ced54e817f99dd596db85b9659c..f9f065bb743275e9b2ce71375e6a9f06 if (!loaded) { module = new CJSModule(filename); diff --git a/lib/internal/modules/run_main.js b/lib/internal/modules/run_main.js -index ab4783a7982b9feb8fa85b62e3e3b181f93309bd..34f91026451d7347ae278712d083e4fe281e50f3 100644 +index 02ba43adc2c8e92a78942bbb04023a16f5870ee9..bbf1ab69b884a9325bebdd07b2c4fd354eee946b 100644 --- a/lib/internal/modules/run_main.js +++ b/lib/internal/modules/run_main.js @@ -2,6 +2,7 @@ diff --git a/patches/node/fix_ensure_traverseparent_bails_on_resource_path_exit.patch b/patches/node/fix_ensure_traverseparent_bails_on_resource_path_exit.patch index 37e8ed1ecbc45..2a3a90362897e 100644 --- a/patches/node/fix_ensure_traverseparent_bails_on_resource_path_exit.patch +++ b/patches/node/fix_ensure_traverseparent_bails_on_resource_path_exit.patch @@ -8,10 +8,10 @@ resource path. This commit ensures that the TraverseParent function bails out if the parent path is outside of the resource path. diff --git a/src/node_modules.cc b/src/node_modules.cc -index 210a01d24e11764dc9fc37a77b354f11383693f8..4e9f70a1c41b44d2a1863b778d4f1e37279178d9 100644 +index 55d628f0c5e7f330e548878807de26d51ef025b5..c06779dea471b6f6a8dd29d4657162ef0faec043 100644 --- a/src/node_modules.cc +++ b/src/node_modules.cc -@@ -290,8 +290,41 @@ const BindingData::PackageConfig* BindingData::TraverseParent( +@@ -291,8 +291,41 @@ const BindingData::PackageConfig* BindingData::TraverseParent( Realm* realm, const std::filesystem::path& check_path) { std::filesystem::path current_path = check_path; auto env = realm->env(); @@ -53,7 +53,7 @@ index 210a01d24e11764dc9fc37a77b354f11383693f8..4e9f70a1c41b44d2a1863b778d4f1e37 do { current_path = current_path.parent_path(); -@@ -310,6 +343,12 @@ const BindingData::PackageConfig* BindingData::TraverseParent( +@@ -311,6 +344,12 @@ const BindingData::PackageConfig* BindingData::TraverseParent( return nullptr; } diff --git a/patches/node/fix_expose_readfilesync_override_for_modules.patch b/patches/node/fix_expose_readfilesync_override_for_modules.patch index c54548cd8b874..c2b377ee140aa 100644 --- a/patches/node/fix_expose_readfilesync_override_for_modules.patch +++ b/patches/node/fix_expose_readfilesync_override_for_modules.patch @@ -8,10 +8,10 @@ an API override to replace the native `ReadFileSync` in the `modules` binding. diff --git a/src/env_properties.h b/src/env_properties.h -index ba8c80ff2842c63f16cae51cfa8084617bb35bf5..820aebd18d22bcef4992b09ffc8924e9b758fd3e 100644 +index cbb7eab2df0416087cd3e6fb80eef2079143d9c8..7e9f5e977506149d69c6015e85d031770325e1da 100644 --- a/src/env_properties.h +++ b/src/env_properties.h -@@ -485,6 +485,7 @@ +@@ -501,6 +501,7 @@ V(maybe_cache_generated_source_map, v8::Function) \ V(messaging_deserialize_create_object, v8::Function) \ V(message_port, v8::Object) \ @@ -20,7 +20,7 @@ index ba8c80ff2842c63f16cae51cfa8084617bb35bf5..820aebd18d22bcef4992b09ffc8924e9 V(performance_entry_callback, v8::Function) \ V(prepare_stack_trace_callback, v8::Function) \ diff --git a/src/node_modules.cc b/src/node_modules.cc -index 4e9f70a1c41b44d2a1863b778d4f1e37279178d9..c56a32885b8debbd5b95a2c11f3838d4088e05ac 100644 +index c06779dea471b6f6a8dd29d4657162ef0faec043..6204986dc97686a248d6ae483f3a413ee5c51e47 100644 --- a/src/node_modules.cc +++ b/src/node_modules.cc @@ -21,6 +21,7 @@ namespace modules { @@ -31,7 +31,7 @@ index 4e9f70a1c41b44d2a1863b778d4f1e37279178d9..c56a32885b8debbd5b95a2c11f3838d4 using v8::FunctionCallbackInfo; using v8::HandleScope; using v8::Isolate; -@@ -88,6 +89,7 @@ Local BindingData::PackageConfig::Serialize(Realm* realm) const { +@@ -89,6 +90,7 @@ Local BindingData::PackageConfig::Serialize(Realm* realm) const { const BindingData::PackageConfig* BindingData::GetPackageJSON( Realm* realm, std::string_view path, ErrorContext* error_context) { @@ -39,7 +39,7 @@ index 4e9f70a1c41b44d2a1863b778d4f1e37279178d9..c56a32885b8debbd5b95a2c11f3838d4 auto binding_data = realm->GetBindingData(); auto cache_entry = binding_data->package_configs_.find(path.data()); -@@ -97,8 +99,36 @@ const BindingData::PackageConfig* BindingData::GetPackageJSON( +@@ -98,8 +100,36 @@ const BindingData::PackageConfig* BindingData::GetPackageJSON( PackageConfig package_config{}; package_config.file_path = path; @@ -77,7 +77,7 @@ index 4e9f70a1c41b44d2a1863b778d4f1e37279178d9..c56a32885b8debbd5b95a2c11f3838d4 return nullptr; } // In some systems, std::string is annotated to generate an -@@ -248,6 +278,12 @@ const BindingData::PackageConfig* BindingData::GetPackageJSON( +@@ -249,6 +279,12 @@ const BindingData::PackageConfig* BindingData::GetPackageJSON( return &cached.first->second; } @@ -90,7 +90,7 @@ index 4e9f70a1c41b44d2a1863b778d4f1e37279178d9..c56a32885b8debbd5b95a2c11f3838d4 void BindingData::ReadPackageJSON(const FunctionCallbackInfo& args) { CHECK_GE(args.Length(), 1); // path, [is_esm, base, specifier] CHECK(args[0]->IsString()); // path -@@ -556,6 +592,8 @@ void GetCompileCacheDir(const FunctionCallbackInfo& args) { +@@ -643,6 +679,8 @@ void InitImportMetaPathHelpers(const FunctionCallbackInfo& args) { void BindingData::CreatePerIsolateProperties(IsolateData* isolate_data, Local target) { Isolate* isolate = isolate_data->isolate(); @@ -99,7 +99,7 @@ index 4e9f70a1c41b44d2a1863b778d4f1e37279178d9..c56a32885b8debbd5b95a2c11f3838d4 SetMethod(isolate, target, "readPackageJSON", ReadPackageJSON); SetMethod(isolate, target, -@@ -595,6 +633,8 @@ void BindingData::CreatePerContextProperties(Local target, +@@ -685,6 +723,8 @@ void BindingData::CreatePerContextProperties(Local target, void BindingData::RegisterExternalReferences( ExternalReferenceRegistry* registry) { @@ -109,7 +109,7 @@ index 4e9f70a1c41b44d2a1863b778d4f1e37279178d9..c56a32885b8debbd5b95a2c11f3838d4 registry->Register(GetNearestParentPackageJSONType); registry->Register(GetNearestParentPackageJSON); diff --git a/src/node_modules.h b/src/node_modules.h -index 17909b2270454b3275c7bf2e50d4b9b35673ecc8..3d5b0e3ac65524adfe221bfd6f85360dee1f0bee 100644 +index eb2900d8f8385238f89a6dcc972a28e5fcb1d288..e28f38d98f4f8749048af135f0dcbe55aa69c4fe 100644 --- a/src/node_modules.h +++ b/src/node_modules.h @@ -54,6 +54,8 @@ class BindingData : public SnapshotableObject { diff --git a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch index 8548df12be7ec..709e710e07aa5 100644 --- a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch +++ b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch @@ -17,20 +17,10 @@ Upstreams: - https://github.com/nodejs/node/pull/39136 diff --git a/deps/ncrypto/ncrypto.cc b/deps/ncrypto/ncrypto.cc -index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac4e767d90 100644 +index 6f9406eecacb7411a2e84a7b51e60b726d1961f3..bffdb0259eeed7389adb54a8ff13a1ac4e767d90 100644 --- a/deps/ncrypto/ncrypto.cc +++ b/deps/ncrypto/ncrypto.cc -@@ -11,9 +11,6 @@ - #if OPENSSL_VERSION_MAJOR >= 3 - #include - #endif --#ifdef OPENSSL_IS_BORINGSSL --#include "dh-primes.h" --#endif // OPENSSL_IS_BORINGSSL - - namespace ncrypto { - namespace { -@@ -789,7 +786,7 @@ bool SafeX509SubjectAltNamePrint(const BIOPointer& out, X509_EXTENSION* ext) { +@@ -786,7 +786,7 @@ bool SafeX509SubjectAltNamePrint(const BIOPointer& out, X509_EXTENSION* ext) { bool ok = true; @@ -39,7 +29,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac GENERAL_NAME* gen = sk_GENERAL_NAME_value(names, i); if (i != 0) BIO_write(out.get(), ", ", 2); -@@ -813,7 +810,7 @@ bool SafeX509InfoAccessPrint(const BIOPointer& out, X509_EXTENSION* ext) { +@@ -810,7 +810,7 @@ bool SafeX509InfoAccessPrint(const BIOPointer& out, X509_EXTENSION* ext) { bool ok = true; @@ -48,7 +38,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac ACCESS_DESCRIPTION* desc = sk_ACCESS_DESCRIPTION_value(descs, i); if (i != 0) BIO_write(out.get(), "\n", 1); -@@ -955,13 +952,17 @@ BIOPointer X509View::getValidTo() const { +@@ -952,13 +952,17 @@ BIOPointer X509View::getValidTo() const { int64_t X509View::getValidToTime() const { struct tm tp; @@ -67,7 +57,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac return PortableTimeGM(&tp); } -@@ -1236,7 +1237,11 @@ BIOPointer BIOPointer::NewMem() { +@@ -1233,7 +1237,11 @@ BIOPointer BIOPointer::NewMem() { } BIOPointer BIOPointer::NewSecMem() { @@ -80,7 +70,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac } BIOPointer BIOPointer::New(const BIO_METHOD* method) { -@@ -1306,8 +1311,10 @@ BignumPointer DHPointer::FindGroup(const std::string_view name, +@@ -1303,8 +1311,10 @@ BignumPointer DHPointer::FindGroup(const std::string_view name, #define V(n, p) \ if (EqualNoCase(name, n)) return BignumPointer(p(nullptr)); if (option != FindGroupOption::NO_SMALL_PRIMES) { @@ -91,7 +81,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac V("modp5", BN_get_rfc3526_prime_1536); } V("modp14", BN_get_rfc3526_prime_2048); -@@ -1383,11 +1390,13 @@ DHPointer::CheckPublicKeyResult DHPointer::checkPublicKey( +@@ -1380,11 +1390,13 @@ DHPointer::CheckPublicKeyResult DHPointer::checkPublicKey( int codes = 0; if (DH_check_pub_key(dh_.get(), pub_key.get(), &codes) != 1) return DHPointer::CheckPublicKeyResult::CHECK_FAILED; @@ -106,7 +96,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac return DHPointer::CheckPublicKeyResult::INVALID; } return CheckPublicKeyResult::NONE; -@@ -2330,7 +2339,7 @@ const std::string_view SSLPointer::getClientHelloAlpn() const { +@@ -2327,7 +2339,7 @@ const std::string_view SSLPointer::getClientHelloAlpn() const { const unsigned char* buf; size_t len; size_t rem; @@ -115,7 +105,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac if (!SSL_client_hello_get0_ext( get(), TLSEXT_TYPE_application_layer_protocol_negotiation, -@@ -2343,6 +2352,8 @@ const std::string_view SSLPointer::getClientHelloAlpn() const { +@@ -2340,6 +2352,8 @@ const std::string_view SSLPointer::getClientHelloAlpn() const { len = (buf[0] << 8) | buf[1]; if (len + 2 != rem) return {}; return reinterpret_cast(buf + 3); @@ -124,7 +114,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac } const std::string_view SSLPointer::getClientHelloServerName() const { -@@ -2350,7 +2361,7 @@ const std::string_view SSLPointer::getClientHelloServerName() const { +@@ -2347,7 +2361,7 @@ const std::string_view SSLPointer::getClientHelloServerName() const { const unsigned char* buf; size_t len; size_t rem; @@ -133,7 +123,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac if (!SSL_client_hello_get0_ext(get(), TLSEXT_TYPE_server_name, &buf, &rem) || rem <= 2) { return {}; -@@ -2366,6 +2377,8 @@ const std::string_view SSLPointer::getClientHelloServerName() const { +@@ -2363,6 +2377,8 @@ const std::string_view SSLPointer::getClientHelloServerName() const { len = (*(buf + 3) << 8) | *(buf + 4); if (len + 2 > rem) return {}; return reinterpret_cast(buf + 5); @@ -142,7 +132,7 @@ index ce2e7b384eb1987ddb081f79884fb8cb62ade60b..bffdb0259eeed7389adb54a8ff13a1ac } std::optional SSLPointer::GetServerName( -@@ -2399,8 +2412,11 @@ bool SSLPointer::isServer() const { +@@ -2396,8 +2412,11 @@ bool SSLPointer::isServer() const { EVPKeyPointer SSLPointer::getPeerTempKey() const { if (!ssl_) return {}; EVP_PKEY* raw_key = nullptr; @@ -195,10 +185,10 @@ index 245a43920c7baf000ba63192a84a4c3fd219be7d..56a554175b805c1703f13d62041f8c80 # The location of simdutf - use the one from node's deps by default. node_simdutf_path = "$node_path/deps/simdutf" diff --git a/src/crypto/crypto_cipher.cc b/src/crypto/crypto_cipher.cc -index 1754d1f71b8adbcb584bfe4606e2a341836fb671..ac0f529e75c30add0708dc20470846f2f56e4b86 100644 +index 2176fb6982484e2c42538478eeb4dd81c9d50ee1..c00d3616e08b00b1e0a3a29b2dbb5278e1e14fcc 100644 --- a/src/crypto/crypto_cipher.cc +++ b/src/crypto/crypto_cipher.cc -@@ -1033,7 +1033,7 @@ void PublicKeyCipher::Cipher(const FunctionCallbackInfo& args) { +@@ -1027,7 +1027,7 @@ void PublicKeyCipher::Cipher(const FunctionCallbackInfo& args) { if (EVP_PKEY_decrypt_init(ctx.get()) <= 0) { return ThrowCryptoError(env, ERR_get_error()); } @@ -207,7 +197,7 @@ index 1754d1f71b8adbcb584bfe4606e2a341836fb671..ac0f529e75c30add0708dc20470846f2 int rsa_pkcs1_implicit_rejection = EVP_PKEY_CTX_ctrl_str(ctx.get(), "rsa_pkcs1_implicit_rejection", "1"); // From the doc -2 means that the option is not supported. -@@ -1048,6 +1048,7 @@ void PublicKeyCipher::Cipher(const FunctionCallbackInfo& args) { +@@ -1042,6 +1042,7 @@ void PublicKeyCipher::Cipher(const FunctionCallbackInfo& args) { env, "RSA_PKCS1_PADDING is no longer supported for private decryption"); } @@ -565,10 +555,10 @@ index 6f8cb433ff8059c63d5cf16c8783139ae92fbf61..603ac3dde7d1a1109afbc451b69c8d09 #if NODE_OPENSSL_HAS_QUIC #include diff --git a/src/node_options.cc b/src/node_options.cc -index 1444acd59d42f64831cead5f153419f7c12a88bf..23cb558a22b4462f5ce4f74833d25c7f712f8139 100644 +index 3fc8194475ec0e8a9047c1f3da5d120f25d66190..8be78889e8234eb3100f309829bf7470db544dcd 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -6,7 +6,7 @@ +@@ -7,7 +7,7 @@ #include "node_external_reference.h" #include "node_internals.h" #include "node_sea.h" @@ -578,7 +568,7 @@ index 1444acd59d42f64831cead5f153419f7c12a88bf..23cb558a22b4462f5ce4f74833d25c7f #endif diff --git a/src/node_options.h b/src/node_options.h -index e68a41b60832c4b000e17dd15ce16c1bdaf4b54b..065457acfde6ba4d04ed570cc72005cfd2798fd5 100644 +index 7d14f06370d936a3866f0d988123de9fe614ce09..60068b008b2e2a034c3f0c58b947a8d04d55e3b2 100644 --- a/src/node_options.h +++ b/src/node_options.h @@ -11,7 +11,7 @@ diff --git a/patches/node/fix_remove_fastapitypedarray_usage.patch b/patches/node/fix_remove_fastapitypedarray_usage.patch index 7ce2dea2c4fe0..1d5b56cbe1fea 100644 --- a/patches/node/fix_remove_fastapitypedarray_usage.patch +++ b/patches/node/fix_remove_fastapitypedarray_usage.patch @@ -48,7 +48,7 @@ index 867a1c4aca54b9d41490d23a5eb55088b7e941cc..09f4c65a18efea262b1f854f993c6f18 static v8::CFunction fast_equal(v8::CFunction::Make(FastTimingSafeEqual)); diff --git a/src/node_buffer.cc b/src/node_buffer.cc -index 10659fbf57e4535736fc001c0dbdd9b93e8f60f1..c0bd975bae23d1c05ace42fd8c9846ee4d8ef8f0 100644 +index 5bdffc0a4d7f8f643343593a543f2064b670c1b9..6931404b75dbe17bf3c7b561430b8d7c0921d085 100644 --- a/src/node_buffer.cc +++ b/src/node_buffer.cc @@ -44,6 +44,14 @@ @@ -74,7 +74,7 @@ index 10659fbf57e4535736fc001c0dbdd9b93e8f60f1..c0bd975bae23d1c05ace42fd8c9846ee using v8::FunctionCallbackInfo; using v8::Global; using v8::HandleScope; -@@ -586,19 +593,24 @@ void SlowCopy(const FunctionCallbackInfo& args) { +@@ -584,19 +591,24 @@ void SlowCopy(const FunctionCallbackInfo& args) { // Assume caller has properly validated args. uint32_t FastCopy(Local receiver, @@ -107,7 +107,7 @@ index 10659fbf57e4535736fc001c0dbdd9b93e8f60f1..c0bd975bae23d1c05ace42fd8c9846ee return to_copy; } -@@ -867,19 +879,17 @@ void Compare(const FunctionCallbackInfo &args) { +@@ -865,19 +877,17 @@ void Compare(const FunctionCallbackInfo &args) { } int32_t FastCompare(v8::Local, @@ -135,7 +135,7 @@ index 10659fbf57e4535736fc001c0dbdd9b93e8f60f1..c0bd975bae23d1c05ace42fd8c9846ee } static v8::CFunction fast_compare(v8::CFunction::Make(FastCompare)); -@@ -1150,14 +1160,13 @@ void SlowIndexOfNumber(const FunctionCallbackInfo& args) { +@@ -1148,14 +1158,13 @@ void SlowIndexOfNumber(const FunctionCallbackInfo& args) { } int32_t FastIndexOfNumber(v8::Local, @@ -153,7 +153,7 @@ index 10659fbf57e4535736fc001c0dbdd9b93e8f60f1..c0bd975bae23d1c05ace42fd8c9846ee } static v8::CFunction fast_index_of_number( -@@ -1511,21 +1520,31 @@ void SlowWriteString(const FunctionCallbackInfo& args) { +@@ -1495,21 +1504,31 @@ void SlowWriteString(const FunctionCallbackInfo& args) { template uint32_t FastWriteString(Local receiver, @@ -192,7 +192,7 @@ index 10659fbf57e4535736fc001c0dbdd9b93e8f60f1..c0bd975bae23d1c05ace42fd8c9846ee + std::min(dst_size - offset, max_length)); } - static v8::CFunction fast_write_string_ascii( + static const v8::CFunction fast_write_string_ascii( diff --git a/src/node_external_reference.h b/src/node_external_reference.h index bb007dbdcce486659afeed07b78103e44b00307b..314a4ded6908a94107de1ae1e550b7d46afdce75 100644 --- a/src/node_external_reference.h @@ -246,10 +246,10 @@ index bb007dbdcce486659afeed07b78103e44b00307b..314a4ded6908a94107de1ae1e550b7d4 // This class manages the external references from the V8 heap // to the C++ addresses in Node.js. diff --git a/src/util.h b/src/util.h -index 48d3c7b8a304049cdb4d4ab2c027b300dc533dc0..f9d5a5b36701b3c65fda65ed8920521ff68e32cd 100644 +index a77332f583402af956cc886fd5b9771390cc4827..f0d7571caa458a3f9a9c252a95f72eb5fbddd06d 100644 --- a/src/util.h +++ b/src/util.h -@@ -59,6 +59,7 @@ +@@ -60,6 +60,7 @@ namespace node { constexpr char kPathSeparator = std::filesystem::path::preferred_separator; @@ -257,7 +257,7 @@ index 48d3c7b8a304049cdb4d4ab2c027b300dc533dc0..f9d5a5b36701b3c65fda65ed8920521f #ifdef _WIN32 /* MAX_PATH is in characters, not bytes. Make sure we have enough headroom. */ -@@ -584,6 +585,16 @@ class BufferValue : public MaybeStackBuffer { +@@ -585,6 +586,16 @@ class BufferValue : public MaybeStackBuffer { static_cast(name->Buffer()->Data()) + name##_offset; \ if (name##_length > 0) CHECK_NE(name##_data, nullptr); diff --git a/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch b/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch index adb0fcc8506a3..81346e984b9a8 100644 --- a/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch +++ b/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch @@ -11,10 +11,10 @@ This patch can be removed when we upgrade to a V8 version that contains the above CL. diff --git a/src/node.cc b/src/node.cc -index a0f1deadfc58f18f23467889680219360386f9dd..8da5f5344051663f92d72848fbac9d041ac4fac3 100644 +index 0fbcd55d674b1d0cae88f04fe337cfcca702255f..092b1c525c7d4d50a09f99dc088d0698afcaf8a6 100644 --- a/src/node.cc +++ b/src/node.cc -@@ -808,7 +808,7 @@ static ExitCode ProcessGlobalArgsInternal(std::vector* args, +@@ -814,7 +814,7 @@ static ExitCode ProcessGlobalArgsInternal(std::vector* args, } // TODO(nicolo-ribaudo): remove this once V8 doesn't enable it by default // anymore. diff --git a/patches/node/pass_all_globals_through_require.patch b/patches/node/pass_all_globals_through_require.patch index 024cfdbfdddd5..918c6d2aac4f2 100644 --- a/patches/node/pass_all_globals_through_require.patch +++ b/patches/node/pass_all_globals_through_require.patch @@ -6,7 +6,7 @@ Subject: Pass all globals through "require" (cherry picked from commit 7d015419cb7a0ecfe6728431a4ed2056cd411d62) diff --git a/lib/internal/modules/cjs/loader.js b/lib/internal/modules/cjs/loader.js -index 33385fa792b71ea3802904dd3c59ce845342c595..92b368394e17a9257578cd5b7422391689732d6d 100644 +index ccd2b4ced3134d81ddd37b8b5b90218457633421..a19fc5e52109bf2ad63fbe554c02a458c3096081 100644 --- a/lib/internal/modules/cjs/loader.js +++ b/lib/internal/modules/cjs/loader.js @@ -200,6 +200,13 @@ const { diff --git a/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch b/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch index 7d775d9ef61ba..a526b752d46d3 100644 --- a/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch +++ b/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch @@ -18,10 +18,10 @@ This can be removed when Node.js upgrades to a version of V8 containing CLs from the above issue. diff --git a/src/api/environment.cc b/src/api/environment.cc -index 7f4f233b26425493a58ce71dfc0c3a92b7c0bef8..c3f422c6b212bf737a906d2a89df85b63c218617 100644 +index 5b7f6e0609c8414c686d2d5ca603ea5c8bc484d0..6c9c81ff3c08fc28dc35578229a785521322b5dc 100644 --- a/src/api/environment.cc +++ b/src/api/environment.cc -@@ -312,6 +312,10 @@ Isolate* NewIsolate(Isolate::CreateParams* params, +@@ -313,6 +313,10 @@ Isolate* NewIsolate(Isolate::CreateParams* params, MultiIsolatePlatform* platform, const SnapshotData* snapshot_data, const IsolateSettings& settings) { @@ -32,7 +32,7 @@ index 7f4f233b26425493a58ce71dfc0c3a92b7c0bef8..c3f422c6b212bf737a906d2a89df85b6 Isolate* isolate = Isolate::Allocate(); if (isolate == nullptr) return nullptr; -@@ -355,9 +359,12 @@ Isolate* NewIsolate(ArrayBufferAllocator* allocator, +@@ -356,9 +360,12 @@ Isolate* NewIsolate(ArrayBufferAllocator* allocator, uv_loop_t* event_loop, MultiIsolatePlatform* platform, const EmbedderSnapshotData* snapshot_data, @@ -102,36 +102,44 @@ index 9f1c7ef45b6df10f811936a78ea6d9fcc13fef4f..c429eecd937d1df32a2ff90bc0a22a2e worker::Worker* worker_context_ = nullptr; PerIsolateWrapperData* wrapper_data_; diff --git a/src/node.cc b/src/node.cc -index 8da5f5344051663f92d72848fbac9d041ac4fac3..2f58a6fa69069dabb99b5ddb8011991b07fa5f02 100644 +index 092b1c525c7d4d50a09f99dc088d0698afcaf8a6..6f8f6386d0db8aef1e2e0126cc9064101cbe6112 100644 --- a/src/node.cc +++ b/src/node.cc -@@ -1222,10 +1222,6 @@ InitializeOncePerProcessInternal(const std::vector& args, +@@ -1258,6 +1258,14 @@ InitializeOncePerProcessInternal(const std::vector& args, result->platform_ = per_process::v8_platform.Platform(); } -- if (!(flags & ProcessInitializationFlags::kNoInitializeV8)) { -- V8::Initialize(); -- } -- - if (!(flags & ProcessInitializationFlags::kNoInitializeCppgc)) { - v8::PageAllocator* allocator = nullptr; - if (result->platform_ != nullptr) { -@@ -1234,6 +1230,10 @@ InitializeOncePerProcessInternal(const std::vector& args, - cppgc::InitializeProcess(allocator); - } - -+ if (!(flags & ProcessInitializationFlags::kNoInitializeV8)) { -+ V8::Initialize(); ++ if (!(flags & ProcessInitializationFlags::kNoInitializeCppgc)) { ++ v8::PageAllocator* allocator = nullptr; ++ if (result->platform_ != nullptr) { ++ allocator = result->platform_->GetPageAllocator(); ++ } ++ cppgc::InitializeProcess(allocator); + } + + if (!(flags & ProcessInitializationFlags::kNoInitializeV8)) { + V8::Initialize(); + +@@ -1267,14 +1275,6 @@ InitializeOncePerProcessInternal(const std::vector& args, + absl::SetMutexDeadlockDetectionMode(absl::OnDeadlockCycle::kIgnore); + } + +- if (!(flags & ProcessInitializationFlags::kNoInitializeCppgc)) { +- v8::PageAllocator* allocator = nullptr; +- if (result->platform_ != nullptr) { +- allocator = result->platform_->GetPageAllocator(); +- } +- cppgc::InitializeProcess(allocator); +- } +- #if NODE_USE_V8_WASM_TRAP_HANDLER bool use_wasm_trap_handler = !per_process::cli_options->disable_wasm_trap_handler; diff --git a/src/node.h b/src/node.h -index 98ad0ea649eaef43d1f5231f7bc4044e100e08d7..c295cce8f5c7965cce4d2e4c0614dbe076986a4c 100644 +index 42d55d24bd0770795ae0c0e19241d25a6350ae08..4335c7cf53b7e08c95dcee3461384ac12c8ebe41 100644 --- a/src/node.h +++ b/src/node.h -@@ -589,7 +589,8 @@ NODE_EXTERN v8::Isolate* NewIsolate( +@@ -590,7 +590,8 @@ NODE_EXTERN v8::Isolate* NewIsolate( struct uv_loop_s* event_loop, MultiIsolatePlatform* platform, const EmbedderSnapshotData* snapshot_data = nullptr, @@ -166,7 +174,7 @@ index 4119ac1b002681d39711eac810ca2fcc2702ffc7..790347056cde949ffe6cf8498a7eca0c ExitCode NodeMainInstance::Run() { diff --git a/src/node_worker.cc b/src/node_worker.cc -index 1fc3774948dae3c0aae7d2aef563e18ecd4243a3..9d35cbf3dff538f38e8d5b8660d40c1fbaa56474 100644 +index 9d56d8f793ef48a79867f465530554ae0226f2cd..842eb999c6ef0cb877cc2ee4acf75bb597a117da 100644 --- a/src/node_worker.cc +++ b/src/node_worker.cc @@ -162,6 +162,9 @@ class WorkerThreadData { @@ -195,7 +203,7 @@ index 1fc3774948dae3c0aae7d2aef563e18ecd4243a3..9d35cbf3dff538f38e8d5b8660d40c1f // Wait until the platform has cleaned up all relevant resources. while (!platform_finished) { diff --git a/src/util.cc b/src/util.cc -index 3e9dfb4392fb3e3deaab5506771f01be65bc5dda..416e0479ddf740c6d3e2d4ea9466ac060b038294 100644 +index 0c01d338b9d1ced7f173ac862239315f91326791..5ca32f026f9f001ddadc14965705fe005600eddd 100644 --- a/src/util.cc +++ b/src/util.cc @@ -726,8 +726,8 @@ RAIIIsolateWithoutEntering::RAIIIsolateWithoutEntering(const SnapshotData* data) diff --git a/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch b/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch index eb31ed5e0e4a6..3936c9bc7017a 100644 --- a/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch +++ b/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch @@ -161,10 +161,10 @@ index cfe917c797a6e4bb0f0284ec56be82637f840129..9f1c7ef45b6df10f811936a78ea6d9fc inline MultiIsolatePlatform* platform() const; inline const SnapshotData* snapshot_data() const; diff --git a/src/node.h b/src/node.h -index bdc77f8eb7abffa9e6c98cd254daedad3e44b981..98ad0ea649eaef43d1f5231f7bc4044e100e08d7 100644 +index 174fd4d1af4c8cd75aec09f4548a674fd5539fb2..42d55d24bd0770795ae0c0e19241d25a6350ae08 100644 --- a/src/node.h +++ b/src/node.h -@@ -1553,24 +1553,14 @@ void RegisterSignalHandler(int signal, +@@ -1560,24 +1560,14 @@ void RegisterSignalHandler(int signal, bool reset_handler = false); #endif // _WIN32 diff --git a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch index 250c9daa8f16a..4a6e3d5147779 100644 --- a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch +++ b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch @@ -26,7 +26,7 @@ index 3d8ccc77b5952a999c5fe48792259d32b402c460..867a1c4aca54b9d41490d23a5eb55088 } diff --git a/src/histogram.cc b/src/histogram.cc -index 0f0cde7be431dcb80c5314b1a9da49886c436d1c..f6d2bd439cad8b9f91c9d9a6cdb302e64130a5e2 100644 +index 5641990e0bac455c33ddf7b9a865deba871516e7..bd757f42e02391abbeec007d9c4cea60bcdfa6a4 100644 --- a/src/histogram.cc +++ b/src/histogram.cc @@ -195,7 +195,8 @@ void HistogramBase::FastRecord(Local unused, diff --git a/patches/node/support_v8_sandboxed_pointers.patch b/patches/node/support_v8_sandboxed_pointers.patch index 6a3edccfab578..2aedd3ceeae9a 100644 --- a/patches/node/support_v8_sandboxed_pointers.patch +++ b/patches/node/support_v8_sandboxed_pointers.patch @@ -7,10 +7,10 @@ This refactors several allocators to allocate within the V8 memory cage, allowing them to be compatible with the V8_SANDBOXED_POINTERS feature. diff --git a/src/api/environment.cc b/src/api/environment.cc -index 88c2c932a6b045317c83c911b1cd8267b60d9334..7f4f233b26425493a58ce71dfc0c3a92b7c0bef8 100644 +index df5fb942aa893c22d14d7eb21a5211a46a472a5f..5b7f6e0609c8414c686d2d5ca603ea5c8bc484d0 100644 --- a/src/api/environment.cc +++ b/src/api/environment.cc -@@ -102,6 +102,14 @@ MaybeLocal PrepareStackTraceCallback(Local context, +@@ -103,6 +103,14 @@ MaybeLocal PrepareStackTraceCallback(Local context, return result; } @@ -156,7 +156,7 @@ index 1592134716da2de40de4ba028ee937b765423e37..8f3ba65f1fef2c066d6df6087a08ba71 v8::Local ToArrayBuffer(Environment* env); diff --git a/src/crypto/crypto_x509.cc b/src/crypto/crypto_x509.cc -index 3465454e4de4a78912b81e7eca0de395fbe89911..c8ae863460107c69dd77d67c76c11843114e99c4 100644 +index f616223cfb0f6e10f7cf57ada9704316bde2797e..eb6dad44a49d997097c8fb5009eeb60a7305da27 100644 --- a/src/crypto/crypto_x509.cc +++ b/src/crypto/crypto_x509.cc @@ -167,6 +167,19 @@ MaybeLocal ToV8Value(Local context, const BIOPointer& bio) { @@ -229,10 +229,10 @@ index ea7810e41e2667713a896250dc1b904b0a7cf198..865b3128c1edfe7074769f25a0b87878 constexpr const char* EncodingName(const enum encoding encoding) { diff --git a/src/node_internals.h b/src/node_internals.h -index 382df89a2312f76b5293412a8d51969ae5d9fa9c..1c90da9bbcb9547ab36de4d01088c03f3350b787 100644 +index 275534285ec28f02b46639142ab4195b24267476..5f9d123f9d4b9feb7bc0b627b1e6309fdbd6e30d 100644 --- a/src/node_internals.h +++ b/src/node_internals.h -@@ -117,7 +117,9 @@ v8::Maybe InitializePrimordials(v8::Local context); +@@ -120,7 +120,9 @@ v8::MaybeLocal InitializePrivateSymbols( class NodeArrayBufferAllocator : public ArrayBufferAllocator { public: @@ -243,7 +243,7 @@ index 382df89a2312f76b5293412a8d51969ae5d9fa9c..1c90da9bbcb9547ab36de4d01088c03f void* Allocate(size_t size) override; // Defined in src/node.cc void* AllocateUninitialized(size_t size) override; -@@ -135,7 +137,7 @@ class NodeArrayBufferAllocator : public ArrayBufferAllocator { +@@ -138,7 +140,7 @@ class NodeArrayBufferAllocator : public ArrayBufferAllocator { } private: diff --git a/patches/node/zlib_fix_pointer_alignment.patch b/patches/node/zlib_fix_pointer_alignment.patch deleted file mode 100644 index 418e74d53ccdd..0000000000000 --- a/patches/node/zlib_fix_pointer_alignment.patch +++ /dev/null @@ -1,50 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Jeroen Hofstee -Date: Tue, 1 Apr 2025 20:09:31 +0000 -Subject: zlib: fix pointer alignment - -The function AllocForBrotli prefixes the allocated memory with its -size, and returns a pointer to the region after it. This pointer can -however no longer be suitably aligned. Correct this by allocating -the maximum of the the size of the size_t and the max alignment. - -On Arm 32bits the size_t is 4 bytes long, but the alignment is 8 for -some NEON instructions. When Brotli is compiled with optimizations -enabled newer GCC versions will use the NEON instructions and trigger -a bus error killing node. - -see https://github.com/google/brotli/issues/1159 - -diff --git a/src/node_zlib.cc b/src/node_zlib.cc -index 0b7c47b326c7c5480086228b3d40d54c260ef16a..7e6b38ecd1aa360012c0d73e94412530a48cb8c3 100644 ---- a/src/node_zlib.cc -+++ b/src/node_zlib.cc -@@ -608,7 +608,8 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { - } - - static void* AllocForBrotli(void* data, size_t size) { -- size += sizeof(size_t); -+ constexpr size_t offset = std::max(sizeof(size_t), alignof(max_align_t)); -+ size += offset; - CompressionStream* ctx = static_cast(data); - char* memory = UncheckedMalloc(size); - if (memory == nullptr) [[unlikely]] { -@@ -617,7 +618,7 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { - *reinterpret_cast(memory) = size; - ctx->unreported_allocations_.fetch_add(size, - std::memory_order_relaxed); -- return memory + sizeof(size_t); -+ return memory + offset; - } - - static void FreeForZlib(void* data, void* pointer) { -@@ -625,7 +626,8 @@ class CompressionStream : public AsyncWrap, public ThreadPoolWork { - return; - } - CompressionStream* ctx = static_cast(data); -- char* real_pointer = static_cast(pointer) - sizeof(size_t); -+ constexpr size_t offset = std::max(sizeof(size_t), alignof(max_align_t)); -+ char* real_pointer = static_cast(pointer) - offset; - size_t real_size = *reinterpret_cast(real_pointer); - ctx->unreported_allocations_.fetch_sub(real_size, - std::memory_order_relaxed); diff --git a/script/node-disabled-tests.json b/script/node-disabled-tests.json index 469f9cf2ff649..8acefe60934da 100644 --- a/script/node-disabled-tests.json +++ b/script/node-disabled-tests.json @@ -7,6 +7,7 @@ "parallel/test-code-cache", "parallel/test-cluster-primary-error", "parallel/test-cluster-primary-kill", + "parallel/test-config-file", "parallel/test-crypto-aes-wrap", "parallel/test-crypto-authenticated", "parallel/test-crypto-authenticated-stream", @@ -72,6 +73,7 @@ "parallel/test-snapshot-weak-reference", "parallel/test-snapshot-worker", "parallel/test-strace-openat-openssl", + "parallel/test-sqlite-backup", "parallel/test-tls-alpn-server-client", "parallel/test-tls-cli-min-version-1.0", "parallel/test-tls-cli-max-version-1.2", diff --git a/shell/common/node_bindings.cc b/shell/common/node_bindings.cc index 029a3b9bf1d45..4ff3fda19c1f8 100644 --- a/shell/common/node_bindings.cc +++ b/shell/common/node_bindings.cc @@ -1002,11 +1002,10 @@ void OnNodePreload(node::Environment* env, } // Execute lib/node/init.ts. - std::vector> bundle_params = { - node::FIXED_ONE_BYTE_STRING(env->isolate(), "process"), - node::FIXED_ONE_BYTE_STRING(env->isolate(), "require"), - }; - std::vector> bundle_args = {process, require}; + v8::LocalVector bundle_params( + env->isolate(), {node::FIXED_ONE_BYTE_STRING(env->isolate(), "process"), + node::FIXED_ONE_BYTE_STRING(env->isolate(), "require")}); + v8::LocalVector bundle_args(env->isolate(), {process, require}); electron::util::CompileAndCall(env->context(), "electron/js2c/node_init", &bundle_params, &bundle_args); } diff --git a/shell/common/node_util.cc b/shell/common/node_util.cc index 98e618471f4ef..57090f8d3c00b 100644 --- a/shell/common/node_util.cc +++ b/shell/common/node_util.cc @@ -23,8 +23,8 @@ namespace electron::util { v8::MaybeLocal CompileAndCall( v8::Local context, const char* id, - std::vector>* parameters, - std::vector>* arguments) { + v8::LocalVector* parameters, + v8::LocalVector* arguments) { v8::Isolate* isolate = context->GetIsolate(); v8::TryCatch try_catch(isolate); diff --git a/shell/common/node_util.h b/shell/common/node_util.h index b159fcf657768..1ad7fc22a2968 100644 --- a/shell/common/node_util.h +++ b/shell/common/node_util.h @@ -53,8 +53,8 @@ void EmitDeprecationWarning(std::string_view warning_msg, v8::MaybeLocal CompileAndCall( v8::Local context, const char* id, - std::vector>* parameters, - std::vector>* arguments); + v8::LocalVector* parameters, + v8::LocalVector* arguments); // Wrapper for node::CreateEnvironment that logs failure node::Environment* CreateEnvironment(v8::Isolate* isolate, diff --git a/shell/renderer/electron_sandboxed_renderer_client.cc b/shell/renderer/electron_sandboxed_renderer_client.cc index 2f8511a3a70d0..5efabd396c10f 100644 --- a/shell/renderer/electron_sandboxed_renderer_client.cc +++ b/shell/renderer/electron_sandboxed_renderer_client.cc @@ -125,10 +125,10 @@ void ElectronSandboxedRendererClient::DidCreateScriptContext( auto binding = v8::Object::New(isolate); InitializeBindings(binding, context, render_frame); - std::vector> sandbox_preload_bundle_params = { - node::FIXED_ONE_BYTE_STRING(isolate, "binding")}; + v8::LocalVector sandbox_preload_bundle_params( + isolate, {node::FIXED_ONE_BYTE_STRING(isolate, "binding")}); - std::vector> sandbox_preload_bundle_args = {binding}; + v8::LocalVector sandbox_preload_bundle_args(isolate, {binding}); util::CompileAndCall( isolate->GetCurrentContext(), "electron/js2c/sandbox_bundle", diff --git a/shell/renderer/preload_realm_context.cc b/shell/renderer/preload_realm_context.cc index 5f104fe26bcf1..a8e47b2d0ab69 100644 --- a/shell/renderer/preload_realm_context.cc +++ b/shell/renderer/preload_realm_context.cc @@ -176,10 +176,10 @@ class PreloadRealmLifetimeController process.SetReadOnly("type", "service-worker"); process.SetReadOnly("contextIsolated", true); - std::vector> preload_realm_bundle_params = { - node::FIXED_ONE_BYTE_STRING(isolate, "binding")}; + v8::LocalVector preload_realm_bundle_params( + isolate, {node::FIXED_ONE_BYTE_STRING(isolate, "binding")}); - std::vector> preload_realm_bundle_args = {binding}; + v8::LocalVector preload_realm_bundle_args(isolate, {binding}); util::CompileAndCall(context, "electron/js2c/preload_realm_bundle", &preload_realm_bundle_params, diff --git a/shell/renderer/renderer_client_base.cc b/shell/renderer/renderer_client_base.cc index e1aeaae304a5c..5eb0fe04fc6e1 100644 --- a/shell/renderer/renderer_client_base.cc +++ b/shell/renderer/renderer_client_base.cc @@ -597,11 +597,11 @@ void RendererClientBase::SetupMainWorldOverrides( } } - std::vector> isolated_bundle_params = { - node::FIXED_ONE_BYTE_STRING(isolate, "isolatedApi")}; + v8::LocalVector isolated_bundle_params( + isolate, {node::FIXED_ONE_BYTE_STRING(isolate, "isolatedApi")}); - std::vector> isolated_bundle_args = { - isolated_api.GetHandle()}; + v8::LocalVector isolated_bundle_args(isolate, + {isolated_api.GetHandle()}); util::CompileAndCall(context, "electron/js2c/isolated_bundle", &isolated_bundle_params, &isolated_bundle_args); From 1d8e9e1d529312b835be9bff85d82275f7656a4e Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 4 Jun 2025 14:08:49 +0200 Subject: [PATCH 081/186] fix: addChildView() crashes when adding a closed WebContentsView (#47338) fix: addChildView() crashes when add a closed WebContentsView Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Sida Zhu --- shell/browser/api/electron_api_view.cc | 6 ++++++ spec/api-web-contents-view-spec.ts | 14 ++++++++++++++ 2 files changed, 20 insertions(+) diff --git a/shell/browser/api/electron_api_view.cc b/shell/browser/api/electron_api_view.cc index 10127a5f257e6..5d82abe2d213d 100644 --- a/shell/browser/api/electron_api_view.cc +++ b/shell/browser/api/electron_api_view.cc @@ -216,6 +216,12 @@ void View::AddChildViewAt(gin::Handle child, if (!view_) return; + if (!child->view()) { + gin_helper::ErrorThrower(isolate()).ThrowError( + "Can't add a destroyed child view to a parent view"); + return; + } + // This will CHECK and crash in View::AddChildViewAtImpl if not handled here. if (view_ == child->view()) { gin_helper::ErrorThrower(isolate()).ThrowError( diff --git a/spec/api-web-contents-view-spec.ts b/spec/api-web-contents-view-spec.ts index 077cb96e30d7b..63f45c140edd1 100644 --- a/spec/api-web-contents-view-spec.ts +++ b/spec/api-web-contents-view-spec.ts @@ -55,6 +55,20 @@ describe('WebContentsView', () => { })).to.throw('options.webContents is already attached to a window'); }); + it('should throw an error when adding a destroyed child view to the parent view', async () => { + const browserWindow = new BrowserWindow(); + + const webContentsView = new WebContentsView(); + webContentsView.webContents.loadURL('about:blank'); + webContentsView.webContents.destroy(); + + const destroyed = once(webContentsView.webContents, 'destroyed'); + await destroyed; + expect(() => browserWindow.contentView.addChildView(webContentsView)).to.throw( + 'Can\'t add a destroyed child view to a parent view' + ); + }); + it('should throw error when created with already attached webContents to other WebContentsView', () => { const browserWindow = new BrowserWindow(); From 2fb2cc030def316f9eb0226d7af4c667919df22c Mon Sep 17 00:00:00 2001 From: Keeley Hammond Date: Wed, 4 Jun 2025 17:38:39 +0200 Subject: [PATCH 082/186] chore: cherry-pick f1e6422a355c from chromium (#47358) * chore: cherry-pick f1e6422a355c from chromium * chore: update patches --- patches/chromium/.patches | 1 + .../chromium/cherry-pick-f1e6422a355c.patch | 273 ++++++++++++++++++ 2 files changed, 274 insertions(+) create mode 100644 patches/chromium/cherry-pick-f1e6422a355c.patch diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 6cd66748b9cc4..51c1748e48957 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -144,3 +144,4 @@ fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch +cherry-pick-f1e6422a355c.patch diff --git a/patches/chromium/cherry-pick-f1e6422a355c.patch b/patches/chromium/cherry-pick-f1e6422a355c.patch new file mode 100644 index 0000000000000..5dcafde545708 --- /dev/null +++ b/patches/chromium/cherry-pick-f1e6422a355c.patch @@ -0,0 +1,273 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Yoshisato Yanagisawa +Date: Wed, 21 May 2025 23:25:12 -0700 +Subject: Enforce SharedWorker::Terminate() procedure order + +During the investigation of crbug.com/409059706, we observed that +PerformShutdownOnWorkerThread() is called during the status is +running. + +I suppose the root cause is race condition between `Terminate()` +procedure and a child process termination procedure in different +thread. WorkerThread can be terminated if two conditions are met; +`Terminate()` is called and all child worker threads have been +terminated. Both `Terminate()` and the child process termination +procedure may call `PerformShutdownOnWorkerThread()`, and former +is executed regardless of two conditions are met. The latter +is called if `Terminate()` is called and no child processes. +To be clear, "`Terminate()` is called" does not mean +`PrepareForShutdownOnWorkerThread()` is executed. `Terminate()` +queues it after the flag to tell `Terminate()` call. And, when +the issue happen, I am quite sure the flag is set but, +`PrepareForShutdownOnWorkerThread()` won't be executed yet. + +The fix is that: +1. The "Terminate() is called" flag to be multi staged. + The flag is used for two purpose; a. avoid re-enter of + `Terminate()`, and b. `PrepareForShutdownOnWorkerThread()` is + in flight. The CL changed the flag to enum to represent + the stage properly. +2. `PerformShutdownOnWorkerThread()` is queued even if it is + called within the child process termination procedure. + It avoid the execution order flip between + `PrepareForShutdownOnWorkerThread()` and + `PerformShutdownOnWorkerThread()`. + +In addition, this change ensures `PerformShutdownOnWorkerThread()` +is called once. While `PerformShutdownOnWorkerThread()` touches +fields inside, the fields must not be touched at some point within +the function, the function is actually not re-entrant when it reaches +to the end. Upon mikt@ suggestion, I made +`PerformShutdownOnWorkerThread()` is called only when two conditions +are fulfilled. i.e. `Terminate()` is called and the number of child +threads is 0. Also, the CL uses the enum to show +`PerformShutdownOnWorkerThread()` is in-flight to avoid re-entrance +in this level. + +Bug: 409059706 +Change-Id: I81a1c3b1a34e827fa75ec2d1a9b37023965dbe27 +Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6543412 +Reviewed-by: Hiroki Nakagawa +Commit-Queue: Yoshisato Yanagisawa +Cr-Commit-Position: refs/heads/main@{#1463892} + +diff --git a/third_party/blink/common/features.cc b/third_party/blink/common/features.cc +index 58caf0050b649f8c43e30b6e59eab968b0bb7334..7863bf237a9a5c273120c8de29e71db589367b3d 100644 +--- a/third_party/blink/common/features.cc ++++ b/third_party/blink/common/features.cc +@@ -2845,6 +2845,13 @@ BASE_FEATURE(kWebviewAccelerateSmallCanvases, + "WebviewAccelerateSmallCanvases", + base::FEATURE_DISABLED_BY_DEFAULT); + ++// WorkerThread termination procedure (prepare and shutdown) runs sequentially ++// in the same task without calling another cross thread post task. ++// Kill switch for crbug.com/409059706. ++BASE_FEATURE(kWorkerThreadSequentialShutdown, ++ "WorkerThreadSequentialShutdown", ++ base::FEATURE_ENABLED_BY_DEFAULT); ++ + BASE_FEATURE(kNoReferrerForPreloadFromSubresource, + "NoReferrerForPreloadFromSubresource", + base::FEATURE_ENABLED_BY_DEFAULT); +diff --git a/third_party/blink/public/common/features.h b/third_party/blink/public/common/features.h +index 2d3ffda8afe1772c817517d1542dbd3aa8bccbce..340ea360177c00424f0eb3461e65c6ba011e43c5 100644 +--- a/third_party/blink/public/common/features.h ++++ b/third_party/blink/public/common/features.h +@@ -1841,6 +1841,8 @@ BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kWebUSBTransferSizeLimit); + + BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kWebviewAccelerateSmallCanvases); + ++BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kWorkerThreadSequentialShutdown); ++ + // Kill switch for https://crbug.com/415810136. + BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kNoReferrerForPreloadFromSubresource); + +diff --git a/third_party/blink/renderer/core/workers/worker_thread.cc b/third_party/blink/renderer/core/workers/worker_thread.cc +index 7d13d80a7f09e47d9f3c6da860e8d3373d5b8afd..6e95eba151e3a002b66d55d1ee538e9cd88cd4bb 100644 +--- a/third_party/blink/renderer/core/workers/worker_thread.cc ++++ b/third_party/blink/renderer/core/workers/worker_thread.cc +@@ -263,9 +263,10 @@ void WorkerThread::Terminate() { + DCHECK_CALLED_ON_VALID_THREAD(parent_thread_checker_); + { + base::AutoLock locker(lock_); +- if (requested_to_terminate_) ++ if (termination_progress_ != TerminationProgress::kNotRequested) { + return; +- requested_to_terminate_ = true; ++ } ++ termination_progress_ = TerminationProgress::kRequested; + } + + // Schedule a task to forcibly terminate the script execution in case that the +@@ -281,10 +282,33 @@ void WorkerThread::Terminate() { + *task_runner, FROM_HERE, + CrossThreadBindOnce(&WorkerThread::PrepareForShutdownOnWorkerThread, + CrossThreadUnretained(this))); +- PostCrossThreadTask( +- *task_runner, FROM_HERE, +- CrossThreadBindOnce(&WorkerThread::PerformShutdownOnWorkerThread, +- CrossThreadUnretained(this))); ++ ++ if (!base::FeatureList::IsEnabled( ++ blink::features::kWorkerThreadSequentialShutdown)) { ++ PostCrossThreadTask( ++ *task_runner, FROM_HERE, ++ CrossThreadBindOnce(&WorkerThread::PerformShutdownOnWorkerThread, ++ CrossThreadUnretained(this))); ++ return; ++ } ++ ++ bool perform_shutdown = false; ++ { ++ base::AutoLock locker(lock_); ++ CHECK_EQ(TerminationProgress::kRequested, termination_progress_); ++ termination_progress_ = TerminationProgress::kPrepared; ++ if (num_child_threads_ == 0) { ++ termination_progress_ = TerminationProgress::kPerforming; ++ perform_shutdown = true; ++ } ++ } ++ ++ if (perform_shutdown) { ++ PostCrossThreadTask( ++ *task_runner, FROM_HERE, ++ CrossThreadBindOnce(&WorkerThread::PerformShutdownOnWorkerThread, ++ CrossThreadUnretained(this))); ++ } + } + + void WorkerThread::TerminateForTesting() { +@@ -421,20 +445,48 @@ scoped_refptr WorkerThread::GetTaskRunner( + + void WorkerThread::ChildThreadStartedOnWorkerThread(WorkerThread* child) { + DCHECK(IsCurrentThread()); +-#if DCHECK_IS_ON() ++ child_threads_.insert(child); + { + base::AutoLock locker(lock_); + DCHECK_EQ(ThreadState::kRunning, thread_state_); ++ CHECK_EQ(TerminationProgress::kNotRequested, termination_progress_); ++ if (base::FeatureList::IsEnabled( ++ blink::features::kWorkerThreadSequentialShutdown)) { ++ ++num_child_threads_; ++ CHECK_EQ(child_threads_.size(), num_child_threads_); ++ } + } +-#endif +- child_threads_.insert(child); + } + + void WorkerThread::ChildThreadTerminatedOnWorkerThread(WorkerThread* child) { + DCHECK(IsCurrentThread()); + child_threads_.erase(child); +- if (child_threads_.empty() && CheckRequestedToTerminate()) +- PerformShutdownOnWorkerThread(); ++ if (!base::FeatureList::IsEnabled( ++ blink::features::kWorkerThreadSequentialShutdown)) { ++ if (child_threads_.empty() && CheckRequestedToTerminate()) { ++ PerformShutdownOnWorkerThread(); ++ } ++ return; ++ } ++ ++ bool perform_shutdown = false; ++ { ++ base::AutoLock locker(lock_); ++ --num_child_threads_; ++ CHECK_EQ(child_threads_.size(), num_child_threads_); ++ if (num_child_threads_ == 0 && ++ termination_progress_ == TerminationProgress::kPrepared) { ++ termination_progress_ = TerminationProgress::kPerforming; ++ perform_shutdown = true; ++ } ++ } ++ if (perform_shutdown) { ++ scoped_refptr task_runner = ++ GetWorkerBackingThread().BackingThread().GetTaskRunner(); ++ GetWorkerBackingThread().BackingThread().GetTaskRunner()->PostTask( ++ FROM_HERE, WTF::BindOnce(&WorkerThread::PerformShutdownOnWorkerThread, ++ WTF::Unretained(this))); ++ } + } + + WorkerThread::WorkerThread(WorkerReportingProxy& worker_reporting_proxy) +@@ -778,18 +830,32 @@ void WorkerThread::PerformShutdownOnWorkerThread() { + DCHECK(IsCurrentThread()); + { + base::AutoLock locker(lock_); +- DCHECK(requested_to_terminate_); ++ if (!base::FeatureList::IsEnabled( ++ blink::features::kWorkerThreadSequentialShutdown)) { ++ DCHECK_NE(TerminationProgress::kNotRequested, termination_progress_); ++ } else { ++ DCHECK_EQ(TerminationProgress::kPerforming, termination_progress_); ++ } + DCHECK_EQ(ThreadState::kReadyToShutdown, thread_state_); + if (exit_code_ == ExitCode::kNotTerminated) + SetExitCode(ExitCode::kGracefullyTerminated); + } + +- // When child workers are present, wait for them to shutdown before shutting +- // down this thread. ChildThreadTerminatedOnWorkerThread() is responsible +- // for completing shutdown on the worker thread after the last child shuts +- // down. +- if (!child_threads_.empty()) +- return; ++ if (!base::FeatureList::IsEnabled( ++ blink::features::kWorkerThreadSequentialShutdown)) { ++ // When child workers are present, wait for them to shutdown before shutting ++ // down this thread. ChildThreadTerminatedOnWorkerThread() is responsible ++ // for completing shutdown on the worker thread after the last child shuts ++ // down. ++ if (!child_threads_.empty()) { ++ return; ++ } ++ } else { ++ // Child workers must not exist when `PerformShutdownOnWorkerThread()` ++ // is called because it has already been checked before calling the ++ // function. ++ CHECK(child_threads_.empty()); ++ } + + inspector_task_runner_->Dispose(); + if (worker_inspector_controller_) { +@@ -845,7 +911,7 @@ void WorkerThread::SetExitCode(ExitCode exit_code) { + + bool WorkerThread::CheckRequestedToTerminate() { + base::AutoLock locker(lock_); +- return requested_to_terminate_; ++ return termination_progress_ != TerminationProgress::kNotRequested; + } + + void WorkerThread::PauseOrFreeze(mojom::blink::FrameLifecycleState state, +diff --git a/third_party/blink/renderer/core/workers/worker_thread.h b/third_party/blink/renderer/core/workers/worker_thread.h +index 49a7ac5868844465c8c863186958e5e590ffef29..f48f05b795ac2490851e23282be3172ddbe3516c 100644 +--- a/third_party/blink/renderer/core/workers/worker_thread.h ++++ b/third_party/blink/renderer/core/workers/worker_thread.h +@@ -319,6 +319,13 @@ class CORE_EXPORT WorkerThread : public Thread::TaskObserver { + kTerminationUnnecessary, + }; + ++ enum class TerminationProgress { ++ kNotRequested, ++ kRequested, ++ kPrepared, ++ kPerforming, ++ }; ++ + // Returns true if we should synchronously terminate the script execution so + // that a shutdown task can be handled by the thread event loop. + TerminationState ShouldTerminateScriptExecution() +@@ -419,8 +426,10 @@ class CORE_EXPORT WorkerThread : public Thread::TaskObserver { + // A unique identifier among all WorkerThreads. + const int worker_thread_id_; + +- // Set on the parent thread. +- bool requested_to_terminate_ GUARDED_BY(lock_) = false; ++ // Represents progress after the Terminate() call. ++ TerminationProgress termination_progress_ GUARDED_BY(lock_) = ++ TerminationProgress::kNotRequested; ++ size_t num_child_threads_ GUARDED_BY(lock_) = 0; + + ThreadState thread_state_ GUARDED_BY(lock_) = ThreadState::kNotStarted; + ExitCode exit_code_ GUARDED_BY(lock_) = ExitCode::kNotTerminated; From c382d4c875c4e264d96880b9acd3c4388e068802 Mon Sep 17 00:00:00 2001 From: Keeley Hammond Date: Wed, 4 Jun 2025 17:46:54 +0200 Subject: [PATCH 083/186] chore: cherry-pick 45eb42cd398e from v8 (#47356) * chore: cherry-pick 45eb42cd398e from v8 * chore: update patches --- patches/v8/.patches | 1 + patches/v8/cherry-pick-45eb42cd398e.patch | 32 +++++++++++++++++++++++ 2 files changed, 33 insertions(+) create mode 100644 patches/v8/cherry-pick-45eb42cd398e.patch diff --git a/patches/v8/.patches b/patches/v8/.patches index 5fb328123db0b..21da17ba0f4b2 100644 --- a/patches/v8/.patches +++ b/patches/v8/.patches @@ -1,2 +1,3 @@ chore_allow_customizing_microtask_policy_per_context.patch cherry-pick-7bc0a67ebfbf.patch +cherry-pick-45eb42cd398e.patch diff --git a/patches/v8/cherry-pick-45eb42cd398e.patch b/patches/v8/cherry-pick-45eb42cd398e.patch new file mode 100644 index 0000000000000..c1fa3426717ee --- /dev/null +++ b/patches/v8/cherry-pick-45eb42cd398e.patch @@ -0,0 +1,32 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Igor Sheludko +Date: Tue, 27 May 2025 21:34:45 +0200 +Subject: Convert Smi to Word64 using zero extension + +... when a known type range contains only positive values. + +Bug: 420637585 +Change-Id: I8d9bb3f2fe2e5268e1659bb4ea7bbf97bfb52288 +Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/6594731 +Reviewed-by: Nico Hartmann +Commit-Queue: Igor Sheludko +Cr-Commit-Position: refs/heads/main@{#100538} + +diff --git a/src/compiler/representation-change.cc b/src/compiler/representation-change.cc +index a05b47e602e9707c17ba0ddcc9cfc071b95db168..116dcb6ce9a10e8fd3c681292ceaa2894db55052 100644 +--- a/src/compiler/representation-change.cc ++++ b/src/compiler/representation-change.cc +@@ -1394,7 +1394,12 @@ Node* RepresentationChanger::GetWord64RepresentationFor( + } + } else if (output_rep == MachineRepresentation::kTaggedSigned) { + if (output_type.Is(Type::SignedSmall())) { +- op = simplified()->ChangeTaggedSignedToInt64(); ++ if (output_type.IsRange() && output_type.AsRange()->Min() >= 0) { ++ node = InsertChangeTaggedSignedToInt32(node); ++ op = machine()->ChangeUint32ToUint64(); ++ } else { ++ op = simplified()->ChangeTaggedSignedToInt64(); ++ } + } else { + return TypeError(node, output_rep, output_type, + MachineRepresentation::kWord64); From 380351c01b30f4e648f2cbcb6b1d23010029d5a5 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 5 Jun 2025 10:04:11 +0200 Subject: [PATCH 084/186] fix: do not load source for `electron` module in ESM loader synchronous flow (#47342) * fix: do not load electron from ESM loader's CJS compatibility Co-authored-by: clavin * chore: upgrade patches --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: clavin --- ..._do_not_resolve_electron_entrypoints.patch | 13 -------- ...n_electron_module_via_the_esm_loader.patch | 33 ++++++++++++++++++- ...in_esm_loaders_to_apply_asar_patches.patch | 2 +- 3 files changed, 33 insertions(+), 15 deletions(-) diff --git a/patches/node/fix_do_not_resolve_electron_entrypoints.patch b/patches/node/fix_do_not_resolve_electron_entrypoints.patch index 679f1bf31632d..a489cf55632f5 100644 --- a/patches/node/fix_do_not_resolve_electron_entrypoints.patch +++ b/patches/node/fix_do_not_resolve_electron_entrypoints.patch @@ -5,19 +5,6 @@ Subject: fix: do not resolve electron entrypoints This wastes fs cycles and can result in strange behavior if this path actually exists on disk -diff --git a/lib/internal/modules/esm/load.js b/lib/internal/modules/esm/load.js -index c9d4a3536d0f60375ae623b48ca2fa7095c88d42..d818320fbbc430d06a0c2852e4723981d6e1a844 100644 ---- a/lib/internal/modules/esm/load.js -+++ b/lib/internal/modules/esm/load.js -@@ -109,7 +109,7 @@ async function defaultLoad(url, context = kEmptyObject) { - source = null; - format ??= 'builtin'; - } else if (format !== 'commonjs' || defaultType === 'module') { -- if (source == null) { -+ if (format !== 'electron' && source == null) { - ({ responseURL, source } = await getSource(urlInstance, context)); - context = { __proto__: context, source }; - } diff --git a/lib/internal/modules/esm/translators.js b/lib/internal/modules/esm/translators.js index 49aacb6262502ced54e817f99dd596db85b9659c..f9f065bb743275e9b2ce71375e6a9f06e00c0f36 100644 --- a/lib/internal/modules/esm/translators.js diff --git a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch index baa89612d412d..3fbb7b9faf5c4 100644 --- a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch +++ b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch @@ -18,9 +18,18 @@ index 9519f947b8dfdc69808839948c9cb8434a0acf0e..23ce72d479f638c33edffcea7c35f5da /** diff --git a/lib/internal/modules/esm/load.js b/lib/internal/modules/esm/load.js -index 5ba13096b98047ff33e4d44167c2a069ccc5e69d..a00b5979e3b5deb4ba315b4635c7e5d2801c376e 100644 +index 5ba13096b98047ff33e4d44167c2a069ccc5e69d..09a332c0999086b30fd952d9456f788925240e27 100644 --- a/lib/internal/modules/esm/load.js +++ b/lib/internal/modules/esm/load.js +@@ -106,7 +106,7 @@ async function defaultLoad(url, context = kEmptyObject) { + + throwIfUnsupportedURLScheme(urlInstance); + +- if (urlInstance.protocol === 'node:') { ++ if (urlInstance.protocol === 'node:' || format === 'electron') { + source = null; + format ??= 'builtin'; + } else if (format !== 'commonjs' || defaultType === 'module') { @@ -119,7 +119,7 @@ async function defaultLoad(url, context = kEmptyObject) { // Now that we have the source for the module, run `defaultGetFormat` to detect its format. format = await defaultGetFormat(urlInstance, context); @@ -30,6 +39,15 @@ index 5ba13096b98047ff33e4d44167c2a069ccc5e69d..a00b5979e3b5deb4ba315b4635c7e5d2 // For backward compatibility reasons, we need to discard the source in // order for the CJS loader to re-fetch it. source = null; +@@ -167,7 +167,7 @@ function defaultLoadSync(url, context = kEmptyObject) { + + throwIfUnsupportedURLScheme(urlInstance, false); + +- if (urlInstance.protocol === 'node:') { ++ if (urlInstance.protocol === 'node:' || format === 'electron') { + source = null; + } else if (source == null) { + ({ responseURL, source } = getSourceSync(urlInstance, context)); @@ -200,12 +200,13 @@ function throwIfUnsupportedURLScheme(parsed) { protocol !== 'file:' && protocol !== 'data:' && @@ -45,6 +63,19 @@ index 5ba13096b98047ff33e4d44167c2a069ccc5e69d..a00b5979e3b5deb4ba315b4635c7e5d2 throw new ERR_UNSUPPORTED_ESM_URL_SCHEME(parsed, schemes); } } +diff --git a/lib/internal/modules/esm/loader.js b/lib/internal/modules/esm/loader.js +index ae03073aff8140b11c63b6c05d831ba573568dba..b70c7cfe40e2eaaeea7b5ad6fcf0aaee87276aa1 100644 +--- a/lib/internal/modules/esm/loader.js ++++ b/lib/internal/modules/esm/loader.js +@@ -492,7 +492,7 @@ class ModuleLoader { + } + + const cjsModule = wrap[imported_cjs_symbol]; +- if (cjsModule) { ++ if (cjsModule && finalFormat !== 'electron') { + assert(finalFormat === 'commonjs-sync'); + // Check if the ESM initiating import CJS is being required by the same CJS module. + if (cjsModule?.[kIsExecuting]) { diff --git a/lib/internal/modules/esm/resolve.js b/lib/internal/modules/esm/resolve.js index bfd9bd3d127404de1cbb6f30c43ab0342590759d..9e7d8ef0adef3b68a3ec186e4b218f591aa69266 100644 --- a/lib/internal/modules/esm/resolve.js diff --git a/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch b/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch index 8de78da28f2fe..3eb241ca1eb19 100644 --- a/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch +++ b/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch @@ -6,7 +6,7 @@ Subject: fix: lazyload fs in esm loaders to apply asar patches Changes { foo } from fs to just "fs.foo" so that our patching of fs is applied to esm loaders diff --git a/lib/internal/modules/esm/load.js b/lib/internal/modules/esm/load.js -index a00b5979e3b5deb4ba315b4635c7e5d2801c376e..c9d4a3536d0f60375ae623b48ca2fa7095c88d42 100644 +index 09a332c0999086b30fd952d9456f788925240e27..910ac85cdc86e7fb3f850f7edf0b95ea09d464dc 100644 --- a/lib/internal/modules/esm/load.js +++ b/lib/internal/modules/esm/load.js @@ -10,7 +10,7 @@ const { From c68389ad9882ae41b13cfb0f1bbe15822d34e828 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 5 Jun 2025 15:20:35 +0200 Subject: [PATCH 085/186] docs: update link to `runAsNode` fuse (#47376) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Erick Zhao --- docs/api/environment-variables.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/api/environment-variables.md b/docs/api/environment-variables.md index 643b5fb7be419..f0efc56404ac6 100644 --- a/docs/api/environment-variables.md +++ b/docs/api/environment-variables.md @@ -104,7 +104,7 @@ you would when running the normal Node.js executable, with the exception of the These flags are disabled owing to the fact that Electron uses BoringSSL instead of OpenSSL when building Node.js' `crypto` module, and so will not work as designed. -If the [`runAsNode` fuse](../tutorial/fuses.md#L13) is disabled, `ELECTRON_RUN_AS_NODE` will be ignored. +If the [`runAsNode` fuse](../tutorial/fuses.md#runasnode) is disabled, `ELECTRON_RUN_AS_NODE` will be ignored. ### `ELECTRON_NO_ATTACH_CONSOLE` _Windows_ From 2e2d1f16121f4a5e1af1594f4eb330ee690f8f8b Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 5 Jun 2025 15:46:57 +0200 Subject: [PATCH 086/186] feat: expose `win.isContentProtected()` (#47310) * feat: expose win.isContentProtected() Co-authored-by: Shelley Vohr * chore: remove stray _isContentProtected Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- docs/api/base-window.md | 4 ++++ docs/api/browser-window.md | 4 ++++ shell/browser/api/electron_api_base_window.cc | 2 +- spec/api-browser-window-spec.ts | 9 +++------ 4 files changed, 12 insertions(+), 7 deletions(-) diff --git a/docs/api/base-window.md b/docs/api/base-window.md index 52e6deb288f8c..98909de846e22 100644 --- a/docs/api/base-window.md +++ b/docs/api/base-window.md @@ -1346,6 +1346,10 @@ On Windows it calls SetWindowDisplayAffinity with `WDA_EXCLUDEFROMCAPTURE`. For Windows 10 version 2004 and up the window will be removed from capture entirely, older Windows versions behave as if `WDA_MONITOR` is applied capturing a black window. +#### `win.isContentProtected()` _macOS_ _Windows_ + +Returns `boolean` - whether or not content protection is currently enabled. + #### `win.setFocusable(focusable)` _macOS_ _Windows_ * `focusable` boolean diff --git a/docs/api/browser-window.md b/docs/api/browser-window.md index e61faa458fe26..78997aabd44fe 100644 --- a/docs/api/browser-window.md +++ b/docs/api/browser-window.md @@ -1528,6 +1528,10 @@ On Windows it calls SetWindowDisplayAffinity with `WDA_EXCLUDEFROMCAPTURE`. For Windows 10 version 2004 and up the window will be removed from capture entirely, older Windows versions behave as if `WDA_MONITOR` is applied capturing a black window. +#### `win.isContentProtected()` _macOS_ _Windows_ + +Returns `boolean` - whether or not content protection is currently enabled. + #### `win.setFocusable(focusable)` _macOS_ _Windows_ * `focusable` boolean diff --git a/shell/browser/api/electron_api_base_window.cc b/shell/browser/api/electron_api_base_window.cc index b795b5eeb263b..5070a6c2dd376 100644 --- a/shell/browser/api/electron_api_base_window.cc +++ b/shell/browser/api/electron_api_base_window.cc @@ -1260,7 +1260,7 @@ void BaseWindow::BuildPrototype(v8::Isolate* isolate, .SetMethod("isDocumentEdited", &BaseWindow::IsDocumentEdited) .SetMethod("setIgnoreMouseEvents", &BaseWindow::SetIgnoreMouseEvents) .SetMethod("setContentProtection", &BaseWindow::SetContentProtection) - .SetMethod("_isContentProtected", &BaseWindow::IsContentProtected) + .SetMethod("isContentProtected", &BaseWindow::IsContentProtected) .SetMethod("setFocusable", &BaseWindow::SetFocusable) .SetMethod("isFocusable", &BaseWindow::IsFocusable) .SetMethod("setMenu", &BaseWindow::SetMenu) diff --git a/spec/api-browser-window-spec.ts b/spec/api-browser-window-spec.ts index 2afadcfcdf80c..a54992049afda 100755 --- a/spec/api-browser-window-spec.ts +++ b/spec/api-browser-window-spec.ts @@ -300,8 +300,7 @@ describe('BrowserWindow module', () => { afterEach(closeAllWindows); it('can set content protection', async () => { const w = new BrowserWindow({ show: false }); - // @ts-expect-error This is a private API - expect(w._isContentProtected()).to.equal(false); + expect(w.isContentProtected()).to.equal(false); const shown = once(w, 'show'); @@ -309,8 +308,7 @@ describe('BrowserWindow module', () => { await shown; w.setContentProtection(true); - // @ts-expect-error This is a private API - expect(w._isContentProtected()).to.equal(true); + expect(w.isContentProtected()).to.equal(true); }); it('does not remove content protection after the window is hidden and shown', async () => { @@ -329,8 +327,7 @@ describe('BrowserWindow module', () => { w.show(); await shown; - // @ts-expect-error This is a private API - expect(w._isContentProtected()).to.equal(true); + expect(w.isContentProtected()).to.equal(true); }); }); From 3fdb77abf1a112d60ae99d32894f40a4cca122b1 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 5 Jun 2025 15:47:42 +0200 Subject: [PATCH 087/186] feat: allow intercepting mouse events (#47364) * feat: allow intercepting mouse events Co-authored-by: Shelley Vohr * test: add specs Co-authored-by: Shelley Vohr * Update spec/api-web-contents-spec.ts Co-authored-by: David Sanders Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- docs/api/web-contents.md | 53 ++++++++++++-- .../browser/api/electron_api_web_contents.cc | 6 ++ shell/browser/api/electron_api_web_contents.h | 2 + .../common/gin_converters/blink_converter.cc | 45 ++++++++++++ shell/common/gin_converters/blink_converter.h | 2 + spec/api-web-contents-spec.ts | 70 +++++++++++++++++++ spec/fixtures/pages/mouse-events.html | 20 ++++++ 7 files changed, 192 insertions(+), 6 deletions(-) create mode 100644 spec/fixtures/pages/mouse-events.html diff --git a/docs/api/web-contents.md b/docs/api/web-contents.md index 85d2ee83406eb..37876c608966e 100644 --- a/docs/api/web-contents.md +++ b/docs/api/web-contents.md @@ -534,14 +534,55 @@ To only prevent the menu shortcuts, use [`setIgnoreMenuShortcuts`](#contentssetignoremenushortcutsignore): ```js -const { BrowserWindow } = require('electron') +const { app, BrowserWindow } = require('electron') -const win = new BrowserWindow({ width: 800, height: 600 }) +app.whenReady().then(() => { + const win = new BrowserWindow({ width: 800, height: 600 }) + + win.webContents.on('before-input-event', (event, input) => { + // Enable application menu keyboard shortcuts when Ctrl/Cmd are down. + win.webContents.setIgnoreMenuShortcuts(!input.control && !input.meta) + }) +}) +``` + +#### Event: 'before-mouse-event' + +Returns: -win.webContents.on('before-input-event', (event, input) => { - // For example, only enable application menu keyboard shortcuts when - // Ctrl/Cmd are down. - win.webContents.setIgnoreMenuShortcuts(!input.control && !input.meta) +* `event` Event +* `mouse` [MouseInputEvent](structures/mouse-input-event.md) + +Emitted before dispatching mouse events in the page. + +Calling `event.preventDefault` will prevent the page mouse events. + +```js +const { app, BrowserWindow } = require('electron') + +app.whenReady().then(() => { + const win = new BrowserWindow({ width: 800, height: 600 }) + + win.webContents.on('before-mouse-event', (event, mouse) => { + // Prevent mouseDown events. + if (mouse.type === 'mouseDown') { + console.log(mouse) + /* + { + type: 'mouseDown', + clickCount: 1, + movementX: 0, + movementY: 0, + button: 'left', + x: 632.359375, + y: 480.6875, + globalX: 168.359375, + globalY: 193.6875 + } + */ + event.preventDefault() + } + }) }) ``` diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index b984d57f865bd..271fe13ec49e9 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -1356,6 +1356,12 @@ bool WebContents::PlatformHandleKeyboardEvent( } #endif +bool WebContents::PreHandleMouseEvent(content::WebContents* source, + const blink::WebMouseEvent& event) { + // |true| means that the event should be prevented. + return Emit("before-mouse-event", event); +} + content::KeyboardEventProcessingResult WebContents::PreHandleKeyboardEvent( content::WebContents* source, const input::NativeWebKeyboardEvent& event) { diff --git a/shell/browser/api/electron_api_web_contents.h b/shell/browser/api/electron_api_web_contents.h index 00547c5a82463..d31c94c97f4c4 100644 --- a/shell/browser/api/electron_api_web_contents.h +++ b/shell/browser/api/electron_api_web_contents.h @@ -533,6 +533,8 @@ class WebContents final : public ExclusiveAccessContext, const input::NativeWebKeyboardEvent& event) override; bool PlatformHandleKeyboardEvent(content::WebContents* source, const input::NativeWebKeyboardEvent& event); + bool PreHandleMouseEvent(content::WebContents* source, + const blink::WebMouseEvent& event) override; content::KeyboardEventProcessingResult PreHandleKeyboardEvent( content::WebContents* source, const input::NativeWebKeyboardEvent& event) override; diff --git a/shell/common/gin_converters/blink_converter.cc b/shell/common/gin_converters/blink_converter.cc index f172c74cfd2e1..2b79b6b2ac702 100644 --- a/shell/common/gin_converters/blink_converter.cc +++ b/shell/common/gin_converters/blink_converter.cc @@ -146,6 +146,26 @@ struct Converter { }); return FromV8WithLowerLookup(isolate, val, Lookup, out); } + static v8::Local ToV8(v8::Isolate* isolate, + const blink::WebMouseEvent::Button& in) { + switch (in) { + case blink::WebMouseEvent::Button::kLeft: + return StringToV8(isolate, "left"); + case blink::WebMouseEvent::Button::kMiddle: + return StringToV8(isolate, "middle"); + case blink::WebMouseEvent::Button::kRight: + return StringToV8(isolate, "right"); + case blink::WebMouseEvent::Button::kNoButton: + return StringToV8(isolate, "none"); + case blink::WebMouseEvent::Button::kBack: + return StringToV8(isolate, "back"); + case blink::WebMouseEvent::Button::kForward: + return StringToV8(isolate, "forward"); + case blink::WebMouseEvent::Button::kEraser: + return StringToV8(isolate, "eraser"); + } + return v8::Null(isolate); + } }; // clang-format off @@ -246,6 +266,9 @@ v8::Local Converter::ToV8( if (blink::WebInputEvent::IsKeyboardEventType(in.GetType())) return gin::ConvertToV8(isolate, *static_cast(&in)); + else if (blink::WebInputEvent::IsMouseEventType(in.GetType())) + return gin::ConvertToV8(isolate, + *static_cast(&in)); return gin::DataObjectBuilder(isolate) .Set("type", in.GetType()) .Set("modifiers", ModifiersToArray(in.GetModifiers())) @@ -379,6 +402,28 @@ bool Converter::FromV8(v8::Isolate* isolate, return true; } +v8::Local Converter::ToV8( + v8::Isolate* isolate, + const blink::WebMouseEvent& in) { + auto dict = gin_helper::Dictionary::CreateEmpty(isolate); + + dict.Set("type", in.GetType()); + dict.Set("clickCount", in.ClickCount()); + dict.Set("movementX", in.movement_x); + dict.Set("movementY", in.movement_y); + dict.Set("button", in.button); + + gfx::PointF position_in_screen = in.PositionInScreen(); + dict.Set("globalX", position_in_screen.x()); + dict.Set("globalY", position_in_screen.y()); + + gfx::PointF position_in_widget = in.PositionInWidget(); + dict.Set("x", position_in_widget.x()); + dict.Set("y", position_in_widget.y()); + + return dict.GetHandle(); +} + bool Converter::FromV8( v8::Isolate* isolate, v8::Local val, diff --git a/shell/common/gin_converters/blink_converter.h b/shell/common/gin_converters/blink_converter.h index f293181c4a6be..6197a09de2cec 100644 --- a/shell/common/gin_converters/blink_converter.h +++ b/shell/common/gin_converters/blink_converter.h @@ -57,6 +57,8 @@ struct Converter { static bool FromV8(v8::Isolate* isolate, v8::Local val, blink::WebMouseEvent* out); + static v8::Local ToV8(v8::Isolate* isolate, + const blink::WebMouseEvent& in); }; template <> diff --git a/spec/api-web-contents-spec.ts b/spec/api-web-contents-spec.ts index 69e462c1df2c4..4d0a3eebda205 100644 --- a/spec/api-web-contents-spec.ts +++ b/spec/api-web-contents-spec.ts @@ -1071,6 +1071,76 @@ describe('webContents module', () => { }); }); + describe('before-mouse-event event', () => { + afterEach(closeAllWindows); + it('can prevent document mouse events', async () => { + const w = new BrowserWindow({ show: false, webPreferences: { nodeIntegration: true, contextIsolation: false } }); + await w.loadFile(path.join(fixturesPath, 'pages', 'mouse-events.html')); + const mouseDown = new Promise(resolve => { + ipcMain.once('mousedown', (event, button) => resolve(button)); + }); + w.webContents.once('before-mouse-event', (event, input) => { + if (input.button === 'left') event.preventDefault(); + }); + w.webContents.sendInputEvent({ type: 'mouseDown', button: 'left', x: 100, y: 100 }); + w.webContents.sendInputEvent({ type: 'mouseDown', button: 'right', x: 100, y: 100 }); + expect(await mouseDown).to.equal(2); // Right button is 2 + }); + + it('has the correct properties', async () => { + const w = new BrowserWindow({ show: false }); + await w.loadFile(path.join(fixturesPath, 'pages', 'base-page.html')); + const testBeforeMouse = async (opts: Electron.MouseInputEvent) => { + const p = once(w.webContents, 'before-mouse-event'); + w.webContents.sendInputEvent({ + type: opts.type, + button: opts.button, + x: opts.x, + y: opts.y, + globalX: opts.globalX, + globalY: opts.globalY, + clickCount: opts.clickCount + }); + const [, input] = await p; + + expect(input.type).to.equal(opts.type); + expect(input.button).to.equal(opts.button); + expect(input.x).to.equal(opts.x); + expect(input.y).to.equal(opts.y); + expect(input.globalX).to.equal(opts.globalX); + expect(input.globalY).to.equal(opts.globalY); + expect(input.clickCount).to.equal(opts.clickCount); + }; + await testBeforeMouse({ + type: 'mouseDown', + button: 'left', + x: 100, + y: 100, + globalX: 200, + globalY: 200, + clickCount: 1 + }); + await testBeforeMouse({ + type: 'mouseUp', + button: 'right', + x: 150, + y: 150, + globalX: 250, + globalY: 250, + clickCount: 2 + }); + await testBeforeMouse({ + type: 'mouseMove', + button: 'middle', + x: 200, + y: 200, + globalX: 300, + globalY: 300, + clickCount: 0 + }); + }); + }); + describe('before-input-event event', () => { afterEach(closeAllWindows); it('can prevent document keyboard events', async () => { diff --git a/spec/fixtures/pages/mouse-events.html b/spec/fixtures/pages/mouse-events.html new file mode 100644 index 0000000000000..51610f4a1e86e --- /dev/null +++ b/spec/fixtures/pages/mouse-events.html @@ -0,0 +1,20 @@ + + + + + + + + \ No newline at end of file From 8275e86f0a55c02b284ec43c5c74688c7864625c Mon Sep 17 00:00:00 2001 From: John Kleinschmidt Date: Thu, 5 Jun 2025 10:51:39 -0400 Subject: [PATCH 088/186] chore: update patches (#47382) --- ...expose_the_built-in_electron_module_via_the_esm_loader.patch | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch index 3fbb7b9faf5c4..dec3592cbdc61 100644 --- a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch +++ b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch @@ -64,7 +64,7 @@ index 5ba13096b98047ff33e4d44167c2a069ccc5e69d..09a332c0999086b30fd952d9456f7889 } } diff --git a/lib/internal/modules/esm/loader.js b/lib/internal/modules/esm/loader.js -index ae03073aff8140b11c63b6c05d831ba573568dba..b70c7cfe40e2eaaeea7b5ad6fcf0aaee87276aa1 100644 +index aff686577df3c366f06f90666e23a03fc376cf53..e8857a151428acd6f8ece74d92774a18accc1e13 100644 --- a/lib/internal/modules/esm/loader.js +++ b/lib/internal/modules/esm/loader.js @@ -492,7 +492,7 @@ class ModuleLoader { From 08e27c02eacc0b3bfccc7dfb304e36443574d093 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 5 Jun 2025 19:12:37 +0200 Subject: [PATCH 089/186] docs: Add Swift/macOS tutorial (#47381) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Felix Rieseberg --- .../native-code-and-electron-swift-macos.md | 1175 +++++++++++++++++ 1 file changed, 1175 insertions(+) create mode 100644 docs/tutorial/native-code-and-electron-swift-macos.md diff --git a/docs/tutorial/native-code-and-electron-swift-macos.md b/docs/tutorial/native-code-and-electron-swift-macos.md new file mode 100644 index 0000000000000..1e11b6ac3d3b1 --- /dev/null +++ b/docs/tutorial/native-code-and-electron-swift-macos.md @@ -0,0 +1,1175 @@ +# Native Code and Electron: Swift (macOS) + +This tutorial builds on the [general introduction to Native Code and Electron](./native-code-and-electron.md) and focuses on creating a native addon for macOS using Swift. + +Swift is a modern, powerful language designed for safety and performance. While you can't use Swift directly with the Node.js N-API as used by Electron, you can create a bridge using Objective-C++ to connect Swift with JavaScript in your Electron application. + +To illustrate how you can embed native macOS code in your Electron app, we'll be building a basic native macOS GUI (using SwiftUI) that communicates with Electron's JavaScript. + +This tutorial will be most useful to those who already have some familiarity with Objective-C, Swift, and SwiftUI development. You should understand basic concepts like Swift syntax, optionals, closures, SwiftUI views, property wrappers, and the Objective-C/Swift interoperability mechanisms such as the `@objc` attribute and bridging headers. + +> [!NOTE] +> If you're not already familiar with these concepts, Apple's [Swift Programming Language Guide](https://docs.swift.org/swift-book/), [SwiftUI Documentation](https://developer.apple.com/documentation/swiftui/), and [Swift and Objective-C Interoperability Guide](https://developer.apple.com/documentation/swift/importing-swift-into-objective-c) are excellent starting points. + +## Requirements + +Just like our [general introduction to Native Code and Electron](./native-code-and-electron.md), this tutorial assumes you have Node.js and npm installed, as well as the basic tools necessary for compiling native code on macOS. You'll need: + +* Xcode installed (available from the Mac App Store) +* Xcode Command Line Tools (can be installed by running `xcode-select --install` in Terminal) + +## 1) Creating a package + +You can re-use the package we created in our [Native Code and Electron](./native-code-and-electron.md) tutorial. This tutorial will not be repeating the steps described there. Let's first setup our basic addon folder structure: + +```txt +swift-native-addon/ +ā”œā”€ā”€ binding.gyp # Build configuration +ā”œā”€ā”€ include/ +│ └── SwiftBridge.h # Objective-C header for the bridge +ā”œā”€ā”€ js/ +│ └── index.js # JavaScript interface +ā”œā”€ā”€ package.json # Package configuration +└── src/ + ā”œā”€ā”€ SwiftCode.swift # Swift implementation + ā”œā”€ā”€ SwiftBridge.m # Objective-C bridge implementation + └── swift_addon.mm # Node.js addon implementation +``` + +Our `package.json` should look like this: + +```json title='package.json' +{ + "name": "swift-macos", + "version": "1.0.0", + "description": "A demo module that exposes Swift code to Electron", + "main": "js/index.js", + "scripts": { + "clean": "rm -rf build", + "build-electron": "electron-rebuild", + "build": "node-gyp configure && node-gyp build" + }, + "license": "MIT", + "dependencies": { + "bindings": "^1.5.0", + "node-addon-api": "^8.3.0" + }, + "devDependencies": { + "node-gyp": "^11.1.0" + } +} +``` + +## 2) Setting Up the Build Configuration + +In our other tutorials focusing on other native languages, we could use `node-gyp` to build the entirety of our code. With Swift, things are a bit more tricky: We need to first build and then link our Swift code. This is because Swift has its own compilation model and runtime requirements that don't directly integrate with node-gyp's C/C++ focused build system. + +The process involves: + +1. Compiling Swift code separately into a static library (.a file) +2. Creating an Objective-C bridge that exposes Swift functionality +3. Linking the compiled Swift library with our Node.js addon +4. Managing Swift runtime dependencies + +This two-step compilation process ensures that Swift's advanced language features and runtime are properly handled while still allowing us to expose the functionality to JavaScript through Node.js's native addon system. + +Let's start by adding a basic structure: + +```json title='binding.gyp' +{ + "targets": [{ + "target_name": "swift_addon", + "conditions": [ + ['OS=="mac"', { + "sources": [ + "src/swift_addon.mm", + "src/SwiftBridge.m", + "src/SwiftCode.swift" + ], + "include_dirs": [ + " + +@interface SwiftBridge : NSObject ++ (NSString*)helloWorld:(NSString*)input; ++ (void)helloGui; + ++ (void)setTodoAddedCallback:(void(^)(NSString* todoJson))callback; ++ (void)setTodoUpdatedCallback:(void(^)(NSString* todoJson))callback; ++ (void)setTodoDeletedCallback:(void(^)(NSString* todoId))callback; +@end + +#endif +``` + +This header defines the Objective-C interface that we'll use to bridge between our Swift code and the Node.js addon. It includes: + +* A simple `helloWorld` method that takes a string input and returns a string +* A `helloGui` method that will display a native SwiftUI interface +* Methods to set callbacks for todo operations (add, update, delete) + +## 4) Implementing the Objective-C Bridge + +Now, let's create the Objective-C bridge itself in `src/SwiftBridge.m`: + +```objc title='src/SwiftBridge.m' +#import "SwiftBridge.h" +#import "swift_addon-Swift.h" +#import + +@implementation SwiftBridge + +static void (^todoAddedCallback)(NSString*); +static void (^todoUpdatedCallback)(NSString*); +static void (^todoDeletedCallback)(NSString*); + ++ (NSString*)helloWorld:(NSString*)input { + return [SwiftCode helloWorld:input]; +} + ++ (void)helloGui { + [SwiftCode helloGui]; +} + ++ (void)setTodoAddedCallback:(void(^)(NSString*))callback { + todoAddedCallback = callback; + [SwiftCode setTodoAddedCallback:callback]; +} + ++ (void)setTodoUpdatedCallback:(void(^)(NSString*))callback { + todoUpdatedCallback = callback; + [SwiftCode setTodoUpdatedCallback:callback]; +} + ++ (void)setTodoDeletedCallback:(void(^)(NSString*))callback { + todoDeletedCallback = callback; + [SwiftCode setTodoDeletedCallback:callback]; +} + +@end +``` + +This bridge: + +* Imports the Swift-generated header (`swift_addon-Swift.h`) +* Implements the methods defined in our header +* Simply forwards calls to the Swift code +* Stores the callbacks for later use in static variables, allowing them to persist throughout the application's lifecycle. This ensures that the JavaScript callbacks can be invoked at any time when todo items are added, updated, or deleted. + +## 5) Implementing the Swift Code + +Now, let's implement our Objective-C code in `src/SwiftCode.swift`. This is where we'll create our native macOS GUI using SwiftUI. + +To make this tutorial easier to follow, we'll start with the basic structure and add features incrementally - step by step. + +### Setting Up the Basic Structure + +Let's start with the basic structure. Here, we're just setting up variables, some basic callback methods, and a simple helper method we'll use later to convert data into formats ready for the JavaScript world. + +```swift title='src/SwiftCode.swift' +import Foundation +import SwiftUI + +@objc +public class SwiftCode: NSObject { + private static var windowController: NSWindowController? + private static var todoAddedCallback: ((String) -> Void)? + private static var todoUpdatedCallback: ((String) -> Void)? + private static var todoDeletedCallback: ((String) -> Void)? + + @objc + public static func helloWorld(_ input: String) -> String { + return "Hello from Swift! You said: \(input)" + } + + @objc + public static func setTodoAddedCallback(_ callback: @escaping (String) -> Void) { + todoAddedCallback = callback + } + + @objc + public static func setTodoUpdatedCallback(_ callback: @escaping (String) -> Void) { + todoUpdatedCallback = callback + } + + @objc + public static func setTodoDeletedCallback(_ callback: @escaping (String) -> Void) { + todoDeletedCallback = callback + } + + private static func encodeToJson(_ item: T) -> String? { + let encoder = JSONEncoder() + + // Encode date as milliseconds since 1970, which is what the JS side expects + encoder.dateEncodingStrategy = .custom { date, encoder in + let milliseconds = Int64(date.timeIntervalSince1970 * 1000) + var container = encoder.singleValueContainer() + try container.encode(milliseconds) + } + + guard let jsonData = try? encoder.encode(item), + let jsonString = String(data: jsonData, encoding: .utf8) else { + return nil + } + return jsonString + } + + // More code to follow... +} +``` + +This first part of our Swift code: + +1. Declares a class with the `@objc` attribute, making it accessible from Objective-C +2. Implements the `helloWorld` method +3. Adds callback setters for todo operations +4. Includes a helper method to encode Swift objects to JSON strings + +### Implementing `helloGui()` + +Let's continue with the `helloGui` method and the SwiftUI implementation. This is where we start adding user interface elements to the screen. + +```swift title='src/SwiftCode.swift' +// Other code... + +@objc +public class SwiftCode: NSObject { + // Other code... + + @objc + public static func helloGui() -> Void { + let contentView = NSHostingView(rootView: ContentView( + onTodoAdded: { todo in + if let jsonString = encodeToJson(todo) { + todoAddedCallback?(jsonString) + } + }, + onTodoUpdated: { todo in + if let jsonString = encodeToJson(todo) { + todoUpdatedCallback?(jsonString) + } + }, + onTodoDeleted: { todoId in + todoDeletedCallback?(todoId.uuidString) + } + )) + let window = NSWindow( + contentRect: NSRect(x: 0, y: 0, width: 500, height: 500), + styleMask: [.titled, .closable, .miniaturizable, .resizable], + backing: .buffered, + defer: false + ) + + window.title = "Todo List" + window.contentView = contentView + window.center() + + windowController = NSWindowController(window: window) + windowController?.showWindow(nil) + + NSApp.activate(ignoringOtherApps: true) + } +} +``` + +This helloGui method: + +1. Creates a SwiftUI view hosted in an `NSHostingView`. This is a crucial bridging component that allows SwiftUI views to be used in AppKit applications. The `NSHostingView` acts as a container that wraps our SwiftUI `ContentView` and handles the translation between SwiftUI's declarative UI system and AppKit's imperative UI system. This enables us to leverage SwiftUI's modern UI framework while still integrating with the traditional macOS window management system. +2. Sets up callbacks to notify JavaScript when todo items change. We'll setup the actual callbacks later, for now we'll just call them if one is available. +3. Creates and displays a native macOS window. +4. Activates the app to bring the window to the front. + +### Implementing the Todo Item + +Next, we'll define a `TodoItem` model with an ID, text, and date. + +```swift title='src/SwiftCode.swift' +// Other code... + +@objc +public class SwiftCode: NSObject { + // Other code... + + private struct TodoItem: Identifiable, Codable { + let id: UUID + var text: String + var date: Date + + init(id: UUID = UUID(), text: String, date: Date) { + self.id = id + self.text = text + self.date = date + } + } +} +``` + +### Implementing the View + +Next, we can implement the actual view. Swift is fairly verbose here, so the code below might look scary if you're new to Swift. The many lines of code obfuscate the simplicity in it - we're just setting up some UI elements. Nothing here is specific to Electron. + +```swift title='src/SwiftCode.swift' +// Other code... + +@objc +public class SwiftCode: NSObject { + // Other code... + + private struct ContentView: View { + @State private var todos: [TodoItem] = [] + @State private var newTodo: String = "" + @State private var newTodoDate: Date = Date() + @State private var editingTodo: UUID? + @State private var editedText: String = "" + @State private var editedDate: Date = Date() + + let onTodoAdded: (TodoItem) -> Void + let onTodoUpdated: (TodoItem) -> Void + let onTodoDeleted: (UUID) -> Void + + private func todoTextField(_ text: Binding, placeholder: String, maxWidth: CGFloat? = nil) -> some View { + TextField(placeholder, text: text) + .textFieldStyle(RoundedBorderTextFieldStyle()) + .frame(maxWidth: maxWidth ?? .infinity) + } + + private func todoDatePicker(_ date: Binding) -> some View { + DatePicker("Due date", selection: date, displayedComponents: [.date]) + .datePickerStyle(CompactDatePickerStyle()) + .labelsHidden() + .frame(width: 100) + .textFieldStyle(RoundedBorderTextFieldStyle()) + } + + var body: some View { + VStack(spacing: 16) { + HStack(spacing: 12) { + todoTextField($newTodo, placeholder: "New todo") + todoDatePicker($newTodoDate) + Button(action: { + if !newTodo.isEmpty { + let todo = TodoItem(text: newTodo, date: newTodoDate) + todos.append(todo) + onTodoAdded(todo) + newTodo = "" + newTodoDate = Date() + } + }) { + Text("Add") + .frame(width: 50) + } + } + .padding(.horizontal, 12) + .padding(.vertical, 8) + + List { + ForEach(todos) { todo in + if editingTodo == todo.id { + HStack(spacing: 12) { + todoTextField($editedText, placeholder: "Edit todo", maxWidth: 250) + todoDatePicker($editedDate) + Button(action: { + if let index = todos.firstIndex(where: { $0.id == todo.id }) { + let updatedTodo = TodoItem(id: todo.id, text: editedText, date: editedDate) + todos[index] = updatedTodo + onTodoUpdated(updatedTodo) + editingTodo = nil + } + }) { + Text("Save") + .frame(width: 60) + } + } + .padding(.vertical, 4) + } else { + HStack(spacing: 12) { + Text(todo.text) + .lineLimit(1) + .truncationMode(.tail) + Spacer() + Text(todo.date.formatted(date: .abbreviated, time: .shortened)) + .foregroundColor(.gray) + Button(action: { + editingTodo = todo.id + editedText = todo.text + editedDate = todo.date + }) { + Image(systemName: "pencil") + } + .buttonStyle(BorderlessButtonStyle()) + Button(action: { + todos.removeAll(where: { $0.id == todo.id }) + onTodoDeleted(todo.id) + }) { + Image(systemName: "trash") + .foregroundColor(.red) + } + .buttonStyle(BorderlessButtonStyle()) + } + .padding(.vertical, 4) + } + } + } + } + } + } +} +``` + +This part of the code: + +* Creates a SwiftUI view with a form to add new todos, featuring a text field for the todo description, a date picker for setting due dates, and an Add button that validates input, creates a new TodoItem, adds it to the local array, triggers the `onTodoAdded` callback to notify JavaScript, and then resets the input fields for the next entry. +* Implements a list to display todos with edit and delete capabilities +* Calls the appropriate callbacks when todos are added, updated, or deleted + +The final file should look as follows: + +```swift title='src/SwiftCode.swift' +import Foundation +import SwiftUI + +@objc +public class SwiftCode: NSObject { + private static var windowController: NSWindowController? + private static var todoAddedCallback: ((String) -> Void)? + private static var todoUpdatedCallback: ((String) -> Void)? + private static var todoDeletedCallback: ((String) -> Void)? + + @objc + public static func helloWorld(_ input: String) -> String { + return "Hello from Swift! You said: \(input)" + } + + @objc + public static func setTodoAddedCallback(_ callback: @escaping (String) -> Void) { + todoAddedCallback = callback + } + + @objc + public static func setTodoUpdatedCallback(_ callback: @escaping (String) -> Void) { + todoUpdatedCallback = callback + } + + @objc + public static func setTodoDeletedCallback(_ callback: @escaping (String) -> Void) { + todoDeletedCallback = callback + } + + private static func encodeToJson(_ item: T) -> String? { + let encoder = JSONEncoder() + + // Encode date as milliseconds since 1970, which is what the JS side expects + encoder.dateEncodingStrategy = .custom { date, encoder in + let milliseconds = Int64(date.timeIntervalSince1970 * 1000) + var container = encoder.singleValueContainer() + try container.encode(milliseconds) + } + + guard let jsonData = try? encoder.encode(item), + let jsonString = String(data: jsonData, encoding: .utf8) else { + return nil + } + return jsonString + } + + @objc + public static func helloGui() -> Void { + let contentView = NSHostingView(rootView: ContentView( + onTodoAdded: { todo in + if let jsonString = encodeToJson(todo) { + todoAddedCallback?(jsonString) + } + }, + onTodoUpdated: { todo in + if let jsonString = encodeToJson(todo) { + todoUpdatedCallback?(jsonString) + } + }, + onTodoDeleted: { todoId in + todoDeletedCallback?(todoId.uuidString) + } + )) + let window = NSWindow( + contentRect: NSRect(x: 0, y: 0, width: 500, height: 500), + styleMask: [.titled, .closable, .miniaturizable, .resizable], + backing: .buffered, + defer: false + ) + + window.title = "Todo List" + window.contentView = contentView + window.center() + + windowController = NSWindowController(window: window) + windowController?.showWindow(nil) + + NSApp.activate(ignoringOtherApps: true) + } + + private struct TodoItem: Identifiable, Codable { + let id: UUID + var text: String + var date: Date + + init(id: UUID = UUID(), text: String, date: Date) { + self.id = id + self.text = text + self.date = date + } + } + + private struct ContentView: View { + @State private var todos: [TodoItem] = [] + @State private var newTodo: String = "" + @State private var newTodoDate: Date = Date() + @State private var editingTodo: UUID? + @State private var editedText: String = "" + @State private var editedDate: Date = Date() + + let onTodoAdded: (TodoItem) -> Void + let onTodoUpdated: (TodoItem) -> Void + let onTodoDeleted: (UUID) -> Void + + private func todoTextField(_ text: Binding, placeholder: String, maxWidth: CGFloat? = nil) -> some View { + TextField(placeholder, text: text) + .textFieldStyle(RoundedBorderTextFieldStyle()) + .frame(maxWidth: maxWidth ?? .infinity) + } + + private func todoDatePicker(_ date: Binding) -> some View { + DatePicker("Due date", selection: date, displayedComponents: [.date]) + .datePickerStyle(CompactDatePickerStyle()) + .labelsHidden() + .frame(width: 100) + .textFieldStyle(RoundedBorderTextFieldStyle()) + } + + var body: some View { + VStack(spacing: 16) { + HStack(spacing: 12) { + todoTextField($newTodo, placeholder: "New todo") + todoDatePicker($newTodoDate) + Button(action: { + if !newTodo.isEmpty { + let todo = TodoItem(text: newTodo, date: newTodoDate) + todos.append(todo) + onTodoAdded(todo) + newTodo = "" + newTodoDate = Date() + } + }) { + Text("Add") + .frame(width: 50) + } + } + .padding(.horizontal, 12) + .padding(.vertical, 8) + + List { + ForEach(todos) { todo in + if editingTodo == todo.id { + HStack(spacing: 12) { + todoTextField($editedText, placeholder: "Edit todo", maxWidth: 250) + todoDatePicker($editedDate) + Button(action: { + if let index = todos.firstIndex(where: { $0.id == todo.id }) { + let updatedTodo = TodoItem(id: todo.id, text: editedText, date: editedDate) + todos[index] = updatedTodo + onTodoUpdated(updatedTodo) + editingTodo = nil + } + }) { + Text("Save") + .frame(width: 60) + } + } + .padding(.vertical, 4) + } else { + HStack(spacing: 12) { + Text(todo.text) + .lineLimit(1) + .truncationMode(.tail) + Spacer() + Text(todo.date.formatted(date: .abbreviated, time: .shortened)) + .foregroundColor(.gray) + Button(action: { + editingTodo = todo.id + editedText = todo.text + editedDate = todo.date + }) { + Image(systemName: "pencil") + } + .buttonStyle(BorderlessButtonStyle()) + Button(action: { + todos.removeAll(where: { $0.id == todo.id }) + onTodoDeleted(todo.id) + }) { + Image(systemName: "trash") + .foregroundColor(.red) + } + .buttonStyle(BorderlessButtonStyle()) + } + .padding(.vertical, 4) + } + } + } + } + } + } +} +``` + +## 6) Creating the Node.js Addon Bridge + +We now have working Objective-C code, which in turn is able to call working Swift code. To make sure it can be safely and properly called from the JavaScript world, we need to build a bridge between Objective-C and C++, which we can do with Objective-C++. We'll do that in `src/swift_addon.mm`. + +```objc title='src/swift_addon.mm' +#import +#import "SwiftBridge.h" +#include + +class SwiftAddon : public Napi::ObjectWrap { +public: + static Napi::Object Init(Napi::Env env, Napi::Object exports) { + Napi::Function func = DefineClass(env, "SwiftAddon", { + InstanceMethod("helloWorld", &SwiftAddon::HelloWorld), + InstanceMethod("helloGui", &SwiftAddon::HelloGui), + InstanceMethod("on", &SwiftAddon::On) + }); + + Napi::FunctionReference* constructor = new Napi::FunctionReference(); + *constructor = Napi::Persistent(func); + env.SetInstanceData(constructor); + + exports.Set("SwiftAddon", func); + return exports; + } + + // More code to follow... +``` + +This first part: + +1. Defines a C++ class that inherits from `Napi::ObjectWrap` +2. Creates a static `Init` method to register our class with Node.js +3. Defines three methods: `helloWorld`, `helloGui`, and `on` + +### Callback Mechanism + +Next, let's implement the callback mechanism: + +```objc title='src/swift_addon.mm' +// Previous code... + + struct CallbackData { + std::string eventType; + std::string payload; + SwiftAddon* addon; + }; + + SwiftAddon(const Napi::CallbackInfo& info) + : Napi::ObjectWrap(info) + , env_(info.Env()) + , emitter(Napi::Persistent(Napi::Object::New(info.Env()))) + , callbacks(Napi::Persistent(Napi::Object::New(info.Env()))) + , tsfn_(nullptr) { + + napi_status status = napi_create_threadsafe_function( + env_, + nullptr, + nullptr, + Napi::String::New(env_, "SwiftCallback"), + 0, + 1, + nullptr, + nullptr, + this, + [](napi_env env, napi_value js_callback, void* context, void* data) { + auto* callbackData = static_cast(data); + if (!callbackData) return; + + Napi::Env napi_env(env); + Napi::HandleScope scope(napi_env); + + auto addon = static_cast(context); + if (!addon) { + delete callbackData; + return; + } + + try { + auto callback = addon->callbacks.Value().Get(callbackData->eventType).As(); + if (callback.IsFunction()) { + callback.Call(addon->emitter.Value(), {Napi::String::New(napi_env, callbackData->payload)}); + } + } catch (...) {} + + delete callbackData; + }, + &tsfn_ + ); + + if (status != napi_ok) { + Napi::Error::New(env_, "Failed to create threadsafe function").ThrowAsJavaScriptException(); + return; + } +``` + +This part: + +1. Defines a struct to pass data between threads +2. Sets up a constructor for our addon +3. Creates a threadsafe function to handle callbacks from Swift + +Let's continue with setting up the Swift callbacks: + +```objc title='src/swift_addon.mm' +// Previous code... + + auto makeCallback = [this](const char* eventType) { + return ^(NSString* payload) { + if (tsfn_ != nullptr) { + auto* data = new CallbackData{ + eventType, + std::string([payload UTF8String]), + this + }; + napi_call_threadsafe_function(tsfn_, data, napi_tsfn_blocking); + } + }; + }; + + [SwiftBridge setTodoAddedCallback:makeCallback("todoAdded")]; + [SwiftBridge setTodoUpdatedCallback:makeCallback("todoUpdated")]; + [SwiftBridge setTodoDeletedCallback:makeCallback("todoDeleted")]; + } + + ~SwiftAddon() { + if (tsfn_ != nullptr) { + napi_release_threadsafe_function(tsfn_, napi_tsfn_release); + tsfn_ = nullptr; + } + } +``` + +This part: + +1. Creates a helper function to generate Objective-C blocks that will be used as callbacks for Swift events. This lambda function `makeCallback` takes an event type string and returns an Objective-C block that captures the event type and payload. When Swift calls this block, it creates a CallbackData structure with the event information and passes it to the threadsafe function, which safely bridges between Swift's thread and Node.js's event loop. +2. Sets up the carefully constructed callbacks for todo operations +3. Implements a destructor to clean up resources + +### Instance Methods + +Finally, let's implement the instance methods: + +```objc title='src/swift_addon.mm' +// Previous code... + +private: + Napi::Env env_; + Napi::ObjectReference emitter; + Napi::ObjectReference callbacks; + napi_threadsafe_function tsfn_; + + Napi::Value HelloWorld(const Napi::CallbackInfo& info) { + Napi::Env env = info.Env(); + + if (info.Length() < 1 || !info[0].IsString()) { + Napi::TypeError::New(env, "Expected string argument").ThrowAsJavaScriptException(); + return env.Null(); + } + + std::string input = info[0].As(); + NSString* nsInput = [NSString stringWithUTF8String:input.c_str()]; + NSString* result = [SwiftBridge helloWorld:nsInput]; + + return Napi::String::New(env, [result UTF8String]); + } + + void HelloGui(const Napi::CallbackInfo& info) { + [SwiftBridge helloGui]; + } + + Napi::Value On(const Napi::CallbackInfo& info) { + Napi::Env env = info.Env(); + + if (info.Length() < 2 || !info[0].IsString() || !info[1].IsFunction()) { + Napi::TypeError::New(env, "Expected (string, function) arguments").ThrowAsJavaScriptException(); + return env.Undefined(); + } + + callbacks.Value().Set(info[0].As(), info[1].As()); + return env.Undefined(); + } +}; + +Napi::Object Init(Napi::Env env, Napi::Object exports) { + return SwiftAddon::Init(env, exports); +} + +NODE_API_MODULE(swift_addon, Init) +``` + +This final part does multiple things: + +1. The code defines private member variables for the environment, event emitter, callback storage, and thread-safe function that are essential for the addon's operation. +2. The HelloWorld method implementation takes a string input from JavaScript, passes it to the Swift code, and returns the processed result back to the JavaScript environment. +3. The `HelloGui` method implementation provides a simple wrapper that calls the Swift UI creation function to display the native macOS window. +4. The `On` method implementation allows JavaScript code to register callback functions that will be invoked when specific events occur in the native Swift code. +5. The code sets up the module initialization process that registers the addon with Node.js and makes its functionality available to JavaScript. + +The final and full `src/swift_addon.mm` should look like: + +```objc title='src/swift_addon.mm' +#import +#import "SwiftBridge.h" +#include + +class SwiftAddon : public Napi::ObjectWrap { +public: + static Napi::Object Init(Napi::Env env, Napi::Object exports) { + Napi::Function func = DefineClass(env, "SwiftAddon", { + InstanceMethod("helloWorld", &SwiftAddon::HelloWorld), + InstanceMethod("helloGui", &SwiftAddon::HelloGui), + InstanceMethod("on", &SwiftAddon::On) + }); + + Napi::FunctionReference* constructor = new Napi::FunctionReference(); + *constructor = Napi::Persistent(func); + env.SetInstanceData(constructor); + + exports.Set("SwiftAddon", func); + return exports; + } + + struct CallbackData { + std::string eventType; + std::string payload; + SwiftAddon* addon; + }; + + SwiftAddon(const Napi::CallbackInfo& info) + : Napi::ObjectWrap(info) + , env_(info.Env()) + , emitter(Napi::Persistent(Napi::Object::New(info.Env()))) + , callbacks(Napi::Persistent(Napi::Object::New(info.Env()))) + , tsfn_(nullptr) { + + napi_status status = napi_create_threadsafe_function( + env_, + nullptr, + nullptr, + Napi::String::New(env_, "SwiftCallback"), + 0, + 1, + nullptr, + nullptr, + this, + [](napi_env env, napi_value js_callback, void* context, void* data) { + auto* callbackData = static_cast(data); + if (!callbackData) return; + + Napi::Env napi_env(env); + Napi::HandleScope scope(napi_env); + + auto addon = static_cast(context); + if (!addon) { + delete callbackData; + return; + } + + try { + auto callback = addon->callbacks.Value().Get(callbackData->eventType).As(); + if (callback.IsFunction()) { + callback.Call(addon->emitter.Value(), {Napi::String::New(napi_env, callbackData->payload)}); + } + } catch (...) {} + + delete callbackData; + }, + &tsfn_ + ); + + if (status != napi_ok) { + Napi::Error::New(env_, "Failed to create threadsafe function").ThrowAsJavaScriptException(); + return; + } + + auto makeCallback = [this](const char* eventType) { + return ^(NSString* payload) { + if (tsfn_ != nullptr) { + auto* data = new CallbackData{ + eventType, + std::string([payload UTF8String]), + this + }; + napi_call_threadsafe_function(tsfn_, data, napi_tsfn_blocking); + } + }; + }; + + [SwiftBridge setTodoAddedCallback:makeCallback("todoAdded")]; + [SwiftBridge setTodoUpdatedCallback:makeCallback("todoUpdated")]; + [SwiftBridge setTodoDeletedCallback:makeCallback("todoDeleted")]; + } + + ~SwiftAddon() { + if (tsfn_ != nullptr) { + napi_release_threadsafe_function(tsfn_, napi_tsfn_release); + tsfn_ = nullptr; + } + } + +private: + Napi::Env env_; + Napi::ObjectReference emitter; + Napi::ObjectReference callbacks; + napi_threadsafe_function tsfn_; + + Napi::Value HelloWorld(const Napi::CallbackInfo& info) { + Napi::Env env = info.Env(); + + if (info.Length() < 1 || !info[0].IsString()) { + Napi::TypeError::New(env, "Expected string argument").ThrowAsJavaScriptException(); + return env.Null(); + } + + std::string input = info[0].As(); + NSString* nsInput = [NSString stringWithUTF8String:input.c_str()]; + NSString* result = [SwiftBridge helloWorld:nsInput]; + + return Napi::String::New(env, [result UTF8String]); + } + + void HelloGui(const Napi::CallbackInfo& info) { + [SwiftBridge helloGui]; + } + + Napi::Value On(const Napi::CallbackInfo& info) { + Napi::Env env = info.Env(); + + if (info.Length() < 2 || !info[0].IsString() || !info[1].IsFunction()) { + Napi::TypeError::New(env, "Expected (string, function) arguments").ThrowAsJavaScriptException(); + return env.Undefined(); + } + + callbacks.Value().Set(info[0].As(), info[1].As()); + return env.Undefined(); + } +}; + +Napi::Object Init(Napi::Env env, Napi::Object exports) { + return SwiftAddon::Init(env, exports); +} + +NODE_API_MODULE(swift_addon, Init) +``` + +## 6) Creating a JavaScript Wrapper + +You're so close! We now have working Objective-C, Swift, and thread-safe ways to expose methods and events to JavaScript. In this final step, let's create a JavaScript wrapper in `js/index.js` to provide a more friendly API: + +```js title='js/index.js' @ts-expect-error=[10] +const EventEmitter = require('events') + +class SwiftAddon extends EventEmitter { + constructor () { + super() + + if (process.platform !== 'darwin') { + throw new Error('This module is only available on macOS') + } + + const native = require('bindings')('swift_addon') + this.addon = new native.SwiftAddon() + + this.addon.on('todoAdded', (payload) => { + this.emit('todoAdded', this.parse(payload)) + }) + + this.addon.on('todoUpdated', (payload) => { + this.emit('todoUpdated', this.parse(payload)) + }) + + this.addon.on('todoDeleted', (payload) => { + this.emit('todoDeleted', this.parse(payload)) + }) + } + + helloWorld (input = '') { + return this.addon.helloWorld(input) + } + + helloGui () { + this.addon.helloGui() + } + + parse (payload) { + const parsed = JSON.parse(payload) + + return { ...parsed, date: new Date(parsed.date) } + } +} + +if (process.platform === 'darwin') { + module.exports = new SwiftAddon() +} else { + module.exports = {} +} +``` + +This wrapper: + +1. Extends EventEmitter to provide event support +2. Checks if we're running on macOS +3. Loads the native addon +4. Sets up event listeners and forwards them +5. Provides a clean API for our functions +6. Parses JSON payloads and converts timestamps to JavaScript Date objects + +## 7) Building and Testing the Addon + +With all files in place, you can build the addon: + +```sh +npm run build +``` + +Please note that you _cannot_ call this script from Node.js directly, since Node.js doesn't set up an "app" in the eyes of macOS. Electron does though, so you can test your code by requiring and calling it from Electron. + +## Conclusion + +You've now built a complete native Node.js addon for macOS using Swift and SwiftUI. This provides a foundation for building more complex macOS-specific features in your Electron apps, giving you the best of both worlds: the ease of web technologies with the power of native macOS code. + +The approach demonstrated here allows you to: + +* Setting up a project structure that bridges Swift, Objective-C, and JavaScript +* Implementing Swift code with SwiftUI for native UI +* Creating an Objective-C bridge to connect Swift with Node.js +* Setting up bidirectional communication using callbacks and events +* Configuring a custom build process to compile Swift code + +For more information on developing with Swift and Swift, refer to Apple's developer documentation: + +* [Swift Programming Language](https://developer.apple.com/swift/) +* [SwiftUI Framework](https://developer.apple.com/documentation/swiftui) +* [macOS Human Interface Guidelines](https://developer.apple.com/design/human-interface-guidelines/macos) +* [Swift and Objective-C Interoperability Guide](https://developer.apple.com/documentation/swift/importing-swift-into-objective-c) From f1f7bd631fcfe8121fc9a76b0ebe6ff34b7e0df6 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 5 Jun 2025 20:11:30 +0200 Subject: [PATCH 090/186] docs: mention Azure Trusted Signing (#47384) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Niklas Wenzel --- docs/tutorial/code-signing.md | 37 ++++++++++++++++++++++++++++++----- 1 file changed, 32 insertions(+), 5 deletions(-) diff --git a/docs/tutorial/code-signing.md b/docs/tutorial/code-signing.md index 880b36f16f53e..d0eff31e5fe38 100644 --- a/docs/tutorial/code-signing.md +++ b/docs/tutorial/code-signing.md @@ -78,6 +78,8 @@ See the [Mac App Store Guide][]. ## Signing Windows builds +### Using traditional certificates + Before you can code sign your application, you need to acquire a code signing certificate. Unlike Apple, Microsoft allows developers to purchase those certificates on the open market. They are usually sold by the same companies @@ -117,13 +119,13 @@ expose configuration options through a `windowsSign` property. You can either us to sign files directly - or use the same `windowsSign` configuration across Electron Forge, [`@electron/packager`][], [`electron-winstaller`][], and [`electron-wix-msi`][]. -### Using Electron Forge +#### Using Electron Forge Electron Forge is the recommended way to sign your app as well as your `Squirrel.Windows` and `WiX MSI` installers. Detailed instructions on how to configure your application can be found in the [Electron Forge Code Signing Tutorial](https://www.electronforge.io/guides/code-signing/code-signing-windows). -### Using Electron Packager +#### Using Electron Packager If you're not using an integrated build pipeline like Forge, you are likely using [`@electron/packager`][], which includes [`@electron/windows-sign`][]. @@ -146,7 +148,7 @@ packager({ }) ``` -### Using electron-winstaller (Squirrel.Windows) +#### Using electron-winstaller (Squirrel.Windows) [`electron-winstaller`][] is a package that can generate Squirrel.Windows installers for your Electron app. This is the tool used under the hood by Electron Forge's @@ -178,7 +180,7 @@ try { For full configuration options, check out the [`electron-winstaller`][] repository! -### Using electron-wix-msi (WiX MSI) +#### Using electron-wix-msi (WiX MSI) [`electron-wix-msi`][] is a package that can generate MSI installers for your Electron app. This is the tool used under the hood by Electron Forge's [MSI Maker][maker-msi]. @@ -221,11 +223,32 @@ await msiCreator.compile() For full configuration options, check out the [`electron-wix-msi`][] repository! -### Using Electron Builder +#### Using Electron Builder Electron Builder comes with a custom solution for signing your application. You can find [its documentation here](https://www.electron.build/code-signing). +### Using Azure Trusted Signing + +[Azure Trusted Signing][] is Microsoft's modern cloud-based alternative to EV certificates. +It is the cheapest option for code signing on Windows, and it gets rid of SmartScreen warnings. + +As of May 2025, Azure Trusted Signing is [available][trusted-signing-availability] to US and +Canada-based organizations with 3+ years of verifiable business history. Microsoft is looking +to make the program more widely available. If you're reading this at a later point, it could +make sense to check if the eligibility criteria have changed. + +#### Using Electron Forge + +Electron Forge is the recommended way to sign your app as well as your `Squirrel.Windows` +and `WiX MSI` installers. Instructions for Azure Trusted Signing can be found +[here][forge-trusted-signing]. + +#### Using Electron Builder + +The Electron Builder documentation for Azure Trusted Signing can be found +[here][builder-trusted-signing]. + ### Signing Windows Store applications See the [Windows Store Guide][]. @@ -243,3 +266,7 @@ See the [Windows Store Guide][]. [windows store guide]: ./windows-store-guide.md [maker-squirrel]: https://www.electronforge.io/config/makers/squirrel.windows [maker-msi]: https://www.electronforge.io/config/makers/wix-msi +[azure trusted signing]: https://azure.microsoft.com/en-us/products/trusted-signing +[trusted-signing-availability]: https://techcommunity.microsoft.com/blog/microsoft-security-blog/trusted-signing-public-preview-update/4399713 +[forge-trusted-signing]: https://www.electronforge.io/guides/code-signing/code-signing-windows#using-azure-trusted-signing +[builder-trusted-signing]: https://www.electron.build/code-signing-win#using-azure-trusted-signing-beta From b875976f04ba430b3f362f88bfb83d8b55790144 Mon Sep 17 00:00:00 2001 From: John Kleinschmidt Date: Sat, 7 Jun 2025 01:59:03 -0400 Subject: [PATCH 091/186] build: cache gitcache dir (#47396) build: cache gitcache dir (#47328) * revert build: migrate to new chromium git auth * build: cache gitcache dir --- .github/actions/build-git-cache/action.yml | 83 +++++++++++++++++++ .github/actions/checkout/action.yml | 16 +++- .../actions/set-chromium-cookie/action.yml | 58 +++++++++++++ .../set-chromium-git-helper/action.yml | 41 --------- .github/workflows/build-git-cache.yml | 74 +++++++++++++++++ .github/workflows/build.yml | 10 +-- .github/workflows/linux-publish.yml | 3 +- .github/workflows/macos-publish.yml | 3 +- .github/workflows/pipeline-electron-lint.yml | 7 +- .../pipeline-segment-electron-build.yml | 8 +- .../pipeline-segment-electron-gn-check.yml | 4 +- .../pipeline-segment-electron-test.yml | 8 +- .../pipeline-segment-node-nan-test.yml | 11 ++- .github/workflows/windows-publish.yml | 3 +- 14 files changed, 254 insertions(+), 75 deletions(-) create mode 100644 .github/actions/build-git-cache/action.yml create mode 100644 .github/actions/set-chromium-cookie/action.yml delete mode 100644 .github/actions/set-chromium-git-helper/action.yml create mode 100644 .github/workflows/build-git-cache.yml diff --git a/.github/actions/build-git-cache/action.yml b/.github/actions/build-git-cache/action.yml new file mode 100644 index 0000000000000..6a50666a50fbd --- /dev/null +++ b/.github/actions/build-git-cache/action.yml @@ -0,0 +1,83 @@ +name: 'Build Git Cache' +description: 'Runs a gclient sync to build the git cache for Electron' +inputs: + target-platform: + description: 'Target platform, should be linux, win, macos' +runs: + using: "composite" + steps: + - name: Set GIT_CACHE_PATH to make gclient to use the cache + shell: bash + run: | + echo "GIT_CACHE_PATH=$(pwd)/git-cache" >> $GITHUB_ENV + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie + - name: Install Build Tools + uses: ./src/electron/.github/actions/install-build-tools + - name: Set up cache drive + shell: bash + run: | + if [ "${{ inputs.target-platform }}" = "win" ]; then + echo "CACHE_DRIVE=/mnt/win-cache" >> $GITHUB_ENV + else + echo "CACHE_DRIVE=/mnt/cross-instance-cache" >> $GITHUB_ENV + fi + - name: Check cross instance cache disk space + shell: bash + run: | + # if there is less than 35 GB free space then creating the cache might fail so exit early + freespace=`df -m $CACHE_DRIVE | grep -w $CACHE_DRIVE | awk '{print $4}'` + freespace_human=`df -h $CACHE_DRIVE | grep -w $CACHE_DRIVE | awk '{print $4}'` + if [ $freespace -le 35000 ]; then + echo "The cross mount cache has $freespace_human free space which is not enough - exiting" + exit 1 + else + echo "The cross mount cache has $freespace_human free space - continuing" + fi + - name: Restore gitcache + shell: bash + run: | + GIT_CACHE_TAR="$CACHE_DRIVE/gitcache.tar" + if [ ! -f "$GIT_CACHE_TAR" ]; then + echo "Git cache tar file does not exist, skipping restore" + exit 0 + fi + echo "Restoring git cache from $GIT_CACHE_TAR to $GIT_CACHE_PATH" + mkdir -p $GIT_CACHE_PATH + tar -xf $GIT_CACHE_TAR -C $GIT_CACHE_PATH + - name: Gclient Sync + shell: bash + run: | + e d gclient config \ + --name "src/electron" \ + --unmanaged \ + ${GCLIENT_EXTRA_ARGS} \ + "$GITHUB_SERVER_URL/$GITHUB_REPOSITORY" + + if [ "$TARGET_OS" != "" ]; then + echo "target_os=['$TARGET_OS']" >> ./.gclient + fi + + ELECTRON_USE_THREE_WAY_MERGE_FOR_PATCHES=1 e d gclient sync --with_branch_heads --with_tags --nohooks -vv + - name: Compress Git Cache Directory + shell: bash + run: | + echo "Uncompressed gitcache size: $(du -sh $GIT_CACHE_PATH | cut -f1 -d' ')" + cd $GIT_CACHE_PATH + tar -cf ../gitcache.tar . + cd .. + echo "Compressed gitcache to $(du -sh gitcache.tar | cut -f1 -d' ')" + # remove the old cache file if it exists + if [ -f $CACHE_DRIVE/gitcache.tar ]; then + echo "Removing old gitcache.tar from $CACHE_DRIVE" + rm $CACHE_DRIVE/gitcache.tar + fi + cp ./gitcache.tar $CACHE_DRIVE/ + - name: Wait for active SSH sessions + shell: bash + if: always() && !cancelled() + run: | + while [ -f /var/.ssh-lock ] + do + sleep 60 + done diff --git a/.github/actions/checkout/action.yml b/.github/actions/checkout/action.yml index 7cfbd542c1b60..49a08eead649d 100644 --- a/.github/actions/checkout/action.yml +++ b/.github/actions/checkout/action.yml @@ -20,8 +20,8 @@ runs: echo "GIT_CACHE_PATH=$(pwd)/git-cache" >> $GITHUB_ENV - name: Install Dependencies uses: ./src/electron/.github/actions/install-dependencies - - name: Set Chromium Git Helper - uses: ./src/electron/.github/actions/set-chromium-git-helper + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Generate DEPS Hash @@ -83,6 +83,18 @@ runs: - name: Add patch conflict problem matcher shell: bash run: echo "::add-matcher::src/electron/.github/problem-matchers/patch-conflict.json" + - name: Restore gitcache + if: steps.check-cache.outputs.cache_exists == 'false' + shell: bash + run: | + GIT_CACHE_TAR="$CACHE_DRIVE/gitcache.tar" + if [ ! -f "$GIT_CACHE_TAR" ]; then + echo "Git cache tar file does not exist, skipping restore" + exit 0 + fi + echo "Restoring git cache from $GIT_CACHE_TAR to $GIT_CACHE_PATH" + mkdir -p $GIT_CACHE_PATH + tar -xf $GIT_CACHE_TAR -C $GIT_CACHE_PATH - name: Gclient Sync if: steps.check-cache.outputs.cache_exists == 'false' shell: bash diff --git a/.github/actions/set-chromium-cookie/action.yml b/.github/actions/set-chromium-cookie/action.yml new file mode 100644 index 0000000000000..2011655e29b59 --- /dev/null +++ b/.github/actions/set-chromium-cookie/action.yml @@ -0,0 +1,58 @@ +name: 'Set Chromium Git Cookie' +description: 'Sets an authenticated cookie from Chromium to allow for a higher request limit' +runs: + using: "composite" + steps: + - name: Set the git cookie from chromium.googlesource.com (Unix) + if: ${{ runner.os != 'Windows' }} + shell: bash + run: | + if [[ -z "${{ env.CHROMIUM_GIT_COOKIE }}" ]]; then + echo "CHROMIUM_GIT_COOKIE is not set - cannot authenticate." + exit 0 + fi + + eval 'set +o history' 2>/dev/null || setopt HIST_IGNORE_SPACE 2>/dev/null + touch ~/.gitcookies + chmod 0600 ~/.gitcookies + + git config --global http.cookiefile ~/.gitcookies + + tr , \\t <<\__END__ >>~/.gitcookies + ${{ env.CHROMIUM_GIT_COOKIE }} + __END__ + eval 'set -o history' 2>/dev/null || unsetopt HIST_IGNORE_SPACE 2>/dev/null + + RESPONSE=$(curl -s -b ~/.gitcookies https://chromium-review.googlesource.com/a/accounts/self) + if [[ $RESPONSE == ")]}'"* ]]; then + # Extract account email for verification + EMAIL=$(echo "$RESPONSE" | tail -c +5 | jq -r '.email // "No email found"') + echo "Cookie authentication successful - authenticated as: $EMAIL" + else + echo "Cookie authentication failed - ensure CHROMIUM_GIT_COOKIE is set correctly" + echo $RESPONSE + fi + - name: Set the git cookie from chromium.googlesource.com (Windows) + if: ${{ runner.os == 'Windows' }} + shell: cmd + run: | + if "%CHROMIUM_GIT_COOKIE_WINDOWS_STRING%"=="" ( + echo CHROMIUM_GIT_COOKIE_WINDOWS_STRING is not set - cannot authenticate. + exit /b 0 + ) + + git config --global http.cookiefile "%USERPROFILE%\.gitcookies" + powershell -noprofile -nologo -command Write-Output "${{ env.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }}" >>"%USERPROFILE%\.gitcookies" + + curl -s -b "%USERPROFILE%\.gitcookies" https://chromium-review.googlesource.com/a/accounts/self > response.txt + + findstr /B /C:")]}'" response.txt > nul + if %ERRORLEVEL% EQU 0 ( + echo Cookie authentication successful + powershell -NoProfile -Command "& {$content = Get-Content -Raw response.txt; $content = $content.Substring(4); try { $json = ConvertFrom-Json $content; if($json.email) { Write-Host 'Authenticated as:' $json.email } else { Write-Host 'No email found in response' } } catch { Write-Host 'Error parsing JSON:' $_ }}" + ) else ( + echo Cookie authentication failed - ensure CHROMIUM_GIT_COOKIE_WINDOWS_STRING is set correctly + type response.txt + ) + + del response.txt diff --git a/.github/actions/set-chromium-git-helper/action.yml b/.github/actions/set-chromium-git-helper/action.yml deleted file mode 100644 index bdc0ceb303d25..0000000000000 --- a/.github/actions/set-chromium-git-helper/action.yml +++ /dev/null @@ -1,41 +0,0 @@ -name: 'Set Chromium Git Helper' -description: 'Sets Chromium Git Helper to allow for a higher request limit' -runs: - using: "composite" - steps: - - name: Save the chromium git credentials to a file - shell: bash - run: | - if [[ -z "${{ env.CHROMIUM_GIT_AUTH }}" ]]; then - echo "CHROMIUM_GIT_AUTH is not set - cannot authenticate." - exit 0 - fi - if [[ "${{ runner.os }}" != "Windows" ]]; then - cd $HOME - fi - echo "${{ env.CHROMIUM_GIT_AUTH }}" > .chromium_git_auth - - - name: Set the chromium git helper to use auth from a file - shell: bash - run: | - if [[ "${{ runner.os }}" == "Windows" ]]; then - if [[ ! -f "/c/actions-runner/_work/electron/electron/.chromium_git_auth" ]]; then - echo "File /c/actions-runner/_work/electron/electron/.chromium_git_auth does not exist - cannot authenticate." - exit 0 - fi - else - if [[ ! -f "$HOME/.chromium_git_auth" ]]; then - echo "File $HOME/.chromium_git_auth does not exist - cannot authenticate." - exit 0 - fi - fi - if [[ -z "${{ env.CHROMIUM_GIT_USER }}" ]]; then - echo "CHROMIUM_GIT_USER is not set - cannot authenticate." - exit 0 - fi - git config --global credential.https://chromium.googlesource.com.username "${{ env.CHROMIUM_GIT_USER }}" - if [[ "${{ runner.os }}" == "Windows" ]]; then - git config --global credential.https://chromium.googlesource.com.helper '!f() { test "$1" = get && echo "password=$(cat /c/actions-runner/_work/electron/electron/.chromium_git_auth)"; }; f' - else - git config --global credential.https://chromium.googlesource.com.helper '!f() { test "$1" = get && echo "password=$(cat $HOME/.chromium_git_auth)"; }; f' - fi diff --git a/.github/workflows/build-git-cache.yml b/.github/workflows/build-git-cache.yml new file mode 100644 index 0000000000000..0fddbd4522a58 --- /dev/null +++ b/.github/workflows/build-git-cache.yml @@ -0,0 +1,74 @@ +name: Build Git Cache +# This workflow updates git cache on the cross-instance cache volumes +# It runs daily at midnight. + +on: + schedule: + - cron: "0 0 * * *" + +jobs: + build-git-cache-linux: + runs-on: electron-arc-linux-amd64-32core + container: + image: ghcr.io/electron/build:bc2f48b2415a670de18d13605b1cf0eb5fdbaae1 + options: --user root + volumes: + - /mnt/cross-instance-cache:/mnt/cross-instance-cache + env: + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + GCLIENT_EXTRA_ARGS: '--custom-var=checkout_arm=True --custom-var=checkout_arm64=True' + steps: + - name: Checkout Electron + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + path: src/electron + fetch-depth: 0 + - name: Build Git Cache + uses: ./src/electron/.github/actions/build-git-cache + with: + target-platform: linux + + build-git-cache-windows: + runs-on: electron-arc-linux-amd64-32core + container: + image: ghcr.io/electron/build:bc2f48b2415a670de18d13605b1cf0eb5fdbaae1 + options: --user root --device /dev/fuse --cap-add SYS_ADMIN + volumes: + - /mnt/win-cache:/mnt/win-cache + env: + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + GCLIENT_EXTRA_ARGS: '--custom-var=checkout_win=True' + TARGET_OS: 'win' + steps: + - name: Checkout Electron + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + path: src/electron + fetch-depth: 0 + - name: Build Git Cache + uses: ./src/electron/.github/actions/build-git-cache + with: + target-platform: win + + build-git-cache-macos: + runs-on: electron-arc-linux-amd64-32core + # This job updates the same git cache as linux, so it needs to run after the linux one. + needs: build-git-cache-linux + container: + image: ghcr.io/electron/build:bc2f48b2415a670de18d13605b1cf0eb5fdbaae1 + options: --user root + volumes: + - /mnt/cross-instance-cache:/mnt/cross-instance-cache + env: + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + GCLIENT_EXTRA_ARGS: '--custom-var=checkout_mac=True --custom-var=host_os=mac' + steps: + - name: Checkout Electron + uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 + with: + path: src/electron + fetch-depth: 0 + - name: Build Git Cache + uses: ./src/electron/.github/actions/build-git-cache + with: + target-platform: macos \ No newline at end of file diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index ace3bae71f5a4..0eaa4c7d87295 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -100,8 +100,7 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_mac=True --custom-var=host_os=mac' outputs: build-image-sha: ${{ needs.setup.outputs.build-image-sha }} @@ -129,8 +128,7 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_arm=True --custom-var=checkout_arm64=True' PATCH_UP_APP_CREDS: ${{ secrets.PATCH_UP_APP_CREDS }} outputs: @@ -156,8 +154,8 @@ jobs: - /mnt/win-cache:/mnt/win-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_win=True' TARGET_OS: 'win' ELECTRON_DEPOT_TOOLS_WIN_TOOLCHAIN: '1' diff --git a/.github/workflows/linux-publish.yml b/.github/workflows/linux-publish.yml index a003a15fc1184..8cadd26d23bcc 100644 --- a/.github/workflows/linux-publish.yml +++ b/.github/workflows/linux-publish.yml @@ -27,8 +27,7 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_arm=True --custom-var=checkout_arm64=True' steps: - name: Checkout Electron diff --git a/.github/workflows/macos-publish.yml b/.github/workflows/macos-publish.yml index 3e4654445092a..c7241b6a3bb00 100644 --- a/.github/workflows/macos-publish.yml +++ b/.github/workflows/macos-publish.yml @@ -28,8 +28,7 @@ jobs: - /mnt/cross-instance-cache:/mnt/cross-instance-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_mac=True --custom-var=host_os=mac' steps: - name: Checkout Electron diff --git a/.github/workflows/pipeline-electron-lint.yml b/.github/workflows/pipeline-electron-lint.yml index a49ce67b62f85..6cdbff0259952 100644 --- a/.github/workflows/pipeline-electron-lint.yml +++ b/.github/workflows/pipeline-electron-lint.yml @@ -13,8 +13,7 @@ concurrency: cancel-in-progress: ${{ github.ref_protected != true }} env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} jobs: lint: @@ -31,8 +30,8 @@ jobs: ref: ${{ github.event.pull_request.head.sha }} - name: Install Dependencies uses: ./src/electron/.github/actions/install-dependencies - - name: Set Chromium Git Helper - uses: ./src/electron/.github/actions/set-chromium-git-helper + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie - name: Setup third_party Depot Tools shell: bash run: | diff --git a/.github/workflows/pipeline-segment-electron-build.yml b/.github/workflows/pipeline-segment-electron-build.yml index 520511f28a7ef..ac7d2e78c939f 100644 --- a/.github/workflows/pipeline-segment-electron-build.yml +++ b/.github/workflows/pipeline-segment-electron-build.yml @@ -65,8 +65,8 @@ concurrency: cancel-in-progress: ${{ github.ref_protected != true }} env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} ELECTRON_ARTIFACTS_BLOB_STORAGE: ${{ secrets.ELECTRON_ARTIFACTS_BLOB_STORAGE }} ELECTRON_RBE_JWT: ${{ secrets.ELECTRON_RBE_JWT }} SUDOWOODO_EXCHANGE_URL: ${{ secrets.SUDOWOODO_EXCHANGE_URL }} @@ -127,8 +127,8 @@ jobs: GN_EXTRA_ARGS='is_asan=true' fi echo "GN_EXTRA_ARGS=$GN_EXTRA_ARGS" >> $GITHUB_ENV - - name: Set Chromium Git Helper - uses: ./src/electron/.github/actions/set-chromium-git-helper + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Generate DEPS Hash diff --git a/.github/workflows/pipeline-segment-electron-gn-check.yml b/.github/workflows/pipeline-segment-electron-gn-check.yml index 9e74404070b13..48fe703078145 100644 --- a/.github/workflows/pipeline-segment-electron-gn-check.yml +++ b/.github/workflows/pipeline-segment-electron-gn-check.yml @@ -66,8 +66,8 @@ jobs: - name: Check disk space after freeing up space if: ${{ inputs.target-platform == 'macos' }} run: df -h - - name: Set Chromium Git Helper - uses: ./src/electron/.github/actions/set-chromium-git-helper + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Enable windows toolchain diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index 5040ebb1ac046..17cf3f2398b98 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -36,8 +36,8 @@ permissions: pull-requests: read env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} + CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} ELECTRON_OUT_DIR: Default ELECTRON_RBE_JWT: ${{ secrets.ELECTRON_RBE_JWT }} @@ -126,8 +126,8 @@ jobs: ref: ${{ github.event.pull_request.head.sha }} - name: Install Dependencies uses: ./src/electron/.github/actions/install-dependencies - - name: Set Chromium Git Helper - uses: ./src/electron/.github/actions/set-chromium-git-helper + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie - name: Get Depot Tools timeout-minutes: 5 run: | diff --git a/.github/workflows/pipeline-segment-node-nan-test.yml b/.github/workflows/pipeline-segment-node-nan-test.yml index d7375886850aa..7b5e71c3cd347 100644 --- a/.github/workflows/pipeline-segment-node-nan-test.yml +++ b/.github/workflows/pipeline-segment-node-nan-test.yml @@ -31,8 +31,7 @@ concurrency: cancel-in-progress: ${{ github.ref_protected != true }} env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE: ${{ secrets.CHROMIUM_GIT_COOKIE }} ELECTRON_OUT_DIR: Default ELECTRON_RBE_JWT: ${{ secrets.ELECTRON_RBE_JWT }} @@ -52,8 +51,8 @@ jobs: path: src/electron fetch-depth: 0 ref: ${{ github.event.pull_request.head.sha }} - - name: Set Chromium Git Helper - uses: ./src/electron/.github/actions/set-chromium-git-helper + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Init Build Tools @@ -106,8 +105,8 @@ jobs: path: src/electron fetch-depth: 0 ref: ${{ github.event.pull_request.head.sha }} - - name: Set Chromium Git Helper - uses: ./src/electron/.github/actions/set-chromium-git-helper + - name: Set Chromium Git Cookie + uses: ./src/electron/.github/actions/set-chromium-cookie - name: Install Build Tools uses: ./src/electron/.github/actions/install-build-tools - name: Init Build Tools diff --git a/.github/workflows/windows-publish.yml b/.github/workflows/windows-publish.yml index c0acf202f6d30..e8b7c6172fdd8 100644 --- a/.github/workflows/windows-publish.yml +++ b/.github/workflows/windows-publish.yml @@ -28,8 +28,7 @@ jobs: - /mnt/win-cache:/mnt/win-cache - /var/run/sas:/var/run/sas env: - CHROMIUM_GIT_AUTH: ${{ secrets.CHROMIUM_GIT_AUTH }} - CHROMIUM_GIT_USER: ${{ secrets.CHROMIUM_GIT_USER }} + CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} GCLIENT_EXTRA_ARGS: '--custom-var=checkout_win=True' TARGET_OS: 'win' ELECTRON_DEPOT_TOOLS_WIN_TOOLCHAIN: '1' From d657036a1be22feb75c1ff0ef5cddb7ebc7ce2c4 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sat, 7 Jun 2025 07:59:20 +0200 Subject: [PATCH 092/186] docs: remove `electron-quick-start` from README (#47387) Refs https://github.com/electron/.permissions/pull/293 The repo was renamed to `minimal-repro` and is no longer intended to be used as a way to start new projects (see PR above). Since we really want bugs in `electron/electron` to be reported with a Fiddle gist instead of a standalone repo (makes reproducing and bisecting sooo much easier and safer!), I removed the repo from the README completely instead of mentioning as an issue reproduction starting point. Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Niklas Wenzel --- README.md | 14 +------------- 1 file changed, 1 insertion(+), 13 deletions(-) diff --git a/README.md b/README.md index 07edb95ea80da..2ab98ce41009b 100644 --- a/README.md +++ b/README.md @@ -44,29 +44,17 @@ Each Electron release provides binaries for macOS, Windows, and Linux. * Fedora 32 and newer * Debian 10 and newer -## Quick start & Electron Fiddle +## Electron Fiddle Use [`Electron Fiddle`](https://github.com/electron/fiddle) to build, run, and package small Electron experiments, to see code examples for all of Electron's APIs, and to try out different versions of Electron. It's designed to make the start of your journey with Electron easier. -Alternatively, clone and run the -[electron/electron-quick-start](https://github.com/electron/electron-quick-start) -repository to see a minimal Electron app in action: - -```sh -git clone https://github.com/electron/electron-quick-start -cd electron-quick-start -npm install -npm start -``` - ## Resources for learning Electron * [electronjs.org/docs](https://electronjs.org/docs) - All of Electron's documentation * [electron/fiddle](https://github.com/electron/fiddle) - A tool to build, run, and package small Electron experiments -* [electron/electron-quick-start](https://github.com/electron/electron-quick-start) - A very basic starter Electron app * [electronjs.org/community#boilerplates](https://electronjs.org/community#boilerplates) - Sample starter apps created by the community ## Programmatic usage From dd0fb7d24da2c4bf864e83841788da60ba490c03 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sat, 7 Jun 2025 07:59:50 +0200 Subject: [PATCH 093/186] fix: silent printing of PDFs with `webContents.print` (#47397) fix: silent printing Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- patches/chromium/printing.patch | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index 91855d62b57b0..e92e0e63fb6cf 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -666,7 +666,7 @@ index 6809c4576c71bc1e1a6ad4e0a37707272a9a10f4..3aad10424a6a31dab2ca393d00149ec6 PrintingFailed(int32 cookie, PrintFailureReason reason); diff --git a/components/printing/renderer/print_render_frame_helper.cc b/components/printing/renderer/print_render_frame_helper.cc -index 774392650ad07ee56cb931db7d1a46eaedb1eaa1..d42afb1a744113af660aadc832c71244b8918090 100644 +index 774392650ad07ee56cb931db7d1a46eaedb1eaa1..348ba6b23e3dc83196137ef07dc2543830471584 100644 --- a/components/printing/renderer/print_render_frame_helper.cc +++ b/components/printing/renderer/print_render_frame_helper.cc @@ -52,6 +52,7 @@ @@ -744,7 +744,7 @@ index 774392650ad07ee56cb931db7d1a46eaedb1eaa1..d42afb1a744113af660aadc832c71244 print_preview_context_.OnPrintPreview(); #if BUILDFLAG(IS_CHROMEOS) -@@ -2075,17 +2081,19 @@ void PrintRenderFrameHelper::PrintNode(const blink::WebNode& node) { +@@ -2075,17 +2081,25 @@ void PrintRenderFrameHelper::PrintNode(const blink::WebNode& node) { void PrintRenderFrameHelper::Print(blink::WebLocalFrame* frame, const blink::WebNode& node, @@ -759,6 +759,12 @@ index 774392650ad07ee56cb931db7d1a46eaedb1eaa1..d42afb1a744113af660aadc832c71244 FrameReference frame_ref(frame); - if (!InitPrintSettings(frame, node)) { ++ // If we're silently printing a PDF, we bypass settings logic ++ // that sets modifiability to false so ensure it's set here. ++ if (silent && IsPrintingPdfFrame(frame, node)) { ++ settings.Set(kSettingPreviewModifiable, false); ++ } ++ + if (!InitPrintSettings(frame, node, std::move(settings))) { // Browser triggered this code path. It already knows about the failure. notify_browser_of_print_failure_ = false; @@ -767,7 +773,7 @@ index 774392650ad07ee56cb931db7d1a46eaedb1eaa1..d42afb1a744113af660aadc832c71244 DidFinishPrinting(PrintingResult::kFailPrintInit); return; } -@@ -2106,8 +2114,15 @@ void PrintRenderFrameHelper::Print(blink::WebLocalFrame* frame, +@@ -2106,8 +2120,15 @@ void PrintRenderFrameHelper::Print(blink::WebLocalFrame* frame, print_pages_params_->params->print_scaling_option; auto self = weak_ptr_factory_.GetWeakPtr(); @@ -784,7 +790,7 @@ index 774392650ad07ee56cb931db7d1a46eaedb1eaa1..d42afb1a744113af660aadc832c71244 // Check if `this` is still valid. if (!self) return; -@@ -2375,29 +2390,43 @@ void PrintRenderFrameHelper::IPCProcessed() { +@@ -2375,29 +2396,43 @@ void PrintRenderFrameHelper::IPCProcessed() { } bool PrintRenderFrameHelper::InitPrintSettings(blink::WebLocalFrame* frame, From a6569b116e6b96af536dda2a6264bcbab52dc38a Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sun, 8 Jun 2025 12:56:02 +0200 Subject: [PATCH 094/186] fix: printing PDF via `webContents.print()` (#47398) fix: printing PDF via webContents.print() Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/api/electron_api_web_contents.cc | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index 271fe13ec49e9..26f2465d739ee 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -2956,12 +2956,15 @@ void OnGetDeviceNameToUse(base::WeakPtr web_contents, print_settings.Set(printing::kSettingDpiVertical, dpi.height()); } - auto* print_view_manager = - PrintViewManagerElectron::FromWebContents(web_contents.get()); + content::RenderFrameHost* rfh = GetRenderFrameHostToUse(web_contents.get()); + if (!rfh) + return; + + auto* print_view_manager = PrintViewManagerElectron::FromWebContents( + content::WebContents::FromRenderFrameHost(rfh)); if (!print_view_manager) return; - content::RenderFrameHost* rfh = GetRenderFrameHostToUse(web_contents.get()); print_view_manager->PrintNow(rfh, std::move(print_settings), std::move(print_callback)); } @@ -3007,12 +3010,15 @@ void WebContents::Print(gin::Arguments* args) { } if (options.IsEmptyObject()) { - auto* print_view_manager = - PrintViewManagerElectron::FromWebContents(web_contents()); + content::RenderFrameHost* rfh = GetRenderFrameHostToUse(web_contents()); + if (!rfh) + return; + + auto* print_view_manager = PrintViewManagerElectron::FromWebContents( + content::WebContents::FromRenderFrameHost(rfh)); if (!print_view_manager) return; - content::RenderFrameHost* rfh = GetRenderFrameHostToUse(web_contents()); print_view_manager->PrintNow(rfh, std::move(settings), std::move(callback)); return; } From 9f4b16fa810cb9a43f448d2f81fd81f58af240dc Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sun, 8 Jun 2025 12:56:35 +0200 Subject: [PATCH 095/186] fix: rework lifetime mgmt of `ClearDataTask`/`ClearDataOperation` (#47412) * fix: rework lifetime mgmt of ClearDataTask/ClearDataOperation Co-authored-by: Shelley Vohr * Update shell/browser/api/electron_api_session.cc Co-authored-by: Robo Co-authored-by: Shelley Vohr * Update shell/browser/api/electron_api_session.cc Co-authored-by: Robo Co-authored-by: Shelley Vohr * Update shell/browser/api/electron_api_session.cc Co-authored-by: Robo Co-authored-by: Shelley Vohr * Update shell/browser/api/electron_api_session.cc Co-authored-by: Robo Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/api/electron_api_session.cc | 64 ++++++++++++++--------- 1 file changed, 38 insertions(+), 26 deletions(-) diff --git a/shell/browser/api/electron_api_session.cc b/shell/browser/api/electron_api_session.cc index dcb89142e73ff..563d63aa95e7d 100644 --- a/shell/browser/api/electron_api_session.cc +++ b/shell/browser/api/electron_api_session.cc @@ -84,6 +84,7 @@ #include "shell/common/gin_converters/time_converter.h" #include "shell/common/gin_converters/usb_protected_classes_converter.h" #include "shell/common/gin_converters/value_converter.h" +#include "shell/common/gin_helper/cleaned_up_at_exit.h" #include "shell/common/gin_helper/dictionary.h" #include "shell/common/gin_helper/error_thrower.h" #include "shell/common/gin_helper/object_template_builder.h" @@ -198,9 +199,11 @@ std::vector GetDataTypesFromMask( // Represents a task to clear browsing data for the `clearData` API method. // -// This type manages its own lifetime, deleting itself once the task finishes -// completely. -class ClearDataTask { +// This type manages its own lifetime, +// 1) deleting itself once all the operations created by this task are +// completed. 2) through gin_helper::CleanedUpAtExit, ensuring it's destroyed +// before the node environment shuts down. +class ClearDataTask : public gin_helper::CleanedUpAtExit { public: // Starts running a task. This function will return before the task is // finished, but will resolve or reject the |promise| when it finishes. @@ -211,7 +214,7 @@ class ClearDataTask { std::vector origins, BrowsingDataFilterBuilder::Mode filter_mode, BrowsingDataFilterBuilder::OriginMatchingMode origin_matching_mode) { - std::shared_ptr task(new ClearDataTask(std::move(promise))); + auto* task = new ClearDataTask(std::move(promise)); // This method counts as an operation. This is important so we can call // `OnOperationFinished` at the end of this method as a fallback if all the @@ -255,42 +258,36 @@ class ClearDataTask { } // This static method counts as an operation. - task->OnOperationFinished(std::nullopt); + task->OnOperationFinished(nullptr, std::nullopt); } private: // An individual |content::BrowsingDataRemover::Remove...| operation as part - // of a full |ClearDataTask|. This class manages its own lifetime, cleaning - // itself up after the operation completes and notifies the task of the - // result. + // of a full |ClearDataTask|. This class is owned by ClearDataTask and cleaned + // up either when the operation completes or when ClearDataTask is destroyed. class ClearDataOperation : private BrowsingDataRemover::Observer { public: - static void Run(std::shared_ptr task, - BrowsingDataRemover* remover, - BrowsingDataRemover::DataType data_type_mask, - std::unique_ptr filter_builder) { - auto* operation = new ClearDataOperation(task, remover); + ClearDataOperation(ClearDataTask* task, BrowsingDataRemover* remover) + : task_(task) { + observation_.Observe(remover); + } + void Start(BrowsingDataRemover* remover, + BrowsingDataRemover::DataType data_type_mask, + std::unique_ptr filter_builder) { remover->RemoveWithFilterAndReply(base::Time::Min(), base::Time::Max(), data_type_mask, kClearOriginTypeAll, - std::move(filter_builder), operation); + std::move(filter_builder), this); } // BrowsingDataRemover::Observer: void OnBrowsingDataRemoverDone( BrowsingDataRemover::DataType failed_data_types) override { - task_->OnOperationFinished(failed_data_types); - delete this; + task_->OnOperationFinished(this, failed_data_types); } private: - ClearDataOperation(std::shared_ptr task, - BrowsingDataRemover* remover) - : task_(task) { - observation_.Observe(remover); - } - - std::shared_ptr task_; + raw_ptr task_; base::ScopedObservation observation_{this}; }; @@ -299,18 +296,20 @@ class ClearDataTask { : promise_(std::move(promise)) {} static void StartOperation( - std::shared_ptr task, + ClearDataTask* task, BrowsingDataRemover* remover, BrowsingDataRemover::DataType data_type_mask, std::unique_ptr filter_builder) { // Track this operation task->operations_running_ += 1; - ClearDataOperation::Run(task, remover, data_type_mask, - std::move(filter_builder)); + auto& operation = task->operations_.emplace_back( + std::make_unique(task, remover)); + operation->Start(remover, data_type_mask, std::move(filter_builder)); } void OnOperationFinished( + ClearDataOperation* operation, std::optional failed_data_types) { DCHECK_GT(operations_running_, 0); operations_running_ -= 1; @@ -319,6 +318,16 @@ class ClearDataTask { failed_data_types_ |= failed_data_types.value(); } + if (operation) { + operations_.erase( + std::remove_if( + operations_.begin(), operations_.end(), + [operation](const std::unique_ptr& op) { + return op.get() == operation; + }), + operations_.end()); + } + // If this is the last operation, then the task is finished if (operations_running_ == 0) { OnTaskFinished(); @@ -346,11 +355,14 @@ class ClearDataTask { promise_.Reject(error); } + + delete this; } int operations_running_ = 0; BrowsingDataRemover::DataType failed_data_types_ = 0ULL; gin_helper::Promise promise_; + std::vector> operations_; }; base::Value::Dict createProxyConfig(ProxyPrefs::ProxyMode proxy_mode, From 5953dca8befe1dd6985ef98a1efd9977c6fe6135 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Mon, 9 Jun 2025 09:32:23 -0400 Subject: [PATCH 096/186] chore: bump chromium to 138.0.7204.15 (37-x-y) (#46980) * chore: bump chromium in DEPS to 138.0.7166.1 * chore: bump chromium in DEPS to 138.0.7166.2 * chore: bump chromium in DEPS to 138.0.7168.1 * chore: bump chromium in DEPS to 138.0.7169.2 * chore: bump chromium in DEPS to 138.0.7170.1 * chore: bump chromium in DEPS to 138.0.7172.1 * chore: bump chromium in DEPS to 138.0.7173.0 * chore: bump chromium in DEPS to 138.0.7175.0 * chore: bump chromium in DEPS to 138.0.7177.1 * chore: bump chromium in DEPS to 138.0.7178.2 * chore: bump chromium in DEPS to 138.0.7180.1 * chore: bump chromium in DEPS to 138.0.7181.0 * chore: bump chromium in DEPS to 138.0.7182.2 * chore: bump chromium in DEPS to 138.0.7184.0 * chore: bump chromium in DEPS to 138.0.7186.0 * chore: bump chromium in DEPS to 138.0.7188.0 * chore: bump chromium in DEPS to 138.0.7190.1 * chore: bump chromium in DEPS to 138.0.7192.0 * chore: bump chromium in DEPS to 138.0.7194.1 * chore: bump chromium in DEPS to 138.0.7196.1 * chore: bump chromium in DEPS to 138.0.7198.1 * chore: bump chromium in DEPS to 138.0.7200.0 * chore: bump chromium in DEPS to 138.0.7202.0 * chore: bump chromium in DEPS to 138.0.7204.0 * chore: bump chromium in DEPS to 138.0.7204.5 * chore: bump chromium in DEPS to 138.0.7204.4 * 6543986: Mac: decouple deserializing and applying sandbox policy Refs https://chromium-review.googlesource.com/c/chromium/src/+/6543986 (cherry picked from commit d386063e9d2414a35c91c4fa017665d950de5882) * 6566111: Change UtilityProcessHost to manage its instance internally Refs https://chromium-review.googlesource.com/c/chromium/src/+/6566111 (cherry picked from commit 93a0a91d447c118de33efec079365f5d0e8363db) * chore: update patches * 6577970: Remove superfluous includes for base/strings/stringprintf.h in headers Refs https://chromium-review.googlesource.com/c/chromium/src/+/6577970 (cherry picked from commit 9ba045f3715d85792e4aa12139e7e05e0b772634) * 6568811: Add FunctionCall structured metrics event for DevTools Refs https://chromium-review.googlesource.com/c/chromium/src/+/6568811 (cherry picked from commit 79ae6f2c8b53568b6277998cfe9a91e3a1ee595b) * [PDF Ink Signatures] Support PdfAnnotationsEnabled policy https://chromium-review.googlesource.com/c/chromium/src/+/6558970 * Mac: Switch to Xcode 16.3 (16E140) and SDK 15.4 (24E241) https://chromium-review.googlesource.com/c/chromium/src/+/6431799 * chore: bump chromium in DEPS to 138.0.7204.15 * chore: update patches * fixup Mac: decouple deserializing and applying sandbox policy https://chromium-review.googlesource.com/c/chromium/src/+/6543986 * chore: update patches --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Samuel Maddock Co-authored-by: John Kleinschmidt --- .../actions/install-build-tools/action.yml | 2 +- DEPS | 2 +- patches/boringssl/expose_ripemd160.patch | 2 +- patches/chromium/.patches | 2 - ...client_precreatemessageloop_callback.patch | 8 +- .../add_didinstallconditionalfeatures.patch | 2 +- ..._scheduler_throttling_per_renderview.patch | 12 +- ..._windows_to_have_different_web_prefs.patch | 16 +- patches/chromium/blink_local_frame.patch | 2 +- .../build_add_electron_tracing_category.patch | 4 +- ..._depend_on_packed_resource_integrity.patch | 14 +- patches/chromium/build_gn.patch | 2 +- .../build_libc_as_static_library.patch | 4 +- patches/chromium/can_create_window.patch | 24 +- .../chromium/cherry-pick-f1e6422a355c.patch | 273 -- ...hore_add_electron_deps_to_gitignores.patch | 4 +- ...ther_in_electron_views_and_delegates.patch | 10 +- ..._introduce_blocking_api_for_electron.patch | 6 +- ...fy_chromium_handling_of_mouse_events.patch | 6 +- .../chromium/chore_partial_revert_of.patch | 4 +- ...tition_attribute_dcheck_for_webviews.patch | 4 +- ...rofile_methods_in_chrome_browser_pdf.patch | 18 + ...screationoverridden_with_full_params.patch | 10 +- patches/chromium/command-ismediakey.patch | 6 +- ...e_browser_v8_snapshot_file_name_fuse.patch | 2 +- patches/chromium/disable_hidden.patch | 2 +- patches/chromium/disable_unload_metrics.patch | 6 +- .../chromium/enable_reset_aspect_ratio.patch | 4 +- ...xpose_setuseragent_on_networkcontext.patch | 12 +- .../extend_apply_webpreferences.patch | 4 +- ...ing_dialog_features_to_shell_dialogs.patch | 14 +- ...t_allow_code_cache_in_custom_schemes.patch | 20 +- ...e_launch_options_for_service_process.patch | 188 +- ...moothing_css_rule_and_blink_painting.patch | 60 +- ...screen_rendering_with_viz_compositor.patch | 8 +- ...g_exit_code_on_service_process_crash.patch | 14 +- ...etdefersloading_on_webdocumentloader.patch | 2 +- ..._raw_response_headers_from_urlloader.patch | 2 +- ...allback_for_sync_and_async_clipboard.patch | 4 +- ...dless_mode_handling_in_native_widget.patch | 4 +- ...ding_non-standard_schemes_in_iframes.patch | 6 +- ..._background_throttling_in_compositor.patch | 8 +- ...ursorscreenpoint_wrongly_returns_0_0.patch | 4 +- ...media_key_usage_with_globalshortcuts.patch | 4 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ...original_resize_performance_on_macos.patch | 2 +- ...from_localframe_requestexecutescript.patch | 6 +- patches/chromium/frame_host_manager.patch | 6 +- .../gin_enable_disable_v8_platform.patch | 2 +- .../chromium/gritsettings_resource_ids.patch | 4 +- ...nse_interceptor_to_point_to_electron.patch | 2 +- ..._avoid_private_macos_api_usage.patch.patch | 74 +- ...emote_certificate_verification_logic.patch | 20 +- .../chromium/notification_provenance.patch | 6 +- patches/chromium/preconnect_manager.patch | 10 +- patches/chromium/printing.patch | 4 +- ...r_changes_to_the_webcontentsobserver.patch | 10 +- ..._electron_permissiontypes_into_blink.patch | 4 +- ...efactor_unfilter_unresponsive_events.patch | 4 +- patches/chromium/resource_file_conflict.patch | 6 +- ...ean_up_stale_macwebcontentsocclusion.patch | 16 +- ..._stub_webgl_2_renderingcontextwebgpu.patch | 4219 ----------------- .../support_mixed_sandbox_with_zygote.patch | 4 +- patches/chromium/web_contents.patch | 13 +- patches/chromium/webview_fullscreen.patch | 10 +- .../worker_context_will_destroy.patch | 4 +- ...i_to_allow_electron_to_set_dock_side.patch | 2 +- patches/v8/.patches | 2 - patches/v8/cherry-pick-45eb42cd398e.patch | 32 - patches/v8/cherry-pick-7bc0a67ebfbf.patch | 53 - ...pturer_initialization_and_management.patch | 4 +- .../serial/serial_chooser_controller.cc | 1 + shell/browser/ui/inspectable_web_contents.h | 1 + 73 files changed, 395 insertions(+), 4935 deletions(-) delete mode 100644 patches/chromium/cherry-pick-f1e6422a355c.patch delete mode 100644 patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch delete mode 100644 patches/v8/cherry-pick-45eb42cd398e.patch delete mode 100644 patches/v8/cherry-pick-7bc0a67ebfbf.patch diff --git a/.github/actions/install-build-tools/action.yml b/.github/actions/install-build-tools/action.yml index 12cffbc835519..54aa56a42a05a 100644 --- a/.github/actions/install-build-tools/action.yml +++ b/.github/actions/install-build-tools/action.yml @@ -13,7 +13,7 @@ runs: git config --global core.fscache true git config --global core.preloadindex true fi - export BUILD_TOOLS_SHA=6e8526315ea3b4828882497e532b8340e64e053c + export BUILD_TOOLS_SHA=f2a960b4d82e6b5c9dbbd437378a39489f399c50 npm i -g @electron/build-tools # Update depot_tools to ensure python e d update_depot_tools diff --git a/DEPS b/DEPS index 0b63a1984fa29..153ee4542aae4 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7190.0', + '138.0.7204.15', 'node_version': 'v22.16.0', 'nan_version': diff --git a/patches/boringssl/expose_ripemd160.patch b/patches/boringssl/expose_ripemd160.patch index 5b3b1da230646..8ab7be04680b2 100644 --- a/patches/boringssl/expose_ripemd160.patch +++ b/patches/boringssl/expose_ripemd160.patch @@ -82,7 +82,7 @@ index e04b80cd6a1a215fc87f8fd8d750c3d258c3974f..8fdf1c624794f568bfc77b7b6b0c510b void EVP_MD_do_all(void (*callback)(const EVP_MD *cipher, const char *name, diff --git a/include/openssl/digest.h b/include/openssl/digest.h -index 6abab7693ef2cf418e64d4bf5d53e7e0821cb731..ecbf81be6888cf2e95008da054cf4d3d7df6ad49 100644 +index b5f76c34efea47fb52f1642c8ca7e8a78c1ae678..b2420a9614453de35e1918d65d42ff95fbf9cf9e 100644 --- a/include/openssl/digest.h +++ b/include/openssl/digest.h @@ -48,6 +48,9 @@ OPENSSL_EXPORT const EVP_MD *EVP_blake2b256(void); diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 51c1748e48957..e49e542bf3caa 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -143,5 +143,3 @@ fix_enable_wrap_iter_in_string_view_and_array.patch fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch -revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch -cherry-pick-f1e6422a355c.patch diff --git a/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch b/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch index 6ce5197ed3607..2db23d70e9caf 100644 --- a/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch +++ b/patches/chromium/add_contentgpuclient_precreatemessageloop_callback.patch @@ -10,12 +10,12 @@ Allows Electron to restore WER when ELECTRON_DEFAULT_ERROR_MODE is set. This should be upstreamed. diff --git a/content/gpu/gpu_main.cc b/content/gpu/gpu_main.cc -index 73be6273b320574c22fd12e07b93dc3cffaa1be9..58a34cc5b583a7111decf14b755afbb82ba94765 100644 +index 5cf9e02f97e1378b0b1a55feb007b7d664fc4a84..d1fdf00a1b65fe0f5510608c165df93cf6c13e38 100644 --- a/content/gpu/gpu_main.cc +++ b/content/gpu/gpu_main.cc -@@ -268,6 +268,10 @@ int GpuMain(MainFunctionParams parameters) { +@@ -269,6 +269,10 @@ int GpuMain(MainFunctionParams parameters) { // to the GpuProcessHost once the GpuServiceImpl has started. - viz::GpuServiceImpl::InstallPreInitializeLogHandler(); + viz::GpuLogMessageManager::GetInstance()->InstallPreInitializeLogHandler(); + auto* client = GetContentClient()->gpu(); + if (client) @@ -24,7 +24,7 @@ index 73be6273b320574c22fd12e07b93dc3cffaa1be9..58a34cc5b583a7111decf14b755afbb8 // We are experiencing what appear to be memory-stomp issues in the GPU // process. These issues seem to be impacting the task executor and listeners // registered to it. Create the task executor on the heap to guard against -@@ -377,7 +381,6 @@ int GpuMain(MainFunctionParams parameters) { +@@ -378,7 +382,6 @@ int GpuMain(MainFunctionParams parameters) { #endif const bool dead_on_arrival = !init_success; diff --git a/patches/chromium/add_didinstallconditionalfeatures.patch b/patches/chromium/add_didinstallconditionalfeatures.patch index 33795783b824d..881b932e203e3 100644 --- a/patches/chromium/add_didinstallconditionalfeatures.patch +++ b/patches/chromium/add_didinstallconditionalfeatures.patch @@ -23,7 +23,7 @@ index db655a7b52eacb74f2a8637db36abd87f6b86792..8014cb08e2090a12ea8b9e92cb8f93c9 int32_t world_id) {} virtual void DidClearWindowObject() {} diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index 3fa43adedd6ff0258edd195bde1e68977cff3a7c..7fe443aad2ad6207aa46daddea46baa3eb998bc3 100644 +index 5c8ffb1462a21f5d798656efc872ba09d6c0de99..2129c419a3ac4d989f2316484779debaebf90d7c 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc @@ -4808,6 +4808,12 @@ void RenderFrameImpl::DidCreateScriptContext(v8::Local context, diff --git a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch index ee0adbbb894c1..dc137c6f1c0ff 100644 --- a/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch +++ b/patches/chromium/allow_disabling_blink_scheduler_throttling_per_renderview.patch @@ -6,7 +6,7 @@ Subject: allow disabling blink scheduler throttling per RenderView This allows us to disable throttling for hidden windows. diff --git a/content/browser/renderer_host/navigation_controller_impl_unittest.cc b/content/browser/renderer_host/navigation_controller_impl_unittest.cc -index b9e7ef002a8d7842b4e97dbcaa59aa289ba652a1..81bd39f47d8411da53824d47e053b39f8fa24721 100644 +index 74e94044c3e18f513eb2ffa051039270f9bd56a1..f824ec4005b6640bdd3d35382f4dddf975893ea9 100644 --- a/content/browser/renderer_host/navigation_controller_impl_unittest.cc +++ b/content/browser/renderer_host/navigation_controller_impl_unittest.cc @@ -167,6 +167,12 @@ class MockPageBroadcast : public blink::mojom::PageBroadcast { @@ -23,10 +23,10 @@ index b9e7ef002a8d7842b4e97dbcaa59aa289ba652a1..81bd39f47d8411da53824d47e053b39f return receiver_.BindNewEndpointAndPassDedicatedRemote(); } diff --git a/content/browser/renderer_host/render_view_host_impl.cc b/content/browser/renderer_host/render_view_host_impl.cc -index 1654ffbb2184cc1db6c0b862cc745ba2e467b740..567f5279d943a58e451a78fb506606cf17a0ef79 100644 +index a0335fef252b46976ea2caf95e1bf3ef7d52585d..0a97013b60fcfeb8fac55d686b107b1175c9be04 100644 --- a/content/browser/renderer_host/render_view_host_impl.cc +++ b/content/browser/renderer_host/render_view_host_impl.cc -@@ -761,6 +761,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { +@@ -760,6 +760,11 @@ void RenderViewHostImpl::SetBackgroundOpaque(bool opaque) { GetWidget()->GetAssociatedFrameWidget()->SetBackgroundOpaque(opaque); } @@ -116,10 +116,10 @@ index 7c1eb9baabfb9e0f3645421b5cbe467862252638..00d2cd41d795cb550e16fb80944b2382 // Visibility ----------------------------------------------------------- diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index feba9635b40664b1db83ab727798a34b98e5e0b8..f6a248b1de8b313658453dd380529ec7c2e40033 100644 +index 97141017fa2ca72746d5269d6da2e08201e85972..2390395a3df10aca3510a619e91dab674de60e67 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc -@@ -2467,6 +2467,10 @@ void WebViewImpl::SetPageLifecycleStateInternal( +@@ -2469,6 +2469,10 @@ void WebViewImpl::SetPageLifecycleStateInternal( TRACE_EVENT2("navigation", "WebViewImpl::SetPageLifecycleStateInternal", "old_state", old_state, "new_state", new_state); @@ -130,7 +130,7 @@ index feba9635b40664b1db83ab727798a34b98e5e0b8..f6a248b1de8b313658453dd380529ec7 bool storing_in_bfcache = new_state->is_in_back_forward_cache && !old_state->is_in_back_forward_cache; bool restoring_from_bfcache = !new_state->is_in_back_forward_cache && -@@ -3990,10 +3994,23 @@ PageScheduler* WebViewImpl::Scheduler() const { +@@ -3992,10 +3996,23 @@ PageScheduler* WebViewImpl::Scheduler() const { return GetPage()->GetPageScheduler(); } diff --git a/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch b/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch index 912663a418587..ac07bb47cf4ed 100644 --- a/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch +++ b/patches/chromium/allow_in-process_windows_to_have_different_web_prefs.patch @@ -8,10 +8,10 @@ WebPreferences of in-process child windows, rather than relying on process-level command line switches, as before. diff --git a/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc b/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc -index b3e72c9d198a350a164d4abc37fcb19024f43c57..909ac417f24c0e104cba286b6420d8c820784d31 100644 +index 96bb1f2205a4f81b78626f8c277c0b82a048895b..881e6fa91b25758a3b3523119360bd92b5fc5802 100644 --- a/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc +++ b/third_party/blink/common/web_preferences/web_preferences_mojom_traits.cc -@@ -149,6 +149,19 @@ bool StructTraitsv8_cache_options = data.v8_cache_options(); out->record_whole_document = data.record_whole_document(); out->stylus_handwriting_enabled = data.stylus_handwriting_enabled(); @@ -32,7 +32,7 @@ index b3e72c9d198a350a164d4abc37fcb19024f43c57..909ac417f24c0e104cba286b6420d8c8 out->accelerated_video_decode_enabled = data.accelerated_video_decode_enabled(); diff --git a/third_party/blink/public/common/web_preferences/web_preferences.h b/third_party/blink/public/common/web_preferences/web_preferences.h -index 1ee685e777e27a56da50d38ae7710abb240699a1..7f0ed7e9b0c4c0077eaa733e81ebc421f0ddd02a 100644 +index 5c29a554f51023e63948bb7b28fcfdfa02089d66..ce0a19a2a848ac7c3543651a2b4de99dcfc66475 100644 --- a/third_party/blink/public/common/web_preferences/web_preferences.h +++ b/third_party/blink/public/common/web_preferences/web_preferences.h @@ -9,6 +9,7 @@ @@ -43,7 +43,7 @@ index 1ee685e777e27a56da50d38ae7710abb240699a1..7f0ed7e9b0c4c0077eaa733e81ebc421 #include "build/build_config.h" #include "net/nqe/effective_connection_type.h" #include "third_party/blink/public/common/common_export.h" -@@ -450,6 +451,20 @@ struct BLINK_COMMON_EXPORT WebPreferences { +@@ -452,6 +453,20 @@ struct BLINK_COMMON_EXPORT WebPreferences { // WebView and by `kWebPayments` feature flag everywhere. bool payment_request_enabled = false; @@ -65,7 +65,7 @@ index 1ee685e777e27a56da50d38ae7710abb240699a1..7f0ed7e9b0c4c0077eaa733e81ebc421 // chrome, except for the cases where it would require lots of extra work for // the embedder to use the same default value. diff --git a/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h b/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h -index 36a5fb0b42be57e9602c0709b6abb55385f48666..306838bbf7c6d5cddd95e09d703e41d1deac21ab 100644 +index ce4074d601eca1d9ca6b30a8b5904366a47d0595..08cd7f1858a63d0d33fee5d345fefce19d2add93 100644 --- a/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h +++ b/third_party/blink/public/common/web_preferences/web_preferences_mojom_traits.h @@ -8,6 +8,7 @@ @@ -76,7 +76,7 @@ index 36a5fb0b42be57e9602c0709b6abb55385f48666..306838bbf7c6d5cddd95e09d703e41d1 #include "mojo/public/cpp/bindings/struct_traits.h" #include "net/nqe/effective_connection_type.h" #include "third_party/blink/public/common/common_export.h" -@@ -438,6 +439,52 @@ struct BLINK_COMMON_EXPORT StructTraitsDetached(type); diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index 6a80292d0c9d7130c762a0a84ca77f62c4c75168..574f947602f8cf9d5abebf6180dc3fb67dc85496 100644 +index 43759ed40b3356a838e30772b815d51d20136707..afa8d181e836739f4136cf51ae323f29b0b25ebe 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc @@ -727,10 +727,6 @@ bool LocalFrame::DetachImpl(FrameDetachType type) { diff --git a/patches/chromium/build_add_electron_tracing_category.patch b/patches/chromium/build_add_electron_tracing_category.patch index 374dbbf156f70..8e7377c76c248 100644 --- a/patches/chromium/build_add_electron_tracing_category.patch +++ b/patches/chromium/build_add_electron_tracing_category.patch @@ -8,10 +8,10 @@ categories in use are known / declared. This patch is required for us to introduce a new Electron category for Electron-specific tracing. diff --git a/base/trace_event/builtin_categories.h b/base/trace_event/builtin_categories.h -index e149fca0c6c38eb3898735cb38e41443af61b6d8..24ab0a9b37299e62176167507215351ecc54092b 100644 +index 31c41cb8e8cc0d0c43811ce7e97a03f4feb38feb..8adb5a1d415e3424f41d87b19100eedcb55c9e61 100644 --- a/base/trace_event/builtin_categories.h +++ b/base/trace_event/builtin_categories.h -@@ -102,6 +102,7 @@ PERFETTO_DEFINE_CATEGORIES_IN_NAMESPACE_WITH_ATTRS( +@@ -118,6 +118,7 @@ PERFETTO_DEFINE_CATEGORIES_IN_NAMESPACE_WITH_ATTRS( perfetto::Category("drm"), perfetto::Category("drmcursor"), perfetto::Category("dwrite"), diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index 000d9a91df9fb..b32f98bb1dd3b 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -11,7 +11,7 @@ if we ever align our .pak file generation with Chrome we can remove this patch. diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff62717ba00 100644 +index 72c637f9f3ba48bb7ab06678fe833f33d2cfddc8..e9c8ae3cdb7ba400c59cc469a1a80b5063738ffa 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn @@ -197,11 +197,16 @@ if (!is_android && !is_mac) { @@ -33,10 +33,10 @@ index 84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2..f03f0e67c083880dc13f8f90d9375ff6 "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index 74d78554a4816e76cbf800762386444520c32906..c89251393bdd9439aa768e3d516516dfc4b18824 100644 +index efb9b948aca15ae8b4d6257fa685e758d2e3acc1..0e14d0eb15bfcd86831599678eb0f76fe0a803cc 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4681,7 +4681,7 @@ static_library("browser") { +@@ -4716,7 +4716,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } @@ -46,10 +46,10 @@ index 74d78554a4816e76cbf800762386444520c32906..c89251393bdd9439aa768e3d516516df # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 9dc89f62b8cc049955d8faa4dcbd4904776580ee..cd3b00e4c2a22819e8bd4844cfa5048403f9a70a 100644 +index 0f493aeb49901e2917009b942f9b1e14e3fcf758..349079dc25f91fd426d523345ba66271c42ea084 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn -@@ -7216,9 +7216,12 @@ test("unit_tests") { +@@ -7243,9 +7243,12 @@ test("unit_tests") { "//chrome/notification_helper", ] @@ -63,7 +63,7 @@ index 9dc89f62b8cc049955d8faa4dcbd4904776580ee..cd3b00e4c2a22819e8bd4844cfa50484 "//chrome//services/util_win:unit_tests", "//chrome/app:chrome_dll_resources", "//chrome/app:win_unit_tests", -@@ -8182,6 +8185,10 @@ test("unit_tests") { +@@ -8209,6 +8212,10 @@ test("unit_tests") { "../browser/performance_manager/policies/background_tab_loading_policy_unittest.cc", ] @@ -74,7 +74,7 @@ index 9dc89f62b8cc049955d8faa4dcbd4904776580ee..cd3b00e4c2a22819e8bd4844cfa50484 sources += [ # The importer code is not used on Android. "../common/importer/firefox_importer_utils_unittest.cc", -@@ -8239,7 +8246,6 @@ test("unit_tests") { +@@ -8266,7 +8273,6 @@ test("unit_tests") { # TODO(crbug.com/417513088): Maybe merge with the non-android `deps` declaration above? deps += [ "../browser/screen_ai:screen_ai_install_state", diff --git a/patches/chromium/build_gn.patch b/patches/chromium/build_gn.patch index fd519adbff7a2..79b7839119652 100644 --- a/patches/chromium/build_gn.patch +++ b/patches/chromium/build_gn.patch @@ -7,7 +7,7 @@ These are variables we add to the root BUILDCONFIG so that they're available everywhere, without having to import("//electron/.../flags.gni"). diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn -index 32cbfa5cfee7f9a2f2d9e696fb54ee753dda4f6c..cc9d083a598aa1e07bf60bc961c5ddcd730921bf 100644 +index 706f0f32fe3d5b43692167ce8013699575fbf7b7..40ea2de7a32d7b720ebaa21f6bea4c46a9a20697 100644 --- a/build/config/BUILDCONFIG.gn +++ b/build/config/BUILDCONFIG.gn @@ -123,6 +123,9 @@ if (current_os == "") { diff --git a/patches/chromium/build_libc_as_static_library.patch b/patches/chromium/build_libc_as_static_library.patch index 1851ebc6154c3..86890329e5466 100644 --- a/patches/chromium/build_libc_as_static_library.patch +++ b/patches/chromium/build_libc_as_static_library.patch @@ -7,10 +7,10 @@ Build libc++ as static library to compile and pass nan tests diff --git a/buildtools/third_party/libc++/BUILD.gn b/buildtools/third_party/libc++/BUILD.gn -index 73c197f3cecd7ff34e97326cbf615e7c78919a54..1e93e7ce444cd5c31ddeac86fb1549c648a9a5c0 100644 +index 78e270c731f1d40adb231fd16877f83ce1e34e31..cf15334412329f8e0dbdf11e744a425d6d571c7f 100644 --- a/buildtools/third_party/libc++/BUILD.gn +++ b/buildtools/third_party/libc++/BUILD.gn -@@ -298,6 +298,7 @@ target(libcxx_target_type, "libc++") { +@@ -423,6 +423,7 @@ target(libcxx_target_type, "libc++") { # need to explicitly depend on libc++. visibility = [ "//build/config:common_deps", diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index 97d4048b611d7..f68c789132d3e 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -9,10 +9,10 @@ potentially prevent a window from being created. TODO(loc): this patch is currently broken. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index 4c1785b8b7dcc2e0543b12bc4c765c8f0c833451..be73611db5328c76982ecca3caf5eccc30aac45e 100644 +index 23cd457563d7d534e924428ac6da2b475e579326..d8698f9f37eefa50bf4e29a164b2cc302c32ecdf 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -9718,6 +9718,7 @@ void RenderFrameHostImpl::CreateNewWindow( +@@ -9725,6 +9725,7 @@ void RenderFrameHostImpl::CreateNewWindow( last_committed_origin_, params->window_container_type, params->target_url, params->referrer.To(), params->frame_name, params->disposition, *params->features, @@ -21,10 +21,10 @@ index 4c1785b8b7dcc2e0543b12bc4c765c8f0c833451..be73611db5328c76982ecca3caf5eccc &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 8bd0e1d60f6f1af48b106f25d8e8951423eb05ed..c0ef22f3872e96be15867428aff1006b8a14a1df 100644 +index e57951543e9f2b0be5164dde3d4b629b081457cc..811d137c4b77d3347dc8de5bb6207646c952f23b 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5308,6 +5308,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5317,6 +5317,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( // Sets the newly created WebContents WindowOpenDisposition. new_contents_impl->original_window_open_disposition_ = params.disposition; @@ -37,7 +37,7 @@ index 8bd0e1d60f6f1af48b106f25d8e8951423eb05ed..c0ef22f3872e96be15867428aff1006b // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5349,12 +5355,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5358,12 +5364,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } @@ -66,10 +66,10 @@ index 09f1899c9b044a05b2e40c291f17fdf1f9f2fcac..89643bf7059d4fc0d6de6116ffe0fdac // Operation result when the renderer asks the browser to create a new window. diff --git a/content/public/browser/content_browser_client.cc b/content/public/browser/content_browser_client.cc -index eb036b92b42d794cabd71f4c6314962df8988bbb..0ec4e4f41d261f60cb8e963ca1d715b765e7c47d 100644 +index 4a377944faaf947ef478e2d858444b5d3a000c47..f8fffc6d41d26d15ff1f563005d58039099d069e 100644 --- a/content/public/browser/content_browser_client.cc +++ b/content/public/browser/content_browser_client.cc -@@ -842,6 +842,8 @@ bool ContentBrowserClient::CanCreateWindow( +@@ -848,6 +848,8 @@ bool ContentBrowserClient::CanCreateWindow( const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -79,7 +79,7 @@ index eb036b92b42d794cabd71f4c6314962df8988bbb..0ec4e4f41d261f60cb8e963ca1d715b7 bool opener_suppressed, bool* no_javascript_access) { diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 8c53f1aab26cf78ae0526ae51c1738019f1c0b90..0a74c5a3bee425c5c1af33ef27791a6d852baa6e 100644 +index 0d0d957b353e0b147efce4380c445f664741d6f4..08b098fa486c77294250563edbc5d2421fda3d69 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -200,6 +200,7 @@ class NetworkService; @@ -90,7 +90,7 @@ index 8c53f1aab26cf78ae0526ae51c1738019f1c0b90..0a74c5a3bee425c5c1af33ef27791a6d } // namespace network namespace sandbox { -@@ -1403,6 +1404,8 @@ class CONTENT_EXPORT ContentBrowserClient { +@@ -1409,6 +1410,8 @@ class CONTENT_EXPORT ContentBrowserClient { const std::string& frame_name, WindowOpenDisposition disposition, const blink::mojom::WindowFeatures& features, @@ -148,7 +148,7 @@ index d33274984bf6523beeb3ab5ee586499d224bff3c..83bdd195339eb7d61ac88e2994fd8dab // typically happens when popups are created. virtual void WebContentsCreated(WebContents* source_contents, diff --git a/content/renderer/render_frame_impl.cc b/content/renderer/render_frame_impl.cc -index b6da726a70555c2074077a2105b078e1850824d9..3fa43adedd6ff0258edd195bde1e68977cff3a7c 100644 +index d83b79b725d28b22903e3f6227e982a2ed5573f5..5c8ffb1462a21f5d798656efc872ba09d6c0de99 100644 --- a/content/renderer/render_frame_impl.cc +++ b/content/renderer/render_frame_impl.cc @@ -6937,6 +6937,10 @@ WebView* RenderFrameImpl::CreateNewWindow( @@ -210,10 +210,10 @@ index 82e9d3dfb5f7da76d89fe15ae61d379fa46e177d..fd035512099a54dff6cc951a2226c23a } // namespace blink diff --git a/third_party/blink/renderer/core/frame/local_dom_window.cc b/third_party/blink/renderer/core/frame/local_dom_window.cc -index 382daacf9b2ea77c4d8814fa375ecbbd830cce50..4728a4b7c064fc902317115637b6e64f068b25a8 100644 +index 23e8b0820df2546e0097d667758c818ef725a2e7..ef692c6d82dee347bc8956cb2337fa7a35f0c50d 100644 --- a/third_party/blink/renderer/core/frame/local_dom_window.cc +++ b/third_party/blink/renderer/core/frame/local_dom_window.cc -@@ -2293,6 +2293,8 @@ DOMWindow* LocalDOMWindow::open(v8::Isolate* isolate, +@@ -2318,6 +2318,8 @@ DOMWindow* LocalDOMWindow::open(v8::Isolate* isolate, WebWindowFeatures window_features = GetWindowFeaturesFromString(features, entered_window); diff --git a/patches/chromium/cherry-pick-f1e6422a355c.patch b/patches/chromium/cherry-pick-f1e6422a355c.patch deleted file mode 100644 index 5dcafde545708..0000000000000 --- a/patches/chromium/cherry-pick-f1e6422a355c.patch +++ /dev/null @@ -1,273 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Yoshisato Yanagisawa -Date: Wed, 21 May 2025 23:25:12 -0700 -Subject: Enforce SharedWorker::Terminate() procedure order - -During the investigation of crbug.com/409059706, we observed that -PerformShutdownOnWorkerThread() is called during the status is -running. - -I suppose the root cause is race condition between `Terminate()` -procedure and a child process termination procedure in different -thread. WorkerThread can be terminated if two conditions are met; -`Terminate()` is called and all child worker threads have been -terminated. Both `Terminate()` and the child process termination -procedure may call `PerformShutdownOnWorkerThread()`, and former -is executed regardless of two conditions are met. The latter -is called if `Terminate()` is called and no child processes. -To be clear, "`Terminate()` is called" does not mean -`PrepareForShutdownOnWorkerThread()` is executed. `Terminate()` -queues it after the flag to tell `Terminate()` call. And, when -the issue happen, I am quite sure the flag is set but, -`PrepareForShutdownOnWorkerThread()` won't be executed yet. - -The fix is that: -1. The "Terminate() is called" flag to be multi staged. - The flag is used for two purpose; a. avoid re-enter of - `Terminate()`, and b. `PrepareForShutdownOnWorkerThread()` is - in flight. The CL changed the flag to enum to represent - the stage properly. -2. `PerformShutdownOnWorkerThread()` is queued even if it is - called within the child process termination procedure. - It avoid the execution order flip between - `PrepareForShutdownOnWorkerThread()` and - `PerformShutdownOnWorkerThread()`. - -In addition, this change ensures `PerformShutdownOnWorkerThread()` -is called once. While `PerformShutdownOnWorkerThread()` touches -fields inside, the fields must not be touched at some point within -the function, the function is actually not re-entrant when it reaches -to the end. Upon mikt@ suggestion, I made -`PerformShutdownOnWorkerThread()` is called only when two conditions -are fulfilled. i.e. `Terminate()` is called and the number of child -threads is 0. Also, the CL uses the enum to show -`PerformShutdownOnWorkerThread()` is in-flight to avoid re-entrance -in this level. - -Bug: 409059706 -Change-Id: I81a1c3b1a34e827fa75ec2d1a9b37023965dbe27 -Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6543412 -Reviewed-by: Hiroki Nakagawa -Commit-Queue: Yoshisato Yanagisawa -Cr-Commit-Position: refs/heads/main@{#1463892} - -diff --git a/third_party/blink/common/features.cc b/third_party/blink/common/features.cc -index 58caf0050b649f8c43e30b6e59eab968b0bb7334..7863bf237a9a5c273120c8de29e71db589367b3d 100644 ---- a/third_party/blink/common/features.cc -+++ b/third_party/blink/common/features.cc -@@ -2845,6 +2845,13 @@ BASE_FEATURE(kWebviewAccelerateSmallCanvases, - "WebviewAccelerateSmallCanvases", - base::FEATURE_DISABLED_BY_DEFAULT); - -+// WorkerThread termination procedure (prepare and shutdown) runs sequentially -+// in the same task without calling another cross thread post task. -+// Kill switch for crbug.com/409059706. -+BASE_FEATURE(kWorkerThreadSequentialShutdown, -+ "WorkerThreadSequentialShutdown", -+ base::FEATURE_ENABLED_BY_DEFAULT); -+ - BASE_FEATURE(kNoReferrerForPreloadFromSubresource, - "NoReferrerForPreloadFromSubresource", - base::FEATURE_ENABLED_BY_DEFAULT); -diff --git a/third_party/blink/public/common/features.h b/third_party/blink/public/common/features.h -index 2d3ffda8afe1772c817517d1542dbd3aa8bccbce..340ea360177c00424f0eb3461e65c6ba011e43c5 100644 ---- a/third_party/blink/public/common/features.h -+++ b/third_party/blink/public/common/features.h -@@ -1841,6 +1841,8 @@ BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kWebUSBTransferSizeLimit); - - BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kWebviewAccelerateSmallCanvases); - -+BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kWorkerThreadSequentialShutdown); -+ - // Kill switch for https://crbug.com/415810136. - BLINK_COMMON_EXPORT BASE_DECLARE_FEATURE(kNoReferrerForPreloadFromSubresource); - -diff --git a/third_party/blink/renderer/core/workers/worker_thread.cc b/third_party/blink/renderer/core/workers/worker_thread.cc -index 7d13d80a7f09e47d9f3c6da860e8d3373d5b8afd..6e95eba151e3a002b66d55d1ee538e9cd88cd4bb 100644 ---- a/third_party/blink/renderer/core/workers/worker_thread.cc -+++ b/third_party/blink/renderer/core/workers/worker_thread.cc -@@ -263,9 +263,10 @@ void WorkerThread::Terminate() { - DCHECK_CALLED_ON_VALID_THREAD(parent_thread_checker_); - { - base::AutoLock locker(lock_); -- if (requested_to_terminate_) -+ if (termination_progress_ != TerminationProgress::kNotRequested) { - return; -- requested_to_terminate_ = true; -+ } -+ termination_progress_ = TerminationProgress::kRequested; - } - - // Schedule a task to forcibly terminate the script execution in case that the -@@ -281,10 +282,33 @@ void WorkerThread::Terminate() { - *task_runner, FROM_HERE, - CrossThreadBindOnce(&WorkerThread::PrepareForShutdownOnWorkerThread, - CrossThreadUnretained(this))); -- PostCrossThreadTask( -- *task_runner, FROM_HERE, -- CrossThreadBindOnce(&WorkerThread::PerformShutdownOnWorkerThread, -- CrossThreadUnretained(this))); -+ -+ if (!base::FeatureList::IsEnabled( -+ blink::features::kWorkerThreadSequentialShutdown)) { -+ PostCrossThreadTask( -+ *task_runner, FROM_HERE, -+ CrossThreadBindOnce(&WorkerThread::PerformShutdownOnWorkerThread, -+ CrossThreadUnretained(this))); -+ return; -+ } -+ -+ bool perform_shutdown = false; -+ { -+ base::AutoLock locker(lock_); -+ CHECK_EQ(TerminationProgress::kRequested, termination_progress_); -+ termination_progress_ = TerminationProgress::kPrepared; -+ if (num_child_threads_ == 0) { -+ termination_progress_ = TerminationProgress::kPerforming; -+ perform_shutdown = true; -+ } -+ } -+ -+ if (perform_shutdown) { -+ PostCrossThreadTask( -+ *task_runner, FROM_HERE, -+ CrossThreadBindOnce(&WorkerThread::PerformShutdownOnWorkerThread, -+ CrossThreadUnretained(this))); -+ } - } - - void WorkerThread::TerminateForTesting() { -@@ -421,20 +445,48 @@ scoped_refptr WorkerThread::GetTaskRunner( - - void WorkerThread::ChildThreadStartedOnWorkerThread(WorkerThread* child) { - DCHECK(IsCurrentThread()); --#if DCHECK_IS_ON() -+ child_threads_.insert(child); - { - base::AutoLock locker(lock_); - DCHECK_EQ(ThreadState::kRunning, thread_state_); -+ CHECK_EQ(TerminationProgress::kNotRequested, termination_progress_); -+ if (base::FeatureList::IsEnabled( -+ blink::features::kWorkerThreadSequentialShutdown)) { -+ ++num_child_threads_; -+ CHECK_EQ(child_threads_.size(), num_child_threads_); -+ } - } --#endif -- child_threads_.insert(child); - } - - void WorkerThread::ChildThreadTerminatedOnWorkerThread(WorkerThread* child) { - DCHECK(IsCurrentThread()); - child_threads_.erase(child); -- if (child_threads_.empty() && CheckRequestedToTerminate()) -- PerformShutdownOnWorkerThread(); -+ if (!base::FeatureList::IsEnabled( -+ blink::features::kWorkerThreadSequentialShutdown)) { -+ if (child_threads_.empty() && CheckRequestedToTerminate()) { -+ PerformShutdownOnWorkerThread(); -+ } -+ return; -+ } -+ -+ bool perform_shutdown = false; -+ { -+ base::AutoLock locker(lock_); -+ --num_child_threads_; -+ CHECK_EQ(child_threads_.size(), num_child_threads_); -+ if (num_child_threads_ == 0 && -+ termination_progress_ == TerminationProgress::kPrepared) { -+ termination_progress_ = TerminationProgress::kPerforming; -+ perform_shutdown = true; -+ } -+ } -+ if (perform_shutdown) { -+ scoped_refptr task_runner = -+ GetWorkerBackingThread().BackingThread().GetTaskRunner(); -+ GetWorkerBackingThread().BackingThread().GetTaskRunner()->PostTask( -+ FROM_HERE, WTF::BindOnce(&WorkerThread::PerformShutdownOnWorkerThread, -+ WTF::Unretained(this))); -+ } - } - - WorkerThread::WorkerThread(WorkerReportingProxy& worker_reporting_proxy) -@@ -778,18 +830,32 @@ void WorkerThread::PerformShutdownOnWorkerThread() { - DCHECK(IsCurrentThread()); - { - base::AutoLock locker(lock_); -- DCHECK(requested_to_terminate_); -+ if (!base::FeatureList::IsEnabled( -+ blink::features::kWorkerThreadSequentialShutdown)) { -+ DCHECK_NE(TerminationProgress::kNotRequested, termination_progress_); -+ } else { -+ DCHECK_EQ(TerminationProgress::kPerforming, termination_progress_); -+ } - DCHECK_EQ(ThreadState::kReadyToShutdown, thread_state_); - if (exit_code_ == ExitCode::kNotTerminated) - SetExitCode(ExitCode::kGracefullyTerminated); - } - -- // When child workers are present, wait for them to shutdown before shutting -- // down this thread. ChildThreadTerminatedOnWorkerThread() is responsible -- // for completing shutdown on the worker thread after the last child shuts -- // down. -- if (!child_threads_.empty()) -- return; -+ if (!base::FeatureList::IsEnabled( -+ blink::features::kWorkerThreadSequentialShutdown)) { -+ // When child workers are present, wait for them to shutdown before shutting -+ // down this thread. ChildThreadTerminatedOnWorkerThread() is responsible -+ // for completing shutdown on the worker thread after the last child shuts -+ // down. -+ if (!child_threads_.empty()) { -+ return; -+ } -+ } else { -+ // Child workers must not exist when `PerformShutdownOnWorkerThread()` -+ // is called because it has already been checked before calling the -+ // function. -+ CHECK(child_threads_.empty()); -+ } - - inspector_task_runner_->Dispose(); - if (worker_inspector_controller_) { -@@ -845,7 +911,7 @@ void WorkerThread::SetExitCode(ExitCode exit_code) { - - bool WorkerThread::CheckRequestedToTerminate() { - base::AutoLock locker(lock_); -- return requested_to_terminate_; -+ return termination_progress_ != TerminationProgress::kNotRequested; - } - - void WorkerThread::PauseOrFreeze(mojom::blink::FrameLifecycleState state, -diff --git a/third_party/blink/renderer/core/workers/worker_thread.h b/third_party/blink/renderer/core/workers/worker_thread.h -index 49a7ac5868844465c8c863186958e5e590ffef29..f48f05b795ac2490851e23282be3172ddbe3516c 100644 ---- a/third_party/blink/renderer/core/workers/worker_thread.h -+++ b/third_party/blink/renderer/core/workers/worker_thread.h -@@ -319,6 +319,13 @@ class CORE_EXPORT WorkerThread : public Thread::TaskObserver { - kTerminationUnnecessary, - }; - -+ enum class TerminationProgress { -+ kNotRequested, -+ kRequested, -+ kPrepared, -+ kPerforming, -+ }; -+ - // Returns true if we should synchronously terminate the script execution so - // that a shutdown task can be handled by the thread event loop. - TerminationState ShouldTerminateScriptExecution() -@@ -419,8 +426,10 @@ class CORE_EXPORT WorkerThread : public Thread::TaskObserver { - // A unique identifier among all WorkerThreads. - const int worker_thread_id_; - -- // Set on the parent thread. -- bool requested_to_terminate_ GUARDED_BY(lock_) = false; -+ // Represents progress after the Terminate() call. -+ TerminationProgress termination_progress_ GUARDED_BY(lock_) = -+ TerminationProgress::kNotRequested; -+ size_t num_child_threads_ GUARDED_BY(lock_) = 0; - - ThreadState thread_state_ GUARDED_BY(lock_) = ThreadState::kNotStarted; - ExitCode exit_code_ GUARDED_BY(lock_) = ExitCode::kNotTerminated; diff --git a/patches/chromium/chore_add_electron_deps_to_gitignores.patch b/patches/chromium/chore_add_electron_deps_to_gitignores.patch index 495a6c703fffb..b32cf080e12d0 100644 --- a/patches/chromium/chore_add_electron_deps_to_gitignores.patch +++ b/patches/chromium/chore_add_electron_deps_to_gitignores.patch @@ -6,10 +6,10 @@ Subject: chore: add electron deps to gitignores Makes things like "git status" quicker when developing electron locally diff --git a/.gitignore b/.gitignore -index 469572522566fa57f04bc66ade675eea2048b0df..852d842df3801564cfe8dd7c4ffb84a7b3af8fc1 100644 +index d69c2f1ff69789512d89eed5982da803e0fcd813..0d4ba5c34634785d297340a8168f7ea18448f8e2 100644 --- a/.gitignore +++ b/.gitignore -@@ -220,6 +220,7 @@ vs-chromium-project.txt +@@ -222,6 +222,7 @@ vs-chromium-project.txt /data /delegate_execute /device/serial/device_serial_mojo.xml diff --git a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch index 598f8cdb6a2fe..99cd086881e30 100644 --- a/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch +++ b/patches/chromium/chore_grandfather_in_electron_views_and_delegates.patch @@ -49,7 +49,7 @@ index 0dbbd7979ad79a7a74681222fcf36a315f0634ce..b04e77440c1273c5b866ea329e62ac07 // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop class. diff --git a/ui/views/widget/widget_delegate.h b/ui/views/widget/widget_delegate.h -index 89de188e6a0139a236a824b189f1048613d6f457..c438376c34cac4ec7ac7a03d852685c18b10068e 100644 +index d2011a5c04973980e245f498ad4e6e1f65e6cc4b..f1aecd776878a368cc7debccfd5db6bd098c7ec4 100644 --- a/ui/views/widget/widget_delegate.h +++ b/ui/views/widget/widget_delegate.h @@ -165,6 +165,12 @@ namespace crostini { @@ -63,9 +63,9 @@ index 89de188e6a0139a236a824b189f1048613d6f457..c438376c34cac4ec7ac7a03d852685c1 +} + namespace enterprise_connectors { - class ContentAnalysisDialog; + class ContentAnalysisDialogController; class ContentAnalysisDialogBehaviorBrowserTest; -@@ -367,6 +373,7 @@ class VIEWS_EXPORT WidgetDelegate { +@@ -374,6 +380,7 @@ class VIEWS_EXPORT WidgetDelegate { class OwnedByWidgetPassKey { private: @@ -73,7 +73,7 @@ index 89de188e6a0139a236a824b189f1048613d6f457..c438376c34cac4ec7ac7a03d852685c1 // DO NOT ADD TO THIS LIST! // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop `SetOwnedByWidget()`. -@@ -463,6 +470,7 @@ class VIEWS_EXPORT WidgetDelegate { +@@ -470,6 +477,7 @@ class VIEWS_EXPORT WidgetDelegate { }; class RegisterDeleteCallbackPassKey { private: @@ -81,7 +81,7 @@ index 89de188e6a0139a236a824b189f1048613d6f457..c438376c34cac4ec7ac7a03d852685c1 // DO NOT ADD TO THIS LIST! // These existing cases are "grandfathered in", but there shouldn't be more. // See comments atop `RegisterDeleteDelegateCallback()`. -@@ -913,6 +921,7 @@ class VIEWS_EXPORT WidgetDelegateView : public WidgetDelegate, public View { +@@ -927,6 +935,7 @@ class VIEWS_EXPORT WidgetDelegateView : public WidgetDelegate, public View { View* GetContentsView() override; private: diff --git a/patches/chromium/chore_introduce_blocking_api_for_electron.patch b/patches/chromium/chore_introduce_blocking_api_for_electron.patch index cb012a2a811bd..0fbdb80214b08 100644 --- a/patches/chromium/chore_introduce_blocking_api_for_electron.patch +++ b/patches/chromium/chore_introduce_blocking_api_for_electron.patch @@ -7,7 +7,7 @@ This patch comes after Chromium removed the ScopedAllowIO API in favor of explicitly adding ScopedAllowBlocking calls as friends. diff --git a/base/threading/thread_restrictions.h b/base/threading/thread_restrictions.h -index 20d867b5d56cd6d961004b19bd3e69ee306dd816..07db0c05df4ce028017e70e6f593235516aa556e 100644 +index b1abcfaab58df4555d3a26481915d64ef5458e17..f2f43454c1c124da9983998564837ebf3589aefd 100644 --- a/base/threading/thread_restrictions.h +++ b/base/threading/thread_restrictions.h @@ -132,6 +132,7 @@ class KeyStorageLinux; @@ -28,7 +28,7 @@ index 20d867b5d56cd6d961004b19bd3e69ee306dd816..07db0c05df4ce028017e70e6f5932355 namespace enterprise_connectors { class LinuxKeyRotationCommand; } // namespace enterprise_connectors -@@ -578,6 +582,7 @@ class BASE_EXPORT ScopedAllowBlocking { +@@ -577,6 +581,7 @@ class BASE_EXPORT ScopedAllowBlocking { friend class ::DesktopNotificationBalloon; friend class ::FirefoxProfileLock; friend class ::GaiaConfig; @@ -36,7 +36,7 @@ index 20d867b5d56cd6d961004b19bd3e69ee306dd816..07db0c05df4ce028017e70e6f5932355 friend class ::ProfileImpl; friend class ::ScopedAllowBlockingForProfile; friend class ::StartupTabProviderImpl; -@@ -616,6 +621,7 @@ class BASE_EXPORT ScopedAllowBlocking { +@@ -615,6 +620,7 @@ class BASE_EXPORT ScopedAllowBlocking { friend class cronet::CronetPrefsManager; friend class crypto::ScopedAllowBlockingForNSS; // http://crbug.com/59847 friend class drive::FakeDriveService; diff --git a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch index 8dc23c774a1d4..3f578c108f41e 100644 --- a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch +++ b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch @@ -34,10 +34,10 @@ index 39b5a8fdd165efd74b00256552b51b5413107958..bfc4ef4f50efff4a77f2aef64335bb7e class ScrollEvent; diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index 3c273b08e3a0cb1a249334b06244bb6b89fde27f..20fcbe09d9fe9104cbe791e03b02f8e2e5064c2d 100644 +index b687c8505f1afc918fc4994dd6fbb8b6520e3e8a..d8168622ee2e0d42f8d4486d8f9391b4508aff54 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -@@ -1382,6 +1382,10 @@ void DesktopWindowTreeHostWin::HandleHeadlessWindowBoundsChanged( +@@ -1360,6 +1360,10 @@ void DesktopWindowTreeHostWin::HandleHeadlessWindowBoundsChanged( window()->SetProperty(aura::client::kHeadlessBoundsKey, bounds); } @@ -49,7 +49,7 @@ index 3c273b08e3a0cb1a249334b06244bb6b89fde27f..20fcbe09d9fe9104cbe791e03b02f8e2 DesktopWindowTreeHostWin::GetSingletonDesktopNativeCursorManager() { return new DesktopNativeCursorManagerWin(); diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h -index dab595aacaeca4f6f735fd04004c27a4949278d2..177134d439866db9dbbde657ff358a761ad7f39d 100644 +index 28cbd63261275e252381d88c13c1a3b4067d197f..45e47bae0e8b3369072c6e179206aa6d222e0ec5 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h @@ -272,6 +272,7 @@ class VIEWS_EXPORT DesktopWindowTreeHostWin diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 290f57a3ca584..065bc7cdf9349 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 29185fc4c426652d192870c8a11aaa981a08ebf8..de2e8163c6ae5a1a01a79413d3d44b7c11ede311 100644 +index fbe6b5d24185c0b0e664db05c7801434737d4d8d..51798b8ceb81cf9d374cf594aa6afbcb366f4732 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5224,7 +5224,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5233,7 +5233,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch b/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch index a383798ee3330..31a680bd7d01a 100644 --- a/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch +++ b/patches/chromium/chore_patch_out_partition_attribute_dcheck_for_webviews.patch @@ -14,10 +14,10 @@ This change patches it out to prevent the DCHECK. It can be removed once/if we see a better solution to the problem. diff --git a/content/browser/site_instance_impl.cc b/content/browser/site_instance_impl.cc -index 8db7e1a1ac6947a630cdf6993bf9cef772252cd9..4a4f5bb2fa0e26b921b2e40fade705e83c0bc573 100644 +index c88f60749ed5c1371a4b85540f515c2124043f53..cea6f1123dcff9b7531783fb6d50c43e9e1cd5fb 100644 --- a/content/browser/site_instance_impl.cc +++ b/content/browser/site_instance_impl.cc -@@ -226,7 +226,7 @@ scoped_refptr SiteInstanceImpl::CreateForGuest( +@@ -227,7 +227,7 @@ scoped_refptr SiteInstanceImpl::CreateForGuest( BrowserContext* browser_context, const StoragePartitionConfig& partition_config) { DCHECK(browser_context); diff --git a/patches/chromium/chore_patch_out_profile_methods_in_chrome_browser_pdf.patch b/patches/chromium/chore_patch_out_profile_methods_in_chrome_browser_pdf.patch index 4a93ef5d28865..5992bc3b2cf6e 100644 --- a/patches/chromium/chore_patch_out_profile_methods_in_chrome_browser_pdf.patch +++ b/patches/chromium/chore_patch_out_profile_methods_in_chrome_browser_pdf.patch @@ -28,3 +28,21 @@ index e3b9f14a4cf2167064ce6716053e663adffa1542..65f13a4607c8145858fd47d81cb9960c // When the enterprise policy is not set, use finch/feature flag choice. return base::FeatureList::IsEnabled( +diff --git a/chrome/browser/pdf/pdf_extension_util.cc b/chrome/browser/pdf/pdf_extension_util.cc +index 8967bad0bc644d7a1541fdf86fa9d65c0b2c5dd0..25f75dd808e56dbcb3f6a4e284f7485427507e7e 100644 +--- a/chrome/browser/pdf/pdf_extension_util.cc ++++ b/chrome/browser/pdf/pdf_extension_util.cc +@@ -245,10 +245,13 @@ bool IsPrintingEnabled(content::BrowserContext* context) { + + #if BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(ENABLE_PDF_INK2) + bool IsPdfAnnotationsEnabledByPolicy(content::BrowserContext* context) { ++# if 0 + PrefService* prefs = + context ? Profile::FromBrowserContext(context)->GetPrefs() : nullptr; + return !prefs || !prefs->IsManagedPreference(prefs::kPdfAnnotationsEnabled) || + prefs->GetBoolean(prefs::kPdfAnnotationsEnabled); ++#endif ++ return true; + } + #endif // BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(ENABLE_PDF_INK2) + diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index 2014d114c1799..82a9de6faac0c 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -80,7 +80,7 @@ index b6582b4013d9682d32bd524b4053b443a4df00f8..afcbce72e0f247b4d5a637b27c9f25d9 content::WebContents* source, const content::OpenURLParams& params, diff --git a/chrome/browser/ui/browser.cc b/chrome/browser/ui/browser.cc -index 875c7a37c48ce50b5439a51df5e505e1bbcd5155..035432c70a6b65a2520f130e0db8a91f20e92770 100644 +index 8c5e577eb89cf1ee85e76fea6385f7a18a60143b..2ae70471cfa301570d696662182773e868054143 100644 --- a/chrome/browser/ui/browser.cc +++ b/chrome/browser/ui/browser.cc @@ -2392,8 +2392,7 @@ bool Browser::IsWebContentsCreationOverridden( @@ -103,10 +103,10 @@ index 875c7a37c48ce50b5439a51df5e505e1bbcd5155..035432c70a6b65a2520f130e0db8a91f WebContents* Browser::CreateCustomWebContents( diff --git a/chrome/browser/ui/browser.h b/chrome/browser/ui/browser.h -index 9dfba94b0aaa3f27f363bd50b489cae9e0e3cda6..3867e5d5741103ee0b65533dae4b80906b393f59 100644 +index 1de7f9596b2f8f545ad5da7db51a35e5e0fc8592..0db8f52ef8375970f966fe8a2e3e06a8b2eeac02 100644 --- a/chrome/browser/ui/browser.h +++ b/chrome/browser/ui/browser.h -@@ -1037,8 +1037,7 @@ class Browser : public TabStripModelObserver, +@@ -1026,8 +1026,7 @@ class Browser : public TabStripModelObserver, content::SiteInstance* source_site_instance, content::mojom::WindowContainerType window_container_type, const GURL& opener_url, @@ -222,10 +222,10 @@ index b969f1d97b7e3396119b579cfbe61e19ff7d2dd4..b8d6169652da28266a514938b45b39c5 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 6eaa7d566058fdcc9ebfa10f0420c3a234cb0483..bbbc07e36e6de11169f8317c64558b8c4d1699d5 100644 +index 33abfcd326148f32eff2266a4545345e4a561a4e..4bb69438947fff73a6905a1ecc1b711986a89124 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5187,8 +5187,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5196,8 +5196,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( if (delegate_ && delegate_->IsWebContentsCreationOverridden( opener, source_site_instance, params.window_container_type, diff --git a/patches/chromium/command-ismediakey.patch b/patches/chromium/command-ismediakey.patch index 50e25fcbe5e78..c8a7504f742ff 100644 --- a/patches/chromium/command-ismediakey.patch +++ b/patches/chromium/command-ismediakey.patch @@ -95,10 +95,10 @@ index 9e63dd9d33abc89a7bbef75992925356470ebb26..9071afc9bb01db832164909a202effaf bool is_listening_ = false; diff --git a/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_win.cc b/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_win.cc -index 034ccea0cda4265abbfc889178f4cba4f3bd7eb8..384f0968aca07cde1fe6434a318e5334f6ecbe9e 100644 +index d3838460df1f61dbcee1cc6586632cb218fec97a..4351cfeea03b8adc5da8500db1faf6d8b8811454 100644 --- a/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_win.cc +++ b/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener_win.cc -@@ -67,6 +67,8 @@ void GlobalAcceleratorListenerWin::OnWndProc(HWND hwnd, +@@ -66,6 +66,8 @@ void GlobalAcceleratorListenerWin::OnWndProc(HWND hwnd, modifiers |= (LOWORD(lparam) & MOD_SHIFT) ? ui::EF_SHIFT_DOWN : 0; modifiers |= (LOWORD(lparam) & MOD_ALT) ? ui::EF_ALT_DOWN : 0; modifiers |= (LOWORD(lparam) & MOD_CONTROL) ? ui::EF_CONTROL_DOWN : 0; @@ -107,7 +107,7 @@ index 034ccea0cda4265abbfc889178f4cba4f3bd7eb8..384f0968aca07cde1fe6434a318e5334 ui::Accelerator accelerator(ui::KeyboardCodeForWindowsKeyCode(key_code), modifiers); -@@ -97,6 +99,7 @@ bool GlobalAcceleratorListenerWin::StartListeningForAccelerator( +@@ -96,6 +98,7 @@ bool GlobalAcceleratorListenerWin::StartListeningForAccelerator( modifiers |= accelerator.IsShiftDown() ? MOD_SHIFT : 0; modifiers |= accelerator.IsCtrlDown() ? MOD_CONTROL : 0; modifiers |= accelerator.IsAltDown() ? MOD_ALT : 0; diff --git a/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch b/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch index 0e39852cbd01a..2d663454a8eb4 100644 --- a/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch +++ b/patches/chromium/create_browser_v8_snapshot_file_name_fuse.patch @@ -94,7 +94,7 @@ index db611d99a6c0f18f39967b38791822fda7d175b5..cc150475de655d5ef20a107ae3ef80c0 friend class ContentClientCreator; friend class ContentClientInitializer; diff --git a/gin/v8_initializer.cc b/gin/v8_initializer.cc -index 11cafc3e1588cce52b76cc2f09f66b3e451fb087..e07bdaeccecc8015462e35d5cf4606335e2e962c 100644 +index c79f996e2cbfe3e71f7de29424329dfc0d39a726..03c9bc18566794a668981bba6235b226e07eff74 100644 --- a/gin/v8_initializer.cc +++ b/gin/v8_initializer.cc @@ -660,8 +660,7 @@ void V8Initializer::GetV8ExternalSnapshotData(const char** snapshot_data_out, diff --git a/patches/chromium/disable_hidden.patch b/patches/chromium/disable_hidden.patch index 7c6ef540c4a15..72a1a92bcdd9c 100644 --- a/patches/chromium/disable_hidden.patch +++ b/patches/chromium/disable_hidden.patch @@ -6,7 +6,7 @@ Subject: disable_hidden.patch Electron uses this to disable background throttling for hidden windows. diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 8173547224997a68c2878d6dfb26b1cb436353c6..6a60a4b0275e1832216b092c29bc867f4727ca22 100644 +index 52f772876a8878a7dbc95bb8f243d1442d30977f..cdfdd322ffb2e61d5480ac7c88dba35a1cc1b5b9 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc @@ -833,6 +833,10 @@ void RenderWidgetHostImpl::WasHidden() { diff --git a/patches/chromium/disable_unload_metrics.patch b/patches/chromium/disable_unload_metrics.patch index 7e147685b0355..81b7a88680cd8 100644 --- a/patches/chromium/disable_unload_metrics.patch +++ b/patches/chromium/disable_unload_metrics.patch @@ -24,10 +24,10 @@ This patch temporarily disables the metrics so we can have green CI, and we should continue seeking for a real fix. diff --git a/content/browser/renderer_host/navigator.cc b/content/browser/renderer_host/navigator.cc -index d976c082529a62bcef7352531ced808e5970027e..31e95005359f6e8e4e18ebd75324940f4fdd11eb 100644 +index 3c736de224325fec247308ea8adef3c1186029f9..8b5fd128120b2a4db387bf42b632c9e2e94f7cd4 100644 --- a/content/browser/renderer_host/navigator.cc +++ b/content/browser/renderer_host/navigator.cc -@@ -1476,6 +1476,7 @@ void Navigator::RecordNavigationMetrics( +@@ -1478,6 +1478,7 @@ void Navigator::RecordNavigationMetrics( .InMilliseconds()); } @@ -35,7 +35,7 @@ index d976c082529a62bcef7352531ced808e5970027e..31e95005359f6e8e4e18ebd75324940f // If this is a same-process navigation and we have timestamps for unload // durations, fill those metrics out as well. if (params.unload_start && params.unload_end && -@@ -1525,6 +1526,7 @@ void Navigator::RecordNavigationMetrics( +@@ -1527,6 +1528,7 @@ void Navigator::RecordNavigationMetrics( first_before_unload_start_time) .InMilliseconds()); } diff --git a/patches/chromium/enable_reset_aspect_ratio.patch b/patches/chromium/enable_reset_aspect_ratio.patch index e62d786bec980..fc663286cd21c 100644 --- a/patches/chromium/enable_reset_aspect_ratio.patch +++ b/patches/chromium/enable_reset_aspect_ratio.patch @@ -6,10 +6,10 @@ Subject: feat: enable setting aspect ratio to 0 Make SetAspectRatio accept 0 as valid input, which would reset to null. diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index f754ca0c3bc3ba9e7ff2f3f883b29c15be2b410a..3c273b08e3a0cb1a249334b06244bb6b89fde27f 100644 +index 18cd413e8780161d2c1d1993e12e8d87eb12a33f..b687c8505f1afc918fc4994dd6fbb8b6520e3e8a 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -@@ -631,7 +631,7 @@ void DesktopWindowTreeHostWin::SetOpacity(float opacity) { +@@ -609,7 +609,7 @@ void DesktopWindowTreeHostWin::SetOpacity(float opacity) { void DesktopWindowTreeHostWin::SetAspectRatio( const gfx::SizeF& aspect_ratio, const gfx::Size& excluded_margin) { diff --git a/patches/chromium/expose_setuseragent_on_networkcontext.patch b/patches/chromium/expose_setuseragent_on_networkcontext.patch index d0e5af5f54773..fc017e88aa02c 100644 --- a/patches/chromium/expose_setuseragent_on_networkcontext.patch +++ b/patches/chromium/expose_setuseragent_on_networkcontext.patch @@ -33,10 +33,10 @@ index 0ab8187b0db8ae6db46d81738f653a2bc4c566f6..de3d55e85c22317f7f9375eb94d0d5d4 } // namespace net diff --git a/services/network/network_context.cc b/services/network/network_context.cc -index 02853bf6552d49986b782785d3ab5a61ec0d3734..5934676556e25e51d580e063aeb0afde2a3f2a97 100644 +index b91e9da008c121d2afbc5fd4c3c9ea401a6191a8..0b3d0538bd10c0364aa4b1a928f135893ddc7864 100644 --- a/services/network/network_context.cc +++ b/services/network/network_context.cc -@@ -1837,6 +1837,13 @@ void NetworkContext::SetNetworkConditions( +@@ -1842,6 +1842,13 @@ void NetworkContext::SetNetworkConditions( std::move(network_conditions)); } @@ -51,7 +51,7 @@ index 02853bf6552d49986b782785d3ab5a61ec0d3734..5934676556e25e51d580e063aeb0afde // This may only be called on NetworkContexts created with the constructor // that calls MakeURLRequestContext(). diff --git a/services/network/network_context.h b/services/network/network_context.h -index 5b5d8eccb9c84965e996cd8d2a8c7d962df7852a..66da9008486d58ad4835b3ba58a6b0aefb53ab2f 100644 +index fcddda19a4d37052312748a6dd4e5ffdee1d240b..259d97bb314273600ad0541260043ea0ff02e015 100644 --- a/services/network/network_context.h +++ b/services/network/network_context.h @@ -326,6 +326,7 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext @@ -63,10 +63,10 @@ index 5b5d8eccb9c84965e996cd8d2a8c7d962df7852a..66da9008486d58ad4835b3ba58a6b0ae void SetEnableReferrers(bool enable_referrers) override; #if BUILDFLAG(IS_CT_SUPPORTED) diff --git a/services/network/public/mojom/network_context.mojom b/services/network/public/mojom/network_context.mojom -index f510b5c5c79161f32a08219aa7f6cd7a722eed85..6bc2f6221fe61e861ece518381c697e4cf4727a1 100644 +index de945e5f2cb5398c37617fce5e00834b481d3875..0ca66dd8038a0410c4949d9a00f43c156c3b46c5 100644 --- a/services/network/public/mojom/network_context.mojom +++ b/services/network/public/mojom/network_context.mojom -@@ -1278,6 +1278,9 @@ interface NetworkContext { +@@ -1282,6 +1282,9 @@ interface NetworkContext { SetNetworkConditions(mojo_base.mojom.UnguessableToken throttling_profile_id, NetworkConditions? conditions); @@ -77,7 +77,7 @@ index f510b5c5c79161f32a08219aa7f6cd7a722eed85..6bc2f6221fe61e861ece518381c697e4 SetAcceptLanguage(string new_accept_language); diff --git a/services/network/test/test_network_context.h b/services/network/test/test_network_context.h -index 81930f3b5ca760d4db9c65aeb36162ddea68a872..5d67e45515480b769ed6555f6e0c18f25fde1e6c 100644 +index c57dcce278f96c9bd3157fd5d2ce0f9d0ecbef53..5a86df4d57aa255b63e503050d31320e80124700 100644 --- a/services/network/test/test_network_context.h +++ b/services/network/test/test_network_context.h @@ -159,6 +159,7 @@ class TestNetworkContext : public mojom::NetworkContext { diff --git a/patches/chromium/extend_apply_webpreferences.patch b/patches/chromium/extend_apply_webpreferences.patch index 1eb1413326471..36729a582cf23 100644 --- a/patches/chromium/extend_apply_webpreferences.patch +++ b/patches/chromium/extend_apply_webpreferences.patch @@ -12,7 +12,7 @@ Ideally we could add an embedder observer pattern here but that can be done in future work. diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index f6a248b1de8b313658453dd380529ec7c2e40033..15a6b41cacb7b66d95e6dc2cff8148c3d6c8c28b 100644 +index 2390395a3df10aca3510a619e91dab674de60e67..f8fae134e122a223440530bd696db899dce2fe56 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc @@ -172,6 +172,7 @@ @@ -23,7 +23,7 @@ index f6a248b1de8b313658453dd380529ec7c2e40033..15a6b41cacb7b66d95e6dc2cff8148c3 #include "third_party/blink/renderer/platform/graphics/image.h" #include "third_party/blink/renderer/platform/graphics/paint/cull_rect.h" #include "third_party/blink/renderer/platform/graphics/paint/paint_record_builder.h" -@@ -1862,6 +1863,7 @@ void WebView::ApplyWebPreferences(const web_pref::WebPreferences& prefs, +@@ -1864,6 +1865,7 @@ void WebView::ApplyWebPreferences(const web_pref::WebPreferences& prefs, #if BUILDFLAG(IS_MAC) web_view_impl->SetMaximumLegibleScale( prefs.default_maximum_page_scale_factor); diff --git a/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch b/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch index 0b06a833dd5b1..e5639a92858a3 100644 --- a/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch +++ b/patches/chromium/feat_add_support_for_missing_dialog_features_to_shell_dialogs.patch @@ -262,10 +262,10 @@ index 61683d0eddb04c494ca5e650e7d556b44968ec49..5492456a9138b250e97a5479838bb443 } // namespace ui diff --git a/ui/shell_dialogs/select_file_dialog_linux_portal.cc b/ui/shell_dialogs/select_file_dialog_linux_portal.cc -index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db84e8dff6 100644 +index 8dafba0690d9cde3506b60a21ba36c49394d9125..03fdd2d86e776d4be60c52790dcb2946e9341954 100644 --- a/ui/shell_dialogs/select_file_dialog_linux_portal.cc +++ b/ui/shell_dialogs/select_file_dialog_linux_portal.cc -@@ -28,6 +28,7 @@ +@@ -29,6 +29,7 @@ #include "dbus/message.h" #include "dbus/object_path.h" #include "dbus/object_proxy.h" @@ -273,7 +273,7 @@ index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db #include "ui/aura/window_tree_host.h" #include "ui/base/l10n/l10n_util.h" #include "ui/gfx/native_widget_types.h" -@@ -99,7 +100,7 @@ void OnGetPropertyReply(dbus::Response* response) { +@@ -100,7 +101,7 @@ void OnGetPropertyReply(dbus::Response* response) { : ServiceAvailability::kNotAvailable; } @@ -282,7 +282,7 @@ index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db if (!service_started.value_or(false)) { g_service_availability = ServiceAvailability::kNotAvailable; return; -@@ -166,18 +167,24 @@ void SelectFileDialogLinuxPortal::StartAvailabilityTestInBackground() { +@@ -167,18 +168,24 @@ void SelectFileDialogLinuxPortal::StartAvailabilityTestInBackground() { GetMainTaskRunner() = base::SequencedTaskRunner::GetCurrentDefault(); @@ -307,7 +307,7 @@ index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db } bool SelectFileDialogLinuxPortal::IsRunning( -@@ -382,11 +389,14 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( +@@ -383,11 +390,14 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( const PortalFilterSet& filter_set) { DbusDictionary dict; @@ -325,7 +325,7 @@ index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db [[fallthrough]]; case SelectFileDialog::SELECT_FOLDER: case SelectFileDialog::Type::SELECT_EXISTING_FOLDER: -@@ -399,6 +409,10 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( +@@ -400,6 +410,10 @@ DbusDictionary SelectFileDialogLinuxPortal::BuildOptionsDictionary( break; } @@ -333,6 +333,6 @@ index b23d357d4e21f10be82f0ea37b1ec3e959fc2c0b..e768afc05b42d4d026c88f1516d4e9db + dict.PutAs(kFileChooserOptionAcceptLabel, DbusString(accept_label)); + } + - if (!default_path.empty()) { + if (!default_path.empty() && base::IsStringUTF8(default_path.value())) { if (default_path_exists) { // If this is an existing directory, navigate to that directory, with no diff --git a/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch b/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch index e798bf875ad4d..d50324a2cdee1 100644 --- a/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch +++ b/patches/chromium/feat_allow_code_cache_in_custom_schemes.patch @@ -9,7 +9,7 @@ embedders to make custom schemes allow V8 code cache. Chromium CL: https://chromium-review.googlesource.com/c/chromium/src/+/5019665 diff --git a/content/browser/code_cache/generated_code_cache.cc b/content/browser/code_cache/generated_code_cache.cc -index d6ddb79521290790aeb8fbd997117cf3c6157c75..52a9536f4187418327f980fd3dd68211d8103374 100644 +index 1673dd4966365f31f1073a4c90743e6fe73880b6..cb3d3da5bc9da99c950521d18f28aa438467fdf4 100644 --- a/content/browser/code_cache/generated_code_cache.cc +++ b/content/browser/code_cache/generated_code_cache.cc @@ -8,6 +8,7 @@ @@ -20,7 +20,7 @@ index d6ddb79521290790aeb8fbd997117cf3c6157c75..52a9536f4187418327f980fd3dd68211 #include "base/feature_list.h" #include "base/functional/bind.h" #include "base/functional/callback_helpers.h" -@@ -32,6 +33,7 @@ +@@ -31,6 +32,7 @@ #include "net/http/http_cache.h" #include "third_party/blink/public/common/scheme_registry.h" #include "url/gurl.h" @@ -28,7 +28,7 @@ index d6ddb79521290790aeb8fbd997117cf3c6157c75..52a9536f4187418327f980fd3dd68211 using storage::BigIOBuffer; -@@ -44,7 +46,7 @@ constexpr char kSeparator[] = " \n"; +@@ -43,7 +45,7 @@ constexpr char kSeparator[] = " \n"; // We always expect to receive valid URLs that can be used as keys to the code // cache. The relevant checks (for ex: resource_url is valid, origin_lock is @@ -37,7 +37,7 @@ index d6ddb79521290790aeb8fbd997117cf3c6157c75..52a9536f4187418327f980fd3dd68211 // // This function doesn't enforce anything in the production code. It is here // to make the assumptions explicit and to catch any errors when DCHECKs are -@@ -54,33 +56,55 @@ void CheckValidKeys(const GURL& resource_url, +@@ -53,33 +55,55 @@ void CheckValidKeys(const GURL& resource_url, GeneratedCodeCache::CodeCacheType cache_type) { // If the resource url is invalid don't cache the code. DCHECK(resource_url.is_valid()); @@ -117,10 +117,10 @@ index d6ddb79521290790aeb8fbd997117cf3c6157c75..52a9536f4187418327f980fd3dd68211 // Generates the cache key for the given |resource_url|, |origin_lock| and diff --git a/content/browser/code_cache/generated_code_cache.h b/content/browser/code_cache/generated_code_cache.h -index c5fb0546fb8724a6ba34b55d8d52b2f70ad5bc0c..883c4022aa58e5eb5345ec4e8815a1374160d96c 100644 +index 94602e2319d3f7ed557da98e0598c9f96d986260..0a9a856d8bd9d702eb49e45a54c141a39f5ec622 100644 --- a/content/browser/code_cache/generated_code_cache.h +++ b/content/browser/code_cache/generated_code_cache.h -@@ -52,12 +52,14 @@ class CONTENT_EXPORT GeneratedCodeCache { +@@ -51,12 +51,14 @@ class CONTENT_EXPORT GeneratedCodeCache { // Cache type. Used for collecting statistics for JS and Wasm in separate // buckets. enum CodeCacheType { @@ -140,10 +140,10 @@ index c5fb0546fb8724a6ba34b55d8d52b2f70ad5bc0c..883c4022aa58e5eb5345ec4e8815a137 // JavaScript from chrome and chrome-untrusted pages. The resource URLs are diff --git a/content/browser/code_cache/generated_code_cache_browsertest.cc b/content/browser/code_cache/generated_code_cache_browsertest.cc -index c810c580efea05ba9b3b41a90b289224220bb203..55864eed550b09ba41732c706a81a122594949d6 100644 +index 8faec12f8a618d587964c1ffaf868dc104fa7311..6294358f6d28864e761d31a1497f96f8cc454788 100644 --- a/content/browser/code_cache/generated_code_cache_browsertest.cc +++ b/content/browser/code_cache/generated_code_cache_browsertest.cc -@@ -11,17 +11,22 @@ +@@ -12,17 +12,22 @@ #include "base/time/time.h" #include "content/browser/code_cache/generated_code_cache_context.h" #include "content/browser/renderer_host/code_cache_host_impl.h" @@ -166,7 +166,7 @@ index c810c580efea05ba9b3b41a90b289224220bb203..55864eed550b09ba41732c706a81a122 #include "net/base/features.h" #include "net/dns/mock_host_resolver.h" #include "third_party/blink/public/common/features.h" -@@ -31,6 +36,8 @@ namespace content { +@@ -32,6 +37,8 @@ namespace content { namespace { @@ -175,7 +175,7 @@ index c810c580efea05ba9b3b41a90b289224220bb203..55864eed550b09ba41732c706a81a122 bool SupportsSharedWorker() { #if BUILDFLAG(IS_ANDROID) // SharedWorkers are not enabled on Android. https://crbug.com/154571 -@@ -875,4 +882,82 @@ IN_PROC_BROWSER_TEST_F(LocalCompileHintsBrowserTest, LocalCompileHints) { +@@ -955,4 +962,82 @@ IN_PROC_BROWSER_TEST_F(LocalCompileHintsBrowserTest, LocalCompileHints) { } } diff --git a/patches/chromium/feat_configure_launch_options_for_service_process.patch b/patches/chromium/feat_configure_launch_options_for_service_process.patch index a5c061551451e..602ccf3bc4975 100644 --- a/patches/chromium/feat_configure_launch_options_for_service_process.patch +++ b/patches/chromium/feat_configure_launch_options_for_service_process.patch @@ -165,111 +165,118 @@ index 0791b5317fc6846389f65f93734ae5e816d04623..48948b409d6da58ade72c60ed848df49 FinishStartSandboxedProcessOnLauncherThread, this)); diff --git a/content/browser/service_host/service_process_host_impl.cc b/content/browser/service_host/service_process_host_impl.cc -index 96c9563aac5847e742de5d9c9236f78bcb6cfd9c..73c9d585579ad5bdc407687b8becd0b7f2d704af 100644 +index d9c14f91747bde0e76056d7f2f2ada166e67f994..53be16879777a3b9bef58ead5f7e420c1bf6acbe 100644 --- a/content/browser/service_host/service_process_host_impl.cc +++ b/content/browser/service_host/service_process_host_impl.cc -@@ -66,6 +66,17 @@ void LaunchServiceProcess(mojo::GenericPendingReceiver receiver, - options.allow_gpu_client.value()) { - host->SetAllowGpuClient(); +@@ -69,6 +69,17 @@ void LaunchServiceProcess(mojo::GenericPendingReceiver receiver, + utility_options.WithGpuClientAllowed(); } -+ + +#if BUILDFLAG(IS_WIN) -+ host->SetStdioHandles(std::move(options.stdout_handle), std::move(options.stderr_handle)); -+ host->SetFeedbackCursorOff(options.feedback_cursor_off); ++ utility_options.WithStdioHandles(std::move(service_options.stdout_handle), ++ std::move(service_options.stderr_handle)); ++ utility_options.WithFeedbackCursorOff(service_options.feedback_cursor_off); +#elif BUILDFLAG(IS_POSIX) -+ host->SetAdditionalFds(std::move(options.fds_to_remap)); ++ utility_options.WithAdditionalFds(std::move(service_options.fds_to_remap)); +#endif -+ host->SetCurrentDirectory(options.current_directory); -+ host->SetEnv(options.environment); -+ if (options.clear_environment) -+ host->ClearEnvironment(); - host->Start(); - host->GetChildProcess()->BindServiceInterface(std::move(receiver)); - } ++ utility_options.WithCurrentDirectory(service_options.current_directory); ++ utility_options.WithEnvironment(service_options.environment, ++ service_options.clear_environment); ++ + utility_options.WithBoundServiceInterfaceOnChildProcess(std::move(receiver)); + + UtilityProcessHost::Start(std::move(utility_options), diff --git a/content/browser/service_host/utility_process_host.cc b/content/browser/service_host/utility_process_host.cc -index e2c72b43f75b57ef1f49b82d3ecdfb425f8596de..51f8ff9b8424d098979a24c2e8628cdf7c4b758d 100644 +index 7db71d28fa05458bf88f468e67446ccde8a4b964..9d6c67c66576058723a6fb0a5abb279f05f15f4f 100644 --- a/content/browser/service_host/utility_process_host.cc +++ b/content/browser/service_host/utility_process_host.cc -@@ -190,11 +190,13 @@ const ChildProcessData& UtilityProcessHost::GetData() { - return process_->GetData(); +@@ -244,13 +244,13 @@ UtilityProcessHost::Options& UtilityProcessHost::Options::WithFileToPreload( } + #endif // BUILDFLAG(IS_POSIX) && !BUILDFLAG(IS_MAC) -#if BUILDFLAG(IS_POSIX) - void UtilityProcessHost::SetEnv(const base::EnvironmentMap& env) { + UtilityProcessHost::Options& UtilityProcessHost::Options::WithEnvironment( +- const base::EnvironmentMap& env) { ++ const base::EnvironmentMap& env, ++ bool new_environment) { env_ = env; ++ inherit_environment_ = !new_environment; + return *this; } -#endif -+ -+void UtilityProcessHost::ClearEnvironment() { -+ inherit_environment_ = false; -+} - bool UtilityProcessHost::Start() { - return StartProcess(); -@@ -241,6 +243,30 @@ void UtilityProcessHost::SetZygoteForTesting(ZygoteCommunication* handle) { + #if BUILDFLAG(USE_ZYGOTE) + UtilityProcessHost::Options& UtilityProcessHost::Options::WithZygoteForTesting( +@@ -260,6 +260,36 @@ UtilityProcessHost::Options& UtilityProcessHost::Options::WithZygoteForTesting( } #endif // BUILDFLAG(USE_ZYGOTE) +#if BUILDFLAG(IS_WIN) -+void UtilityProcessHost::SetStdioHandles( ++UtilityProcessHost::Options& UtilityProcessHost::Options::WithStdioHandles( + base::win::ScopedHandle stdout_handle, + base::win::ScopedHandle stderr_handle) { + stdout_handle_ = std::move(stdout_handle); + stderr_handle_ = std::move(stderr_handle); ++ return *this; +} +#elif BUILDFLAG(IS_POSIX) -+void UtilityProcessHost::SetAdditionalFds(base::FileHandleMappingVector mapping) { ++UtilityProcessHost::Options& UtilityProcessHost::Options::WithAdditionalFds( ++ base::FileHandleMappingVector mapping) { + fds_to_remap_ = std::move(mapping); ++ return *this; +} +#endif + -+void UtilityProcessHost::SetCurrentDirectory( ++UtilityProcessHost::Options& UtilityProcessHost::Options::WithCurrentDirectory( + const base::FilePath& cwd) { + current_directory_ = cwd; ++ return *this; +} + +#if BUILDFLAG(IS_WIN) -+void UtilityProcessHost::SetFeedbackCursorOff(bool feedback_cursor_off) { ++UtilityProcessHost::Options& UtilityProcessHost::Options::WithFeedbackCursorOff( ++ bool feedback_cursor_off) { + feedback_cursor_off_ = feedback_cursor_off; ++ return *this; +} +#endif // BUILDFLAG(IS_WIN) + - mojom::ChildProcess* UtilityProcessHost::GetChildProcess() { - return static_cast(process_->GetHost()) - ->child_process(); -@@ -456,9 +482,26 @@ bool UtilityProcessHost::StartProcess() { - } + UtilityProcessHost::Options& + UtilityProcessHost::Options::WithBoundReceiverOnChildProcessForTesting( + mojo::GenericPendingReceiver receiver) { +@@ -521,9 +551,26 @@ bool UtilityProcessHost::StartProcess() { + } #endif // BUILDFLAG(ENABLE_GPU_CHANNEL_MEDIA_CAPTURE) && !BUILDFLAG(IS_WIN) +#if BUILDFLAG(IS_WIN) -+ file_data_->stdout_handle = std::move(stdout_handle_); -+ file_data_->stderr_handle = std::move(stderr_handle_); ++ options_.file_data_->stdout_handle = std::move(options_.stdout_handle_); ++ options_.file_data_->stderr_handle = std::move(options_.stderr_handle_); +#elif BUILDFLAG(IS_POSIX) -+ if (!fds_to_remap_.empty()) { -+ for (const auto& remapped_fd : fds_to_remap_) { -+ file_data_->additional_remapped_fds.emplace( -+ remapped_fd.second, remapped_fd.first); -+ } ++ if (!options_.fds_to_remap_.empty()) { ++ for (const auto& remapped_fd : options_.fds_to_remap_) { ++ options_.file_data_->additional_remapped_fds.emplace(remapped_fd.second, ++ remapped_fd.first); + } ++ } +#endif + - std::unique_ptr delegate = - std::make_unique( -- sandbox_type_, env_, *cmd_line); -+ sandbox_type_, env_, current_directory_, *cmd_line, -+ inherit_environment_); + std::unique_ptr delegate = + std::make_unique( +- options_.sandbox_type_, options_.env_, *cmd_line); ++ options_.sandbox_type_, options_.env_, options_.current_directory_, ++ *cmd_line, options_.inherit_environment_); + +#if BUILDFLAG(IS_WIN) -+ delegate->SetFeedbackCursorOff(feedback_cursor_off_); ++ delegate->SetFeedbackCursorOff(options_.feedback_cursor_off_); +#endif // BUILDFLAG(IS_WIN) #if BUILDFLAG(IS_WIN) - if (!preload_libraries_.empty()) { + if (!options_.preload_libraries_.empty()) { diff --git a/content/browser/service_host/utility_process_host.h b/content/browser/service_host/utility_process_host.h -index d13e6db4857242480591bff040709532d16f513d..1164da12ee71a8575c17bf1b84a505e8a32b96b3 100644 +index 4335d7ff718c3d7de92320ba11c39c3957303788..55379fbe9233ba96f6e4729e2b7d534c0c6884a0 100644 --- a/content/browser/service_host/utility_process_host.h +++ b/content/browser/service_host/utility_process_host.h -@@ -30,6 +30,10 @@ +@@ -29,6 +29,10 @@ #include "content/public/common/zygote/zygote_handle.h" #endif // BUILDFLAG(USE_ZYGOTE) @@ -280,72 +287,69 @@ index d13e6db4857242480591bff040709532d16f513d..1164da12ee71a8575c17bf1b84a505e8 namespace base { class Thread; } // namespace base -@@ -99,9 +103,13 @@ class CONTENT_EXPORT UtilityProcessHost +@@ -111,14 +115,31 @@ class CONTENT_EXPORT UtilityProcessHost + std::variant file); + #endif - // Returns information about the utility child process. - const ChildProcessData& GetData(); -#if BUILDFLAG(IS_POSIX) -+ -+ // Set/Unset environment variables. - void SetEnv(const base::EnvironmentMap& env); +- Options& WithEnvironment(const base::EnvironmentMap& env); -#endif -+ -+ // Clear the environment for the new process before processing -+ // changes from SetEnv. -+ void ClearEnvironment(); ++ // Specifies the environment that should be applied to the process. ++ // |new_environment| controls whether the process should inherit ++ // environment from the parent process. ++ Options& WithEnvironment(const base::EnvironmentMap& env, ++ bool new_environment); - // Starts the utility process. - bool Start(); -@@ -139,6 +147,21 @@ class CONTENT_EXPORT UtilityProcessHost - void SetZygoteForTesting(ZygoteCommunication* handle); + #if BUILDFLAG(USE_ZYGOTE) + Options& WithZygoteForTesting(ZygoteCommunication* handle); #endif // BUILDFLAG(USE_ZYGOTE) +#if BUILDFLAG(IS_WIN) -+ void SetStdioHandles(base::win::ScopedHandle stdout_handle, -+ base::win::ScopedHandle stderr_handle); ++ Options& WithStdioHandles(base::win::ScopedHandle stdout_handle, ++ base::win::ScopedHandle stderr_handle); +#elif BUILDFLAG(IS_POSIX) -+ void SetAdditionalFds(base::FileHandleMappingVector mapping); ++ Options& WithAdditionalFds(base::FileHandleMappingVector mapping); +#endif + -+ // Sets the working directory of the process. -+ void SetCurrentDirectory(const base::FilePath& cwd); ++ // Sets the working directory of the process. ++ Options& WithCurrentDirectory(const base::FilePath& cwd); + +#if BUILDFLAG(IS_WIN) -+ // Specifies if the process should trigger mouse cursor feedback. -+ void SetFeedbackCursorOff(bool feedback_cursor_off); ++ // Specifies if the process should trigger mouse cursor feedback. ++ Options& WithFeedbackCursorOff(bool feedback_cursor_off); +#endif // BUILDFLAG(IS_WIN) + - // Returns a control interface for the running child process. - mojom::ChildProcess* GetChildProcess(); - -@@ -192,6 +215,27 @@ class CONTENT_EXPORT UtilityProcessHost - std::optional> zygote_for_testing_; + // Requests that the process bind a receiving pipe targeting the interface + // named by `receiver`. Calls to this method generally end up in + // `ChildThreadImpl::OnBindReceiver()` and the option is used for testing +@@ -162,6 +183,27 @@ class CONTENT_EXPORT UtilityProcessHost + std::optional> zygote_for_testing_; #endif // BUILDFLAG(USE_ZYGOTE) +#if BUILDFLAG(IS_WIN) -+ // Specifies the handles for redirection of stdout and stderr. -+ base::win::ScopedHandle stdout_handle_; -+ base::win::ScopedHandle stderr_handle_; ++ // Specifies the handles for redirection of stdout and stderr. ++ base::win::ScopedHandle stdout_handle_; ++ base::win::ScopedHandle stderr_handle_; +#elif BUILDFLAG(IS_POSIX) -+ // Specifies file descriptors to propagate into the child process -+ // based on the mapping. -+ base::FileHandleMappingVector fds_to_remap_; ++ // Specifies file descriptors to propagate into the child process ++ // based on the mapping. ++ base::FileHandleMappingVector fds_to_remap_; +#endif + -+ // If not empty, change to this directory before executing the new process. -+ base::FilePath current_directory_; ++ // If not empty, change to this directory before executing the new process. ++ base::FilePath current_directory_; + -+ // Inherit enviroment from parent process. -+ bool inherit_environment_ = true; ++ // Inherit enviroment from parent process. ++ bool inherit_environment_ = true; + +#if BUILDFLAG(IS_WIN) -+ // Specifies if the process should trigger mouse cursor feedback. -+ bool feedback_cursor_off_ = false; ++ // Specifies if the process should trigger mouse cursor feedback. ++ bool feedback_cursor_off_ = false; +#endif // BUILDFLAG(IS_WIN) + - // Indicates whether the process has been successfully launched yet, or if - // launch failed. - enum class LaunchState { + #if BUILDFLAG(ENABLE_GPU_CHANNEL_MEDIA_CAPTURE) + // Whether or not to bind viz::mojom::Gpu to the utility process. + bool allowed_gpu_; diff --git a/content/browser/service_host/utility_sandbox_delegate.cc b/content/browser/service_host/utility_sandbox_delegate.cc index 5ff3c5dcb972eb635107557ea7c26eb1f3331d22..5b1939226dcb84a61b09eefe69ab24a5ad595e1b 100644 --- a/content/browser/service_host/utility_sandbox_delegate.cc diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index e51dc822db4b5..448182b8d3b8a 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -75,7 +75,7 @@ index f8361faf6151210d65a597562c533aaa0a5235df..328238c34a9381fbbeb5970af3de721c // used for canvas noising. uint64 canvas_noise_token = 0; diff --git a/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom b/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom -index 8e1737f9d205c511ae8e4103278a2650166f3915..ced3d02fdf338e3e2a07e93a4d22b2f9398c2267 100644 +index a96527c653d2108de572d1e94c3ce703b45f2830..f8eb2af2c97f888307f2be588c336d4209f6cb3e 100644 --- a/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom +++ b/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom @@ -48,6 +48,7 @@ enum CSSSampleId { @@ -87,10 +87,10 @@ index 8e1737f9d205c511ae8e4103278a2650166f3915..ced3d02fdf338e3e2a07e93a4d22b2f9 // This CSSSampleId represents page load for CSS histograms. It is recorded once // per page visit for each CSS histogram being logged on the blink side and the diff --git a/third_party/blink/public/web/web_settings.h b/third_party/blink/public/web/web_settings.h -index a53b4901dde0dc83dce6c9b56616eef0d02d94a5..b419672af985f673f375fbb63b4d2b2c419e3e03 100644 +index c37f784a1309da14354881d48a5a76a965930926..bffd221d2b3f3701710025103fa564c233e203d1 100644 --- a/third_party/blink/public/web/web_settings.h +++ b/third_party/blink/public/web/web_settings.h -@@ -285,6 +285,7 @@ class WebSettings { +@@ -287,6 +287,7 @@ class WebSettings { virtual void SetRequireTransientActivationAndAuthorizationForSubAppsAPIs( bool) = 0; virtual void SetRootScrollbarThemeColor(std::optional) = 0; @@ -112,10 +112,10 @@ index 6e991652d242795e292cea4c94cff59aaea078fa..b6834c78575520bb6e584dd2ce3333ac 'internal-forced-visited-'): internal_visited_order = 0 diff --git a/third_party/blink/renderer/core/css/css_properties.json5 b/third_party/blink/renderer/core/css/css_properties.json5 -index 63fff5e26a00d65818e5a05ae4f3285162521574..23cbe424b6c9de4f66cf1c2ce91682bf706d6f90 100644 +index 5619eae5a36f63627df605eeff049866ea846477..50bad85a916e5bb097d687cbc4d1721ecefa6c39 100644 --- a/third_party/blink/renderer/core/css/css_properties.json5 +++ b/third_party/blink/renderer/core/css/css_properties.json5 -@@ -8824,6 +8824,24 @@ +@@ -8866,6 +8866,24 @@ property_methods: ["ParseShorthand", "CSSValueFromComputedStyleInternal"], }, @@ -141,7 +141,7 @@ index 63fff5e26a00d65818e5a05ae4f3285162521574..23cbe424b6c9de4f66cf1c2ce91682bf { name: "-internal-visited-color", diff --git a/third_party/blink/renderer/core/css/css_property_equality.cc b/third_party/blink/renderer/core/css/css_property_equality.cc -index 11c153b01a111efed101ae53d2148b7f523a66f5..7a3547a2aa70ef7699bf9022a15199d499e8a802 100644 +index 9ec4976d64834bd4c09f3740edcd28334dd4ec50..e47da0a85670e800e74da957d6441d70d1c7ddd8 100644 --- a/third_party/blink/renderer/core/css/css_property_equality.cc +++ b/third_party/blink/renderer/core/css/css_property_equality.cc @@ -348,6 +348,8 @@ bool CSSPropertyEquality::PropertiesEqual(const PropertyHandle& property, @@ -154,10 +154,10 @@ index 11c153b01a111efed101ae53d2148b7f523a66f5..7a3547a2aa70ef7699bf9022a15199d4 return a.EmptyCells() == b.EmptyCells(); case CSSPropertyID::kFill: diff --git a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -index db463eb084f96e661a271be0646d6dbc84913ee2..336564df6f1266d6f186a56efd1836cfba951c72 100644 +index e519e13fea11950cc619e384f774b61a6e2385c0..8289ca0a41da1532692673a3e426e8688d93b32e 100644 --- a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -@@ -12143,5 +12143,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( +@@ -12175,5 +12175,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( CSSValueID::kNone>(stream); } @@ -184,11 +184,11 @@ index db463eb084f96e661a271be0646d6dbc84913ee2..336564df6f1266d6f186a56efd1836cf } // namespace css_longhand } // namespace blink diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -index ae5470212b28d47f8b79799d1ef52757fcd5cbae..667ba05f2595048bcadab0b394c52540f8bceaf1 100644 +index 5618121a0b5621290a19f147bfbe9bf316fb3f27..bb1bd90371ce847d48ff9a228b098a26d28f5c6d 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -@@ -3913,4 +3913,12 @@ PositionArea StyleBuilderConverter::ConvertPositionArea( - return PositionArea(span[0], span[1], span[2], span[3]); +@@ -3962,4 +3962,12 @@ FitText StyleBuilderConverter::ConvertFitText(StyleResolverState& state, + return FitText(target, method, size_limit); } +Length StyleBuilderConverter::ConvertCornerSmoothing(StyleResolverState& state, const CSSValue& value) { @@ -201,23 +201,23 @@ index ae5470212b28d47f8b79799d1ef52757fcd5cbae..667ba05f2595048bcadab0b394c52540 + } // namespace blink diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h -index d761af01cc6b4ef01304dfe384c3aa92f414b8a2..de0f1c09f41b4f348a7163967f6d90d98fe7c06c 100644 +index 7104b5866a9bac0cdd26518eddcf80322280ad92..692b186f302130155fbb1b163bb195c0253276af 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h -@@ -421,6 +421,8 @@ class StyleBuilderConverter { - const CSSValue&); +@@ -422,6 +422,8 @@ class StyleBuilderConverter { static PositionArea ConvertPositionArea(StyleResolverState&, const CSSValue&); + static FitText ConvertFitText(StyleResolverState&, const CSSValue&); + + static Length ConvertCornerSmoothing(StyleResolverState&, const CSSValue&); }; template diff --git a/third_party/blink/renderer/core/exported/web_settings_impl.cc b/third_party/blink/renderer/core/exported/web_settings_impl.cc -index 4a29a2200eaab5084078e928a68c862296c6ff91..fcd879deec0e68b3b6988402d19570cf0065daa2 100644 +index 90692da7bddd9e26e58cb26d8b29dbddf958fbca..6bcd9d736edab85572e405ab74d57adc0fcce921 100644 --- a/third_party/blink/renderer/core/exported/web_settings_impl.cc +++ b/third_party/blink/renderer/core/exported/web_settings_impl.cc -@@ -816,4 +816,8 @@ void WebSettingsImpl::SetRootScrollbarThemeColor( +@@ -820,4 +820,8 @@ void WebSettingsImpl::SetRootScrollbarThemeColor( settings_->SetRootScrollbarThemeColor(theme_color); } @@ -227,10 +227,10 @@ index 4a29a2200eaab5084078e928a68c862296c6ff91..fcd879deec0e68b3b6988402d19570cf + } // namespace blink diff --git a/third_party/blink/renderer/core/exported/web_settings_impl.h b/third_party/blink/renderer/core/exported/web_settings_impl.h -index 5e8d2bfbccd0625c2598544a9cba3d71373eded2..e68a97ee75754fc7196f11cf5c731550b5a12276 100644 +index aa8b248b94ea7f6c0e04dc66e976dc7923ff3a98..868630ed2adb8f40fb7f002d45b260c0881ef10f 100644 --- a/third_party/blink/renderer/core/exported/web_settings_impl.h +++ b/third_party/blink/renderer/core/exported/web_settings_impl.h -@@ -237,6 +237,7 @@ class CORE_EXPORT WebSettingsImpl final : public WebSettings { +@@ -238,6 +238,7 @@ class CORE_EXPORT WebSettingsImpl final : public WebSettings { void SetRequireTransientActivationAndAuthorizationForSubAppsAPIs( bool) override; void SetRootScrollbarThemeColor(std::optional) override; @@ -239,10 +239,10 @@ index 5e8d2bfbccd0625c2598544a9cba3d71373eded2..e68a97ee75754fc7196f11cf5c731550 bool RenderVSyncNotificationEnabled() const { return render_v_sync_notification_enabled_; diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index 15a6b41cacb7b66d95e6dc2cff8148c3d6c8c28b..88bb3d17a4ca0784f1f28fde14b9fa58e15b5c44 100644 +index f8fae134e122a223440530bd696db899dce2fe56..cec68a428fbf63932066ceb296c3db3eb9e34166 100644 --- a/third_party/blink/renderer/core/exported/web_view_impl.cc +++ b/third_party/blink/renderer/core/exported/web_view_impl.cc -@@ -3577,6 +3577,9 @@ void WebViewImpl::UpdateRendererPreferences( +@@ -3579,6 +3579,9 @@ void WebViewImpl::UpdateRendererPreferences( renderer_preferences_.view_source_line_wrap_enabled); MaybePreloadSystemFonts(GetPage()); @@ -253,10 +253,10 @@ index 15a6b41cacb7b66d95e6dc2cff8148c3d6c8c28b..88bb3d17a4ca0784f1f28fde14b9fa58 void WebViewImpl::SetHistoryIndexAndLength(int32_t history_index, diff --git a/third_party/blink/renderer/core/frame/settings.json5 b/third_party/blink/renderer/core/frame/settings.json5 -index f4cdee12ea4352067f5de3e074e43d51ef56d2e5..6377e4b1ea8aa46b0bf69f8420b6c439bea70dba 100644 +index c96100f7d26c14b8be1329cdb4d8a007b14d9c00..8b2429d5ac958f9a2c7aae546b44da903def8e69 100644 --- a/third_party/blink/renderer/core/frame/settings.json5 +++ b/third_party/blink/renderer/core/frame/settings.json5 -@@ -1261,5 +1261,10 @@ +@@ -1265,5 +1265,10 @@ initial: false, type: "bool" }, @@ -307,10 +307,10 @@ index 2c2f4f405074e5baa4a26f255283404f86b40e21..ebeb7d6988ee9e6a4e78cb82fc01fdad ContouredRect PixelSnappedContouredBorderInternal( diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn -index b63dfc16103a6882ffb4dd81a20408092aaed3ab..d56e6f0a527ddc8adccb5fec3adb66fd2f5c99bd 100644 +index e8db5553065fd9a8ea03ec9d6cee136a8ea666dc..05eafec9e86846469e1877fe2a84b75a0dfe23ee 100644 --- a/third_party/blink/renderer/platform/BUILD.gn +++ b/third_party/blink/renderer/platform/BUILD.gn -@@ -1658,6 +1658,8 @@ component("platform") { +@@ -1652,6 +1652,8 @@ component("platform") { "widget/widget_base.h", "widget/widget_base_client.h", "windows_keyboard_codes.h", @@ -320,7 +320,7 @@ index b63dfc16103a6882ffb4dd81a20408092aaed3ab..d56e6f0a527ddc8adccb5fec3adb66fd sources -= blink_platform_avx_files diff --git a/third_party/blink/renderer/platform/geometry/contoured_rect.h b/third_party/blink/renderer/platform/geometry/contoured_rect.h -index 54d3ae85eaed0699714728bcb8ff0c817f6b5e86..3014d286ecbef8b9a90f007527cce5141110eaf6 100644 +index 0dbfffdfbea2cb75f7f3ea94ead20cc8bbe08bb3..021b9cdebb023941e7a78afbc1c3c939f3b9cfa0 100644 --- a/third_party/blink/renderer/platform/geometry/contoured_rect.h +++ b/third_party/blink/renderer/platform/geometry/contoured_rect.h @@ -47,19 +47,29 @@ class PLATFORM_EXPORT ContouredRect { @@ -355,8 +355,8 @@ index 54d3ae85eaed0699714728bcb8ff0c817f6b5e86..3014d286ecbef8b9a90f007527cce514 + return (top_left_ == kRound) && IsUniform() && !IsSmooth(); } - constexpr bool IsUniform() const { -@@ -71,6 +81,7 @@ class PLATFORM_EXPORT ContouredRect { + constexpr bool IsConvex() const { +@@ -76,6 +86,7 @@ class PLATFORM_EXPORT ContouredRect { constexpr float TopRight() const { return top_right_; } constexpr float BottomRight() const { return bottom_right_; } constexpr float BottomLeft() const { return bottom_left_; } @@ -364,7 +364,7 @@ index 54d3ae85eaed0699714728bcb8ff0c817f6b5e86..3014d286ecbef8b9a90f007527cce514 constexpr bool operator==(const CornerCurvature&) const = default; -@@ -81,6 +92,7 @@ class PLATFORM_EXPORT ContouredRect { +@@ -86,6 +97,7 @@ class PLATFORM_EXPORT ContouredRect { float top_right_ = kRound; float bottom_right_ = kRound; float bottom_left_ = kRound; @@ -373,7 +373,7 @@ index 54d3ae85eaed0699714728bcb8ff0c817f6b5e86..3014d286ecbef8b9a90f007527cce514 // A Corner is a axis-aligned quad, with the points ordered (start, outer, diff --git a/third_party/blink/renderer/platform/geometry/path_builder.cc b/third_party/blink/renderer/platform/geometry/path_builder.cc -index 414b73e219a7f4e499414cf120c5b8ebd0ae3a63..2093364a27e89fa10fe9a6921453d2d8285e445e 100644 +index 171cb3dd87609f5ecab79a25fe0978cd6e4b04f4..7e7deae45bfb66c3a3702f30092a23fb5b79bf4b 100644 --- a/third_party/blink/renderer/platform/geometry/path_builder.cc +++ b/third_party/blink/renderer/platform/geometry/path_builder.cc @@ -4,6 +4,7 @@ @@ -384,7 +384,7 @@ index 414b73e219a7f4e499414cf120c5b8ebd0ae3a63..2093364a27e89fa10fe9a6921453d2d8 #include "third_party/blink/renderer/platform/geometry/contoured_rect.h" #include "third_party/blink/renderer/platform/geometry/infinite_int_rect.h" #include "third_party/blink/renderer/platform/geometry/path.h" -@@ -241,6 +242,26 @@ PathBuilder& PathBuilder::AddContouredRect( +@@ -247,6 +248,26 @@ PathBuilder& PathBuilder::AddContouredRect( AddRoundedRect(target_rect); return *this; } diff --git a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch index 107aa4007339f..2f1b81e558628 100644 --- a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch +++ b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch @@ -90,7 +90,7 @@ index 8af69cac78b7488d28f1f05ccb174793fe5148cd..9f74e511c263d147b5fbe81fe100d217 private: const HWND hwnd_; diff --git a/components/viz/service/BUILD.gn b/components/viz/service/BUILD.gn -index 3c43af49c5d6d5f604c71e9a9dc1f7afe9aaf0f7..857e422776e7ec33eaf4c9983d42d6433b7723cc 100644 +index 7f53771dbebb480e5d10fd6926e86120f020b1ee..1ce3faf14e3770c18a67717bcd0a8d07d7720045 100644 --- a/components/viz/service/BUILD.gn +++ b/components/viz/service/BUILD.gn @@ -178,6 +178,8 @@ viz_component("service") { @@ -522,7 +522,7 @@ index f0aca972c4a81c3dfb536e14244daafae21ee716..a15afbc1a3519e657121b4952444d2f4 waiting_on_draw_ack_ = true; diff --git a/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc b/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc -index 391004b202e6f20ad06eb6a53a6d55f5e8981c75..acb849f4e737de45e7aa4640b6866791424f010b 100644 +index 671923d06e450edc191e5717537d74b91678872d..6bae1cc6634256e449b02e92a4e7899573926109 100644 --- a/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc +++ b/components/viz/service/frame_sinks/root_compositor_frame_sink_impl.cc @@ -130,7 +130,8 @@ RootCompositorFrameSinkImpl::Create( @@ -585,10 +585,10 @@ index 130067b91baa360a7234fecfe6342c8239d587b5..d701328102f9a53e12b1b2e2a8626591 compositor_data.display_client->GetBoundRemote(resize_task_runner_); mojo::AssociatedRemote diff --git a/services/viz/privileged/mojom/compositing/display_private.mojom b/services/viz/privileged/mojom/compositing/display_private.mojom -index afdda5292ce89d6dac6eaa1e3476fdfd0e9e7f08..8147e4bf6173699df6ab9492898989c68ffbb2b8 100644 +index e063835e87f08e6a2359886a96d7b78954e3d5b2..34bcf67726f64466d11a56d7a315ce7e05a0cb3d 100644 --- a/services/viz/privileged/mojom/compositing/display_private.mojom +++ b/services/viz/privileged/mojom/compositing/display_private.mojom -@@ -123,7 +123,6 @@ interface DisplayClient { +@@ -119,7 +119,6 @@ interface DisplayClient { // Creates a LayeredWindowUpdater implementation to draw into a layered // window. diff --git a/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch b/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch index 0c133fce18816..a8016618c0d9d 100644 --- a/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch +++ b/patches/chromium/feat_enable_passing_exit_code_on_service_process_crash.patch @@ -11,7 +11,7 @@ ServiceProcessHost::Observer functions, but we need to pass the exit code to the observer. diff --git a/content/browser/service_host/service_process_tracker.cc b/content/browser/service_host/service_process_tracker.cc -index 594629e45acd6cac9deba2d02c682a523c80e2fb..61be7804bbf370df3d2925880804866a631d35fa 100644 +index e900841900325dd090b04f85151dc7b2f04a6613..e402bcf07aa0704c113ce472db547ffcfb04a4bf 100644 --- a/content/browser/service_host/service_process_tracker.cc +++ b/content/browser/service_host/service_process_tracker.cc @@ -48,12 +48,14 @@ void ServiceProcessTracker::NotifyTerminated(ServiceProcessId id) { @@ -22,7 +22,7 @@ index 594629e45acd6cac9deba2d02c682a523c80e2fb..61be7804bbf370df3d2925880804866a +void ServiceProcessTracker::NotifyCrashed(ServiceProcessId id, int exit_code) { DCHECK_CURRENTLY_ON(BrowserThread::UI); auto iter = processes_.find(id); - CHECK(iter != processes_.end(), base::NotFatalUntil::M130); + CHECK(iter != processes_.end()); for (auto& observer : observers_) { - observer.OnServiceProcessCrashed(iter->second.Duplicate()); + auto params = iter->second.Duplicate(); @@ -80,10 +80,10 @@ index 801db538979ba62facdcf3a472dade56723ca639..7abac9a5b13b393713534ae51664c2e5 private: const std::string service_interface_name_; diff --git a/content/browser/service_host/utility_process_host.cc b/content/browser/service_host/utility_process_host.cc -index 51f8ff9b8424d098979a24c2e8628cdf7c4b758d..19d8ed89211402e93632c4d83dbf452d4194a14c 100644 +index 9d6c67c66576058723a6fb0a5abb279f05f15f4f..d692bc5929bce7801d0a91cb99ab9c5f07ba5d7b 100644 --- a/content/browser/service_host/utility_process_host.cc +++ b/content/browser/service_host/utility_process_host.cc -@@ -541,7 +541,7 @@ void UtilityProcessHost::OnProcessCrashed(int exit_code) { +@@ -609,7 +609,7 @@ void UtilityProcessHost::OnProcessCrashed(int exit_code) { // Take ownership of |client_| so the destructor doesn't notify it of // termination. auto client = std::move(client_); @@ -93,10 +93,10 @@ index 51f8ff9b8424d098979a24c2e8628cdf7c4b758d..19d8ed89211402e93632c4d83dbf452d std::optional UtilityProcessHost::GetServiceName() { diff --git a/content/browser/service_host/utility_process_host.h b/content/browser/service_host/utility_process_host.h -index 1164da12ee71a8575c17bf1b84a505e8a32b96b3..4cbc30fc4b57440d06a0a0f642cc44c5c755e7f9 100644 +index 55379fbe9233ba96f6e4729e2b7d534c0c6884a0..850592294efd2c0a0fdc253b7b3fb6441b91d730 100644 --- a/content/browser/service_host/utility_process_host.h +++ b/content/browser/service_host/utility_process_host.h -@@ -79,7 +79,7 @@ class CONTENT_EXPORT UtilityProcessHost +@@ -68,7 +68,7 @@ class CONTENT_EXPORT UtilityProcessHost virtual void OnProcessLaunched(const base::Process& process) {} virtual void OnProcessTerminatedNormally() {} @@ -104,7 +104,7 @@ index 1164da12ee71a8575c17bf1b84a505e8a32b96b3..4cbc30fc4b57440d06a0a0f642cc44c5 + virtual void OnProcessCrashed(int exit_code) {} }; - // This class is self-owned. It must be instantiated using new, and shouldn't + struct CONTENT_EXPORT Options { diff --git a/content/public/browser/service_process_info.h b/content/public/browser/service_process_info.h index 1a8656aef341cd3b23af588fb00569b79d6cd100..6af523eb27a8c1e5529721c029e5b3ba0708b9fc 100644 --- a/content/public/browser/service_process_info.h diff --git a/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch b/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch index db2bb3935c133..8b11c3ad7ee18 100644 --- a/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch +++ b/patches/chromium/feat_expose_documentloader_setdefersloading_on_webdocumentloader.patch @@ -28,7 +28,7 @@ index 33e23680b927d417b0882c7572fe32dc2d2b90c3..9413492f8e0fd6c5371c66329e1ad6d4 // Returns the http referrer of original request which initited this load. diff --git a/third_party/blink/renderer/core/loader/document_loader.h b/third_party/blink/renderer/core/loader/document_loader.h -index 01b97e569a69fb1395e63492ac75432d648bb71f..6e58d859e2afd3bd8b9b17c53ba9ccc6dbdcd458 100644 +index bcf51f743caa1e7da6cb80f2e219661cde0efab6..ddb36c1757ec7e0a3a1f19a2687a1f3e3d590b6e 100644 --- a/third_party/blink/renderer/core/loader/document_loader.h +++ b/third_party/blink/renderer/core/loader/document_loader.h @@ -325,7 +325,7 @@ class CORE_EXPORT DocumentLoader : public GarbageCollected, diff --git a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch index 47c34fd73b1da..5d06ea2e34675 100644 --- a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch +++ b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch @@ -112,7 +112,7 @@ index 99bf736ebe303d46ab1ced924ba929a0cd258909..e10c8782d2704ff9cff8062d201a4339 string mime_type; diff --git a/services/network/url_loader.cc b/services/network/url_loader.cc -index 77569bb055bf2dde5370b05c814ff793f1cf4b19..bc361afc2b2fb5045f43fc49471cfc7f51b4cd74 100644 +index b4e32dd34c6d5f826da777dce7502da7ff75e76a..dcc180c6eab0c145721c4a06f74a3feef859b363 100644 --- a/services/network/url_loader.cc +++ b/services/network/url_loader.cc @@ -388,6 +388,9 @@ URLLoader::URLLoader( diff --git a/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch b/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch index d929dd7d0054b..1ca7c84398220 100644 --- a/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch +++ b/patches/chromium/feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch @@ -20,10 +20,10 @@ This patch will be removed when the deprecated sync api support is removed. diff --git a/components/permissions/permission_util.cc b/components/permissions/permission_util.cc -index f134056b6b255935250721d6fbd417b1d658c87c..f69c10c32011c9da5c235a5199abce44e64982da 100644 +index b379cc24f772260ea360779b26ca0836d21c89c4..bface283d508d1c1a3f9fd297d92e048bdd423af 100644 --- a/components/permissions/permission_util.cc +++ b/components/permissions/permission_util.cc -@@ -502,6 +502,7 @@ ContentSettingsType PermissionUtil::PermissionTypeToContentSettingsTypeSafe( +@@ -520,6 +520,7 @@ ContentSettingsType PermissionUtil::PermissionTypeToContentSettingsTypeSafe( return ContentSettingsType::WEB_APP_INSTALLATION; case PermissionType::LOCAL_NETWORK_ACCESS: return ContentSettingsType::LOCAL_NETWORK_ACCESS; diff --git a/patches/chromium/fix_adjust_headless_mode_handling_in_native_widget.patch b/patches/chromium/fix_adjust_headless_mode_handling_in_native_widget.patch index 88353892f9859..b5a2354bdd434 100644 --- a/patches/chromium/fix_adjust_headless_mode_handling_in_native_widget.patch +++ b/patches/chromium/fix_adjust_headless_mode_handling_in_native_widget.patch @@ -31,10 +31,10 @@ index b51482ecbb8eaed649ae0ea9dd9c7c71125b51a2..0180a182a8b55df4e515d77f696fa442 // Register the CGWindowID (used to identify this window for video capture) diff --git a/ui/views/widget/widget.h b/ui/views/widget/widget.h -index 65154f18c7ce737ea1b48ebd9308896d8a13f622..ec821403356d2d45c9c12831a89704be10ee05f7 100644 +index dfe785f5d0a540086884a925d7340cbf5f48cd92..5023f7f738b4ca227690411a270a58a0faae01b2 100644 --- a/ui/views/widget/widget.h +++ b/ui/views/widget/widget.h -@@ -1238,6 +1238,8 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate, +@@ -1242,6 +1242,8 @@ class VIEWS_EXPORT Widget : public internal::NativeWidgetDelegate, // True if widget was created in headless mode. bool is_headless() const { return is_headless_; } diff --git a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch index e9594ef50b2e2..64d6bd9e0582d 100644 --- a/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch +++ b/patches/chromium/fix_crash_loading_non-standard_schemes_in_iframes.patch @@ -28,10 +28,10 @@ The patch should be removed in favor of either: Upstream bug https://bugs.chromium.org/p/chromium/issues/detail?id=1081397. diff --git a/content/browser/renderer_host/navigation_request.cc b/content/browser/renderer_host/navigation_request.cc -index deb3de267fb5e6a326985fa7943e5a66217888f8..ad53374b86efe1db1e2c2e06056cd3b50696ad9b 100644 +index 17bf91944a4b3c09a17bf91153e360bb5e151f87..0803c64ac92a08f7bb9239e775479a025ca512be 100644 --- a/content/browser/renderer_host/navigation_request.cc +++ b/content/browser/renderer_host/navigation_request.cc -@@ -11158,6 +11158,11 @@ url::Origin NavigationRequest::GetOriginForURLLoaderFactoryUnchecked() { +@@ -11194,6 +11194,11 @@ url::Origin NavigationRequest::GetOriginForURLLoaderFactoryUnchecked() { target_rph_id); } @@ -44,7 +44,7 @@ index deb3de267fb5e6a326985fa7943e5a66217888f8..ad53374b86efe1db1e2c2e06056cd3b5 // origin of |common_params.url| and/or |common_params.initiator_origin|. url::Origin resolved_origin = url::Origin::Resolve( diff --git a/third_party/blink/renderer/core/loader/document_loader.cc b/third_party/blink/renderer/core/loader/document_loader.cc -index 094f7359e5d3b701676daa6c26fa6f8dee9d4a29..ac23e8b6e5b16670e942bf4801d97296176e2a00 100644 +index b021464bc5ceca1bc33fcd6f9de39590c08a6cb0..90bf26b987cd1ab63dfd9dede640acc40588fccc 100644 --- a/third_party/blink/renderer/core/loader/document_loader.cc +++ b/third_party/blink/renderer/core/loader/document_loader.cc @@ -2332,6 +2332,10 @@ Frame* DocumentLoader::CalculateOwnerFrame() { diff --git a/patches/chromium/fix_disabling_background_throttling_in_compositor.patch b/patches/chromium/fix_disabling_background_throttling_in_compositor.patch index 9687ea68c7cf1..c9bb0cf3d92d2 100644 --- a/patches/chromium/fix_disabling_background_throttling_in_compositor.patch +++ b/patches/chromium/fix_disabling_background_throttling_in_compositor.patch @@ -12,10 +12,10 @@ invisible state of the `viz::DisplayScheduler` owned by the `ui::Compositor`. diff --git a/ui/compositor/compositor.cc b/ui/compositor/compositor.cc -index d770a26ca3e49c0aced95dc362802187d7d81269..788afc7ff05bf622d9e495988034ab9ca2207bfb 100644 +index a63fea66e8fa675fb23b0cc2cb2bf63a18a11f94..76be1ae3f1f9981acc8062b831e6bb2b89f0234b 100644 --- a/ui/compositor/compositor.cc +++ b/ui/compositor/compositor.cc -@@ -359,7 +359,8 @@ void Compositor::SetLayerTreeFrameSink( +@@ -358,7 +358,8 @@ void Compositor::SetLayerTreeFrameSink( if (display_private_) { disabled_swap_until_resize_ = false; display_private_->Resize(size()); @@ -25,7 +25,7 @@ index d770a26ca3e49c0aced95dc362802187d7d81269..788afc7ff05bf622d9e495988034ab9c display_private_->SetDisplayColorSpaces(display_color_spaces_); display_private_->SetDisplayColorMatrix( gfx::SkM44ToTransform(display_color_matrix_)); -@@ -610,7 +611,9 @@ void Compositor::SetVisible(bool visible) { +@@ -609,7 +610,9 @@ void Compositor::SetVisible(bool visible) { // updated then. We need to call this even if the visibility hasn't changed, // for the same reason. if (display_private_) @@ -36,7 +36,7 @@ index d770a26ca3e49c0aced95dc362802187d7d81269..788afc7ff05bf622d9e495988034ab9c if (changed) { observer_list_.Notify(&CompositorObserver::OnCompositorVisibilityChanged, -@@ -1074,6 +1077,15 @@ void Compositor::MaybeUpdateObserveBeginFrame() { +@@ -1073,6 +1076,15 @@ void Compositor::MaybeUpdateObserveBeginFrame() { host_begin_frame_observer_->GetBoundRemote()); } diff --git a/patches/chromium/fix_getcursorscreenpoint_wrongly_returns_0_0.patch b/patches/chromium/fix_getcursorscreenpoint_wrongly_returns_0_0.patch index 9888b25d5a34d..5a934c972e95f 100644 --- a/patches/chromium/fix_getcursorscreenpoint_wrongly_returns_0_0.patch +++ b/patches/chromium/fix_getcursorscreenpoint_wrongly_returns_0_0.patch @@ -10,10 +10,10 @@ This patch should be backported to e29, upstreamed to Chromium, and then removed if it lands upstream. diff --git a/ui/events/x/events_x_utils.cc b/ui/events/x/events_x_utils.cc -index 0fcb43d631eb638ad6879539dee8ad8a21da945b..86f8756f038a68bae29072318d874e23e4d00707 100644 +index f7b051baad322919837bcd3c2516d1d838f8b2f8..303f5512cfff9e04dfd83dd25f2331d9ca0b5ace 100644 --- a/ui/events/x/events_x_utils.cc +++ b/ui/events/x/events_x_utils.cc -@@ -594,6 +594,9 @@ gfx::Point EventLocationFromXEvent(const x11::Event& xev) { +@@ -596,6 +596,9 @@ gfx::Point EventLocationFromXEvent(const x11::Event& xev) { gfx::Point EventSystemLocationFromXEvent(const x11::Event& xev) { if (auto* crossing = xev.As()) return gfx::Point(crossing->root_x, crossing->root_y); diff --git a/patches/chromium/fix_media_key_usage_with_globalshortcuts.patch b/patches/chromium/fix_media_key_usage_with_globalshortcuts.patch index 7fa99a886469e..5e9f5aa43a9aa 100644 --- a/patches/chromium/fix_media_key_usage_with_globalshortcuts.patch +++ b/patches/chromium/fix_media_key_usage_with_globalshortcuts.patch @@ -49,10 +49,10 @@ index 42e37564e585987d367921568f0f1d2b7507f953..9baf89efbade01e8b60c579255f10799 } diff --git a/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener.cc b/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener.cc -index cdf35a5bcec7b30f1b75e77cc29a9b7bb591cfd6..b6dfeee587faa742beb4f1d871db4c4f76bf46ab 100644 +index 16b11c6115cc5504dbd15d58c4b9786633e90e96..7c0a2308d437a2d9cec433c6ab0fd6a9d0c08845 100644 --- a/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener.cc +++ b/ui/base/accelerators/global_accelerator_listener/global_accelerator_listener.cc -@@ -65,6 +65,22 @@ void GlobalAcceleratorListener::UnregisterAccelerator( +@@ -64,6 +64,22 @@ void GlobalAcceleratorListener::UnregisterAccelerator( } } diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 0a09c111672c8..1a74119031b3e 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 97df851aa73d1bf8d8c8001646b63cbb43cd9a92..29185fc4c426652d192870c8a11aaa981a08ebf8 100644 +index eefecd6b3b9c940c3ae3e9ef40075c4a109878ef..fbe6b5d24185c0b0e664db05c7801434737d4d8d 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10162,7 +10162,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -10171,7 +10171,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch index 280c1093565ae..7dbf4bee82036 100644 --- a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch +++ b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch @@ -11,7 +11,7 @@ This patch should be upstreamed as a conditional revert of the logic in desktop vs mobile runtimes. i.e. restore the old logic only on desktop platforms diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 6a939edf24643207b26c9cc155ccca661b06f937..c33beb8be5535ad0951013ef0617fb881fe9fac4 100644 +index a3cbb6cb369c2f250c702a0117e36e9aee04068c..05afca0c5560297b3fc4b993e872b6f296971615 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc @@ -2134,9 +2134,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { diff --git a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch index 25a3c6fd18ae0..d53e5cfaffff4 100644 --- a/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch +++ b/patches/chromium/fix_return_v8_value_from_localframe_requestexecutescript.patch @@ -59,7 +59,7 @@ index cba373664bec3a32abad6fe0396bd67b53b7e67f..a54f1b3351efd2d8f324436f7f35cd43 #endif // THIRD_PARTY_BLINK_PUBLIC_WEB_WEB_SCRIPT_EXECUTION_CALLBACK_H_ diff --git a/third_party/blink/renderer/core/frame/local_frame.cc b/third_party/blink/renderer/core/frame/local_frame.cc -index 574f947602f8cf9d5abebf6180dc3fb67dc85496..235742d9ac2787c290c123403160d095609e8c16 100644 +index afa8d181e836739f4136cf51ae323f29b0b25ebe..2d28356c755c9bec18a73937b506c1885358378f 100644 --- a/third_party/blink/renderer/core/frame/local_frame.cc +++ b/third_party/blink/renderer/core/frame/local_frame.cc @@ -3085,6 +3085,7 @@ void LocalFrame::RequestExecuteScript( @@ -80,10 +80,10 @@ index 574f947602f8cf9d5abebf6180dc3fb67dc85496..235742d9ac2787c290c123403160d095 void LocalFrame::SetEvictCachedSessionStorageOnFreezeOrUnload() { diff --git a/third_party/blink/renderer/core/frame/local_frame.h b/third_party/blink/renderer/core/frame/local_frame.h -index a65d5821a23a965ad715377ab15ca9df20ade075..63be18b05aa31ca48202e2809b235348fec61b0e 100644 +index ba0caf0b5791c09cd51adcdcbd733ebb23d5eae1..eb74e44ee93e2a5f2f53e0f8584e2a7a37890ed5 100644 --- a/third_party/blink/renderer/core/frame/local_frame.h +++ b/third_party/blink/renderer/core/frame/local_frame.h -@@ -834,6 +834,7 @@ class CORE_EXPORT LocalFrame final +@@ -831,6 +831,7 @@ class CORE_EXPORT LocalFrame final mojom::blink::EvaluationTiming, mojom::blink::LoadEventBlockingOption, WebScriptExecutionCallback, diff --git a/patches/chromium/frame_host_manager.patch b/patches/chromium/frame_host_manager.patch index 1fb5372d75642..f8fdb435df232 100644 --- a/patches/chromium/frame_host_manager.patch +++ b/patches/chromium/frame_host_manager.patch @@ -6,10 +6,10 @@ Subject: frame_host_manager.patch Allows embedder to intercept site instances created by chromium. diff --git a/content/browser/renderer_host/render_frame_host_manager.cc b/content/browser/renderer_host/render_frame_host_manager.cc -index 39eae72b5f9f05fc9dda3b6b3a51b4d1d2bf7fcf..cd95bbd34218cb3181b887832a84893cd90c67a5 100644 +index a194fbb2bebaa2ea5797d138e13f3c4e1bbf049e..a77307e94c5479a77085b51a1b31ab382090da53 100644 --- a/content/browser/renderer_host/render_frame_host_manager.cc +++ b/content/browser/renderer_host/render_frame_host_manager.cc -@@ -4752,6 +4752,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( +@@ -4768,6 +4768,9 @@ RenderFrameHostManager::GetSiteInstanceForNavigationRequest( request->ResetStateForSiteInstanceChange(); } @@ -20,7 +20,7 @@ index 39eae72b5f9f05fc9dda3b6b3a51b4d1d2bf7fcf..cd95bbd34218cb3181b887832a84893c } diff --git a/content/public/browser/content_browser_client.h b/content/public/browser/content_browser_client.h -index 0a74c5a3bee425c5c1af33ef27791a6d852baa6e..2a657027c39370d7ea839576afe547ad6da6c5a7 100644 +index 08b098fa486c77294250563edbc5d2421fda3d69..8747d3fedd8d0b51c1479ed6b3424bf596ddd0ef 100644 --- a/content/public/browser/content_browser_client.h +++ b/content/public/browser/content_browser_client.h @@ -341,6 +341,11 @@ class CONTENT_EXPORT ContentBrowserClient { diff --git a/patches/chromium/gin_enable_disable_v8_platform.patch b/patches/chromium/gin_enable_disable_v8_platform.patch index b0ac9ec5498b0..7efc1ecc9e73f 100644 --- a/patches/chromium/gin_enable_disable_v8_platform.patch +++ b/patches/chromium/gin_enable_disable_v8_platform.patch @@ -41,7 +41,7 @@ index ff42cfbb6a228e902317c7e3ab035d8437d5dd62..e27f177ce27e177abf6cee84cd466e7a // Returns whether `Initialize` has already been invoked in the process. // Initialization is a one-way operation (i.e., this method cannot return diff --git a/gin/v8_initializer.cc b/gin/v8_initializer.cc -index 69ab1ef4d2a386126009036d4517c69dcaf9a33a..11cafc3e1588cce52b76cc2f09f66b3e451fb087 100644 +index 4e4b552aabc2f0cef91737e45652835c4de501bc..c79f996e2cbfe3e71f7de29424329dfc0d39a726 100644 --- a/gin/v8_initializer.cc +++ b/gin/v8_initializer.cc @@ -543,7 +543,8 @@ void SetFeatureFlags() { diff --git a/patches/chromium/gritsettings_resource_ids.patch b/patches/chromium/gritsettings_resource_ids.patch index 6e31d7bb7ed72..6018fbbb748a5 100644 --- a/patches/chromium/gritsettings_resource_ids.patch +++ b/patches/chromium/gritsettings_resource_ids.patch @@ -6,10 +6,10 @@ Subject: gritsettings_resource_ids.patch Add electron resources file to the list of resource ids generation. diff --git a/tools/gritsettings/resource_ids.spec b/tools/gritsettings/resource_ids.spec -index 6d02cc4f84fc2de0404f006f6895919f6aa21cb4..92882f52b2ba1898608b2eb38702f37dd8cfb8cd 100644 +index 2f4ab49cbe968ec8a47d72a08fefbbc938fb41c8..b664e697dbbf747eb3823587461c34c595f0e4a0 100644 --- a/tools/gritsettings/resource_ids.spec +++ b/tools/gritsettings/resource_ids.spec -@@ -1524,6 +1524,11 @@ +@@ -1532,6 +1532,11 @@ "third_party/search_engines_data/resources/search_engines_scaled_resources.grd": { "structures": [10100], diff --git a/patches/chromium/hack_plugin_response_interceptor_to_point_to_electron.patch b/patches/chromium/hack_plugin_response_interceptor_to_point_to_electron.patch index 88ccc9c5347eb..c6ab380617269 100644 --- a/patches/chromium/hack_plugin_response_interceptor_to_point_to_electron.patch +++ b/patches/chromium/hack_plugin_response_interceptor_to_point_to_electron.patch @@ -8,7 +8,7 @@ require a largeish patch to get working, so just redirect it to our implementation instead. diff --git a/chrome/browser/plugins/plugin_response_interceptor_url_loader_throttle.cc b/chrome/browser/plugins/plugin_response_interceptor_url_loader_throttle.cc -index 9562a4c81714b98df30d2180689eff29f0beca31..5506740f0bfcc1b0692ac014bc628e1208ab3fe0 100644 +index 18fb39fba6e1a6245d22120ba129abf4e5b42b96..62e79cba8161f2acc3ff9e9e20953179ded4ef4e 100644 --- a/chrome/browser/plugins/plugin_response_interceptor_url_loader_throttle.cc +++ b/chrome/browser/plugins/plugin_response_interceptor_url_loader_throttle.cc @@ -12,8 +12,8 @@ diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index 7e3094d85141e..b4988630544a3 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -35,7 +35,7 @@ system font by checking if it's kCTFontPriorityAttribute is set to system priority. diff --git a/base/BUILD.gn b/base/BUILD.gn -index 275f4e0ece8c5bd8cee239c61fdb965eef524650..4726c37e6fc70133af5e2152ec4d0774f2ddfcaa 100644 +index 5b41b3d8052c439d22b4ceada50d2acaa8c57e4a..a5c4e643b8244b83ac71d08c6aef76c80393769b 100644 --- a/base/BUILD.gn +++ b/base/BUILD.gn @@ -1048,6 +1048,7 @@ component("base") { @@ -477,10 +477,10 @@ index ff96d22a11051391423f4a49c7b1478b8176baf8..c7e640e968f8ef183d48a226d43cdac8 // Beware: This view was briefly removed (in favor of a bare CALayer) in // https://crrev.com/c/1236675. The ordering of unassociated layers relative diff --git a/components/viz/service/BUILD.gn b/components/viz/service/BUILD.gn -index 15297546aa2641af1a249ff99bcf51764b107dbd..3c43af49c5d6d5f604c71e9a9dc1f7afe9aaf0f7 100644 +index ccee45644b385f40a5c7dcbac1d92ba74e72c647..7f53771dbebb480e5d10fd6926e86120f020b1ee 100644 --- a/components/viz/service/BUILD.gn +++ b/components/viz/service/BUILD.gn -@@ -385,6 +385,7 @@ viz_component("service") { +@@ -387,6 +387,7 @@ viz_component("service") { "frame_sinks/external_begin_frame_source_mac.h", ] } @@ -488,7 +488,7 @@ index 15297546aa2641af1a249ff99bcf51764b107dbd..3c43af49c5d6d5f604c71e9a9dc1f7af } if (is_ios) { -@@ -699,6 +700,7 @@ viz_source_set("unit_tests") { +@@ -701,6 +702,7 @@ viz_source_set("unit_tests") { "display_embedder/software_output_device_mac_unittest.mm", ] frameworks = [ "IOSurface.framework" ] @@ -582,7 +582,7 @@ index d83f420d25e2c108ad400ebecae02b1ac327c058..77852c5c315ac09dddb7227adf3b840e return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 3f6fb6a8653f1d087cf28396361fc77d98668db9..0603b350939376c6e3499de7f19980b7cd274735 100644 +index 933abcca124aed9d1d621ff02533b2f7cc71c7d7..1f77801262614d36b7803837ce43ef2a499a7a97 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn @@ -342,6 +342,7 @@ source_set("browser") { @@ -797,10 +797,10 @@ index a1068589ad844518038ee7bc15a3de9bc5cba525..1ff781c49f086ec8015c7d3c44567dbe } // namespace content diff --git a/content/test/BUILD.gn b/content/test/BUILD.gn -index 1403a31f878228d835772bffd9b37eea3b742599..5a013396c0990cb3f49a659d4398e9cbe64e0283 100644 +index d7cea6b7efd840d942b4a858e8db3af94a458507..16a7f545d83646ce142825b28a5bdb63ae4dc64a 100644 --- a/content/test/BUILD.gn +++ b/content/test/BUILD.gn -@@ -665,6 +665,7 @@ static_library("test_support") { +@@ -668,6 +668,7 @@ static_library("test_support") { "//url", "//url/mojom:url_mojom_gurl", "//v8", @@ -808,7 +808,7 @@ index 1403a31f878228d835772bffd9b37eea3b742599..5a013396c0990cb3f49a659d4398e9cb ] data_deps = [ -@@ -1121,6 +1122,7 @@ static_library("browsertest_support") { +@@ -1124,6 +1125,7 @@ static_library("browsertest_support") { } configs += [ "//v8:external_startup_data" ] @@ -816,7 +816,7 @@ index 1403a31f878228d835772bffd9b37eea3b742599..5a013396c0990cb3f49a659d4398e9cb } mojom("content_test_mojo_bindings") { -@@ -1964,6 +1966,7 @@ test("content_browsertests") { +@@ -1967,6 +1969,7 @@ test("content_browsertests") { "//ui/shell_dialogs", "//ui/snapshot", "//ui/webui:test_support", @@ -824,7 +824,7 @@ index 1403a31f878228d835772bffd9b37eea3b742599..5a013396c0990cb3f49a659d4398e9cb ] if (!(is_chromeos && target_cpu == "arm64" && current_cpu == "arm")) { -@@ -3297,6 +3300,7 @@ test("content_unittests") { +@@ -3300,6 +3303,7 @@ test("content_unittests") { "//ui/shell_dialogs:shell_dialogs", "//ui/webui:test_support", "//url", @@ -1028,7 +1028,7 @@ index 70d5665ad7b9ef62370497636af919ede2508ad4..f4dc3e2b8053cdb3e8c439ab1a1d6369 } diff --git a/sandbox/mac/BUILD.gn b/sandbox/mac/BUILD.gn -index 453e2185fc85fcb29fa7af3f94cce5bda8118b0c..1c383675bb9113b5b1df9280b8ee994123794dfc 100644 +index 7a69c5d3732cdf14173286c92dc2f7655a791ccf..d4e63015ddc1614179f85a5d9d86d5d5523724fa 100644 --- a/sandbox/mac/BUILD.gn +++ b/sandbox/mac/BUILD.gn @@ -25,6 +25,7 @@ component("seatbelt") { @@ -1092,10 +1092,10 @@ index 950cf7cfee4e11766dccf5c0bf3f15a8562f0f1e..a5adaaabdbbd91fedbc4cb679c865bc3 // |error| is strerror(errno) when a P* logging function is called. Pass diff --git a/sandbox/mac/sandbox_serializer.cc b/sandbox/mac/sandbox_serializer.cc -index 899f231e9bc8e1c76682972dd3f41d4cc38f4868..1da42104cc82cbabfd0c14fdd7025d6963aa50d6 100644 +index ea1627bdd872f89056e97e486feb2d44587a894e..2ed0e03b5253b6ab4fa064abfaf64c60d29cae32 100644 --- a/sandbox/mac/sandbox_serializer.cc +++ b/sandbox/mac/sandbox_serializer.cc -@@ -7,6 +7,7 @@ +@@ -8,6 +8,7 @@ #include #include @@ -1103,7 +1103,7 @@ index 899f231e9bc8e1c76682972dd3f41d4cc38f4868..1da42104cc82cbabfd0c14fdd7025d69 #include "sandbox/mac/sandbox_logging.h" #include "sandbox/mac/seatbelt.h" -@@ -31,6 +32,7 @@ void EncodeVarInt(uint64_t from, std::string* into) { +@@ -32,6 +33,7 @@ void EncodeVarInt(uint64_t from, std::string* into) { } while (from); } @@ -1111,7 +1111,7 @@ index 899f231e9bc8e1c76682972dd3f41d4cc38f4868..1da42104cc82cbabfd0c14fdd7025d69 bool DecodeVarInt(std::string_view* from, uint64_t* into) { std::string_view::const_iterator it = from->begin(); int shift = 0; -@@ -49,12 +51,12 @@ bool DecodeVarInt(std::string_view* from, uint64_t* into) { +@@ -50,12 +52,12 @@ bool DecodeVarInt(std::string_view* from, uint64_t* into) { from->remove_prefix(it - from->begin()); return true; } @@ -1126,7 +1126,7 @@ index 899f231e9bc8e1c76682972dd3f41d4cc38f4868..1da42104cc82cbabfd0c14fdd7025d69 bool DecodeString(std::string_view* slice, std::string* value) { uint64_t length; if (!DecodeVarInt(slice, &length) || length < 0) { -@@ -69,7 +71,7 @@ bool DecodeString(std::string_view* slice, std::string* value) { +@@ -70,7 +72,7 @@ bool DecodeString(std::string_view* slice, std::string* value) { slice->remove_prefix(size); return true; } @@ -1135,17 +1135,33 @@ index 899f231e9bc8e1c76682972dd3f41d4cc38f4868..1da42104cc82cbabfd0c14fdd7025d69 } // namespace SandboxSerializer::SandboxSerializer(Target mode) : mode_(mode) { -@@ -140,6 +142,7 @@ bool SandboxSerializer::SerializePolicy(std::string& serialized_policy, +@@ -147,6 +149,7 @@ bool SandboxSerializer::SerializePolicy(std::string& serialized_policy, + std::optional + SandboxSerializer::DeserializePolicy(const std::string& serialized_policy, + std::string& error) { ++#if !IS_MAS_BUILD() + std::string_view remaining_serialized_policy = serialized_policy; + uint64_t mode; + if (!DecodeVarInt(&remaining_serialized_policy, &mode)) { +@@ -192,11 +195,15 @@ SandboxSerializer::DeserializePolicy(const std::string& serialized_policy, + break; + } + return deserialized_policy; ++#else ++ return std::nullopt; ++#endif + } + // static bool SandboxSerializer::ApplySerializedPolicy( const std::string& serialized_policy) { +#if !IS_MAS_BUILD() - std::string_view policy = serialized_policy; - uint64_t mode; - if (!DecodeVarInt(&policy, &mode)) { -@@ -201,6 +204,9 @@ bool SandboxSerializer::ApplySerializedPolicy( + std::string error; + std::optional deserialized_policy = + DeserializePolicy(serialized_policy, error); +@@ -227,6 +234,9 @@ bool SandboxSerializer::ApplySerializedPolicy( + break; } - return true; +#else + return true; @@ -1448,10 +1464,10 @@ index bae0728aa1b2d8416e815862fd5d4aceb165ee44..a1a653bb5ec345f07027d19110717925 if (is_mac) { diff --git a/third_party/blink/renderer/core/editing/build.gni b/third_party/blink/renderer/core/editing/build.gni -index 8e0ca95409bf8d350658effa26c53453e2d434a0..373e3b8f9522be27ab78448557139054e98ad589 100644 +index c771cee7be34f36521de34ef893ee578b648a8c8..b0bd447b848bfdb7a9ff9cd98ba95574cb846cc2 100644 --- a/third_party/blink/renderer/core/editing/build.gni +++ b/third_party/blink/renderer/core/editing/build.gni -@@ -364,10 +364,14 @@ blink_core_sources_editing = [ +@@ -362,10 +362,14 @@ blink_core_sources_editing = [ if (is_mac) { blink_core_sources_editing += [ "commands/smart_replace_cf.cc", @@ -1678,10 +1694,10 @@ index 6846060ef9622d8fc8d1d6c8da16e2f1b785e6bd..05c22db87e882b246bd7034e027cf149 // Accessible object if (AXElementWrapper::IsValidElement(value)) { diff --git a/ui/base/BUILD.gn b/ui/base/BUILD.gn -index b5456d6483b35efd929aa772be65b68bc03aabc4..2d1bd535d66c2fab0209e5adc957d827d9182737 100644 +index eb8a8d2a275c4499d2f6097651a6a6d90ff63cb0..844ff9140783a95d91cdb9fbdaea304347439525 100644 --- a/ui/base/BUILD.gn +++ b/ui/base/BUILD.gn -@@ -365,6 +365,13 @@ component("base") { +@@ -367,6 +367,13 @@ component("base") { ] } @@ -1695,7 +1711,7 @@ index b5456d6483b35efd929aa772be65b68bc03aabc4..2d1bd535d66c2fab0209e5adc957d827 if (is_ios) { sources += [ "device_form_factor_ios.mm", -@@ -511,6 +518,12 @@ component("base") { +@@ -513,6 +520,12 @@ component("base") { "//url", ] @@ -1848,10 +1864,10 @@ index 033ebc0036bcd373b011ca829d255e8c83701a6d..ad06707f31872c58217d2d034f050c55 // Query the display's refresh rate. if (@available(macos 12.0, *)) { diff --git a/ui/gfx/BUILD.gn b/ui/gfx/BUILD.gn -index 073269d426f55591e2daeff32782d957624d11d4..c6fe49958fd3e0b556352fda5cc35b9455792002 100644 +index 66307a0b27577865f95b37c80dccf2e02bd46029..f8cd4adc73a29610b5a92e276117484d0f580d4b 100644 --- a/ui/gfx/BUILD.gn +++ b/ui/gfx/BUILD.gn -@@ -337,6 +337,12 @@ component("gfx") { +@@ -338,6 +338,12 @@ component("gfx") { "//ui/base:ui_data_pack", ] diff --git a/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch b/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch index 0bf84dae055e3..55e4062472a42 100644 --- a/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch +++ b/patches/chromium/network_service_allow_remote_certificate_verification_logic.patch @@ -7,10 +7,10 @@ This adds a callback from the network service that's used to implement session.setCertificateVerifyCallback. diff --git a/services/network/network_context.cc b/services/network/network_context.cc -index 0339a3733272095428d5717c6df9fce8d16062c3..02853bf6552d49986b782785d3ab5a61ec0d3734 100644 +index e9d152aa78f7c58a0071cf5f9eac48427518612d..b91e9da008c121d2afbc5fd4c3c9ea401a6191a8 100644 --- a/services/network/network_context.cc +++ b/services/network/network_context.cc -@@ -164,6 +164,11 @@ +@@ -163,6 +163,11 @@ #include "services/network/web_transport.h" #include "url/gurl.h" @@ -22,7 +22,7 @@ index 0339a3733272095428d5717c6df9fce8d16062c3..02853bf6552d49986b782785d3ab5a61 #if BUILDFLAG(IS_CT_SUPPORTED) // gn check does not account for BUILDFLAG(). So, for iOS builds, it will // complain about a missing dependency on the target exposing this header. Add a -@@ -603,6 +608,99 @@ void RecordHSTSPreconnectUpgradeReason(HSTSRedirectUpgradeReason reason) { +@@ -602,6 +607,99 @@ void RecordHSTSPreconnectUpgradeReason(HSTSRedirectUpgradeReason reason) { } // namespace @@ -122,7 +122,7 @@ index 0339a3733272095428d5717c6df9fce8d16062c3..02853bf6552d49986b782785d3ab5a61 constexpr uint32_t NetworkContext::kMaxOutstandingRequestsPerProcess; NetworkContext::NetworkContextHttpAuthPreferences:: -@@ -1006,6 +1104,13 @@ void NetworkContext::SetClient( +@@ -1005,6 +1103,13 @@ void NetworkContext::SetClient( client_.Bind(std::move(client)); } @@ -136,7 +136,7 @@ index 0339a3733272095428d5717c6df9fce8d16062c3..02853bf6552d49986b782785d3ab5a61 void NetworkContext::CreateURLLoaderFactory( mojo::PendingReceiver receiver, mojom::URLLoaderFactoryParamsPtr params) { -@@ -2611,6 +2716,10 @@ URLRequestContextOwner NetworkContext::MakeURLRequestContext( +@@ -2617,6 +2722,10 @@ URLRequestContextOwner NetworkContext::MakeURLRequestContext( cert_verifier = std::make_unique( std::make_unique( std::move(cert_verifier))); @@ -148,7 +148,7 @@ index 0339a3733272095428d5717c6df9fce8d16062c3..02853bf6552d49986b782785d3ab5a61 builder.SetCertVerifier(IgnoreErrorsCertVerifier::MaybeWrapCertVerifier( diff --git a/services/network/network_context.h b/services/network/network_context.h -index 867d3002dc9dada51319c5ed15f5746f58f19fd1..5b5d8eccb9c84965e996cd8d2a8c7d962df7852a 100644 +index 1378785d8b2cdf02d9588327f6cb32b341fb0b12..fcddda19a4d37052312748a6dd4e5ffdee1d240b 100644 --- a/services/network/network_context.h +++ b/services/network/network_context.h @@ -115,6 +115,7 @@ class URLMatcher; @@ -168,7 +168,7 @@ index 867d3002dc9dada51319c5ed15f5746f58f19fd1..5b5d8eccb9c84965e996cd8d2a8c7d96 void ResetURLLoaderFactories() override; void GetViaObliviousHttp( mojom::ObliviousHttpRequestPtr request, -@@ -961,6 +964,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext +@@ -963,6 +966,8 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) NetworkContext std::vector dismount_closures_; #endif // BUILDFLAG(IS_DIRECTORY_TRANSFER_REQUIRED) @@ -178,7 +178,7 @@ index 867d3002dc9dada51319c5ed15f5746f58f19fd1..5b5d8eccb9c84965e996cd8d2a8c7d96 std::unique_ptr internal_host_resolver_; std::set, base::UniquePtrComparator> diff --git a/services/network/public/mojom/network_context.mojom b/services/network/public/mojom/network_context.mojom -index 4ea464b2b6c00301ff0f1938fe584292723fafaa..f510b5c5c79161f32a08219aa7f6cd7a722eed85 100644 +index 444379292d06db40203d0f9c8ec93f64d4b1edc6..de945e5f2cb5398c37617fce5e00834b481d3875 100644 --- a/services/network/public/mojom/network_context.mojom +++ b/services/network/public/mojom/network_context.mojom @@ -309,6 +309,17 @@ struct SocketBrokerRemotes { @@ -199,7 +199,7 @@ index 4ea464b2b6c00301ff0f1938fe584292723fafaa..f510b5c5c79161f32a08219aa7f6cd7a // Parameters for constructing a network context. struct NetworkContextParams { // The user agent string. -@@ -957,6 +968,9 @@ interface NetworkContext { +@@ -961,6 +972,9 @@ interface NetworkContext { // Sets a client for this network context. SetClient(pending_remote client); @@ -210,7 +210,7 @@ index 4ea464b2b6c00301ff0f1938fe584292723fafaa..f510b5c5c79161f32a08219aa7f6cd7a CreateURLLoaderFactory( pending_receiver url_loader_factory, diff --git a/services/network/test/test_network_context.h b/services/network/test/test_network_context.h -index 84bdf5143a6ab9cb9f89cd8ae12ea8e68c1608aa..81930f3b5ca760d4db9c65aeb36162ddea68a872 100644 +index 7628357ca82c1c19741a9348212dfa559a203fd2..c57dcce278f96c9bd3157fd5d2ce0f9d0ecbef53 100644 --- a/services/network/test/test_network_context.h +++ b/services/network/test/test_network_context.h @@ -64,6 +64,8 @@ class TestNetworkContext : public mojom::NetworkContext { diff --git a/patches/chromium/notification_provenance.patch b/patches/chromium/notification_provenance.patch index 7266481311147..95a7e448103c8 100644 --- a/patches/chromium/notification_provenance.patch +++ b/patches/chromium/notification_provenance.patch @@ -133,10 +133,10 @@ index 5be62a3fb27e37f3c1db6b811172f6dfebe18f61..34349f9832fe4b9a3d48db613a789afb const GURL& document_url, const WeakDocumentPtr& weak_document_ptr, diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index 9fd362b58903930c3fcb053d561cf8d8c815ce15..c97471d75ab2d11cfe71f34d8d11b27edb5c0fce 100644 +index 67cdf0f30f2295330065550995c81ea0439f7cb7..524191a9a4973c55dc527841f3ea1238877919ac 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc -@@ -2225,7 +2225,7 @@ void RenderProcessHostImpl::CreateNotificationService( +@@ -2236,7 +2236,7 @@ void RenderProcessHostImpl::CreateNotificationService( case RenderProcessHost::NotificationServiceCreatorType::kSharedWorker: case RenderProcessHost::NotificationServiceCreatorType::kDedicatedWorker: { storage_partition_impl_->GetPlatformNotificationContext()->CreateService( @@ -145,7 +145,7 @@ index 9fd362b58903930c3fcb053d561cf8d8c815ce15..c97471d75ab2d11cfe71f34d8d11b27e creator_type, std::move(receiver)); break; } -@@ -2233,7 +2233,7 @@ void RenderProcessHostImpl::CreateNotificationService( +@@ -2244,7 +2244,7 @@ void RenderProcessHostImpl::CreateNotificationService( CHECK(rfh); storage_partition_impl_->GetPlatformNotificationContext()->CreateService( diff --git a/patches/chromium/preconnect_manager.patch b/patches/chromium/preconnect_manager.patch index f3967b3f57bfa..e43f1a61333d8 100644 --- a/patches/chromium/preconnect_manager.patch +++ b/patches/chromium/preconnect_manager.patch @@ -10,10 +10,10 @@ in favor of defining PreconnectRequest in this file since we don't build the header. diff --git a/chrome/browser/predictors/preconnect_manager.cc b/chrome/browser/predictors/preconnect_manager.cc -index 037b624807fbf34843c450876aae70529df5f7da..a8208563f7d339d486d973caf7b29aba40c91ad0 100644 +index 05c0aa8ca2a480b7477a4b877a34855f8beb997b..46f693e6a7ba906baccf4d4d12bca36e80e7387e 100644 --- a/chrome/browser/predictors/preconnect_manager.cc +++ b/chrome/browser/predictors/preconnect_manager.cc -@@ -15,9 +15,11 @@ +@@ -14,9 +14,11 @@ #include "base/types/optional_util.h" #include "chrome/browser/predictors/predictors_features.h" #include "chrome/browser/predictors/predictors_traffic_annotations.h" @@ -25,7 +25,7 @@ index 037b624807fbf34843c450876aae70529df5f7da..a8208563f7d339d486d973caf7b29aba #include "content/public/browser/browser_context.h" #include "content/public/browser/browser_task_traits.h" #include "content/public/browser/browser_thread.h" -@@ -30,6 +32,20 @@ namespace predictors { +@@ -29,6 +31,20 @@ namespace predictors { const bool kAllowCredentialsOnPreconnectByDefault = true; @@ -63,7 +63,7 @@ index 037b624807fbf34843c450876aae70529df5f7da..a8208563f7d339d486d973caf7b29aba void PreconnectManager::Start(const GURL& url, diff --git a/chrome/browser/predictors/preconnect_manager.h b/chrome/browser/predictors/preconnect_manager.h -index 7ffcb5226bed84e0ecf23d0562a0b61db9a0b835..e2314d0328c265353f7cb6fdb9bfd3b937f25444 100644 +index 666d9fb646cf337cf4c6145358fe3ea822220b0e..591ec08e40541058b61628e50ced35b00ff91b5d 100644 --- a/chrome/browser/predictors/preconnect_manager.h +++ b/chrome/browser/predictors/preconnect_manager.h @@ -17,7 +17,9 @@ @@ -75,7 +75,7 @@ index 7ffcb5226bed84e0ecf23d0562a0b61db9a0b835..e2314d0328c265353f7cb6fdb9bfd3b9 +#endif #include "content/public/browser/storage_partition_config.h" #include "net/base/network_anonymization_key.h" - #include "services/network/public/mojom/reconnect_event_observer.mojom.h" + #include "services/network/public/mojom/connection_change_observer_client.mojom.h" @@ -35,7 +37,28 @@ class NetworkContext; namespace predictors { diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index e92e0e63fb6cf..ea054be3fcf1c 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -887,10 +887,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 0603b350939376c6e3499de7f19980b7cd274735..4adc2b7d4a244d60c9523feb9e4b24f7c0e634a7 100644 +index 1f77801262614d36b7803837ce43ef2a499a7a97..de5e27c2960ffd7253aa1dfae46dbc51ca57d2ce 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3167,8 +3167,9 @@ source_set("browser") { +@@ -3171,8 +3171,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 5136b1de11cc5..2b3ac237b2556 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -30,7 +30,7 @@ index a54a0dedf8ef1cfffa4e80a4707debed0e83d277..e66e71fdbabb40a5307b12cd8965e773 // RenderWidgetHost on the primary main frame, and false otherwise. virtual bool IsWidgetForPrimaryMainFrame(RenderWidgetHostImpl*); diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 6a60a4b0275e1832216b092c29bc867f4727ca22..6a939edf24643207b26c9cc155ccca661b06f937 100644 +index cdfdd322ffb2e61d5480ac7c88dba35a1cc1b5b9..a3cbb6cb369c2f250c702a0117e36e9aee04068c 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc @@ -2068,6 +2068,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { @@ -44,10 +44,10 @@ index 6a60a4b0275e1832216b092c29bc867f4727ca22..6a939edf24643207b26c9cc155ccca66 void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index c0ef22f3872e96be15867428aff1006b8a14a1df..6eaa7d566058fdcc9ebfa10f0420c3a234cb0483 100644 +index 811d137c4b77d3347dc8de5bb6207646c952f23b..33abfcd326148f32eff2266a4545345e4a561a4e 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -6060,6 +6060,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -6069,6 +6069,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,10 +60,10 @@ index c0ef22f3872e96be15867428aff1006b8a14a1df..6eaa7d566058fdcc9ebfa10f0420c3a2 RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index bb00cc84d8880911c1b170a0b7084a8d9cd4bbdb..e8db4afa0c4f1061fe1609745cbac815f52b4a28 100644 +index 478c9dfd9019e7acfa2ad63219a268aa5879670e..54c2a41b7ee21f1e6f022c5818e56e24a52ccbef 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h -@@ -1189,6 +1189,7 @@ class CONTENT_EXPORT WebContentsImpl +@@ -1193,6 +1193,7 @@ class CONTENT_EXPORT WebContentsImpl void SendScreenRects() override; void SendActiveState(bool active) override; TextInputManager* GetTextInputManager() override; diff --git a/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch b/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch index d776be1c11dd6..436743a64fdc9 100644 --- a/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch +++ b/patches/chromium/refactor_patch_electron_permissiontypes_into_blink.patch @@ -6,10 +6,10 @@ Subject: refactor: patch electron PermissionTypes into blink 6387077: [PermissionOptions] Generalize PermissionRequestDescription | https://chromium-review.googlesource.com/c/chromium/src/+/6387077 diff --git a/components/permissions/permission_util.cc b/components/permissions/permission_util.cc -index f69c10c32011c9da5c235a5199abce44e64982da..3b166dd8f571538102772a9bcd5bbe55015742f3 100644 +index bface283d508d1c1a3f9fd297d92e048bdd423af..5b6451a5ac484a23a20906b8c3c9b998f7b31a33 100644 --- a/components/permissions/permission_util.cc +++ b/components/permissions/permission_util.cc -@@ -502,7 +502,17 @@ ContentSettingsType PermissionUtil::PermissionTypeToContentSettingsTypeSafe( +@@ -520,7 +520,17 @@ ContentSettingsType PermissionUtil::PermissionTypeToContentSettingsTypeSafe( return ContentSettingsType::WEB_APP_INSTALLATION; case PermissionType::LOCAL_NETWORK_ACCESS: return ContentSettingsType::LOCAL_NETWORK_ACCESS; diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index e9dd22401d93b..7525fb4b186a9 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index de2e8163c6ae5a1a01a79413d3d44b7c11ede311..e1692192bfa25f9949dd3f2fa2b61fc5dcef2e26 100644 +index 51798b8ceb81cf9d374cf594aa6afbcb366f4732..bacfca5b2f54e2db7700bb871fff4f66712f5c32 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10299,25 +10299,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10308,25 +10308,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/resource_file_conflict.patch b/patches/chromium/resource_file_conflict.patch index 19e08c4342b0d..5571fa0701b2a 100644 --- a/patches/chromium/resource_file_conflict.patch +++ b/patches/chromium/resource_file_conflict.patch @@ -52,10 +52,10 @@ Some alternatives to this patch: None of these options seems like a substantial maintainability win over this patch to me (@nornagon). diff --git a/chrome/BUILD.gn b/chrome/BUILD.gn -index f47270687b9a12fb74be2e90cc1e9f25e2e2d34e..84fab7fcdb1a7ded880c0ff4867e09c740e7a5d2 100644 +index 86007c8b041c44c14257245376326bc94ca050a9..72c637f9f3ba48bb7ab06678fe833f33d2cfddc8 100644 --- a/chrome/BUILD.gn +++ b/chrome/BUILD.gn -@@ -1551,7 +1551,7 @@ if (is_chrome_branded && !is_android) { +@@ -1572,7 +1572,7 @@ if (is_chrome_branded && !is_android) { } } @@ -64,7 +64,7 @@ index f47270687b9a12fb74be2e90cc1e9f25e2e2d34e..84fab7fcdb1a7ded880c0ff4867e09c7 chrome_paks("packed_resources") { if (is_mac) { output_dir = "$root_gen_dir/repack" -@@ -1597,6 +1597,12 @@ repack("browser_tests_pak") { +@@ -1618,6 +1618,12 @@ repack("browser_tests_pak") { deps = [ "//chrome/test/data/webui:resources" ] } diff --git a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch index e0e67b527d258..deaf7a7525b31 100644 --- a/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch +++ b/patches/chromium/revert_code_health_clean_up_stale_macwebcontentsocclusion.patch @@ -233,12 +233,12 @@ index 7c99a9512e6f65713fe8483cef7b7c9b494b4491..8fb6cf252961c9773d1a6a09d47bec6a } diff --git a/content/common/features.cc b/content/common/features.cc -index 8c02eee693930e68cc734bbaba9a1fdb403cf8c1..aa3084feb5aa8c6a771016b38f0adcfa39bed9b2 100644 +index e5fec5227be7aa05b9fb5ec9f77f66129b8a9639..d639895ba47a66d3b689094d32b4b9572c7aa9ff 100644 --- a/content/common/features.cc +++ b/content/common/features.cc -@@ -315,6 +315,14 @@ BASE_FEATURE(kIOSurfaceCapturer, - base::FEATURE_ENABLED_BY_DEFAULT); - #endif +@@ -319,6 +319,14 @@ BASE_FEATURE_PARAM(size_t, + 42u); + #endif // BUILDFLAG(IS_ANDROID) +// Feature that controls whether WebContentsOcclusionChecker should handle +// occlusion notifications. @@ -252,12 +252,12 @@ index 8c02eee693930e68cc734bbaba9a1fdb403cf8c1..aa3084feb5aa8c6a771016b38f0adcfa // invalidated upon notifications sent by base::SystemMonitor. If disabled, the // cache is considered invalid on every enumeration request. diff --git a/content/common/features.h b/content/common/features.h -index 032df239241bb73a19f1f3e1c0683764c40e96eb..56d00c458e0702de4830d849aa0639336823112a 100644 +index ccc1ab3f83c6c0e2e8e2d993705bb72a60981ba8..9c52d679c17f690abf1a38f04432a0c14a28af4f 100644 --- a/content/common/features.h +++ b/content/common/features.h -@@ -102,6 +102,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kInterestGroupUpdateIfOlderThan); - #if BUILDFLAG(IS_MAC) - CONTENT_EXPORT BASE_DECLARE_FEATURE(kIOSurfaceCapturer); +@@ -105,6 +105,9 @@ CONTENT_EXPORT BASE_DECLARE_FEATURE(kRendererProcessLimitOnAndroid); + CONTENT_EXPORT BASE_DECLARE_FEATURE_PARAM(size_t, + kRendererProcessLimitOnAndroidCount); #endif +#if BUILDFLAG(IS_MAC) +CONTENT_EXPORT BASE_DECLARE_FEATURE(kMacWebContentsOcclusion); diff --git a/patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch b/patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch deleted file mode 100644 index 965070769efd2..0000000000000 --- a/patches/chromium/revert_webgl_add_stub_webgl_2_renderingcontextwebgpu.patch +++ /dev/null @@ -1,4219 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Colin Blundell -Date: Mon, 19 May 2025 23:49:13 -0700 -Subject: Revert "[webgl] Add stub WebGL[2]RenderingContextWebGPU" - -This reverts commit e530c1578622adea59ae2ac3a586ae090681422b. - -Reason for revert: Multiple eng reporting that this is causing build failures due to too-long pathnames, with no immediate feasible workaround - -Bug: 414506479 -Original change's description: -> [webgl] Add stub WebGL[2]RenderingContextWebGPU -> -> These implementations of the WebGL IDL are meant to be implemented with -> ANGLE running on top of the WebGPU using dawn::wire, the same way that -> WebGPU's JS bindings are implemented. If successful, this would allow -> reducing the GPU process attack surface as it wouldn't need to support -> the GLES command buffer anymore. -> -> Binary-Size: Required initial increase to add WebGLOnWebGPU. -> Fuchsia-Binary-Size: Increase is temporary, will be more than compensated by linking ANGLE statically (-400kb). -> Bug: 414506479 -> Change-Id: I63d88a06d0d91e9842b48414d335df99522bba8d -> Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6494836 -> Reviewed-by: Brandon Jones -> Commit-Queue: Corentin Wallez -> Reviewed-by: Colin Blundell -> Cr-Commit-Position: refs/heads/main@{#1462154} - -Bug: 414506479 -No-Presubmit: true -No-Tree-Checks: true -No-Try: true -Change-Id: I0d4f94e9ceabd770250390d6f4ffe844a4ad00cb -Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6565622 -Auto-Submit: Colin Blundell -Commit-Queue: Rubber Stamper -Bot-Commit: Rubber Stamper -Cr-Commit-Position: refs/heads/main@{#1462590} - -diff --git a/third_party/blink/renderer/bindings/generated_in_modules.gni b/third_party/blink/renderer/bindings/generated_in_modules.gni -index b42efe786712f81b5b86ff90f62a7ee486c16c9a..c8177157631aeb7a0d8c65c57ac6da5b74da8b1f 100644 ---- a/third_party/blink/renderer/bindings/generated_in_modules.gni -+++ b/third_party/blink/renderer/bindings/generated_in_modules.gni -@@ -2986,8 +2986,6 @@ generated_interface_sources_in_modules = [ - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_web_transport_error.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context.h", -- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context_webgpu.cc", -- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl2_rendering_context_webgpu.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_active_info.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_active_info.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_blend_func_extended.cc", -@@ -3046,8 +3044,6 @@ generated_interface_sources_in_modules = [ - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_renderbuffer.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context.h", -- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context_webgpu.cc", -- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_rendering_context_webgpu.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_sampler.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_sampler.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_webgl_shader.cc", -@@ -3282,8 +3278,8 @@ generated_union_sources_in_modules = [ - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_boolean_mediatrackconstraints.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasfilter_string.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasfilter_string.h", -- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.cc", -- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h", -+ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webglrenderingcontext.cc", -+ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webglrenderingcontext.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_client_messageport_serviceworker.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_client_messageport_serviceworker.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_constraindomstringparameters_string_stringsequence.cc", -@@ -3310,8 +3306,8 @@ generated_union_sources_in_modules = [ - "$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_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.cc", -- "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h", -+ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webglrenderingcontext.cc", -+ "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webglrenderingcontext.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuextent3ddict_unsignedlongenforcerangesequence.cc", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuextent3ddict_unsignedlongenforcerangesequence.h", - "$root_gen_dir/third_party/blink/renderer/bindings/modules/v8/v8_union_gpuorigin2ddict_unsignedlongenforcerangesequence.cc", -diff --git a/third_party/blink/renderer/bindings/idl_in_modules.gni b/third_party/blink/renderer/bindings/idl_in_modules.gni -index e48d158c150ab1a0bc9ed309310171e12c6de22e..e378f59cd4a6a7d3482fbb7b43e207d9f14ffb45 100644 ---- a/third_party/blink/renderer/bindings/idl_in_modules.gni -+++ b/third_party/blink/renderer/bindings/idl_in_modules.gni -@@ -997,7 +997,6 @@ static_idl_files_in_modules = [ - "//third_party/blink/renderer/modules/webgl/ovr_multiview_2.idl", - "//third_party/blink/renderer/modules/webgl/webgl2_rendering_context.idl", - "//third_party/blink/renderer/modules/webgl/webgl2_rendering_context_base.idl", -- "//third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl", - "//third_party/blink/renderer/modules/webgl/webgl_active_info.idl", - "//third_party/blink/renderer/modules/webgl/webgl_blend_func_extended.idl", - "//third_party/blink/renderer/modules/webgl/webgl_buffer.idl", -@@ -1030,7 +1029,6 @@ static_idl_files_in_modules = [ - "//third_party/blink/renderer/modules/webgl/webgl_renderbuffer.idl", - "//third_party/blink/renderer/modules/webgl/webgl_rendering_context.idl", - "//third_party/blink/renderer/modules/webgl/webgl_rendering_context_base.idl", -- "//third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl", - "//third_party/blink/renderer/modules/webgl/webgl_sampler.idl", - "//third_party/blink/renderer/modules/webgl/webgl_shader.idl", - "//third_party/blink/renderer/modules/webgl/webgl_shader_pixel_local_storage.idl", -diff --git a/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h b/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h -index 23dea4bb35b90c20dc6d7de9cc5c8356cbcde2f2..392b7a1c1574045d5118be10fd50068cc419afb3 100644 ---- a/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h -+++ b/third_party/blink/renderer/core/html/canvas/canvas_rendering_context.h -@@ -80,9 +80,9 @@ class ImageBitmap; - class ScriptState; - class StaticBitmapImage; - using V8RenderingContext = class -- V8UnionCanvasRenderingContext2DOrGPUCanvasContextOrImageBitmapRenderingContextOrWebGL2RenderingContextOrWebGL2RenderingContextWebGPUOrWebGLRenderingContextOrWebGLRenderingContextWebGPU; -+ V8UnionCanvasRenderingContext2DOrGPUCanvasContextOrImageBitmapRenderingContextOrWebGL2RenderingContextOrWebGLRenderingContext; - using V8OffscreenRenderingContext = class -- V8UnionGPUCanvasContextOrImageBitmapRenderingContextOrOffscreenCanvasRenderingContext2DOrWebGL2RenderingContextOrWebGL2RenderingContextWebGPUOrWebGLRenderingContextOrWebGLRenderingContextWebGPU; -+ V8UnionGPUCanvasContextOrImageBitmapRenderingContextOrOffscreenCanvasRenderingContext2DOrWebGL2RenderingContextOrWebGLRenderingContext; - class WebGraphicsContext3DVideoFramePool; - - class CORE_EXPORT CanvasRenderingContext -diff --git a/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl b/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl -index 261e9ad46901da85ea2d72c8f6b8e12b23641b94..70d0c26f00fc947af54d8ac8388a68c15d3b43dd 100644 ---- a/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl -+++ b/third_party/blink/renderer/modules/canvas/htmlcanvas/html_canvas_element_module.idl -@@ -7,8 +7,6 @@ - typedef (CanvasRenderingContext2D or - WebGLRenderingContext or - WebGL2RenderingContext or -- WebGLRenderingContextWebGPU or -- WebGL2RenderingContextWebGPU or - ImageBitmapRenderingContext or - GPUCanvasContext) RenderingContext; - -diff --git a/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h b/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h -index aa7114367cfefe7871fcf6eb69bc1ac96739bf37..cfa8ac671aa20c8631c2524bd970da21bdf57c06 100644 ---- a/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h -+++ b/third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h -@@ -8,6 +8,6 @@ - // This is just a forwarding header to avoid including an enormous filename in - // each file that needs the declaration of the union that is used for - // RenderingContext. --#include "third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h" -+#include "third_party/blink/renderer/bindings/modules/v8/v8_union_canvasrenderingcontext2d_gpucanvascontext_imagebitmaprenderingcontext_webgl2renderingcontext_webglrenderingcontext.h" - - #endif // THIRD_PARTY_BLINK_RENDERER_MODULES_CANVAS_HTMLCANVAS_V8_RENDERING_CONTEXT_H_ -diff --git a/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl b/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl -index a15d8d671f7504c9e771e607485413728479423b..f88b06ce555b0a49ac40a93ce52cb49a5bf8c6e6 100644 ---- a/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl -+++ b/third_party/blink/renderer/modules/canvas/offscreencanvas/offscreen_canvas_module.idl -@@ -7,8 +7,6 @@ - typedef (OffscreenCanvasRenderingContext2D or - WebGLRenderingContext or - WebGL2RenderingContext or -- WebGLRenderingContextWebGPU or -- WebGL2RenderingContextWebGPU or - ImageBitmapRenderingContext or - GPUCanvasContext) OffscreenRenderingContext; - enum OffscreenRenderingContextType { "2d", "webgl", "webgl2", "bitmaprenderer", "webgpu" }; -diff --git a/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h b/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h -index 3742d1e586615165f3bfdddbbd054e13a45e244d..b44bacfe4240240b0f65bdafd1ae8bc37182bdc7 100644 ---- a/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h -+++ b/third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h -@@ -8,6 +8,6 @@ - // This is just a forwarding header to avoid including an enormous filename in - // each file that needs the declaration of the union that is used for - // OffscreenRenderingContext. --#include "third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webgl2renderingcontextwebgpu_webglrenderingcontext_webglrenderingcontextwebgpu.h" -+#include "third_party/blink/renderer/bindings/modules/v8/v8_union_gpucanvascontext_imagebitmaprenderingcontext_offscreencanvasrenderingcontext2d_webgl2renderingcontext_webglrenderingcontext.h" - - #endif // THIRD_PARTY_BLINK_RENDERER_MODULES_CANVAS_OFFSCREENCANVAS_V8_OFFSCREEN_RENDERING_CONTEXT_H_ -diff --git a/third_party/blink/renderer/modules/webgl/BUILD.gn b/third_party/blink/renderer/modules/webgl/BUILD.gn -index 5c1ff9afbfea45aba7b1fa68234fc1c35914aa95..08d7b3f52c5c2cd6d1199396b2ce1775f2289798 100644 ---- a/third_party/blink/renderer/modules/webgl/BUILD.gn -+++ b/third_party/blink/renderer/modules/webgl/BUILD.gn -@@ -79,8 +79,6 @@ blink_modules_sources("webgl") { - "webgl2_rendering_context.h", - "webgl2_rendering_context_base.cc", - "webgl2_rendering_context_base.h", -- "webgl2_rendering_context_webgpu.cc", -- "webgl2_rendering_context_webgpu.h", - "webgl_active_info.h", - "webgl_blend_func_extended.cc", - "webgl_blend_func_extended.h", -@@ -153,10 +151,6 @@ blink_modules_sources("webgl") { - "webgl_rendering_context.h", - "webgl_rendering_context_base.cc", - "webgl_rendering_context_base.h", -- "webgl_rendering_context_webgpu.cc", -- "webgl_rendering_context_webgpu.h", -- "webgl_rendering_context_webgpu_base.cc", -- "webgl_rendering_context_webgpu_base.h", - "webgl_sampler.cc", - "webgl_sampler.h", - "webgl_shader.cc", -diff --git a/third_party/blink/renderer/modules/webgl/DEPS b/third_party/blink/renderer/modules/webgl/DEPS -index b0efa5dd316811a166016c144c048e15130586a3..ec20717bde034b51a30a949efee2e24db9bac499 100644 ---- a/third_party/blink/renderer/modules/webgl/DEPS -+++ b/third_party/blink/renderer/modules/webgl/DEPS -@@ -1,5 +1,4 @@ - include_rules = [ -- "+base/notimplemented.h", - "+device/vr/buildflags/buildflags.h", - "+device/vr/public/mojom/vr_service.mojom-blink.h", - "+device/vr/public/mojom/vr_service.mojom-blink-forward.h", -diff --git a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.cc b/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.cc -deleted file mode 100644 -index 290b5d688cbe44bb17ea73e388393f618c9e42c4..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.cc -+++ /dev/null -@@ -1,29 +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 "third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h" -- --#include "base/notimplemented.h" --#include "third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h" --#include "third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h" -- --namespace blink { -- --WebGL2RenderingContextWebGPU::WebGL2RenderingContextWebGPU( -- CanvasRenderingContextHost* host, -- const CanvasContextCreationAttributesCore& requested_attributes) -- : WebGLRenderingContextWebGPUBase(host, -- requested_attributes, -- CanvasRenderingAPI::kWebgl2) {} -- --V8RenderingContext* WebGL2RenderingContextWebGPU::AsV8RenderingContext() { -- return MakeGarbageCollected(this); --} -- --V8OffscreenRenderingContext* --WebGL2RenderingContextWebGPU::AsV8OffscreenRenderingContext() { -- return MakeGarbageCollected(this); --} -- --} // namespace blink -diff --git a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h b/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h -deleted file mode 100644 -index db83b4ac9d3138dc82a2522adc22ded58f7d1627..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h -+++ /dev/null -@@ -1,28 +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 THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL2_RENDERING_CONTEXT_WEBGPU_H_ --#define THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL2_RENDERING_CONTEXT_WEBGPU_H_ -- --#include "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h" -- --namespace blink { -- --class WebGL2RenderingContextWebGPU final -- : public WebGLRenderingContextWebGPUBase { -- DEFINE_WRAPPERTYPEINFO(); -- -- public: -- WebGL2RenderingContextWebGPU( -- CanvasRenderingContextHost* host, -- const CanvasContextCreationAttributesCore& requested_attributes); -- -- // CanvasRenderingContext implementation -- V8RenderingContext* AsV8RenderingContext() final; -- V8OffscreenRenderingContext* AsV8OffscreenRenderingContext() final; --}; -- --} // namespace blink -- --#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL2_RENDERING_CONTEXT_WEBGPU_H_ -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 -deleted file mode 100644 -index ac76ded5b53871030a6b7496fa3b24d79f27b56d..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.idl -+++ /dev/null -@@ -1,13 +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. -- --// https://www.khronos.org/registry/webgl/specs/latest/2.0/#3.7 -- --[ -- ActiveScriptWrappable, -- Exposed=(Window,Worker), -- RuntimeEnabled=WebGLOnWebGPU --] interface WebGL2RenderingContextWebGPU { }; --WebGL2RenderingContextWebGPU includes WebGLRenderingContextBase; --WebGL2RenderingContextWebGPU includes WebGL2RenderingContextBase; -diff --git a/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc b/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc -index 8a983f1720d94391f641be229c8fcac0fb07d148..048feec570e2bcdac3c57ac14094ba28635b112f 100644 ---- a/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc -+++ b/third_party/blink/renderer/modules/webgl/webgl_context_factory.cc -@@ -4,15 +4,11 @@ - - #include "third_party/blink/renderer/modules/webgl/webgl_context_factory.h" - --#include "base/notimplemented.h" - #include "third_party/blink/renderer/core/html/canvas/canvas_context_creation_attributes_core.h" - #include "third_party/blink/renderer/core/html/canvas/html_canvas_element.h" - #include "third_party/blink/renderer/modules/webgl/webgl2_rendering_context.h" --#include "third_party/blink/renderer/modules/webgl/webgl2_rendering_context_webgpu.h" - #include "third_party/blink/renderer/modules/webgl/webgl_context_event.h" - #include "third_party/blink/renderer/modules/webgl/webgl_rendering_context.h" --#include "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h" --#include "third_party/blink/renderer/platform/runtime_enabled_features.h" - - namespace blink { - -@@ -32,11 +28,7 @@ WebGLContextFactory::WebGLContextFactory(bool is_webgl2) - CanvasRenderingContext* WebGLContextFactory::Create( - CanvasRenderingContextHost* host, - const CanvasContextCreationAttributesCore& attrs) { -- if (RuntimeEnabledFeatures::WebGLOnWebGPUEnabled()) { -- return CreateInternalWebGPU(host, attrs); -- } else { -- return CreateInternal(host, attrs); -- } -+ return CreateInternal(host, attrs); - } - - CanvasRenderingContext* WebGLContextFactory::CreateInternal( -@@ -106,16 +98,6 @@ CanvasRenderingContext* WebGLContextFactory::CreateInternal( - } - } - --CanvasRenderingContext* WebGLContextFactory::CreateInternalWebGPU( -- CanvasRenderingContextHost* host, -- const CanvasContextCreationAttributesCore& attrs) { -- if (is_webgl2_) { -- return MakeGarbageCollected(host, attrs); -- } else { -- return MakeGarbageCollected(host, attrs); -- } --} -- - CanvasRenderingContext::CanvasRenderingAPI - WebGLContextFactory::GetRenderingAPI() const { - if (is_webgl2_) { -diff --git a/third_party/blink/renderer/modules/webgl/webgl_context_factory.h b/third_party/blink/renderer/modules/webgl/webgl_context_factory.h -index e58bbe3f6eec6e64a89d08e7e83d63d9b0841a04..df24c7085def9fc934a835635c10ebf7382ba528 100644 ---- a/third_party/blink/renderer/modules/webgl/webgl_context_factory.h -+++ b/third_party/blink/renderer/modules/webgl/webgl_context_factory.h -@@ -39,9 +39,6 @@ class WebGLContextFactory : public CanvasRenderingContextFactory { - CanvasRenderingContext* CreateInternal( - CanvasRenderingContextHost*, - const CanvasContextCreationAttributesCore&); -- CanvasRenderingContext* CreateInternalWebGPU( -- CanvasRenderingContextHost*, -- const CanvasContextCreationAttributesCore&); - - const char* GetContextName() const; - Platform::ContextType GetContextType() const; -diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.cc b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.cc -deleted file mode 100644 -index ead39056f29ff7080c66d983489b090ad4b1ce8d..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.cc -+++ /dev/null -@@ -1,29 +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 "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h" -- --#include "base/notimplemented.h" --#include "third_party/blink/renderer/modules/canvas/htmlcanvas/v8_rendering_context.h" --#include "third_party/blink/renderer/modules/canvas/offscreencanvas/v8_offscreen_rendering_context.h" -- --namespace blink { -- --WebGLRenderingContextWebGPU::WebGLRenderingContextWebGPU( -- CanvasRenderingContextHost* host, -- const CanvasContextCreationAttributesCore& requested_attributes) -- : WebGLRenderingContextWebGPUBase(host, -- requested_attributes, -- CanvasRenderingAPI::kWebgl) {} -- --V8RenderingContext* WebGLRenderingContextWebGPU::AsV8RenderingContext() { -- return MakeGarbageCollected(this); --} -- --V8OffscreenRenderingContext* --WebGLRenderingContextWebGPU::AsV8OffscreenRenderingContext() { -- return MakeGarbageCollected(this); --} -- --} // namespace blink -diff --git a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h b/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h -deleted file mode 100644 -index d0f3d1c34212165549eacf89b8d62ad611c0e168..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.h -+++ /dev/null -@@ -1,28 +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 THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_H_ --#define THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_H_ -- --#include "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h" -- --namespace blink { -- --class WebGLRenderingContextWebGPU final -- : public WebGLRenderingContextWebGPUBase { -- DEFINE_WRAPPERTYPEINFO(); -- -- public: -- WebGLRenderingContextWebGPU( -- CanvasRenderingContextHost* host, -- const CanvasContextCreationAttributesCore& requested_attributes); -- -- // CanvasRenderingContext implementation -- V8RenderingContext* AsV8RenderingContext() final; -- V8OffscreenRenderingContext* AsV8OffscreenRenderingContext() final; --}; -- --} // namespace blink -- --#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_H_ -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 -deleted file mode 100644 -index 2f4c23c68dc658cd8f91a72948b78f1f39c92578..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu.idl -+++ /dev/null -@@ -1,16 +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. -- --// https://www.khronos.org/registry/webgl/specs/latest/1.0/#WebGLRenderingContext -- --[ -- ActiveScriptWrappable, -- Exposed=(Window,Worker), -- RuntimeEnabled=WebGLOnWebGPU --] interface WebGLRenderingContextWebGPU { -- -- [RuntimeEnabled=WebGLDrawingBufferStorage] const GLenum RGB8 = 0x8051; -- [RuntimeEnabled=WebGLDrawingBufferStorage] const GLenum RGBA8 = 0x8058; --}; --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 -deleted file mode 100644 -index 18d26cfe4faea0937d6f6c0c35424b29acc43786..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.cc -+++ /dev/null -@@ -1,2475 +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 "third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h" -- --#include "base/notimplemented.h" -- --namespace blink { -- --WebGLRenderingContextWebGPUBase::WebGLRenderingContextWebGPUBase( -- CanvasRenderingContextHost* host, -- const CanvasContextCreationAttributesCore& requested_attributes, -- CanvasRenderingAPI api) -- : WebGLContextObjectSupport( -- host->GetTopExecutionContext()->GetTaskRunner(TaskType::kWebGL), -- /* is_webgl2 */ api == CanvasRenderingAPI::kWebgl2), -- CanvasRenderingContext(host, requested_attributes, api) {} -- --WebGLRenderingContextWebGPUBase::~WebGLRenderingContextWebGPUBase() {} -- --// **************************************************************************** --// Start of WebGLRenderingContextBase's IDL methods --// **************************************************************************** -- --V8UnionHTMLCanvasElementOrOffscreenCanvas* --WebGLRenderingContextWebGPUBase::getHTMLOrOffscreenCanvas() const { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --int WebGLRenderingContextWebGPUBase::drawingBufferWidth() const { -- NOTIMPLEMENTED(); -- return 0; --} -- --int WebGLRenderingContextWebGPUBase::drawingBufferHeight() const { -- NOTIMPLEMENTED(); -- return 0; --} -- --GLenum WebGLRenderingContextWebGPUBase::drawingBufferFormat() const { -- NOTIMPLEMENTED(); -- return 0; --} -- --V8PredefinedColorSpace --WebGLRenderingContextWebGPUBase::drawingBufferColorSpace() const { -- NOTIMPLEMENTED(); -- return V8PredefinedColorSpace(V8PredefinedColorSpace::Enum::kSRGB); --} -- --void WebGLRenderingContextWebGPUBase::setDrawingBufferColorSpace( -- const V8PredefinedColorSpace& color_space, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --V8PredefinedColorSpace WebGLRenderingContextWebGPUBase::unpackColorSpace() -- const { -- NOTIMPLEMENTED(); -- return V8PredefinedColorSpace(V8PredefinedColorSpace::Enum::kSRGB); --} -- --void WebGLRenderingContextWebGPUBase::setUnpackColorSpace( -- const V8PredefinedColorSpace& color_space, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::activeTexture(GLenum texture) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::attachShader(WebGLProgram*, -- WebGLShader*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bindAttribLocation(WebGLProgram*, -- GLuint index, -- const String& name) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bindBuffer(GLenum target, -- WebGLBuffer* buffer) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bindFramebuffer(GLenum target, -- WebGLFramebuffer*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bindRenderbuffer(GLenum target, -- WebGLRenderbuffer*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bindTexture(GLenum target, -- WebGLTexture*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::blendColor(GLfloat red, -- GLfloat green, -- GLfloat blue, -- GLfloat alpha) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::blendEquation(GLenum mode) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::blendEquationSeparate(GLenum mode_rgb, -- GLenum mode_alpha) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::blendFunc(GLenum sfactor, -- GLenum dfactor) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::blendFuncSeparate(GLenum src_rgb, -- GLenum dst_rgb, -- GLenum src_alpha, -- GLenum dst_alpha) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bufferData(GLenum target, -- int64_t size, -- GLenum usage) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bufferData(GLenum target, -- DOMArrayBufferBase* data, -- GLenum usage) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bufferData( -- GLenum target, -- MaybeShared data, -- GLenum usage) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bufferSubData( -- GLenum target, -- int64_t offset, -- base::span data) { -- NOTIMPLEMENTED(); --} -- --GLenum WebGLRenderingContextWebGPUBase::checkFramebufferStatus(GLenum target) { -- NOTIMPLEMENTED(); -- return 0; --} -- --void WebGLRenderingContextWebGPUBase::clear(GLbitfield mask) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::clearColor(GLfloat red, -- GLfloat green, -- GLfloat blue, -- GLfloat alpha) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::clearDepth(GLfloat) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::clearStencil(GLint) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::colorMask(GLboolean red, -- GLboolean green, -- GLboolean blue, -- GLboolean alpha) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compileShader(WebGLShader*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexImage2D( -- GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- MaybeShared data) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexSubImage2D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- MaybeShared data) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::copyTexImage2D(GLenum target, -- GLint level, -- GLenum internalformat, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLint border) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::copyTexSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --WebGLBuffer* WebGLRenderingContextWebGPUBase::createBuffer() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --WebGLFramebuffer* WebGLRenderingContextWebGPUBase::createFramebuffer() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --WebGLProgram* WebGLRenderingContextWebGPUBase::createProgram() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --WebGLRenderbuffer* WebGLRenderingContextWebGPUBase::createRenderbuffer() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --WebGLShader* WebGLRenderingContextWebGPUBase::createShader(GLenum type) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --WebGLTexture* WebGLRenderingContextWebGPUBase::createTexture() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::cullFace(GLenum mode) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::deleteBuffer(WebGLBuffer*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::deleteFramebuffer(WebGLFramebuffer*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::deleteProgram(WebGLProgram*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::deleteRenderbuffer(WebGLRenderbuffer*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::deleteShader(WebGLShader*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::deleteTexture(WebGLTexture*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::depthFunc(GLenum) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::depthMask(GLboolean) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::depthRange(GLfloat z_near, -- GLfloat z_far) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::detachShader(WebGLProgram*, -- WebGLShader*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::disable(GLenum cap) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::disableVertexAttribArray(GLuint index) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::drawArrays(GLenum mode, -- GLint first, -- GLsizei count) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::drawElements(GLenum mode, -- GLsizei count, -- GLenum type, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::enable(GLenum cap) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::enableVertexAttribArray(GLuint index) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::finish() { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::flush() { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::framebufferRenderbuffer( -- GLenum target, -- GLenum attachment, -- GLenum renderbuffertarget, -- WebGLRenderbuffer*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::framebufferTexture2D(GLenum target, -- GLenum attachment, -- GLenum textarget, -- WebGLTexture*, -- GLint level) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::frontFace(GLenum mode) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::generateMipmap(GLenum target) { -- NOTIMPLEMENTED(); --} -- --WebGLActiveInfo* WebGLRenderingContextWebGPUBase::getActiveAttrib( -- WebGLProgram*, -- GLuint index) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --WebGLActiveInfo* WebGLRenderingContextWebGPUBase::getActiveUniform( -- WebGLProgram*, -- GLuint index) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --std::optional>> --WebGLRenderingContextWebGPUBase::getAttachedShaders(WebGLProgram*) { -- NOTIMPLEMENTED(); -- return {}; --} -- --GLint WebGLRenderingContextWebGPUBase::getAttribLocation(WebGLProgram*, -- const String& name) { -- NOTIMPLEMENTED(); -- return 0; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getBufferParameter(ScriptState*, -- GLenum target, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --WebGLContextAttributes* WebGLRenderingContextWebGPUBase::getContextAttributes() -- const { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --GLenum WebGLRenderingContextWebGPUBase::getError() { -- NOTIMPLEMENTED(); -- return 0; --} -- --ScriptObject WebGLRenderingContextWebGPUBase::getExtension(ScriptState*, -- const String& name) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getFramebufferAttachmentParameter( -- ScriptState*, -- GLenum target, -- GLenum attachment, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getParameter(ScriptState*, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getProgramParameter(ScriptState*, -- WebGLProgram*, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --String WebGLRenderingContextWebGPUBase::getProgramInfoLog(WebGLProgram*) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getRenderbufferParameter( -- ScriptState*, -- GLenum target, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getShaderParameter(ScriptState*, -- WebGLShader*, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --String WebGLRenderingContextWebGPUBase::getShaderInfoLog(WebGLShader*) { -- NOTIMPLEMENTED(); -- return {}; --} -- --WebGLShaderPrecisionFormat* --WebGLRenderingContextWebGPUBase::getShaderPrecisionFormat( -- GLenum shader_type, -- GLenum precision_type) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --String WebGLRenderingContextWebGPUBase::getShaderSource(WebGLShader*) { -- NOTIMPLEMENTED(); -- return {}; --} -- --std::optional> --WebGLRenderingContextWebGPUBase::getSupportedExtensions() { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getTexParameter(ScriptState*, -- GLenum target, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getUniform( -- ScriptState*, -- WebGLProgram*, -- const WebGLUniformLocation*) { -- NOTIMPLEMENTED(); -- return {}; --} -- --WebGLUniformLocation* WebGLRenderingContextWebGPUBase::getUniformLocation( -- WebGLProgram*, -- const String&) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getVertexAttrib(ScriptState*, -- GLuint index, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --int64_t WebGLRenderingContextWebGPUBase::getVertexAttribOffset(GLuint index, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return 0; --} -- --void WebGLRenderingContextWebGPUBase::hint(GLenum target, GLenum mode) { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::isBuffer(WebGLBuffer*) { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::isEnabled(GLenum cap) { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::isFramebuffer(WebGLFramebuffer*) { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::isProgram(WebGLProgram*) { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::isRenderbuffer(WebGLRenderbuffer*) { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::isShader(WebGLShader*) { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::isTexture(WebGLTexture*) { -- NOTIMPLEMENTED(); -- return false; --} -- --void WebGLRenderingContextWebGPUBase::lineWidth(GLfloat) { -- NOTIMPLEMENTED(); --} --void WebGLRenderingContextWebGPUBase::linkProgram(WebGLProgram*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::pixelStorei(GLenum pname, GLint param) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::polygonOffset(GLfloat factor, -- GLfloat units) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::readPixels( -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared pixels) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::renderbufferStorage(GLenum target, -- GLenum internalformat, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::sampleCoverage(GLfloat value, -- GLboolean invert) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::scissor(GLint x, -- GLint y, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::shaderSource(WebGLShader*, -- const String&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::stencilFunc(GLenum func, -- GLint ref, -- GLuint mask) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::stencilFuncSeparate(GLenum face, -- GLenum func, -- GLint ref, -- GLuint mask) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::stencilMask(GLuint) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::stencilMaskSeparate(GLenum face, -- GLuint mask) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::stencilOp(GLenum fail, -- GLenum zfail, -- GLenum zpass) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::stencilOpSeparate(GLenum face, -- GLenum fail, -- GLenum zfail, -- GLenum zpass) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texParameterf(GLenum target, -- GLenum pname, -- GLfloat param) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texParameteri(GLenum target, -- GLenum pname, -- GLint param) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D( -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- ImageData*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- HTMLImageElement*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- HTMLVideoElement*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- VideoFrame*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- ImageBitmap*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- ImageData*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- HTMLImageElement*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} --void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- HTMLVideoElement*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- VideoFrame*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- ImageBitmap*, -- ExceptionState&) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform1f(const WebGLUniformLocation*, -- GLfloat x) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform1fv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform1i(const WebGLUniformLocation*, -- GLint x) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform1iv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2f(const WebGLUniformLocation*, -- GLfloat x, -- GLfloat y) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2fv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2i(const WebGLUniformLocation*, -- GLint x, -- GLint y) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2iv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3f(const WebGLUniformLocation*, -- GLfloat x, -- GLfloat y, -- GLfloat z) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3fv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3i(const WebGLUniformLocation*, -- GLint x, -- GLint y, -- GLint z) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3iv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4f(const WebGLUniformLocation*, -- GLfloat x, -- GLfloat y, -- GLfloat z, -- GLfloat w) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4fv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4i(const WebGLUniformLocation*, -- GLint x, -- GLint y, -- GLint z, -- GLint w) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4iv(const WebGLUniformLocation*, -- base::span) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix2fv( -- const WebGLUniformLocation*, -- GLboolean transpose, -- base::span value) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix3fv( -- const WebGLUniformLocation*, -- GLboolean transpose, -- base::span value) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix4fv( -- const WebGLUniformLocation*, -- GLboolean transpose, -- base::span value) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::useProgram(WebGLProgram*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::validateProgram(WebGLProgram*) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib1f(GLuint index, GLfloat x) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib1fv( -- GLuint index, -- base::span values) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib2f(GLuint index, -- GLfloat x, -- GLfloat y) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib2fv( -- GLuint index, -- base::span values) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib3f(GLuint index, -- GLfloat x, -- GLfloat y, -- GLfloat z) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib3fv( -- GLuint index, -- base::span values) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib4f(GLuint index, -- GLfloat x, -- GLfloat y, -- GLfloat z, -- GLfloat w) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttrib4fv( -- GLuint index, -- base::span values) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttribPointer(GLuint index, -- GLint size, -- GLenum type, -- GLboolean normalized, -- GLsizei stride, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::viewport(GLint x, -- GLint y, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::drawingBufferStorage(GLenum sizedformat, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::commit() { -- NOTIMPLEMENTED(); --} -- --ScriptPromise WebGLRenderingContextWebGPUBase::makeXRCompatible( -- ScriptState*, -- ExceptionState&) { -- NOTIMPLEMENTED(); -- return {}; --} -- --// **************************************************************************** --// End of WebGLRenderingContextBase's IDL methods --// **************************************************************************** -- --// ************************************************************************** --// Start of WebGL2RenderingContextBase's IDL methods --// ************************************************************************** -- --void WebGLRenderingContextWebGPUBase::bufferData( -- GLenum target, -- MaybeShared srcData, -- GLenum usage, -- int64_t srcOffset, -- GLuint length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bufferSubData( -- GLenum target, -- int64_t offset, -- MaybeShared srcData, -- int64_t srcOffset, -- GLuint length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::copyBufferSubData(GLenum readTarget, -- GLenum writeTarget, -- int64_t readOffset, -- int64_t writeOffset, -- int64_t size) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::getBufferSubData( -- GLenum target, -- int64_t srcByteOffset, -- MaybeShared dstData, -- int64_t dstOffset, -- GLuint length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::blitFramebuffer(GLint src_x0, -- GLint src_y0, -- GLint src_x1, -- GLint src_y1, -- GLint dst_x0, -- GLint dst_y0, -- GLint dst_x1, -- GLint dst_y1, -- GLbitfield mask, -- GLenum filter) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::framebufferTextureLayer( -- GLenum target, -- GLenum attachment, -- WebGLTexture* texture, -- GLint level, -- GLint layer) { -- NOTIMPLEMENTED(); --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getInternalformatParameter( -- ScriptState* script_state, -- GLenum target, -- GLenum internalformat, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --void WebGLRenderingContextWebGPUBase::invalidateFramebuffer( -- GLenum target, -- const Vector& attachments) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::invalidateSubFramebuffer( -- GLenum target, -- const Vector& attachments, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::readBuffer(GLenum mode) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::renderbufferStorageMultisample( -- GLenum target, -- GLsizei samples, -- GLenum internalformat, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- ImageData* pixels) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* canvas, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D( -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage2D( -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared data, -- int64_t src_offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texElement2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- Element* element, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- ImageData* pixels) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* canvas, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage2D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- int64_t src_offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texStorage2D(GLenum target, -- GLsizei levels, -- GLenum internalformat, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texStorage3D(GLenum target, -- GLsizei levels, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- ImageData* pixels) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* canvas, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D( -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D( -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared pixels) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texImage3D( -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- GLuint src_offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- ImageData* pixels) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* context_host, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D( -- ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- MaybeShared pixels) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::texSubImage3D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- GLuint src_offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::copyTexSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexImage2D( -- GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexSubImage2D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexImage3D( -- GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexSubImage3D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexImage2D( -- GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLsizei image_size, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexSubImage2D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLsizei image_size, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexImage3D( -- GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLsizei image_size, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::compressedTexSubImage3D( -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLsizei image_size, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --GLint WebGLRenderingContextWebGPUBase::getFragDataLocation( -- WebGLProgram* program, -- const String& name) { -- NOTIMPLEMENTED(); -- return 0; --} -- --void WebGLRenderingContextWebGPUBase::uniform1ui( -- const WebGLUniformLocation* location, -- GLuint v0) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2ui( -- const WebGLUniformLocation* location, -- GLuint v0, -- GLuint v1) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3ui( -- const WebGLUniformLocation* location, -- GLuint v0, -- GLuint v1, -- GLuint v2) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4ui( -- const WebGLUniformLocation* location, -- GLuint v0, -- GLuint v1, -- GLuint v2, -- GLuint v3) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform1fv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2fv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3fv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4fv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform1iv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2iv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3iv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4iv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform1uiv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform2uiv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform3uiv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniform4uiv( -- const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix2fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix3fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix4fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix2x3fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix3x2fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix2x4fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix4x2fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix3x4fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::uniformMatrix4x3fv( -- const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttribI4i(GLuint index, -- GLint x, -- GLint y, -- GLint z, -- GLint w) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttribI4iv( -- GLuint index, -- base::span v) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttribI4ui(GLuint index, -- GLuint x, -- GLuint y, -- GLuint z, -- GLuint w) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttribI4uiv( -- GLuint index, -- base::span v) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttribIPointer(GLuint index, -- GLint size, -- GLenum type, -- GLsizei stride, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::vertexAttribDivisor(GLuint index, -- GLuint divisor) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::drawArraysInstanced( -- GLenum mode, -- GLint first, -- GLsizei count, -- GLsizei instance_count) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::drawElementsInstanced( -- GLenum mode, -- GLsizei count, -- GLenum type, -- int64_t offset, -- GLsizei instance_count) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::drawRangeElements(GLenum mode, -- GLuint start, -- GLuint end, -- GLsizei count, -- GLenum type, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::drawBuffers( -- const Vector& buffers) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::clearBufferiv( -- GLenum buffer, -- GLint drawbuffer, -- base::span value, -- GLuint src_offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::clearBufferuiv( -- GLenum buffer, -- GLint drawbuffer, -- base::span value, -- GLuint src_offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::clearBufferfv( -- GLenum buffer, -- GLint drawbuffer, -- base::span value, -- GLuint src_offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::clearBufferfi(GLenum buffer, -- GLint drawbuffer, -- GLfloat depth, -- GLint stencil) { -- NOTIMPLEMENTED(); --} -- --WebGLQuery* WebGLRenderingContextWebGPUBase::createQuery() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::deleteQuery(WebGLQuery* query) { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::isQuery(WebGLQuery* query) { -- NOTIMPLEMENTED(); -- return false; --} -- --void WebGLRenderingContextWebGPUBase::beginQuery(GLenum target, -- WebGLQuery* query) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::endQuery(GLenum target) { -- NOTIMPLEMENTED(); --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getQuery(ScriptState* script_state, -- GLenum target, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getQueryParameter( -- ScriptState* script_state, -- WebGLQuery* query, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --WebGLSampler* WebGLRenderingContextWebGPUBase::createSampler() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::deleteSampler(WebGLSampler* sampler) { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::isSampler(WebGLSampler* sampler) { -- NOTIMPLEMENTED(); -- return false; --} -- --void WebGLRenderingContextWebGPUBase::bindSampler(GLuint unit, -- WebGLSampler* sampler) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::samplerParameteri(WebGLSampler* sampler, -- GLenum pname, -- GLint param) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::samplerParameterf(WebGLSampler* sampler, -- GLenum pname, -- GLfloat param) { -- NOTIMPLEMENTED(); --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getSamplerParameter( -- ScriptState* script_state, -- WebGLSampler* sampler, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --WebGLSync* WebGLRenderingContextWebGPUBase::fenceSync(GLenum condition, -- GLbitfield flags) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --bool WebGLRenderingContextWebGPUBase::isSync(WebGLSync* sync) { -- NOTIMPLEMENTED(); -- return false; --} -- --void WebGLRenderingContextWebGPUBase::deleteSync(WebGLSync* sync) { -- NOTIMPLEMENTED(); --} -- --GLenum WebGLRenderingContextWebGPUBase::clientWaitSync(WebGLSync* sync, -- GLbitfield flags, -- GLuint64 timeout) { -- NOTIMPLEMENTED(); -- return 0; --} -- --void WebGLRenderingContextWebGPUBase::waitSync(WebGLSync* sync, -- GLbitfield flags, -- GLint64 timeout) { -- NOTIMPLEMENTED(); --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getSyncParameter( -- ScriptState* script_state, -- WebGLSync* sync, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --WebGLTransformFeedback* --WebGLRenderingContextWebGPUBase::createTransformFeedback() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::deleteTransformFeedback( -- WebGLTransformFeedback* feedback) { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::isTransformFeedback( -- WebGLTransformFeedback* feedback) { -- NOTIMPLEMENTED(); -- return false; --} -- --void WebGLRenderingContextWebGPUBase::bindTransformFeedback( -- GLenum target, -- WebGLTransformFeedback* feedback) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::beginTransformFeedback( -- GLenum primitive_mode) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::endTransformFeedback() { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::transformFeedbackVaryings( -- WebGLProgram* program, -- const Vector& varyings, -- GLenum buffer_mode) { -- NOTIMPLEMENTED(); --} -- --WebGLActiveInfo* WebGLRenderingContextWebGPUBase::getTransformFeedbackVarying( -- WebGLProgram* program, -- GLuint index) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::pauseTransformFeedback() { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::resumeTransformFeedback() { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bindBufferBase(GLenum target, -- GLuint index, -- WebGLBuffer* buffer) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::bindBufferRange(GLenum target, -- GLuint index, -- WebGLBuffer* buffer, -- int64_t offset, -- int64_t size) { -- NOTIMPLEMENTED(); --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getIndexedParameter( -- ScriptState* script_state, -- GLenum target, -- GLuint index) { -- NOTIMPLEMENTED(); -- return {}; --} -- --std::optional> --WebGLRenderingContextWebGPUBase::getUniformIndices( -- WebGLProgram* program, -- const Vector& uniform_names) { -- NOTIMPLEMENTED(); -- return {}; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getActiveUniforms( -- ScriptState* script_state, -- WebGLProgram* program, -- const Vector& uniform_indices, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --GLuint WebGLRenderingContextWebGPUBase::getUniformBlockIndex( -- WebGLProgram* program, -- const String& uniform_block_name) { -- NOTIMPLEMENTED(); -- return 0; --} -- --ScriptValue WebGLRenderingContextWebGPUBase::getActiveUniformBlockParameter( -- ScriptState* script_state, -- WebGLProgram* program, -- GLuint uniform_block_index, -- GLenum pname) { -- NOTIMPLEMENTED(); -- return {}; --} -- --String WebGLRenderingContextWebGPUBase::getActiveUniformBlockName( -- WebGLProgram* program, -- GLuint uniform_block_index) { -- NOTIMPLEMENTED(); -- return {}; --} -- --void WebGLRenderingContextWebGPUBase::uniformBlockBinding( -- WebGLProgram* program, -- GLuint uniform_block_index, -- GLuint uniform_block_binding) { -- NOTIMPLEMENTED(); --} -- --WebGLVertexArrayObject* WebGLRenderingContextWebGPUBase::createVertexArray() { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::deleteVertexArray( -- WebGLVertexArrayObject* vertex_array) { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::isVertexArray( -- WebGLVertexArrayObject* vertex_array) { -- NOTIMPLEMENTED(); -- return false; --} -- --void WebGLRenderingContextWebGPUBase::bindVertexArray( -- WebGLVertexArrayObject* vertex_array) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::readPixels(GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::readPixels( -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- int64_t offset) { -- NOTIMPLEMENTED(); --} -- --// ************************************************************************** --// End of WebGL2RenderingContextBase's IDL methods --// ************************************************************************** -- --// **************************************************************************** --// Start of CanvasRenderingContext implementation --// **************************************************************************** --SkAlphaType WebGLRenderingContextWebGPUBase::GetAlphaType() const { -- NOTIMPLEMENTED(); -- return SkAlphaType::kUnknown_SkAlphaType; --} -- --viz::SharedImageFormat WebGLRenderingContextWebGPUBase::GetSharedImageFormat() -- const { -- NOTIMPLEMENTED(); -- return {}; --} -- --gfx::ColorSpace WebGLRenderingContextWebGPUBase::GetColorSpace() const { -- NOTIMPLEMENTED(); -- return {}; --} -- --bool WebGLRenderingContextWebGPUBase::isContextLost() const { -- NOTIMPLEMENTED(); -- return false; --} -- --scoped_refptr WebGLRenderingContextWebGPUBase::GetImage( -- FlushReason) { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::SetHdrMetadata( -- const gfx::HDRMetadata& hdr_metadata) { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::IsComposited() const { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::IsPaintable() const { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::UsingSwapChain() const { -- NOTIMPLEMENTED(); -- return false; --} -- --void WebGLRenderingContextWebGPUBase::PageVisibilityChanged() { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::PaintRenderingResultsToCanvas( -- SourceDrawingBuffer) { -- NOTIMPLEMENTED(); -- return false; --} -- --bool WebGLRenderingContextWebGPUBase::CopyRenderingResultsToVideoFrame( -- WebGraphicsContext3DVideoFramePool*, -- SourceDrawingBuffer, -- const gfx::ColorSpace&, -- VideoFrameCopyCompletedCallback) { -- NOTIMPLEMENTED(); -- return false; --} -- --cc::Layer* WebGLRenderingContextWebGPUBase::CcLayer() const { -- NOTIMPLEMENTED(); -- return nullptr; --} -- --void WebGLRenderingContextWebGPUBase::Stop() { -- NOTIMPLEMENTED(); --} -- --void WebGLRenderingContextWebGPUBase::FinalizeFrame(FlushReason) { -- NOTIMPLEMENTED(); --} -- --bool WebGLRenderingContextWebGPUBase::PushFrame() { -- NOTIMPLEMENTED(); -- return false; --} -- --// **************************************************************************** --// End of CanvasRenderingContext implementation --// **************************************************************************** -- --void WebGLRenderingContextWebGPUBase::Trace(Visitor* visitor) const { -- WebGLContextObjectSupport::Trace(visitor); -- CanvasRenderingContext::Trace(visitor); --} --} // 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 -deleted file mode 100644 -index 10df703f34e8357a08f3d891e4b7291e247e3adc..0000000000000000000000000000000000000000 ---- a/third_party/blink/renderer/modules/webgl/webgl_rendering_context_webgpu_base.h -+++ /dev/null -@@ -1,1285 +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 THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_BASE_H_ --#define THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_BASE_H_ -- --#include "third_party/blink/renderer/bindings/core/v8/script_promise_resolver.h" --#include "third_party/blink/renderer/bindings/core/v8/script_value.h" --#include "third_party/blink/renderer/bindings/core/v8/v8_predefined_color_space.h" --#include "third_party/blink/renderer/bindings/modules/v8/v8_webgl_context_attributes.h" --#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/wtf/text/wtf_string.h" -- --namespace blink { -- --class ExceptionState; --class HTMLImageElement; --class HTMLVideoElement; --class ImageBitmap; --class ImageData; --class ScriptState; --class V8PredefinedColorSpace; --class V8UnionHTMLCanvasElementOrOffscreenCanvas; --class VideoFrame; --class WebGLActiveInfo; --class WebGLBuffer; --class WebGLFramebuffer; --class WebGLProgram; --class WebGLQuery; --class WebGLRenderbuffer; --class WebGLSampler; --class WebGLShader; --class WebGLShaderPrecisionFormat; --class WebGLSync; --class WebGLTexture; --class WebGLTransformFeedback; --class WebGLUniformLocation; --class WebGLVertexArrayObject; -- --class MODULES_EXPORT WebGLRenderingContextWebGPUBase -- : public WebGLContextObjectSupport, -- public CanvasRenderingContext { -- public: -- WebGLRenderingContextWebGPUBase( -- CanvasRenderingContextHost* host, -- const CanvasContextCreationAttributesCore& requested_attributes, -- CanvasRenderingAPI api); -- ~WebGLRenderingContextWebGPUBase() override; -- -- WebGLRenderingContextWebGPUBase(const WebGLRenderingContextWebGPUBase&) = -- delete; -- WebGLRenderingContextWebGPUBase& operator=( -- const WebGLRenderingContextWebGPUBase&) = delete; -- -- // ************************************************************************** -- // Start of WebGLRenderingContextBase's IDL methods -- // ************************************************************************** -- V8UnionHTMLCanvasElementOrOffscreenCanvas* getHTMLOrOffscreenCanvas() const; -- -- int drawingBufferWidth() const; -- int drawingBufferHeight() const; -- GLenum drawingBufferFormat() const; -- V8PredefinedColorSpace drawingBufferColorSpace() const; -- void setDrawingBufferColorSpace(const V8PredefinedColorSpace& color_space, -- ExceptionState&); -- V8PredefinedColorSpace unpackColorSpace() const; -- void setUnpackColorSpace(const V8PredefinedColorSpace& color_space, -- ExceptionState&); -- -- void activeTexture(GLenum texture); -- void attachShader(WebGLProgram*, WebGLShader*); -- -- void bindAttribLocation(WebGLProgram*, GLuint index, const String& name); -- void bindBuffer(GLenum target, WebGLBuffer* buffer); -- void bindFramebuffer(GLenum target, WebGLFramebuffer*); -- void bindRenderbuffer(GLenum target, WebGLRenderbuffer*); -- void bindTexture(GLenum target, WebGLTexture*); -- void blendColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha); -- void blendEquation(GLenum mode); -- void blendEquationSeparate(GLenum mode_rgb, GLenum mode_alpha); -- void blendFunc(GLenum sfactor, GLenum dfactor); -- void blendFuncSeparate(GLenum src_rgb, -- GLenum dst_rgb, -- GLenum src_alpha, -- GLenum dst_alpha); -- -- void bufferData(GLenum target, int64_t size, GLenum usage); -- void bufferData(GLenum target, DOMArrayBufferBase* data, GLenum usage); -- void bufferData(GLenum target, -- MaybeShared data, -- GLenum usage); -- void bufferSubData(GLenum target, -- int64_t offset, -- base::span data); -- -- GLenum checkFramebufferStatus(GLenum target); -- void clear(GLbitfield mask); -- void clearColor(GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha); -- void clearDepth(GLfloat); -- void clearStencil(GLint); -- void colorMask(GLboolean red, -- GLboolean green, -- GLboolean blue, -- GLboolean alpha); -- void compileShader(WebGLShader*); -- -- void compressedTexImage2D(GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- MaybeShared data); -- void compressedTexSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- MaybeShared data); -- void copyTexImage2D(GLenum target, -- GLint level, -- GLenum internalformat, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLint border); -- void copyTexSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height); -- -- WebGLBuffer* createBuffer(); -- WebGLFramebuffer* createFramebuffer(); -- WebGLProgram* createProgram(); -- WebGLRenderbuffer* createRenderbuffer(); -- WebGLShader* createShader(GLenum type); -- WebGLTexture* createTexture(); -- -- void cullFace(GLenum mode); -- -- void deleteBuffer(WebGLBuffer*); -- void deleteFramebuffer(WebGLFramebuffer*); -- void deleteProgram(WebGLProgram*); -- void deleteRenderbuffer(WebGLRenderbuffer*); -- void deleteShader(WebGLShader*); -- void deleteTexture(WebGLTexture*); -- -- void depthFunc(GLenum); -- void depthMask(GLboolean); -- void depthRange(GLfloat z_near, GLfloat z_far); -- void detachShader(WebGLProgram*, WebGLShader*); -- void disable(GLenum cap); -- void disableVertexAttribArray(GLuint index); -- void drawArrays(GLenum mode, GLint first, GLsizei count); -- void drawElements(GLenum mode, GLsizei count, GLenum type, int64_t offset); -- -- void enable(GLenum cap); -- void enableVertexAttribArray(GLuint index); -- void finish(); -- void flush(); -- void framebufferRenderbuffer(GLenum target, -- GLenum attachment, -- GLenum renderbuffertarget, -- WebGLRenderbuffer*); -- void framebufferTexture2D(GLenum target, -- GLenum attachment, -- GLenum textarget, -- WebGLTexture*, -- GLint level); -- void frontFace(GLenum mode); -- void generateMipmap(GLenum target); -- -- WebGLActiveInfo* getActiveAttrib(WebGLProgram*, GLuint index); -- WebGLActiveInfo* getActiveUniform(WebGLProgram*, GLuint index); -- std::optional>> getAttachedShaders( -- WebGLProgram*); -- GLint getAttribLocation(WebGLProgram*, const String& name); -- ScriptValue getBufferParameter(ScriptState*, GLenum target, GLenum pname); -- WebGLContextAttributes* getContextAttributes() const; -- GLenum getError(); -- ScriptObject getExtension(ScriptState*, const String& name); -- ScriptValue getFramebufferAttachmentParameter(ScriptState*, -- GLenum target, -- GLenum attachment, -- GLenum pname); -- ScriptValue getParameter(ScriptState*, GLenum pname); -- ScriptValue getProgramParameter(ScriptState*, WebGLProgram*, GLenum pname); -- String getProgramInfoLog(WebGLProgram*); -- ScriptValue getRenderbufferParameter(ScriptState*, -- GLenum target, -- GLenum pname); -- ScriptValue getShaderParameter(ScriptState*, WebGLShader*, GLenum pname); -- String getShaderInfoLog(WebGLShader*); -- WebGLShaderPrecisionFormat* getShaderPrecisionFormat(GLenum shader_type, -- GLenum precision_type); -- String getShaderSource(WebGLShader*); -- std::optional> getSupportedExtensions(); -- ScriptValue getTexParameter(ScriptState*, GLenum target, GLenum pname); -- ScriptValue getUniform(ScriptState*, -- WebGLProgram*, -- const WebGLUniformLocation*); -- WebGLUniformLocation* getUniformLocation(WebGLProgram*, const String&); -- ScriptValue getVertexAttrib(ScriptState*, GLuint index, GLenum pname); -- int64_t getVertexAttribOffset(GLuint index, GLenum pname); -- -- void hint(GLenum target, GLenum mode); -- bool isBuffer(WebGLBuffer*); -- bool isEnabled(GLenum cap); -- bool isFramebuffer(WebGLFramebuffer*); -- bool isProgram(WebGLProgram*); -- bool isRenderbuffer(WebGLRenderbuffer*); -- bool isShader(WebGLShader*); -- bool isTexture(WebGLTexture*); -- -- void lineWidth(GLfloat); -- void linkProgram(WebGLProgram*); -- void pixelStorei(GLenum pname, GLint param); -- void polygonOffset(GLfloat factor, GLfloat units); -- -- void readPixels(GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared pixels); -- -- void renderbufferStorage(GLenum target, -- GLenum internalformat, -- GLsizei width, -- GLsizei height); -- -- void sampleCoverage(GLfloat value, GLboolean invert); -- void scissor(GLint x, GLint y, GLsizei width, GLsizei height); -- void shaderSource(WebGLShader*, const String&); -- void stencilFunc(GLenum func, GLint ref, GLuint mask); -- void stencilFuncSeparate(GLenum face, GLenum func, GLint ref, GLuint mask); -- void stencilMask(GLuint); -- void stencilMaskSeparate(GLenum face, GLuint mask); -- void stencilOp(GLenum fail, GLenum zfail, GLenum zpass); -- void stencilOpSeparate(GLenum face, GLenum fail, GLenum zfail, GLenum zpass); -- -- void texParameterf(GLenum target, GLenum pname, GLfloat param); -- void texParameteri(GLenum target, GLenum pname, GLint param); -- -- void texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared); -- void texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- ImageData*); -- void texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- HTMLImageElement*, -- ExceptionState&); -- void texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost*, -- ExceptionState&); -- void texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- HTMLVideoElement*, -- ExceptionState&); -- void texImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- VideoFrame*, -- ExceptionState&); -- void texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- ImageBitmap*, -- ExceptionState&); -- -- void texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared); -- void texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- ImageData*); -- void texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- HTMLImageElement*, -- ExceptionState&); -- void texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost*, -- ExceptionState&); -- void texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- HTMLVideoElement*, -- ExceptionState&); -- void texSubImage2D(ScriptState*, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- VideoFrame*, -- ExceptionState&); -- void texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLenum format, -- GLenum type, -- ImageBitmap*, -- ExceptionState&); -- -- void uniform1f(const WebGLUniformLocation*, GLfloat x); -- void uniform1fv(const WebGLUniformLocation*, base::span); -- void uniform1i(const WebGLUniformLocation*, GLint x); -- void uniform1iv(const WebGLUniformLocation*, base::span); -- void uniform2f(const WebGLUniformLocation*, GLfloat x, GLfloat y); -- void uniform2fv(const WebGLUniformLocation*, base::span); -- void uniform2i(const WebGLUniformLocation*, GLint x, GLint y); -- void uniform2iv(const WebGLUniformLocation*, base::span); -- void uniform3f(const WebGLUniformLocation*, GLfloat x, GLfloat y, GLfloat z); -- void uniform3fv(const WebGLUniformLocation*, base::span); -- void uniform3i(const WebGLUniformLocation*, GLint x, GLint y, GLint z); -- void uniform3iv(const WebGLUniformLocation*, base::span); -- void uniform4f(const WebGLUniformLocation*, -- GLfloat x, -- GLfloat y, -- GLfloat z, -- GLfloat w); -- void uniform4fv(const WebGLUniformLocation*, base::span); -- void uniform4i(const WebGLUniformLocation*, -- GLint x, -- GLint y, -- GLint z, -- GLint w); -- void uniform4iv(const WebGLUniformLocation*, base::span); -- -- void uniformMatrix2fv(const WebGLUniformLocation*, -- GLboolean transpose, -- base::span value); -- void uniformMatrix3fv(const WebGLUniformLocation*, -- GLboolean transpose, -- base::span value); -- void uniformMatrix4fv(const WebGLUniformLocation*, -- GLboolean transpose, -- base::span value); -- -- void useProgram(WebGLProgram*); -- void validateProgram(WebGLProgram*); -- -- void vertexAttrib1f(GLuint index, GLfloat x); -- void vertexAttrib1fv(GLuint index, base::span values); -- void vertexAttrib2f(GLuint index, GLfloat x, GLfloat y); -- void vertexAttrib2fv(GLuint index, base::span values); -- void vertexAttrib3f(GLuint index, GLfloat x, GLfloat y, GLfloat z); -- void vertexAttrib3fv(GLuint index, base::span values); -- void vertexAttrib4f(GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w); -- void vertexAttrib4fv(GLuint index, base::span values); -- void vertexAttribPointer(GLuint index, -- GLint size, -- GLenum type, -- GLboolean normalized, -- GLsizei stride, -- int64_t offset); -- -- void viewport(GLint x, GLint y, GLsizei width, GLsizei height); -- -- void drawingBufferStorage(GLenum sizedformat, GLsizei width, GLsizei height); -- -- void commit(); -- -- ScriptPromise makeXRCompatible(ScriptState*, ExceptionState&); -- // ************************************************************************** -- // End of WebGLRenderingContextBase's IDL methods -- // ************************************************************************** -- -- // ************************************************************************** -- // Start of WebGL2RenderingContextBase's IDL methods -- // ************************************************************************** -- -- /* Buffer objects */ -- void bufferData(GLenum target, -- MaybeShared srcData, -- GLenum usage, -- int64_t srcOffset, -- GLuint length); -- void bufferSubData(GLenum target, -- int64_t offset, -- MaybeShared srcData, -- int64_t srcOffset, -- GLuint length); -- void copyBufferSubData(GLenum readTarget, -- GLenum writeTarget, -- int64_t readOffset, -- int64_t writeOffset, -- int64_t size); -- void getBufferSubData(GLenum target, -- int64_t srcByteOffset, -- MaybeShared dstData, -- int64_t dstOffset, -- GLuint length); -- -- /* Framebuffer objects */ -- void blitFramebuffer(GLint src_x0, -- GLint src_y0, -- GLint src_x1, -- GLint src_y1, -- GLint dst_x0, -- GLint dst_y0, -- GLint dst_x1, -- GLint dst_y1, -- GLbitfield mask, -- GLenum filter); -- void framebufferTextureLayer(GLenum target, -- GLenum attachment, -- WebGLTexture* texture, -- GLint level, -- GLint layer); -- ScriptValue getInternalformatParameter(ScriptState* script_state, -- GLenum target, -- GLenum internalformat, -- GLenum pname); -- void invalidateFramebuffer(GLenum target, const Vector& attachments); -- void invalidateSubFramebuffer(GLenum target, -- const Vector& attachments, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height); -- void readBuffer(GLenum mode); -- -- /* Renderbuffer objects */ -- void renderbufferStorageMultisample(GLenum target, -- GLsizei samples, -- GLenum internalformat, -- GLsizei width, -- GLsizei height); -- -- /* Texture objects */ -- void texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- int64_t offset); -- void texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- ImageData* pixels); -- void texImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state); -- // Handles both OffscreenCanvas and HTMLCanvasElement -- void texImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* canvas, -- ExceptionState& exception_state); -- void texImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state); -- void texImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state); -- void texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state); -- void texImage2D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared data, -- int64_t src_offset); -- -- void texElement2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLenum format, -- GLenum type, -- Element* element, -- ExceptionState& exception_state); -- -- void texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- int64_t offset); -- void texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- ImageData* pixels); -- void texSubImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state); -- // Handles both OffscreenCanvas and HTMLCanvasElement -- void texSubImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* canvas, -- ExceptionState& exception_state); -- void texSubImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state); -- void texSubImage2D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state); -- void texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state); -- void texSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- int64_t src_offset); -- -- void texStorage2D(GLenum target, -- GLsizei levels, -- GLenum internalformat, -- GLsizei width, -- GLsizei height); -- void texStorage3D(GLenum target, -- GLsizei levels, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth); -- void texImage3D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- int64_t offset); -- void texImage3D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- ImageData* pixels); -- void texImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state); -- // Handles both OffscreenCanvas and HTMLCanvasElement -- void texImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* canvas, -- ExceptionState& exception_state); -- void texImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state); -- void texImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state); -- void texImage3D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state); -- void texImage3D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared pixels); -- void texImage3D(GLenum target, -- GLint level, -- GLint internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- GLuint src_offset); -- void texSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- int64_t offset); -- void texSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- ImageData* pixels); -- void texSubImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- HTMLImageElement* image, -- ExceptionState& exception_state); -- // Handles both OffscreenCanvas and HTMLCanvasElement -- void texSubImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- CanvasRenderingContextHost* context_host, -- ExceptionState& exception_state); -- void texSubImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- HTMLVideoElement* video, -- ExceptionState& exception_state); -- void texSubImage3D(ScriptState* script_state, -- GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- VideoFrame* frame, -- ExceptionState& exception_state); -- void texSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- ImageBitmap* bitmap, -- ExceptionState& exception_state); -- void texSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- MaybeShared pixels); -- void texSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- GLuint src_offset); -- -- void copyTexSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLint x, -- GLint y, -- GLsizei width, -- GLsizei height); -- -- void compressedTexImage2D(GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override); -- void compressedTexSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override); -- void compressedTexImage3D(GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override); -- void compressedTexSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- MaybeShared data, -- GLuint src_offset, -- GLuint src_length_override); -- void compressedTexImage2D(GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLint border, -- GLsizei image_size, -- int64_t offset); -- void compressedTexSubImage2D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLsizei image_size, -- int64_t offset); -- void compressedTexImage3D(GLenum target, -- GLint level, -- GLenum internalformat, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLint border, -- GLsizei image_size, -- int64_t offset); -- void compressedTexSubImage3D(GLenum target, -- GLint level, -- GLint xoffset, -- GLint yoffset, -- GLint zoffset, -- GLsizei width, -- GLsizei height, -- GLsizei depth, -- GLenum format, -- GLsizei image_size, -- int64_t offset); -- -- /* Programs and shaders */ -- GLint getFragDataLocation(WebGLProgram* program, const String& name); -- -- /* Uniforms and attributes */ -- void uniform1ui(const WebGLUniformLocation* location, GLuint v0); -- void uniform2ui(const WebGLUniformLocation* location, GLuint v0, GLuint v1); -- void uniform3ui(const WebGLUniformLocation* location, -- GLuint v0, -- GLuint v1, -- GLuint v2); -- void uniform4ui(const WebGLUniformLocation* location, -- GLuint v0, -- GLuint v1, -- GLuint v2, -- GLuint v3); -- void uniform1fv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform2fv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform3fv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform4fv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform1iv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform2iv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform3iv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform4iv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform1uiv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform2uiv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform3uiv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniform4uiv(const WebGLUniformLocation* location, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix2fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix3fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix4fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix2x3fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix3x2fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix2x4fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix4x2fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix3x4fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- void uniformMatrix4x3fv(const WebGLUniformLocation* location, -- GLboolean transpose, -- base::span v, -- GLuint src_offset, -- GLuint src_length); -- -- void vertexAttribI4i(GLuint index, GLint x, GLint y, GLint z, GLint w); -- void vertexAttribI4iv(GLuint index, base::span v); -- void vertexAttribI4ui(GLuint index, GLuint x, GLuint y, GLuint z, GLuint w); -- void vertexAttribI4uiv(GLuint index, base::span v); -- void vertexAttribIPointer(GLuint index, -- GLint size, -- GLenum type, -- GLsizei stride, -- int64_t offset); -- -- /* Writing to the drawing buffer */ -- void vertexAttribDivisor(GLuint index, GLuint divisor); -- void drawArraysInstanced(GLenum mode, -- GLint first, -- GLsizei count, -- GLsizei instance_count); -- void drawElementsInstanced(GLenum mode, -- GLsizei count, -- GLenum type, -- int64_t offset, -- GLsizei instance_count); -- void drawRangeElements(GLenum mode, -- GLuint start, -- GLuint end, -- GLsizei count, -- GLenum type, -- int64_t offset); -- -- /* Multiple Render Targets */ -- void drawBuffers(const Vector& buffers); -- void clearBufferiv(GLenum buffer, -- GLint drawbuffer, -- base::span value, -- GLuint src_offset); -- void clearBufferuiv(GLenum buffer, -- GLint drawbuffer, -- base::span value, -- GLuint src_offset); -- void clearBufferfv(GLenum buffer, -- GLint drawbuffer, -- base::span value, -- GLuint src_offset); -- void clearBufferfi(GLenum buffer, -- GLint drawbuffer, -- GLfloat depth, -- GLint stencil); -- -- /* Query Objects */ -- WebGLQuery* createQuery(); -- void deleteQuery(WebGLQuery* query); -- bool isQuery(WebGLQuery* query); -- void beginQuery(GLenum target, WebGLQuery* query); -- void endQuery(GLenum target); -- ScriptValue getQuery(ScriptState* script_state, GLenum target, GLenum pname); -- ScriptValue getQueryParameter(ScriptState* script_state, -- WebGLQuery* query, -- GLenum pname); -- -- /* Sampler Objects */ -- WebGLSampler* createSampler(); -- void deleteSampler(WebGLSampler* sampler); -- bool isSampler(WebGLSampler* sampler); -- void bindSampler(GLuint unit, WebGLSampler* sampler); -- void samplerParameteri(WebGLSampler* sampler, GLenum pname, GLint param); -- void samplerParameterf(WebGLSampler* sampler, GLenum pname, GLfloat param); -- ScriptValue getSamplerParameter(ScriptState* script_state, -- WebGLSampler* sampler, -- GLenum pname); -- -- /* Sync objects */ -- WebGLSync* fenceSync(GLenum condition, GLbitfield flags); -- bool isSync(WebGLSync* sync); -- void deleteSync(WebGLSync* sync); -- GLenum clientWaitSync(WebGLSync* sync, GLbitfield flags, GLuint64 timeout); -- void waitSync(WebGLSync* sync, GLbitfield flags, GLint64 timeout); -- -- ScriptValue getSyncParameter(ScriptState* script_state, -- WebGLSync* sync, -- GLenum pname); -- -- /* Transform Feedback */ -- WebGLTransformFeedback* createTransformFeedback(); -- void deleteTransformFeedback(WebGLTransformFeedback* feedback); -- bool isTransformFeedback(WebGLTransformFeedback* feedback); -- void bindTransformFeedback(GLenum target, WebGLTransformFeedback* feedback); -- void beginTransformFeedback(GLenum primitive_mode); -- void endTransformFeedback(); -- void transformFeedbackVaryings(WebGLProgram* program, -- const Vector& varyings, -- GLenum buffer_mode); -- WebGLActiveInfo* getTransformFeedbackVarying(WebGLProgram* program, -- GLuint index); -- void pauseTransformFeedback(); -- void resumeTransformFeedback(); -- -- /* Uniform Buffer Objects and Transform Feedback Buffers */ -- void bindBufferBase(GLenum target, GLuint index, WebGLBuffer* buffer); -- void bindBufferRange(GLenum target, -- GLuint index, -- WebGLBuffer* buffer, -- int64_t offset, -- int64_t size); -- ScriptValue getIndexedParameter(ScriptState* script_state, -- GLenum target, -- GLuint index); -- std::optional> getUniformIndices( -- WebGLProgram* program, -- const Vector& uniform_names); -- ScriptValue getActiveUniforms(ScriptState* script_state, -- WebGLProgram* program, -- const Vector& uniform_indices, -- GLenum pname); -- GLuint getUniformBlockIndex(WebGLProgram* program, -- const String& uniform_block_name); -- ScriptValue getActiveUniformBlockParameter(ScriptState* script_state, -- WebGLProgram* program, -- GLuint uniform_block_index, -- GLenum pname); -- String getActiveUniformBlockName(WebGLProgram* program, -- GLuint uniform_block_index); -- void uniformBlockBinding(WebGLProgram* program, -- GLuint uniform_block_index, -- GLuint uniform_block_binding); -- -- /* Vertex Array Objects */ -- WebGLVertexArrayObject* createVertexArray(); -- void deleteVertexArray(WebGLVertexArrayObject* vertex_array); -- bool isVertexArray(WebGLVertexArrayObject* vertex_array); -- void bindVertexArray(WebGLVertexArrayObject* vertex_array); -- -- /* Reading */ -- void readPixels(GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- int64_t offset); -- void readPixels(GLint x, -- GLint y, -- GLsizei width, -- GLsizei height, -- GLenum format, -- GLenum type, -- MaybeShared pixels, -- int64_t offset); -- -- // ************************************************************************** -- // End of WebGL2RenderingContextBase's IDL methods -- // ************************************************************************** -- -- // ************************************************************************** -- // Start of CanvasRenderingContext implementation -- // ************************************************************************** -- SkAlphaType GetAlphaType() const override; -- viz::SharedImageFormat GetSharedImageFormat() const override; -- gfx::ColorSpace GetColorSpace() const override; -- bool isContextLost() const override; -- scoped_refptr 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; -- bool PaintRenderingResultsToCanvas(SourceDrawingBuffer) override; -- bool CopyRenderingResultsToVideoFrame( -- WebGraphicsContext3DVideoFramePool*, -- SourceDrawingBuffer, -- const gfx::ColorSpace&, -- VideoFrameCopyCompletedCallback) override; -- -- cc::Layer* CcLayer() const override; -- void Stop() override; -- void FinalizeFrame(FlushReason) override; -- bool PushFrame() override; -- -- // ************************************************************************** -- // End of CanvasRenderingContext implementation -- // ************************************************************************** -- -- void Trace(Visitor*) const override; -- -- private: --}; -- --} // namespace blink -- --#endif // THIRD_PARTY_BLINK_RENDERER_MODULES_WEBGL_WEBGL_RENDERING_CONTEXT_WEBGPU_BASE_H_ diff --git a/patches/chromium/support_mixed_sandbox_with_zygote.patch b/patches/chromium/support_mixed_sandbox_with_zygote.patch index 27d086b643d57..23ae723640789 100644 --- a/patches/chromium/support_mixed_sandbox_with_zygote.patch +++ b/patches/chromium/support_mixed_sandbox_with_zygote.patch @@ -22,10 +22,10 @@ However, the patch would need to be reviewed by the security team, as it does touch a security-sensitive class. diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc -index c97471d75ab2d11cfe71f34d8d11b27edb5c0fce..44a8635ba28722b30e34695c130f7b271978391a 100644 +index 524191a9a4973c55dc527841f3ea1238877919ac..48d3325f5f20e20b73d248e27bb5dd06cc30302d 100644 --- a/content/browser/renderer_host/render_process_host_impl.cc +++ b/content/browser/renderer_host/render_process_host_impl.cc -@@ -1833,6 +1833,10 @@ bool RenderProcessHostImpl::Init() { +@@ -1844,6 +1844,10 @@ bool RenderProcessHostImpl::Init() { std::unique_ptr sandbox_delegate = std::make_unique( *cmd_line, IsPdf(), IsJitDisabled()); diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index a388d87790125..c5101982d3ffd 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index bbbc07e36e6de11169f8317c64558b8c4d1699d5..0cf259360950a7063c4f9d6dc71b004706330f37 100644 +index 4bb69438947fff73a6905a1ecc1b711986a89124..e745a26a4e877ace994be80c2134147500205d0b 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4094,6 +4094,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -4103,6 +4103,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index bbbc07e36e6de11169f8317c64558b8c4d1699d5..0cf259360950a7063c4f9d6dc71b0047 std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -4104,6 +4111,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -4113,6 +4120,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } @@ -35,10 +35,10 @@ index bbbc07e36e6de11169f8317c64558b8c4d1699d5..0cf259360950a7063c4f9d6dc71b0047 CHECK(view_.get()); diff --git a/content/public/browser/web_contents.h b/content/public/browser/web_contents.h -index 37061d761f18ea143a8095393c42c4cf5c9eca0e..e70f25a52dbe66bf1a9bbbcb6bf56f072b23eb34 100644 +index ab2df2fac23584574ca75a30084b3a47c626a1a1..754d083e1c8500092e60f484e4e9d97679704431 100644 --- a/content/public/browser/web_contents.h +++ b/content/public/browser/web_contents.h -@@ -121,10 +121,13 @@ class BrowserPluginGuestDelegate; +@@ -121,11 +121,14 @@ class BrowserPluginGuestDelegate; class GuestPageHolder; class RenderFrameHost; class RenderViewHost; @@ -47,12 +47,13 @@ index 37061d761f18ea143a8095393c42c4cf5c9eca0e..e70f25a52dbe66bf1a9bbbcb6bf56f07 +class RenderWidgetHostViewBase; class ScreenOrientationDelegate; class SiteInstance; + class UnownedInnerWebContentsClient; class WebContentsDelegate; +class WebContentsView; class WebUI; struct DropData; struct MHTMLGenerationParams; -@@ -278,6 +281,10 @@ class WebContents : public PageNavigator, public base::SupportsUserData { +@@ -279,6 +282,10 @@ class WebContents : public PageNavigator, public base::SupportsUserData { network::mojom::WebSandboxFlags starting_sandbox_flags = network::mojom::WebSandboxFlags::kNone; diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index 6b2997ef95156..c0b5efc77afbd 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -15,10 +15,10 @@ Note that we also need to manually update embedder's `api::WebContents::IsFullscreenForTabOrPending` value. diff --git a/content/browser/renderer_host/render_frame_host_impl.cc b/content/browser/renderer_host/render_frame_host_impl.cc -index be73611db5328c76982ecca3caf5eccc30aac45e..0c4d801b3705fb609a40b8c58d2ee7f9b690461f 100644 +index d8698f9f37eefa50bf4e29a164b2cc302c32ecdf..3a8dc82b882aa00e9a5430bc8b7ba40985e17ff1 100644 --- a/content/browser/renderer_host/render_frame_host_impl.cc +++ b/content/browser/renderer_host/render_frame_host_impl.cc -@@ -8824,6 +8824,17 @@ void RenderFrameHostImpl::EnterFullscreen( +@@ -8831,6 +8831,17 @@ void RenderFrameHostImpl::EnterFullscreen( } } @@ -37,10 +37,10 @@ index be73611db5328c76982ecca3caf5eccc30aac45e..0c4d801b3705fb609a40b8c58d2ee7f9 if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 0cf259360950a7063c4f9d6dc71b004706330f37..97df851aa73d1bf8d8c8001646b63cbb43cd9a92 100644 +index e745a26a4e877ace994be80c2134147500205d0b..eefecd6b3b9c940c3ae3e9ef40075c4a109878ef 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4384,21 +4384,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4393,21 +4393,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index 0cf259360950a7063c4f9d6dc71b004706330f37..97df851aa73d1bf8d8c8001646b63cbb } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4557,7 +4561,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4566,7 +4570,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/patches/chromium/worker_context_will_destroy.patch b/patches/chromium/worker_context_will_destroy.patch index 1e7ac85738928..1a9be8a261b20 100644 --- a/patches/chromium/worker_context_will_destroy.patch +++ b/patches/chromium/worker_context_will_destroy.patch @@ -67,10 +67,10 @@ index 54e25fb12f680eb4bbe0d51f162e227610065345..3648f1be362dc4c13071e73fed478454 const WebSecurityOrigin& script_origin) { return false; diff --git a/third_party/blink/renderer/core/workers/worker_thread.cc b/third_party/blink/renderer/core/workers/worker_thread.cc -index e4d70bc0f577809cf6b9876044fe78192a098ec6..7d13d80a7f09e47d9f3c6da860e8d3373d5b8afd 100644 +index ce448895f52bcd17c093ff12b9eb4e1703882278..1c1858ce54f2c27666b3aed92fcb545a13e7bf2b 100644 --- a/third_party/blink/renderer/core/workers/worker_thread.cc +++ b/third_party/blink/renderer/core/workers/worker_thread.cc -@@ -748,6 +748,12 @@ void WorkerThread::PrepareForShutdownOnWorkerThread() { +@@ -821,6 +821,12 @@ void WorkerThread::PrepareForShutdownOnWorkerThread() { } pause_handle_.reset(); diff --git a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch index d291daafbaee7..1d579670210dc 100644 --- a/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch +++ b/patches/devtools_frontend/chore_expose_ui_to_allow_electron_to_set_dock_side.patch @@ -10,7 +10,7 @@ to handle this without patching, but this is fairly clean for now and no longer patching legacy devtools code. diff --git a/front_end/entrypoints/main/MainImpl.ts b/front_end/entrypoints/main/MainImpl.ts -index 2be25257dfc26d280733f6b55fa13da5e316ba3c..263bfe5be5becb18c73b0fc27ab1a41d455a5508 100644 +index e4ac33c985627cc80be3262c335535ecd42f1c67..8a4c8cbcfbf23ff5a56fdcf9e582efb6291d6ef5 100644 --- a/front_end/entrypoints/main/MainImpl.ts +++ b/front_end/entrypoints/main/MainImpl.ts @@ -721,6 +721,8 @@ export class MainImpl { diff --git a/patches/v8/.patches b/patches/v8/.patches index 21da17ba0f4b2..dc98544242e85 100644 --- a/patches/v8/.patches +++ b/patches/v8/.patches @@ -1,3 +1 @@ chore_allow_customizing_microtask_policy_per_context.patch -cherry-pick-7bc0a67ebfbf.patch -cherry-pick-45eb42cd398e.patch diff --git a/patches/v8/cherry-pick-45eb42cd398e.patch b/patches/v8/cherry-pick-45eb42cd398e.patch deleted file mode 100644 index c1fa3426717ee..0000000000000 --- a/patches/v8/cherry-pick-45eb42cd398e.patch +++ /dev/null @@ -1,32 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Igor Sheludko -Date: Tue, 27 May 2025 21:34:45 +0200 -Subject: Convert Smi to Word64 using zero extension - -... when a known type range contains only positive values. - -Bug: 420637585 -Change-Id: I8d9bb3f2fe2e5268e1659bb4ea7bbf97bfb52288 -Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/6594731 -Reviewed-by: Nico Hartmann -Commit-Queue: Igor Sheludko -Cr-Commit-Position: refs/heads/main@{#100538} - -diff --git a/src/compiler/representation-change.cc b/src/compiler/representation-change.cc -index a05b47e602e9707c17ba0ddcc9cfc071b95db168..116dcb6ce9a10e8fd3c681292ceaa2894db55052 100644 ---- a/src/compiler/representation-change.cc -+++ b/src/compiler/representation-change.cc -@@ -1394,7 +1394,12 @@ Node* RepresentationChanger::GetWord64RepresentationFor( - } - } else if (output_rep == MachineRepresentation::kTaggedSigned) { - if (output_type.Is(Type::SignedSmall())) { -- op = simplified()->ChangeTaggedSignedToInt64(); -+ if (output_type.IsRange() && output_type.AsRange()->Min() >= 0) { -+ node = InsertChangeTaggedSignedToInt32(node); -+ op = machine()->ChangeUint32ToUint64(); -+ } else { -+ op = simplified()->ChangeTaggedSignedToInt64(); -+ } - } else { - return TypeError(node, output_rep, output_type, - MachineRepresentation::kWord64); diff --git a/patches/v8/cherry-pick-7bc0a67ebfbf.patch b/patches/v8/cherry-pick-7bc0a67ebfbf.patch deleted file mode 100644 index ff5e0b4f29805..0000000000000 --- a/patches/v8/cherry-pick-7bc0a67ebfbf.patch +++ /dev/null @@ -1,53 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Leszek Swirski -Date: Tue, 27 May 2025 20:33:19 +0200 -Subject: Weaken alias analysis in store-store elimination - -Bug: 420636529 -Change-Id: I7c5a8f47960708cecbb27d811eedc7f754933deb -Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/6594051 -Reviewed-by: Shu-yu Guo -Auto-Submit: Leszek Swirski -Commit-Queue: Leszek Swirski -Cr-Commit-Position: refs/heads/main@{#100530} - -diff --git a/src/compiler/turboshaft/store-store-elimination-reducer-inl.h b/src/compiler/turboshaft/store-store-elimination-reducer-inl.h -index 45654a022fbaa67634d68d7d6e9dab7a5a50cb28..e058a41f23e29bbe4f5098608b340ccfef50bf98 100644 ---- a/src/compiler/turboshaft/store-store-elimination-reducer-inl.h -+++ b/src/compiler/turboshaft/store-store-elimination-reducer-inl.h -@@ -325,10 +325,11 @@ class RedundantStoreAnalysis { - // TODO(nicohartmann@): Use the new effect flags to distinguish heap - // access once available. - const bool is_on_heap_store = store.kind.tagged_base; -- const bool is_field_store = !store.index().valid(); -+ const bool is_fixed_offset_store = !store.index().valid(); - const uint8_t size = store.stored_rep.SizeInBytes(); -- // For now we consider only stores of fields of objects on the heap. -- if (is_on_heap_store && is_field_store) { -+ // For now we consider only stores of fixed offsets of objects on the -+ // heap. -+ if (is_on_heap_store && is_fixed_offset_store) { - bool is_eliminable_store = false; - switch (table_.GetObservability(store.base(), store.offset, size)) { - case StoreObservability::kUnobservable: -@@ -415,11 +416,16 @@ class RedundantStoreAnalysis { - // TODO(nicohartmann@): Use the new effect flags to distinguish heap - // access once available. - const bool is_on_heap_load = load.kind.tagged_base; -- const bool is_field_load = !load.index().valid(); -+ const bool is_fixed_offset_load = !load.index().valid(); - // For now we consider only loads of fields of objects on the heap. -- if (is_on_heap_load && is_field_load) { -- table_.MarkPotentiallyAliasingStoresAsObservable(load.base(), -- load.offset); -+ if (is_on_heap_load) { -+ if (is_fixed_offset_load) { -+ table_.MarkPotentiallyAliasingStoresAsObservable(load.base(), -+ load.offset); -+ } else { -+ // A dynamically indexed load might alias any fixed offset. -+ table_.MarkAllStoresAsObservable(); -+ } - } - break; - } diff --git a/patches/webrtc/fix_handle_pipewire_capturer_initialization_and_management.patch b/patches/webrtc/fix_handle_pipewire_capturer_initialization_and_management.patch index 88dcd771ca4e5..c1101aa795108 100644 --- a/patches/webrtc/fix_handle_pipewire_capturer_initialization_and_management.patch +++ b/patches/webrtc/fix_handle_pipewire_capturer_initialization_and_management.patch @@ -49,10 +49,10 @@ index 94605f409cd1523036f3e7d167a8d1f3c030e586..fae73654c84a7a8185ddf7255b49a86f options, CaptureType::kAnyScreenContent); } diff --git a/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc b/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc -index 722806340163be3371f29263e56bcc808b6846c6..6453101606e2088de640e70a730817803d0a1a09 100644 +index 76340ced4101d3c04a853dacd522365ae70bc5b4..309804a88c19b1e1d5c8592d8b0a5addc74ad844 100644 --- a/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc +++ b/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc -@@ -111,6 +111,7 @@ void BaseCapturerPipeWire::OnScreenCastRequestResult(RequestResponse result, +@@ -112,6 +112,7 @@ void BaseCapturerPipeWire::OnScreenCastRequestResult(RequestResponse result, void BaseCapturerPipeWire::OnScreenCastSessionClosed() { if (!capturer_failed_) { options_.screencast_stream()->StopScreenCastStream(); diff --git a/shell/browser/serial/serial_chooser_controller.cc b/shell/browser/serial/serial_chooser_controller.cc index 217f495fd02af..66a98fde224be 100644 --- a/shell/browser/serial/serial_chooser_controller.cc +++ b/shell/browser/serial/serial_chooser_controller.cc @@ -11,6 +11,7 @@ #include "base/containers/contains.h" #include "base/functional/bind.h" #include "base/strings/string_number_conversions.h" +#include "base/strings/stringprintf.h" #include "chrome/browser/serial/serial_blocklist.h" #include "content/public/browser/console_message.h" #include "content/public/browser/web_contents.h" diff --git a/shell/browser/ui/inspectable_web_contents.h b/shell/browser/ui/inspectable_web_contents.h index 87fe41aaad7fc..3a003747daa79 100644 --- a/shell/browser/ui/inspectable_web_contents.h +++ b/shell/browser/ui/inspectable_web_contents.h @@ -182,6 +182,7 @@ class InspectableWebContents 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 ShowSurvey(DispatchCallback callback, const std::string& trigger) override {} void CanShowSurvey(DispatchCallback callback, From b494ae62badd5b96e86dd276fd355dc7778fc241 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 10 Jun 2025 10:28:46 +0200 Subject: [PATCH 097/186] feat: [net] add "priority" option to net.request (#47321) document the default value of priority option Update the priority test to not use the httpbin.org as server Fixed the lint errors Fixed the build error Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Zeeker <13848632+zeeker999@users.noreply.github.com> --- docs/api/client-request.md | 4 ++ lib/common/api/net-client-request.ts | 6 +- shell/common/api/electron_api_url_loader.cc | 18 +++++ spec/api-net-spec.ts | 75 ++++++++++++++++++++- typings/internal-ambient.d.ts | 2 + 5 files changed, 103 insertions(+), 2 deletions(-) diff --git a/docs/api/client-request.md b/docs/api/client-request.md index 21490bf1f1018..d6e27d6deb951 100644 --- a/docs/api/client-request.md +++ b/docs/api/client-request.md @@ -60,6 +60,10 @@ following properties: `strict-origin-when-cross-origin`. * `cache` string (optional) - can be `default`, `no-store`, `reload`, `no-cache`, `force-cache` or `only-if-cached`. + * `priority` string (optional) - can be `throttled`, `idle`, `lowest`, + `low`, `medium`, or `highest`. Defaults to `idle`. + * `priorityIncremental` boolean (optional) - the incremental loading flag as part + of HTTP extensible priorities (RFC 9218). Default is `true`. `options` properties such as `protocol`, `host`, `hostname`, `port` and `path` strictly follow the Node.js model as described in the diff --git a/lib/common/api/net-client-request.ts b/lib/common/api/net-client-request.ts index 1a087ae476477..a2682da670d22 100644 --- a/lib/common/api/net-client-request.ts +++ b/lib/common/api/net-client-request.ts @@ -288,8 +288,12 @@ function parseOptions (optionsIn: ClientRequestConstructorOptions | string): Nod origin: options.origin, referrerPolicy: options.referrerPolicy, cache: options.cache, - allowNonHttpProtocols: Object.hasOwn(options, kAllowNonHttpProtocols) + allowNonHttpProtocols: Object.hasOwn(options, kAllowNonHttpProtocols), + priority: options.priority }; + if ('priorityIncremental' in options) { + urlLoaderOptions.priorityIncremental = options.priorityIncremental; + } const headers: Record = options.headers || {}; for (const [name, value] of Object.entries(headers)) { validateHeader(name, value); diff --git a/shell/common/api/electron_api_url_loader.cc b/shell/common/api/electron_api_url_loader.cc index dcf539060c18b..9ab2b2379bac7 100644 --- a/shell/common/api/electron_api_url_loader.cc +++ b/shell/common/api/electron_api_url_loader.cc @@ -638,6 +638,24 @@ gin::Handle SimpleURLLoaderWrapper::Create( break; } + if (std::string priority; opts.Get("priority", &priority)) { + static constexpr auto Lookup = + base::MakeFixedFlatMap({ + {"throttled", net::THROTTLED}, + {"idle", net::IDLE}, + {"lowest", net::LOWEST}, + {"low", net::LOW}, + {"medium", net::MEDIUM}, + {"highest", net::HIGHEST}, + }); + if (auto iter = Lookup.find(priority); iter != Lookup.end()) + request->priority = iter->second; + } + if (bool priorityIncremental = request->priority_incremental; + opts.Get("priorityIncremental", &priorityIncremental)) { + request->priority_incremental = priorityIncremental; + } + const bool use_session_cookies = opts.ValueOrDefault("useSessionCookies", false); int options = network::mojom::kURLLoadOptionSniffMimeType; diff --git a/spec/api-net-spec.ts b/spec/api-net-spec.ts index 5d98385d60f4a..dbbab83c8947d 100644 --- a/spec/api-net-spec.ts +++ b/spec/api-net-spec.ts @@ -1,15 +1,19 @@ -import { net, ClientRequest, ClientRequestConstructorOptions, utilityProcess } from 'electron/main'; +import { net, session, ClientRequest, ClientRequestConstructorOptions, utilityProcess } from 'electron/main'; import { expect } from 'chai'; import { once } from 'node:events'; +import * as fs from 'node:fs'; import * as http from 'node:http'; +import * as http2 from 'node:http2'; import * as path from 'node:path'; import { setTimeout } from 'node:timers/promises'; import { collectStreamBody, collectStreamBodyBuffer, getResponse, kOneKiloByte, kOneMegaByte, randomBuffer, randomString, respondNTimes, respondOnce } from './lib/net-helpers'; +import { listen, defer } from './lib/spec-helpers'; const utilityFixturePath = path.resolve(__dirname, 'fixtures', 'api', 'utility-process', 'api-net-spec.js'); +const fixturesPath = path.resolve(__dirname, 'fixtures'); async function itUtility (name: string, fn?: Function, args?: {[key:string]: any}) { it(`${name} in utility process`, async () => { @@ -46,6 +50,34 @@ describe('net module', () => { } }); + let http2URL: string; + + const certPath = path.join(fixturesPath, 'certificates'); + const h2server = http2.createSecureServer({ + key: fs.readFileSync(path.join(certPath, 'server.key')), + cert: fs.readFileSync(path.join(certPath, 'server.pem')) + }, async (req, res) => { + if (req.method === 'POST') { + const chunks = []; + for await (const chunk of req) chunks.push(chunk); + res.end(Buffer.concat(chunks).toString('utf8')); + } else if (req.method === 'GET' && req.headers[':path'] === '/get') { + res.end(JSON.stringify({ + headers: req.headers + })); + } else { + res.end(''); + } + }); + + before(async () => { + http2URL = (await listen(h2server)).url + '/'; + }); + + after(() => { + h2server.close(); + }); + for (const test of [itIgnoringArgs, itUtility]) { describe('HTTP basics', () => { test('should be able to issue a basic GET request', async () => { @@ -1615,4 +1647,45 @@ describe('net module', () => { }); }); } + + for (const test of [itIgnoringArgs]) { + describe('ClientRequest API', () => { + for (const [priorityName, urgency] of Object.entries({ + throttled: 'u=5', + idle: 'u=4', + lowest: '', + low: 'u=2', + medium: 'u=1', + highest: 'u=0' + })) { + for (const priorityIncremental of [true, false]) { + test(`should set priority to ${priorityName}/${priorityIncremental} if requested`, async () => { + // Priority header is available on HTTP/2, which is only + // supported over TLS, so... + session.defaultSession.setCertificateVerifyProc((req, cb) => cb(0)); + defer(() => { + session.defaultSession.setCertificateVerifyProc(null); + }); + + const urlRequest = net.request({ + url: `${http2URL}get`, + priority: priorityName as any, + priorityIncremental + }); + const response = await getResponse(urlRequest); + const data = JSON.parse(await collectStreamBody(response)); + let expectedPriority = urgency; + if (priorityIncremental) { + expectedPriority = expectedPriority ? expectedPriority + ', i' : 'i'; + } + if (expectedPriority === '') { + expect(data.headers.priority).to.be.undefined(); + } else { + expect(data.headers.priority).to.be.a('string').and.equal(expectedPriority); + } + }, { priorityName, urgency, priorityIncremental }); + } + } + }); + } }); diff --git a/typings/internal-ambient.d.ts b/typings/internal-ambient.d.ts index 21e652df5e453..2f0e6b87f0e4d 100644 --- a/typings/internal-ambient.d.ts +++ b/typings/internal-ambient.d.ts @@ -177,6 +177,8 @@ declare namespace NodeJS { mode?: string; destination?: string; bypassCustomProtocolHandlers?: boolean; + priority?: 'throttled' | 'idle' | 'lowest' | 'low' | 'medium' | 'highest'; + priorityIncremental?: boolean; }; type ResponseHead = { statusCode: number; From e90404be7d09938fe8b8a090e299a6a730eae80d Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 10 Jun 2025 13:12:24 +0200 Subject: [PATCH 098/186] docs: no class inheritance (#47433) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Erick Zhao --- docs/api/base-window.md | 4 ++++ docs/api/browser-view.md | 4 ++++ docs/api/browser-window.md | 4 ++++ docs/api/image-view.md | 4 ++++ docs/api/ipc-main-service-worker.md | 4 ++++ docs/api/menu-item.md | 4 ++++ docs/api/menu.md | 4 ++++ docs/api/message-channel-main.md | 4 ++++ docs/api/notification.md | 13 +++++++------ docs/api/share-menu.md | 4 ++++ docs/api/touch-bar.md | 4 ++++ docs/api/tray.md | 4 ++++ docs/api/view.md | 4 ++++ docs/api/web-contents-view.md | 4 ++++ docs/faq.md | 8 ++++++++ 15 files changed, 67 insertions(+), 6 deletions(-) diff --git a/docs/api/base-window.md b/docs/api/base-window.md index 98909de846e22..29461967d942f 100644 --- a/docs/api/base-window.md +++ b/docs/api/base-window.md @@ -99,6 +99,10 @@ Process: [Main](../glossary.md#main-process) It creates a new `BaseWindow` with native properties as set by the `options`. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new BaseWindow([options])` * `options` [BaseWindowConstructorOptions](structures/base-window-options.md?inline) (optional) diff --git a/docs/api/browser-view.md b/docs/api/browser-view.md index 693363ec4b2eb..87f6ead865960 100644 --- a/docs/api/browser-view.md +++ b/docs/api/browser-view.md @@ -38,6 +38,10 @@ Process: [Main](../glossary.md#main-process) This module cannot be used until the `ready` event of the `app` module is emitted. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### Example ```js diff --git a/docs/api/browser-window.md b/docs/api/browser-window.md index 78997aabd44fe..83bea39c5c1cd 100644 --- a/docs/api/browser-window.md +++ b/docs/api/browser-window.md @@ -150,6 +150,10 @@ Process: [Main](../glossary.md#main-process) It creates a new `BrowserWindow` with native properties as set by the `options`. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new BrowserWindow([options])` * `options` [BrowserWindowConstructorOptions](structures/browser-window-options.md?inline) (optional) diff --git a/docs/api/image-view.md b/docs/api/image-view.md index 854de3054601a..fcc7135ecfa7a 100644 --- a/docs/api/image-view.md +++ b/docs/api/image-view.md @@ -42,6 +42,10 @@ Process: [Main](../glossary.md#main-process) `ImageView` is an [EventEmitter][event-emitter]. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new ImageView()` _Experimental_ Creates an ImageView. diff --git a/docs/api/ipc-main-service-worker.md b/docs/api/ipc-main-service-worker.md index 8995d66ba7a7c..08a9d63a98174 100644 --- a/docs/api/ipc-main-service-worker.md +++ b/docs/api/ipc-main-service-worker.md @@ -11,6 +11,10 @@ Process: [Main](../glossary.md#main-process) +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### Instance Methods #### `ipcMainServiceWorker.on(channel, listener)` diff --git a/docs/api/menu-item.md b/docs/api/menu-item.md index 3c53afc222bc6..8ee760d1cb44a 100644 --- a/docs/api/menu-item.md +++ b/docs/api/menu-item.md @@ -6,6 +6,10 @@ Process: [Main](../glossary.md#main-process) See [`Menu`](menu.md) for examples. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new MenuItem(options)` * `options` Object diff --git a/docs/api/menu.md b/docs/api/menu.md index c94d8fe70d794..9ba6ce00242c0 100644 --- a/docs/api/menu.md +++ b/docs/api/menu.md @@ -6,6 +6,10 @@ Process: [Main](../glossary.md#main-process) +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new Menu()` Creates a new menu. diff --git a/docs/api/message-channel-main.md b/docs/api/message-channel-main.md index 18339848db6ac..3dff6a6269629 100644 --- a/docs/api/message-channel-main.md +++ b/docs/api/message-channel-main.md @@ -33,6 +33,10 @@ ipcRenderer.on('port', (e) => { }) ``` +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### Instance Properties #### `channel.port1` diff --git a/docs/api/notification.md b/docs/api/notification.md index efaa93b39e217..1c5a6e9c98162 100644 --- a/docs/api/notification.md +++ b/docs/api/notification.md @@ -4,12 +4,9 @@ Process: [Main](../glossary.md#main-process) -:::info Renderer process notifications - -If you want to show notifications from a renderer process you should use the -[web Notifications API](../tutorial/notifications.md) - -::: +> [!NOTE] +> If you want to show notifications from a renderer process you should use the +> [web Notifications API](../tutorial/notifications.md) ## Class: Notification @@ -21,6 +18,10 @@ Process: [Main](../glossary.md#main-process) It creates a new `Notification` with native properties as set by the `options`. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### Static Methods The `Notification` class has the following static methods: diff --git a/docs/api/share-menu.md b/docs/api/share-menu.md index a886ea52682af..c1ffd455743b0 100644 --- a/docs/api/share-menu.md +++ b/docs/api/share-menu.md @@ -13,6 +13,10 @@ For including the share menu as a submenu of other menus, please use the Process: [Main](../glossary.md#main-process) +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new ShareMenu(sharingItem)` * `sharingItem` SharingItem - The item to share. diff --git a/docs/api/touch-bar.md b/docs/api/touch-bar.md index c304f57430832..35f3105416ba3 100644 --- a/docs/api/touch-bar.md +++ b/docs/api/touch-bar.md @@ -1,5 +1,9 @@ # TouchBar +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ## Class: TouchBar > Create TouchBar layouts for native macOS applications diff --git a/docs/api/tray.md b/docs/api/tray.md index 6b112def35918..2ffc4dc671847 100644 --- a/docs/api/tray.md +++ b/docs/api/tray.md @@ -25,6 +25,10 @@ app.whenReady().then(() => { }) ``` +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + **Platform Considerations** **Linux** diff --git a/docs/api/view.md b/docs/api/view.md index 8e0a23a5d8def..5858d08c0abb8 100644 --- a/docs/api/view.md +++ b/docs/api/view.md @@ -25,6 +25,10 @@ Process: [Main](../glossary.md#main-process) `View` is an [EventEmitter][event-emitter]. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new View()` Creates a new `View`. diff --git a/docs/api/web-contents-view.md b/docs/api/web-contents-view.md index 66bb257cf0edb..802580e26b9bd 100644 --- a/docs/api/web-contents-view.md +++ b/docs/api/web-contents-view.md @@ -32,6 +32,10 @@ Process: [Main](../glossary.md#main-process) `WebContentsView` is an [EventEmitter][event-emitter]. +> [!WARNING] +> Electron's built-in classes cannot be subclassed in user code. +> For more information, see [the FAQ](../faq.md#class-inheritance-does-not-work-with-electron-built-in-modules). + ### `new WebContentsView([options])` * `options` Object (optional) diff --git a/docs/faq.md b/docs/faq.md index 114731d69d689..9b5e656d81659 100644 --- a/docs/faq.md +++ b/docs/faq.md @@ -152,6 +152,14 @@ The effect is visible only on (some?) LCD screens. Even if you don't see a diffe Notice that just setting the background in the CSS does not have the desired effect. +## Class inheritance does not work with Electron built-in modules + +Electron classes cannot be subclassed with the [`extends`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes/extends) +keyword (also known as class inheritance). This feature was never implemented in Electron due +to the added complexity it would add to C++/JavaScript interop in Electron's internals. + +For more information, see [electron/electron#23](https://github.com/electron/electron/issues/23). + [memory-management]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Memory_Management [closures]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Closures [storage]: https://developer.mozilla.org/en-US/docs/Web/API/Storage From d2c95a28bbbaddb2e31dad1a0690f85f7895db32 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 10 Jun 2025 18:02:14 +0200 Subject: [PATCH 099/186] fix: add back fallback wasm-trap handling (#47345) * fix: add back fallback wasm-trap handling Refs https://chromium-review.googlesource.com/c/chromium/src/+/5372409 This change sets up wasm-trap handling for the case where content_shell has not enabled crash reporting but moves the responsibility to ElectronRendererClient. The default ContentRendererClient assumes that crash reporting is enabled (crashpad enabled by default) and does not set up its own handler. Co-authored-by: Shelley Vohr * chore: fix build Co-authored-by: deepak1556 --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr Co-authored-by: deepak1556 --- patches/chromium/.patches | 1 - ...le_freezing_flags_after_init_in_node.patch | 30 ---------- shell/renderer/electron_renderer_client.cc | 58 +++++++++++++++++++ shell/renderer/electron_renderer_client.h | 3 + 4 files changed, 61 insertions(+), 31 deletions(-) delete mode 100644 patches/chromium/disable_freezing_flags_after_init_in_node.patch diff --git a/patches/chromium/.patches b/patches/chromium/.patches index e49e542bf3caa..471d0813543ac 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -79,7 +79,6 @@ introduce_ozoneplatform_electron_can_call_x11_property.patch make_gtk_getlibgtk_public.patch custom_protocols_plzserviceworker.patch feat_filter_out_non-shareable_windows_in_the_current_application_in.patch -disable_freezing_flags_after_init_in_node.patch short-circuit_permissions_checks_in_mediastreamdevicescontroller.patch chore_add_electron_deps_to_gitignores.patch chore_modify_chromium_handling_of_mouse_events.patch diff --git a/patches/chromium/disable_freezing_flags_after_init_in_node.patch b/patches/chromium/disable_freezing_flags_after_init_in_node.patch deleted file mode 100644 index 39e2e7efaf509..0000000000000 --- a/patches/chromium/disable_freezing_flags_after_init_in_node.patch +++ /dev/null @@ -1,30 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Jeremy Rose -Date: Mon, 20 Jun 2022 14:53:37 -0700 -Subject: disable freezing flags after init in node - -This was introduced in -https://chromium-review.googlesource.com/c/chromium/src/+/3687671. - -When running node in the renderer, flags are updated after initialization, so -freezing the flags in Blink causes node initialization to fail. - -If possible, it would be ideal to do this without a patch. -https://bugs.chromium.org/p/v8/issues/detail?id=12887 suggests that there may -at some point be an API to "unfreeze" the flags, or we may be able to refactor -node initialization to not update flags after V8 initialization. - -diff --git a/content/renderer/render_process_impl.cc b/content/renderer/render_process_impl.cc -index 7a20f5199bd6cb5d13f31ec5db3e3cc03821bc3a..22167f808cb7b27d5b2a8e517cdeee63205ab9ad 100644 ---- a/content/renderer/render_process_impl.cc -+++ b/content/renderer/render_process_impl.cc -@@ -212,6 +212,9 @@ RenderProcessImpl::RenderProcessImpl() - v8::V8::SetFlagsFromString(kSABPerContextFlag, sizeof(kSABPerContextFlag)); - } - -+ // Freezing flags after init conflicts with node in the renderer. -+ v8::V8::SetFlagsFromString("--no-freeze-flags-after-init"); -+ - if (base::FeatureList::IsEnabled(features::kWebAssemblyTrapHandler)) { - content::GetContentClient()->renderer()->SetUpWebAssemblyTrapHandler(); - } diff --git a/shell/renderer/electron_renderer_client.cc b/shell/renderer/electron_renderer_client.cc index 5757c2c76cad5..4316faca17cc6 100644 --- a/shell/renderer/electron_renderer_client.cc +++ b/shell/renderer/electron_renderer_client.cc @@ -6,6 +6,7 @@ #include +#include "base/base_switches.h" #include "base/command_line.h" #include "base/containers/contains.h" #include "base/debug/stack_trace.h" @@ -26,6 +27,13 @@ #include "third_party/blink/renderer/core/execution_context/execution_context.h" // nogncheck #include "third_party/blink/renderer/core/frame/web_local_frame_impl.h" // nogncheck +#if BUILDFLAG(IS_LINUX) && (defined(ARCH_CPU_X86_64) || defined(ARCH_CPU_ARM64)) +#define ENABLE_WEB_ASSEMBLY_TRAP_HANDLER_LINUX +#include "components/crash/core/app/crashpad.h" +#include "content/public/common/content_switches.h" +#include "v8/include/v8-wasm-trap-handler-posix.h" +#endif + namespace electron { ElectronRendererClient::ElectronRendererClient() @@ -36,6 +44,14 @@ ElectronRendererClient::ElectronRendererClient() ElectronRendererClient::~ElectronRendererClient() = default; +void ElectronRendererClient::PostIOThreadCreated( + base::SingleThreadTaskRunner* io_thread_task_runner) { + // Freezing flags after init conflicts with node in the renderer. + // We do this here in order to avoid having to patch the ctor in + // content/renderer/render_process_impl.cc. + v8::V8::SetFlagsFromString("--no-freeze-flags-after-init"); +} + void ElectronRendererClient::RenderFrameCreated( content::RenderFrame* render_frame) { new ElectronRenderFrameObserver(render_frame, this); @@ -230,6 +246,48 @@ void ElectronRendererClient::WillDestroyWorkerContextOnWorkerThread( } } +void ElectronRendererClient::SetUpWebAssemblyTrapHandler() { +// See CL:5372409 - copied from ShellContentRendererClient. +#if BUILDFLAG(IS_WIN) || BUILDFLAG(IS_MAC) + // Mac and Windows use the default implementation (where the default v8 trap + // handler gets set up). + ContentRendererClient::SetUpWebAssemblyTrapHandler(); + return; +#elif defined(ENABLE_WEB_ASSEMBLY_TRAP_HANDLER_LINUX) + const bool crash_reporter_enabled = + crash_reporter::GetHandlerSocket(nullptr, nullptr); + + if (crash_reporter_enabled) { + // If either --enable-crash-reporter or --enable-crash-reporter-for-testing + // is enabled it should take care of signal handling for us, use the default + // implementation which doesn't register an additional handler. + ContentRendererClient::SetUpWebAssemblyTrapHandler(); + return; + } + + const bool use_v8_default_handler = + base::CommandLine::ForCurrentProcess()->HasSwitch( + ::switches::kDisableInProcessStackTraces); + + if (use_v8_default_handler) { + // There is no signal handler yet, but it's okay if v8 registers one. + v8::V8::EnableWebAssemblyTrapHandler(/*use_v8_signal_handler=*/true); + return; + } + + if (base::debug::SetStackDumpFirstChanceCallback( + v8::TryHandleWebAssemblyTrapPosix)) { + // Crashpad and Breakpad are disabled, but the in-process stack dump + // handlers are enabled, so set the callback on the stack dump handlers. + v8::V8::EnableWebAssemblyTrapHandler(/*use_v8_signal_handler=*/false); + return; + } + + // As the registration of the callback failed, we don't enable trap + // handlers. +#endif // defined(ENABLE_WEB_ASSEMBLY_TRAP_HANDLER_LINUX) +} + node::Environment* ElectronRendererClient::GetEnvironment( content::RenderFrame* render_frame) const { if (!injected_frames_.contains(render_frame)) diff --git a/shell/renderer/electron_renderer_client.h b/shell/renderer/electron_renderer_client.h index 5471f872eb394..1cabd0a546a12 100644 --- a/shell/renderer/electron_renderer_client.h +++ b/shell/renderer/electron_renderer_client.h @@ -38,6 +38,8 @@ class ElectronRendererClient : public RendererClientBase { void UndeferLoad(content::RenderFrame* render_frame); // content::ContentRendererClient: + void PostIOThreadCreated( + base::SingleThreadTaskRunner* io_thread_task_runner) override; void RenderFrameCreated(content::RenderFrame*) override; void RunScriptsAtDocumentStart(content::RenderFrame* render_frame) override; void RunScriptsAtDocumentEnd(content::RenderFrame* render_frame) override; @@ -45,6 +47,7 @@ class ElectronRendererClient : public RendererClientBase { v8::Local context) override; void WillDestroyWorkerContextOnWorkerThread( v8::Local context) override; + void SetUpWebAssemblyTrapHandler() override; node::Environment* GetEnvironment(content::RenderFrame* frame) const; From 32599dda4451cfda40621654105e0b4e2be1988e Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 10 Jun 2025 18:37:12 -0500 Subject: [PATCH 100/186] docs: mention `kwallet6` command line option (#47437) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Niklas Wenzel --- docs/api/safe-storage.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/docs/api/safe-storage.md b/docs/api/safe-storage.md index d9c7dc3feab47..4f985db5e1951 100644 --- a/docs/api/safe-storage.md +++ b/docs/api/safe-storage.md @@ -73,5 +73,6 @@ command line flag is provided `--password-store="basic"`. is provided `--password-store="kwallet"`. * `kwallet5` - When the desktop session is `kde5` or if the following command line flag is provided `--password-store="kwallet5"`. -* `kwallet6` - When the desktop session is `kde6`. +* `kwallet6` - When the desktop session is `kde6` or if the following command line flag +is provided `--password-store="kwallet6"`. * `unknown` - When the function is called before app has emitted the `ready` event. From 2f4472f0582be9bc53f2f7bad07c6efabff071b8 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 11 Jun 2025 12:25:18 -0500 Subject: [PATCH 101/186] fix: crash calling `Fetch.continueResponse` with `WebContentsView` (#47444) fix: crash calling Fetch.continueResponse with WebContentsView Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/api/electron_api_debugger.cc | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/shell/browser/api/electron_api_debugger.cc b/shell/browser/api/electron_api_debugger.cc index 61440400e7528..740e87dd2cb26 100644 --- a/shell/browser/api/electron_api_debugger.cc +++ b/shell/browser/api/electron_api_debugger.cc @@ -81,7 +81,11 @@ void Debugger::DispatchProtocolMessage(DevToolsAgentHost* agent_host, void Debugger::RenderFrameHostChanged(content::RenderFrameHost* old_rfh, content::RenderFrameHost* new_rfh) { - if (agent_host_) { + // ConnectWebContents uses the primary main frame of the webContents, + // so if the new_rfh is not the primary main frame, we don't want to + // reconnect otherwise we'll end up trying to reconnect to a RenderFrameHost + // that already has a DevToolsAgentHost associated with it. + if (agent_host_ && new_rfh->IsInPrimaryMainFrame()) { agent_host_->DisconnectWebContents(); auto* web_contents = content::WebContents::FromRenderFrameHost(new_rfh); agent_host_->ConnectWebContents(web_contents); From ba6f0358b0d176b4a711e8d33b30f6658c991de1 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 12 Jun 2025 12:25:24 +0200 Subject: [PATCH 102/186] docs: update remaining references to `electron-quick-start` (#47448) * chore: udpate remaining references to electron-quick-start Co-authored-by: Anny Yang * chore: Update docs/tutorial/tutorial-1-prerequisites.md Co-authored-by: Niklas Wenzel Co-authored-by: Anny Yang * chore: Update docs/tutorial/tutorial-3-preload.md Co-authored-by: Niklas Wenzel Co-authored-by: Anny Yang * chore: Update docs/tutorial/tutorial-2-first-app.md Co-authored-by: Niklas Wenzel Co-authored-by: Anny Yang * chore: linebreak Co-authored-by: Anny Yang * chore: swap minimal-repro for npx create-electron-app Co-authored-by: Anny Yang * chore: add back code commands Co-authored-by: Anny Yang * chore: add whitespace Co-authored-by: Anny Yang * chore: remove reference to repo containing old quick start Co-authored-by: Anny Yang --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Anny Yang Co-authored-by: Anny Yang --- docs/tutorial/debugging-vscode.md | 43 +++++++++++++++-------- docs/tutorial/snapcraft.md | 33 +++++++++-------- docs/tutorial/tutorial-1-prerequisites.md | 2 +- docs/tutorial/tutorial-2-first-app.md | 2 +- docs/tutorial/tutorial-3-preload.md | 2 +- 5 files changed, 50 insertions(+), 32 deletions(-) diff --git a/docs/tutorial/debugging-vscode.md b/docs/tutorial/debugging-vscode.md index fa5ccd8f76879..9f8d29d25c22c 100644 --- a/docs/tutorial/debugging-vscode.md +++ b/docs/tutorial/debugging-vscode.md @@ -1,6 +1,7 @@ # Debugging in VSCode -This guide goes over how to set up VSCode debugging for both your own Electron project as well as the native Electron codebase. +This guide goes over how to set up VSCode debugging for both your own Electron +project as well as the native Electron codebase. ## Debugging your Electron app @@ -9,8 +10,8 @@ This guide goes over how to set up VSCode debugging for both your own Electron p #### 1. Open an Electron project in VSCode. ```sh -$ git clone git@github.com:electron/electron-quick-start.git -$ code electron-quick-start +$ npx create-electron-app@latest my-app +$ code my-app ``` #### 2. Add a file `.vscode/launch.json` with the following configuration: @@ -37,23 +38,27 @@ $ code electron-quick-start #### 3. Debugging -Set some breakpoints in `main.js`, and start debugging in the [Debug View](https://code.visualstudio.com/docs/editor/debugging). You should be able to hit the breakpoints. - -Here is a pre-configured project that you can download and directly debug in VSCode: https://github.com/octref/vscode-electron-debug/tree/master/electron-quick-start +Set some breakpoints in `main.js`, and start debugging in the +[Debug View](https://code.visualstudio.com/docs/editor/debugging). You should +be able to hit the breakpoints. ## Debugging the Electron codebase -If you want to build Electron from source and modify the native Electron codebase, this section will help you in testing your modifications. +If you want to build Electron from source and modify the native Electron codebase, +this section will help you in testing your modifications. -For those unsure where to acquire this code or how to build it, [Electron's Build Tools](https://github.com/electron/build-tools) automates and explains most of this process. If you wish to manually set up the environment, you can instead use these [build instructions](../development/build-instructions-gn.md). +For those unsure where to acquire this code or how to build it, +[Electron's Build Tools](https://github.com/electron/build-tools) automates and +explains most of this process. If you wish to manually set up the environment, +you can instead use these [build instructions](../development/build-instructions-gn.md). ### Windows (C++) #### 1. Open an Electron project in VSCode. ```sh -$ git clone git@github.com:electron/electron-quick-start.git -$ code electron-quick-start +$ npx create-electron-app@latest my-app +$ code my-app ``` #### 2. Add a file `.vscode/launch.json` with the following configuration: @@ -86,14 +91,22 @@ $ code electron-quick-start **Configuration Notes** -* `cppvsdbg` requires the [built-in C/C++ extension](https://marketplace.visualstudio.com/items?itemName=ms-vscode.cpptools) be enabled. +* `cppvsdbg` requires the +[built-in C/C++ extension](https://marketplace.visualstudio.com/items?itemName=ms-vscode.cpptools) +be enabled. * `${workspaceFolder}` is the full path to Chromium's `src` directory. * `your-executable-location` will be one of the following depending on a few items: - * `Testing`: If you are using the default settings of [Electron's Build-Tools](https://github.com/electron/build-tools) or the default instructions when [building from source](../development/build-instructions-gn.md#building). + * `Testing`: If you are using the default settings of + [Electron's Build-Tools](https://github.com/electron/build-tools) or the default + instructions when [building from source](../development/build-instructions-gn.md#building). * `Release`: If you built a Release build rather than a Testing build. - * `your-directory-name`: If you modified this during your build process from the default, this will be whatever you specified. -* The `args` array string `"your-electron-project-path"` should be the absolute path to either the directory or `main.js` file of the Electron project you are using for testing. In this example, it should be your path to `electron-quick-start`. + * `your-directory-name`: If you modified this during your build process from + the default, this will be whatever you specified. +* The `args` array string `"your-electron-project-path"` should be the absolute +path to either the directory or `main.js` file of the Electron project you are +using for testing. In this example, it should be your path to `my-app`. #### 3. Debugging -Set some breakpoints in the .cc files of your choosing in the native Electron C++ code, and start debugging in the [Debug View](https://code.visualstudio.com/docs/editor/debugging). +Set some breakpoints in the .cc files of your choosing in the native Electron C++ +code, and start debugging in the [Debug View](https://code.visualstudio.com/docs/editor/debugging). diff --git a/docs/tutorial/snapcraft.md b/docs/tutorial/snapcraft.md index dd4e84495077f..9e6094c28ca9b 100644 --- a/docs/tutorial/snapcraft.md +++ b/docs/tutorial/snapcraft.md @@ -5,8 +5,8 @@ for any Snapcraft environment, including the Ubuntu Software Center. ## Background and Requirements -Together with the broader Linux community, Canonical aims to fix many of the -common software installation problems with the [`snapcraft`](https://snapcraft.io/) +Together with the broader Linux community, Canonical aims to address common +software installation issues through the [`snapcraft`](https://snapcraft.io/) project. Snaps are containerized software packages that include required dependencies, auto-update, and work on all major Linux distributions without system modification. @@ -83,7 +83,14 @@ snap(options) ### Step 1: Create Sample Snapcraft Project -Create your project directory and add the following to `snap/snapcraft.yaml`: +```sh +$ npx create-electron-app@latest my-app +``` + +### Step 2: Create Sample Snapcraft Project + +Create a `snap` directory in your project root and add the following to +`snap/snapcraft.yaml`: ```yaml name: electron-packager-hello-world @@ -97,7 +104,7 @@ grade: stable apps: electron-packager-hello-world: - command: electron-quick-start/electron-quick-start --no-sandbox + command: my-app/my-app --no-sandbox extensions: [gnome] plugs: - browser-support @@ -109,13 +116,13 @@ apps: TMPDIR: $XDG_RUNTIME_DIR parts: - electron-quick-start: + my-app: plugin: nil - source: https://github.com/electron/electron-quick-start.git + source: . override-build: | npm install electron @electron/packager npx electron-packager . --overwrite --platform=linux --output=release-build --prune=true - cp -rv ./electron-quick-start-linux-* $SNAPCRAFT_PART_INSTALL/electron-quick-start + cp -rv ./my-app-linux-* $SNAPCRAFT_PART_INSTALL/my-app build-snaps: - node/14/stable build-packages: @@ -125,12 +132,10 @@ parts: - libnspr4 ``` -If you want to apply this example to an existing project: - -- Replace `source: https://github.com/electron/electron-quick-start.git` with `source: .`. -- Replace all instances of `electron-quick-start` with your project's name. +If you want to apply this example to an existing project, replace all instances +of `my-app` with your project's name. -### Step 2: Build the snap +### Step 3: Build the snap ```sh $ snapcraft @@ -139,13 +144,13 @@ $ snapcraft Snapped electron-packager-hello-world_0.1_amd64.snap ``` -### Step 3: Install the snap +### Step 4: Install the snap ```sh sudo snap install electron-packager-hello-world_0.1_amd64.snap --dangerous ``` -### Step 4: Run the snap +### Step 5: Run the snap ```sh electron-packager-hello-world diff --git a/docs/tutorial/tutorial-1-prerequisites.md b/docs/tutorial/tutorial-1-prerequisites.md index c0990dfbe2c05..e47938bdf81e4 100644 --- a/docs/tutorial/tutorial-1-prerequisites.md +++ b/docs/tutorial/tutorial-1-prerequisites.md @@ -1,6 +1,6 @@ --- title: 'Prerequisites' -description: 'This guide will step you through the process of creating a barebones Hello World app in Electron, similar to electron/electron-quick-start.' +description: 'This guide will step you through the process of creating a barebones Hello World app in Electron.' slug: tutorial-prerequisites hide_title: false --- diff --git a/docs/tutorial/tutorial-2-first-app.md b/docs/tutorial/tutorial-2-first-app.md index 7364d7faf84ac..465c98c0bf26e 100644 --- a/docs/tutorial/tutorial-2-first-app.md +++ b/docs/tutorial/tutorial-2-first-app.md @@ -1,6 +1,6 @@ --- title: 'Building your First App' -description: 'This guide will step you through the process of creating a barebones Hello World app in Electron, similar to electron/electron-quick-start.' +description: 'This guide will step you through the process of creating a barebones Hello World app in Electron.' slug: tutorial-first-app hide_title: false --- diff --git a/docs/tutorial/tutorial-3-preload.md b/docs/tutorial/tutorial-3-preload.md index 0854de8305092..377293d3fe06c 100644 --- a/docs/tutorial/tutorial-3-preload.md +++ b/docs/tutorial/tutorial-3-preload.md @@ -1,6 +1,6 @@ --- title: 'Using Preload Scripts' -description: 'This guide will step you through the process of creating a barebones Hello World app in Electron, similar to electron/electron-quick-start.' +description: 'This guide will step you through the process of creating a barebones Hello World app in Electron.' slug: tutorial-preload hide_title: false --- From f72ec2c45abfe536bfef6fe1d6653aaf54895531 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 13 Jun 2025 10:03:03 +0200 Subject: [PATCH 103/186] refactor: have ShowSaveDialogSync() return a std::optional (#47453) * refactor: have ShowSaveDialogSync() return a std::optional Co-authored-by: Charles Kerr * fixup! refactor: have ShowSaveDialogSync() return a std::optional Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_dialog.cc | 5 ++- .../browser/api/electron_api_web_contents.cc | 32 +++++++++++-------- shell/browser/ui/file_dialog.h | 4 ++- shell/browser/ui/file_dialog_linux.cc | 27 +++++++++------- shell/browser/ui/file_dialog_mac.mm | 11 +++---- shell/browser/ui/file_dialog_win.cc | 22 ++++++------- 6 files changed, 56 insertions(+), 45 deletions(-) diff --git a/shell/browser/api/electron_api_dialog.cc b/shell/browser/api/electron_api_dialog.cc index 66c7bf2937539..b5feef3eed004 100644 --- a/shell/browser/api/electron_api_dialog.cc +++ b/shell/browser/api/electron_api_dialog.cc @@ -71,9 +71,8 @@ v8::Local ShowOpenDialog( void ShowSaveDialogSync(const file_dialog::DialogSettings& settings, gin::Arguments* args) { - base::FilePath path; - if (file_dialog::ShowSaveDialogSync(settings, &path)) - args->Return(path); + if (const auto path = file_dialog::ShowSaveDialogSync(settings)) + args->Return(*path); } v8::Local ShowSaveDialog( diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index 26f2465d739ee..d25171ea116ff 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -18,6 +18,7 @@ #include "base/containers/fixed_flat_map.h" #include "base/containers/flat_set.h" #include "base/containers/id_map.h" +#include "base/containers/map_util.h" #include "base/files/file_util.h" #include "base/json/json_reader.h" #include "base/no_destructor.h" @@ -4013,30 +4014,35 @@ void WebContents::DevToolsSaveToFile(const std::string& url, const std::string& content, bool save_as, bool is_base64) { - base::FilePath path; - auto it = saved_files_.find(url); - if (it != saved_files_.end() && !save_as) { - path = it->second; - } else { + const base::FilePath* path = nullptr; + + if (!save_as) + base::FindOrNull(saved_files_, url); + + if (path == nullptr) { file_dialog::DialogSettings settings; settings.parent_window = owner_window(); settings.force_detached = offscreen_; settings.title = url; settings.default_path = base::FilePath::FromUTF8Unsafe(url); - if (!file_dialog::ShowSaveDialogSync(settings, &path)) { - inspectable_web_contents_->CallClientFunction( - "DevToolsAPI", "canceledSaveURL", base::Value(url)); - return; + if (auto new_path = file_dialog::ShowSaveDialogSync(settings)) { + auto [iter, _] = saved_files_.try_emplace(url, std::move(*new_path)); + path = &iter->second; } } - saved_files_[url] = path; + if (path == nullptr) { + inspectable_web_contents_->CallClientFunction( + "DevToolsAPI", "canceledSaveURL", base::Value{url}); + return; + } + // Notify DevTools. inspectable_web_contents_->CallClientFunction( - "DevToolsAPI", "savedURL", base::Value(url), - base::Value(path.AsUTF8Unsafe())); + "DevToolsAPI", "savedURL", base::Value{url}, + base::Value{path->AsUTF8Unsafe()}); file_task_runner_->PostTask( - FROM_HERE, base::BindOnce(&WriteToFile, path, content, is_base64)); + FROM_HERE, base::BindOnce(&WriteToFile, *path, content, is_base64)); } void WebContents::DevToolsAppendToFile(const std::string& url, diff --git a/shell/browser/ui/file_dialog.h b/shell/browser/ui/file_dialog.h index b8858c06ecb3b..f7757da491c65 100644 --- a/shell/browser/ui/file_dialog.h +++ b/shell/browser/ui/file_dialog.h @@ -5,6 +5,7 @@ #ifndef ELECTRON_SHELL_BROWSER_UI_FILE_DIALOG_H_ #define ELECTRON_SHELL_BROWSER_UI_FILE_DIALOG_H_ +#include #include #include #include @@ -72,7 +73,8 @@ bool ShowOpenDialogSync(const DialogSettings& settings, void ShowOpenDialog(const DialogSettings& settings, gin_helper::Promise promise); -bool ShowSaveDialogSync(const DialogSettings& settings, base::FilePath* path); +std::optional ShowSaveDialogSync( + const DialogSettings& settings); void ShowSaveDialog(const DialogSettings& settings, gin_helper::Promise promise); diff --git a/shell/browser/ui/file_dialog_linux.cc b/shell/browser/ui/file_dialog_linux.cc index 732820aa193a9..56251d9717629 100644 --- a/shell/browser/ui/file_dialog_linux.cc +++ b/shell/browser/ui/file_dialog_linux.cc @@ -233,20 +233,25 @@ void ShowOpenDialog(const DialogSettings& settings, dialog->RunOpenDialog(std::move(promise), settings); } -bool ShowSaveDialogSync(const DialogSettings& settings, base::FilePath* path) { - base::RunLoop run_loop(base::RunLoop::Type::kNestableTasksAllowed); - auto cb = base::BindOnce( - [](base::RepeatingClosure cb, base::FilePath* file_path, - gin_helper::Dictionary result) { - result.Get("filePath", file_path); - std::move(cb).Run(); +std::optional ShowSaveDialogSync( + const DialogSettings& settings) { + std::optional path; + + base::RunLoop run_loop{base::RunLoop::Type::kNestableTasksAllowed}; + auto on_chooser_dialog_done = base::BindOnce( + [](base::RepeatingClosure run_loop_closure, + std::optional* path, gin_helper::Dictionary result) { + if (base::FilePath val; result.Get("filePath", &val)) + *path = std::move(val); + std::move(run_loop_closure).Run(); }, - run_loop.QuitClosure(), path); + run_loop.QuitClosure(), &path); - FileChooserDialog* dialog = new FileChooserDialog(); - dialog->RunSaveDialog(std::move(cb), settings); + auto* const dialog = new FileChooserDialog{}; + dialog->RunSaveDialog(std::move(on_chooser_dialog_done), settings); run_loop.Run(); - return !path->empty(); + + return path; } void ShowSaveDialog(const DialogSettings& settings, diff --git a/shell/browser/ui/file_dialog_mac.mm b/shell/browser/ui/file_dialog_mac.mm index c3967ef0d3c8d..98896b6dfac4e 100644 --- a/shell/browser/ui/file_dialog_mac.mm +++ b/shell/browser/ui/file_dialog_mac.mm @@ -436,19 +436,18 @@ void ShowOpenDialog(const DialogSettings& settings, } } -bool ShowSaveDialogSync(const DialogSettings& settings, base::FilePath* path) { - DCHECK(path); +std::optional ShowSaveDialogSync( + const DialogSettings& settings) { NSSavePanel* dialog = [NSSavePanel savePanel]; SetupDialog(dialog, settings); SetupSaveDialogForProperties(dialog, settings.properties); - int chosen = RunModalDialog(dialog, settings); + const int chosen = RunModalDialog(dialog, settings); if (chosen == NSModalResponseCancel || ![[dialog URL] isFileURL]) - return false; + return {}; - *path = base::FilePath(base::SysNSStringToUTF8([[dialog URL] path])); - return true; + return base::FilePath{base::SysNSStringToUTF8([[dialog URL] path])}; } void SaveDialogCompletion(int chosen, diff --git a/shell/browser/ui/file_dialog_win.cc b/shell/browser/ui/file_dialog_win.cc index 7e48879c41304..5ded77f646610 100644 --- a/shell/browser/ui/file_dialog_win.cc +++ b/shell/browser/ui/file_dialog_win.cc @@ -219,11 +219,12 @@ void ShowOpenDialog(const DialogSettings& settings, base::BindOnce(done, std::move(promise))); } -bool ShowSaveDialogSync(const DialogSettings& settings, base::FilePath* path) { +std::optional ShowSaveDialogSync( + const DialogSettings& settings) { ATL::CComPtr file_save_dialog; HRESULT hr = file_save_dialog.CoCreateInstance(CLSID_FileSaveDialog); if (FAILED(hr)) - return false; + return {}; DWORD options = FOS_FORCEFILESYSTEM | FOS_PATHMUSTEXIST | FOS_OVERWRITEPROMPT; if (settings.properties & SAVE_DIALOG_SHOW_HIDDEN_FILES) @@ -236,32 +237,31 @@ bool ShowSaveDialogSync(const DialogSettings& settings, base::FilePath* path) { hr = ShowFileDialog(file_save_dialog, settings); if (FAILED(hr)) - return false; + return {}; CComPtr pItem; hr = file_save_dialog->GetResult(&pItem); if (FAILED(hr)) - return false; + return {}; PWSTR result_path = nullptr; hr = pItem->GetDisplayName(SIGDN_FILESYSPATH, &result_path); if (!SUCCEEDED(hr)) - return false; + return {}; - *path = base::FilePath(result_path); + auto path = base::FilePath{result_path}; CoTaskMemFree(result_path); - - return true; + return path; } void ShowSaveDialog(const DialogSettings& settings, gin_helper::Promise promise) { auto done = [](gin_helper::Promise promise, - bool success, base::FilePath result) { + std::optional result) { v8::HandleScope handle_scope(promise.isolate()); auto dict = gin::Dictionary::CreateEmpty(promise.isolate()); - dict.Set("canceled", !success); - dict.Set("filePath", result); + dict.Set("canceled", !result.has_value()); + dict.Set("filePath", result.value_or(base::FilePath{})); promise.Resolve(dict); }; dialog_thread::Run(base::BindOnce(ShowSaveDialogSync, settings), From bef6e11b9d2609bd1577d36e1399fcca4aef1706 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 16 Jun 2025 11:10:01 -0400 Subject: [PATCH 104/186] refactor: move `gin::Converter` impl to a .cc file (#47466) refactor: move gin::Converter impl to a .cc file Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- filenames.gni | 1 + shell/browser/preload_script.cc | 82 +++++++++++++++++++++++++++++++++ shell/browser/preload_script.h | 63 +++---------------------- 3 files changed, 89 insertions(+), 57 deletions(-) create mode 100644 shell/browser/preload_script.cc diff --git a/filenames.gni b/filenames.gni index 50242a7e7a1c1..499e8dc95ce93 100644 --- a/filenames.gni +++ b/filenames.gni @@ -479,6 +479,7 @@ filenames = { "shell/browser/osr/osr_web_contents_view.h", "shell/browser/plugins/plugin_utils.cc", "shell/browser/plugins/plugin_utils.h", + "shell/browser/preload_script.cc", "shell/browser/preload_script.h", "shell/browser/protocol_registry.cc", "shell/browser/protocol_registry.h", diff --git a/shell/browser/preload_script.cc b/shell/browser/preload_script.cc new file mode 100644 index 0000000000000..0f60687eba06b --- /dev/null +++ b/shell/browser/preload_script.cc @@ -0,0 +1,82 @@ +// Copyright (c) 2025 Salesforce, Inc. +// Use of this source code is governed by the MIT license that can be +// found in the LICENSE file. + +#include "shell/browser/preload_script.h" + +#include "base/containers/fixed_flat_map.h" +#include "base/files/file_path.h" +#include "base/uuid.h" +#include "shell/common/gin_converters/file_path_converter.h" +#include "shell/common/gin_helper/dictionary.h" + +namespace gin { + +using electron::PreloadScript; + +// static +v8::Local Converter::ToV8( + v8::Isolate* isolate, + const PreloadScript::ScriptType& in) { + using Val = PreloadScript::ScriptType; + static constexpr auto Lookup = base::MakeFixedFlatMap({ + {Val::kWebFrame, "frame"}, + {Val::kServiceWorker, "service-worker"}, + }); + return StringToV8(isolate, Lookup.at(in)); +} + +// static +bool Converter::FromV8( + v8::Isolate* isolate, + v8::Local val, + PreloadScript::ScriptType* out) { + using Val = PreloadScript::ScriptType; + static constexpr auto Lookup = base::MakeFixedFlatMap({ + {"frame", Val::kWebFrame}, + {"service-worker", Val::kServiceWorker}, + }); + return FromV8WithLookup(isolate, val, Lookup, out); +} + +// static +v8::Local Converter::ToV8( + v8::Isolate* isolate, + const PreloadScript& script) { + gin::Dictionary dict(isolate, v8::Object::New(isolate)); + dict.Set("filePath", script.file_path.AsUTF8Unsafe()); + dict.Set("id", script.id); + dict.Set("type", script.script_type); + return ConvertToV8(isolate, dict).As(); +} + +// static +bool Converter::FromV8(v8::Isolate* isolate, + v8::Local val, + PreloadScript* out) { + gin_helper::Dictionary options; + if (!ConvertFromV8(isolate, val, &options)) + return false; + if (PreloadScript::ScriptType script_type; + options.Get("type", &script_type)) { + out->script_type = script_type; + } else { + return false; + } + if (base::FilePath file_path; options.Get("filePath", &file_path)) { + out->file_path = file_path; + } else { + return false; + } + if (std::string id; options.Get("id", &id)) { + out->id = id; + } else { + out->id = base::Uuid::GenerateRandomV4().AsLowercaseString(); + } + if (bool deprecated; options.Get("_deprecated", &deprecated)) { + out->deprecated = deprecated; + } + return true; +} + +} // namespace gin diff --git a/shell/browser/preload_script.h b/shell/browser/preload_script.h index bae243c7cafc2..62e945a5698c1 100644 --- a/shell/browser/preload_script.h +++ b/shell/browser/preload_script.h @@ -5,14 +5,11 @@ #ifndef ELECTRON_SHELL_BROWSER_PRELOAD_SCRIPT_H_ #define ELECTRON_SHELL_BROWSER_PRELOAD_SCRIPT_H_ -#include +#include -#include "base/containers/fixed_flat_map.h" #include "base/files/file_path.h" -#include "base/uuid.h" #include "gin/converter.h" -#include "shell/common/gin_converters/file_path_converter.h" -#include "shell/common/gin_helper/dictionary.h" +#include "v8/include/v8-forward.h" namespace electron { @@ -36,67 +33,19 @@ using electron::PreloadScript; template <> struct Converter { static v8::Local ToV8(v8::Isolate* isolate, - const PreloadScript::ScriptType& in) { - using Val = PreloadScript::ScriptType; - static constexpr auto Lookup = - base::MakeFixedFlatMap({ - {Val::kWebFrame, "frame"}, - {Val::kServiceWorker, "service-worker"}, - }); - return StringToV8(isolate, Lookup.at(in)); - } - + const PreloadScript::ScriptType& in); static bool FromV8(v8::Isolate* isolate, v8::Local val, - PreloadScript::ScriptType* out) { - using Val = PreloadScript::ScriptType; - static constexpr auto Lookup = - base::MakeFixedFlatMap({ - {"frame", Val::kWebFrame}, - {"service-worker", Val::kServiceWorker}, - }); - return FromV8WithLookup(isolate, val, Lookup, out); - } + PreloadScript::ScriptType* out); }; template <> struct Converter { static v8::Local ToV8(v8::Isolate* isolate, - const PreloadScript& script) { - gin::Dictionary dict(isolate, v8::Object::New(isolate)); - dict.Set("filePath", script.file_path.AsUTF8Unsafe()); - dict.Set("id", script.id); - dict.Set("type", script.script_type); - return ConvertToV8(isolate, dict).As(); - } - + const PreloadScript& script); static bool FromV8(v8::Isolate* isolate, v8::Local val, - PreloadScript* out) { - gin_helper::Dictionary options; - if (!ConvertFromV8(isolate, val, &options)) - return false; - if (PreloadScript::ScriptType script_type; - options.Get("type", &script_type)) { - out->script_type = script_type; - } else { - return false; - } - if (base::FilePath file_path; options.Get("filePath", &file_path)) { - out->file_path = file_path; - } else { - return false; - } - if (std::string id; options.Get("id", &id)) { - out->id = id; - } else { - out->id = base::Uuid::GenerateRandomV4().AsLowercaseString(); - } - if (bool deprecated; options.Get("_deprecated", &deprecated)) { - out->deprecated = deprecated; - } - return true; - } + PreloadScript* out); }; } // namespace gin From 03c32ba3be43ef4d22021fcdd4aa753599eed551 Mon Sep 17 00:00:00 2001 From: Keeley Hammond Date: Mon, 16 Jun 2025 21:20:53 -0700 Subject: [PATCH 105/186] fix: revert moving IsClosed() and IsClosable() into NativeWindow::Close() (#47485) fix: revert moving IsClosed() and IsClosable() into NativeWindow::Close() (#47482) Revert "refactor: move `IsClosed()` and `IsClosable()` tests into `NativeWindow::Close()` (#46888)" This reverts commit 3faddd5ae2ae03be8ba037c77989630576bb8167. --- shell/browser/api/electron_api_base_window.cc | 3 ++- shell/browser/native_window.cc | 21 +++++-------------- shell/browser/native_window.h | 14 +++++-------- shell/browser/native_window_mac.h | 4 ++-- shell/browser/native_window_mac.mm | 12 ++++++++--- shell/browser/native_window_views.cc | 10 +++++++-- shell/browser/native_window_views.h | 4 ++-- shell/browser/window_list.cc | 4 ++-- 8 files changed, 35 insertions(+), 37 deletions(-) diff --git a/shell/browser/api/electron_api_base_window.cc b/shell/browser/api/electron_api_base_window.cc index 5070a6c2dd376..81ada7acf9294 100644 --- a/shell/browser/api/electron_api_base_window.cc +++ b/shell/browser/api/electron_api_base_window.cc @@ -362,7 +362,8 @@ void BaseWindow::SetContentView(gin::Handle view) { } void BaseWindow::CloseImmediately() { - window_->CloseImmediately(); + if (!window_->IsClosed()) + window_->CloseImmediately(); } void BaseWindow::Close() { diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 19db0ef56d76e..4be8f95b23d73 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -279,6 +279,10 @@ NativeWindow* NativeWindow::FromWidget(const views::Widget* widget) { widget->GetNativeWindowProperty(kNativeWindowKey.c_str())); } +bool NativeWindow::IsClosed() const { + return is_closed_; +} + void NativeWindow::SetSize(const gfx::Size& size, bool animate) { SetBounds(gfx::Rect(GetPosition(), size), animate); } @@ -516,23 +520,8 @@ void NativeWindow::NotifyWindowCloseButtonClicked() { CloseImmediately(); } -void NativeWindow::Close() { - if (!IsClosable()) { - WindowList::WindowCloseCancelled(this); - return; - } - - if (!is_closed()) - CloseImpl(); -} - -void NativeWindow::CloseImmediately() { - if (!is_closed()) - CloseImmediatelyImpl(); -} - void NativeWindow::NotifyWindowClosed() { - if (is_closed()) + if (is_closed_) return; is_closed_ = true; diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index f2a8334a951ac..be828691dc595 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -81,10 +81,9 @@ class NativeWindow : public base::SupportsUserData, virtual void SetContentView(views::View* view) = 0; - // wrapper around CloseImpl that checks that window_ can be closed - void Close(); - // wrapper around CloseImmediatelyImpl that checks that window_ can be closed - void CloseImmediately(); + virtual void Close() = 0; + virtual void CloseImmediately() = 0; + virtual bool IsClosed() const; virtual void Focus(bool focus) = 0; virtual bool IsFocused() const = 0; virtual void Show() = 0; @@ -433,9 +432,9 @@ class NativeWindow : public base::SupportsUserData, void UpdateBackgroundThrottlingState(); protected: - constexpr void set_has_frame(const bool val) { has_frame_ = val; } + friend class api::BrowserView; - [[nodiscard]] constexpr bool is_closed() const { return is_closed_; } + constexpr void set_has_frame(const bool val) { has_frame_ = val; } NativeWindow(const gin_helper::Dictionary& options, NativeWindow* parent); @@ -452,9 +451,6 @@ class NativeWindow : public base::SupportsUserData, void set_content_view(views::View* view) { content_view_ = view; } - virtual void CloseImpl() = 0; - virtual void CloseImmediatelyImpl() = 0; - static inline constexpr base::cstring_view kNativeWindowKey = "__ELECTRON_NATIVE_WINDOW__"; diff --git a/shell/browser/native_window_mac.h b/shell/browser/native_window_mac.h index d4c07ba6fc06f..5420e14aecd7d 100644 --- a/shell/browser/native_window_mac.h +++ b/shell/browser/native_window_mac.h @@ -38,8 +38,8 @@ class NativeWindowMac : public NativeWindow, // NativeWindow: void SetContentView(views::View* view) override; - void CloseImpl() override; - void CloseImmediatelyImpl() override; + void Close() override; + void CloseImmediately() override; void Focus(bool focus) override; bool IsFocused() const override; void Show() override; diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 2dcbdd07ae04e..9278ece8ea14b 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -33,6 +33,7 @@ #include "shell/browser/ui/cocoa/root_view_mac.h" #include "shell/browser/ui/cocoa/window_buttons_proxy.h" #include "shell/browser/ui/drag_util.h" +#include "shell/browser/window_list.h" #include "shell/common/gin_converters/gfx_converter.h" #include "shell/common/gin_helper/dictionary.h" #include "shell/common/node_util.h" @@ -340,7 +341,12 @@ static bool FromV8(v8::Isolate* isolate, root_view->DeprecatedLayoutImmediately(); } -void NativeWindowMac::CloseImpl() { +void NativeWindowMac::Close() { + if (!IsClosable()) { + WindowList::WindowCloseCancelled(this); + return; + } + if (is_transitioning_fullscreen()) { SetHasDeferredWindowClose(true); return; @@ -376,7 +382,7 @@ static bool FromV8(v8::Isolate* isolate, } } -void NativeWindowMac::CloseImmediatelyImpl() { +void NativeWindowMac::CloseImmediately() { // Ensure we're detached from the parent window before closing. RemoveChildFromParentWindow(); @@ -1693,7 +1699,7 @@ static bool FromV8(v8::Isolate* isolate, } void NativeWindowMac::Cleanup() { - DCHECK(!is_closed()); + DCHECK(!IsClosed()); ui::NativeTheme::GetInstanceForNativeUi()->RemoveObserver(this); display::Screen::GetScreen()->RemoveObserver(this); [window_ cleanup]; diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index b90133927aee5..77250ef9e7272 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -31,6 +31,7 @@ #include "shell/browser/ui/views/root_view.h" #include "shell/browser/web_contents_preferences.h" #include "shell/browser/web_view_manager.h" +#include "shell/browser/window_list.h" #include "shell/common/electron_constants.h" #include "shell/common/gin_converters/image_converter.h" #include "shell/common/gin_helper/dictionary.h" @@ -478,11 +479,16 @@ void NativeWindowViews::SetContentView(views::View* view) { root_view_.GetMainView()->DeprecatedLayoutImmediately(); } -void NativeWindowViews::CloseImpl() { +void NativeWindowViews::Close() { + if (!IsClosable()) { + WindowList::WindowCloseCancelled(this); + return; + } + widget()->Close(); } -void NativeWindowViews::CloseImmediatelyImpl() { +void NativeWindowViews::CloseImmediately() { widget()->CloseNow(); } diff --git a/shell/browser/native_window_views.h b/shell/browser/native_window_views.h index 650a026b4807c..b65221bcdba21 100644 --- a/shell/browser/native_window_views.h +++ b/shell/browser/native_window_views.h @@ -48,8 +48,8 @@ class NativeWindowViews : public NativeWindow, // NativeWindow: void SetContentView(views::View* view) override; - void CloseImpl() override; - void CloseImmediatelyImpl() override; + void Close() override; + void CloseImmediately() override; void Focus(bool focus) override; bool IsFocused() const override; void Show() override; diff --git a/shell/browser/window_list.cc b/shell/browser/window_list.cc index bd9cfbfe53e23..188402d0e6bb1 100644 --- a/shell/browser/window_list.cc +++ b/shell/browser/window_list.cc @@ -84,7 +84,7 @@ void WindowList::CloseAllWindows() { std::ranges::reverse(weak_windows); #endif for (const auto& window : weak_windows) { - if (window) + if (window && !window->IsClosed()) window->Close(); } } @@ -95,7 +95,7 @@ void WindowList::DestroyAllWindows() { ConvertToWeakPtrVector(GetInstance()->windows_); for (const auto& window : weak_windows) { - if (window) + if (window && !window->IsClosed()) window->CloseImmediately(); } } From 5bd18aac95eafa569d854358125921e22bddc57a Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Tue, 17 Jun 2025 11:38:13 -0400 Subject: [PATCH 106/186] chore: bump chromium to 138.0.7204.23 (37-x-y) (#47455) * chore: bump chromium in DEPS to 138.0.7204.23 * chore: update patches * test: fixup api-desktop-capturer-spec.ts for linux --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- DEPS | 2 +- ..._depend_on_packed_resource_integrity.patch | 4 +- patches/chromium/can_create_window.patch | 6 +- ...fy_chromium_handling_of_mouse_events.patch | 20 ++-- .../chromium/chore_partial_revert_of.patch | 4 +- ...screationoverridden_with_full_params.patch | 4 +- .../custom_protocols_plzserviceworker.patch | 8 +- patches/chromium/disable_hidden.patch | 6 +- .../chromium/enable_reset_aspect_ratio.patch | 4 +- ...screen_rendering_with_viz_compositor.patch | 2 +- ...ivate_background_material_on_windows.patch | 2 +- .../fix_aspect_ratio_with_max_size.patch | 4 +- ...board_hides_on_input_blur_in_webview.patch | 4 +- ...x_remove_caption-removing_style_call.patch | 2 +- ...original_resize_performance_on_macos.patch | 4 +- ..._avoid_private_macos_api_usage.patch.patch | 2 +- patches/chromium/printing.patch | 4 +- ...r_changes_to_the_webcontentsobserver.patch | 14 +-- ...efactor_unfilter_unresponsive_events.patch | 4 +- patches/chromium/web_contents.patch | 6 +- patches/chromium/webview_fullscreen.patch | 6 +- spec/api-desktop-capturer-spec.ts | 102 +++++++----------- 22 files changed, 97 insertions(+), 117 deletions(-) diff --git a/DEPS b/DEPS index 153ee4542aae4..2e5288ebd25b0 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.15', + '138.0.7204.23', 'node_version': 'v22.16.0', 'nan_version': diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index b32f98bb1dd3b..23c000d2d5947 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -33,10 +33,10 @@ index 72c637f9f3ba48bb7ab06678fe833f33d2cfddc8..e9c8ae3cdb7ba400c59cc469a1a80b50 "//base", "//build:branding_buildflags", diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn -index efb9b948aca15ae8b4d6257fa685e758d2e3acc1..0e14d0eb15bfcd86831599678eb0f76fe0a803cc 100644 +index 36fe07a692e9be5b99f9e59157b90963a6485f8b..d8cf68e953213f309537e74d954d874950ede24a 100644 --- a/chrome/browser/BUILD.gn +++ b/chrome/browser/BUILD.gn -@@ -4716,7 +4716,7 @@ static_library("browser") { +@@ -4715,7 +4715,7 @@ static_library("browser") { [ "//chrome/browser/ui/webui/signin:profile_impl" ] } diff --git a/patches/chromium/can_create_window.patch b/patches/chromium/can_create_window.patch index f68c789132d3e..c5f7776ce7430 100644 --- a/patches/chromium/can_create_window.patch +++ b/patches/chromium/can_create_window.patch @@ -21,10 +21,10 @@ index 23cd457563d7d534e924428ac6da2b475e579326..d8698f9f37eefa50bf4e29a164b2cc30 &no_javascript_access); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index e57951543e9f2b0be5164dde3d4b629b081457cc..811d137c4b77d3347dc8de5bb6207646c952f23b 100644 +index f3204a39253652a906f8976c666395e8afa033a8..a45bf004f5096809b5fc7b70faa0b7fa7b257049 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5317,6 +5317,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5293,6 +5293,12 @@ FrameTree* WebContentsImpl::CreateNewWindow( // Sets the newly created WebContents WindowOpenDisposition. new_contents_impl->original_window_open_disposition_ = params.disposition; @@ -37,7 +37,7 @@ index e57951543e9f2b0be5164dde3d4b629b081457cc..811d137c4b77d3347dc8de5bb6207646 // If the new frame has a name, make sure any SiteInstances that can find // this named frame have proxies for it. Must be called after // SetSessionStorageNamespace, since this calls CreateRenderView, which uses -@@ -5358,12 +5364,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5334,12 +5340,6 @@ FrameTree* WebContentsImpl::CreateNewWindow( AddWebContentsDestructionObserver(new_contents_impl); } diff --git a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch index 3f578c108f41e..73c858db29f2c 100644 --- a/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch +++ b/patches/chromium/chore_modify_chromium_handling_of_mouse_events.patch @@ -34,10 +34,10 @@ index 39b5a8fdd165efd74b00256552b51b5413107958..bfc4ef4f50efff4a77f2aef64335bb7e class ScrollEvent; diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index b687c8505f1afc918fc4994dd6fbb8b6520e3e8a..d8168622ee2e0d42f8d4486d8f9391b4508aff54 100644 +index cc9f13770da77d9522a48abeb9d831b7b8b742f9..a415140b94e467adfbc3dbbaa026e897a0f66c06 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -@@ -1360,6 +1360,10 @@ void DesktopWindowTreeHostWin::HandleHeadlessWindowBoundsChanged( +@@ -1358,6 +1358,10 @@ void DesktopWindowTreeHostWin::HandleHeadlessWindowBoundsChanged( window()->SetProperty(aura::client::kHeadlessBoundsKey, bounds); } @@ -49,10 +49,10 @@ index b687c8505f1afc918fc4994dd6fbb8b6520e3e8a..d8168622ee2e0d42f8d4486d8f9391b4 DesktopWindowTreeHostWin::GetSingletonDesktopNativeCursorManager() { return new DesktopNativeCursorManagerWin(); diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h -index 28cbd63261275e252381d88c13c1a3b4067d197f..45e47bae0e8b3369072c6e179206aa6d222e0ec5 100644 +index c8339591dc55a792fd20f6c4340eac49f56a7f50..b85d1cdec49b10628d2f3d3d2e07513beb830456 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h -@@ -272,6 +272,7 @@ class VIEWS_EXPORT DesktopWindowTreeHostWin +@@ -271,6 +271,7 @@ class VIEWS_EXPORT DesktopWindowTreeHostWin void HandleWindowSizeUnchanged() override; void HandleWindowScaleFactorChanged(float window_scale_factor) override; void HandleHeadlessWindowBoundsChanged(const gfx::Rect& bounds) override; @@ -61,10 +61,10 @@ index 28cbd63261275e252381d88c13c1a3b4067d197f..45e47bae0e8b3369072c6e179206aa6d Widget* GetWidget(); const Widget* GetWidget() const; diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 418dc47b6d4df097e8f0cfd61de8485af2a8d2c2..8c13b9db078e690240eca0a48a7c546dcdac3c11 100644 +index 011448d24c557059423f6901b7e1100e476f0c9f..06fc8190385139f165bad0c2da2fb22d7a2c3d76 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -3171,15 +3171,19 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3161,15 +3161,19 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, } // We must let Windows handle the caption buttons if it's drawing them, or // they won't work. @@ -86,7 +86,7 @@ index 418dc47b6d4df097e8f0cfd61de8485af2a8d2c2..8c13b9db078e690240eca0a48a7c546d return 0; } } -@@ -3202,6 +3206,7 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3192,6 +3196,7 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, // handle alt-space, or in the frame itself. is_right_mouse_pressed_on_caption_ = false; ReleaseCapture(); @@ -94,7 +94,7 @@ index 418dc47b6d4df097e8f0cfd61de8485af2a8d2c2..8c13b9db078e690240eca0a48a7c546d // |point| is in window coordinates, but WM_NCHITTEST and TrackPopupMenu() // expect screen coordinates. POINT screen_point = CR_POINT_INITIALIZER_FROM_LPARAM(l_param); -@@ -3209,7 +3214,17 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, +@@ -3199,7 +3204,17 @@ LRESULT HWNDMessageHandler::HandleMouseEventInternal(UINT message, w_param = static_cast(SendMessage( hwnd(), WM_NCHITTEST, 0, MAKELPARAM(screen_point.x, screen_point.y))); if (w_param == HTCAPTION || w_param == HTSYSMENU) { @@ -114,10 +114,10 @@ index 418dc47b6d4df097e8f0cfd61de8485af2a8d2c2..8c13b9db078e690240eca0a48a7c546d } } else if (message == WM_NCLBUTTONDOWN && diff --git a/ui/views/win/hwnd_message_handler_delegate.h b/ui/views/win/hwnd_message_handler_delegate.h -index 252d7ce78ad49596fb030160cb69d9bf3dc0951f..5e7975cf5cb3435b844fda58d7582d54cb583a72 100644 +index 320b3263875807ccca2f013d51bc67a0c341cba3..67c761715aa2cc2ad52a5105a485af0514a4148f 100644 --- a/ui/views/win/hwnd_message_handler_delegate.h +++ b/ui/views/win/hwnd_message_handler_delegate.h -@@ -255,6 +255,10 @@ class VIEWS_EXPORT HWNDMessageHandlerDelegate { +@@ -252,6 +252,10 @@ class VIEWS_EXPORT HWNDMessageHandlerDelegate { // Called when the headless window bounds has changed. virtual void HandleHeadlessWindowBoundsChanged(const gfx::Rect& bounds) = 0; diff --git a/patches/chromium/chore_partial_revert_of.patch b/patches/chromium/chore_partial_revert_of.patch index 065bc7cdf9349..1b87ecd0db974 100644 --- a/patches/chromium/chore_partial_revert_of.patch +++ b/patches/chromium/chore_partial_revert_of.patch @@ -14,10 +14,10 @@ track down the source of this problem & figure out if we can fix it by changing something in Electron. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index fbe6b5d24185c0b0e664db05c7801434737d4d8d..51798b8ceb81cf9d374cf594aa6afbcb366f4732 100644 +index 0fba6e8b5f1f9ecde06b9d846b4ace984cdfc943..b50e3c2ecb6f9f3322cfd16fc7bcbd8935f863a2 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5233,7 +5233,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5209,7 +5209,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( : IsGuest(); // While some guest types do not have a guest SiteInstance, the ones that // don't all override WebContents creation above. diff --git a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch index 82a9de6faac0c..eaaef662c7410 100644 --- a/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch +++ b/patches/chromium/chore_provide_iswebcontentscreationoverridden_with_full_params.patch @@ -222,10 +222,10 @@ index b969f1d97b7e3396119b579cfbe61e19ff7d2dd4..b8d6169652da28266a514938b45b39c5 content::WebContents* AddNewContents( content::WebContents* source, diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 33abfcd326148f32eff2266a4545345e4a561a4e..4bb69438947fff73a6905a1ecc1b711986a89124 100644 +index c034b546289ba069194ad65d3d3bc0703a3afe9c..e603c0fddbf4efaeb225686c1791ffb581e9e6c0 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -5196,8 +5196,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( +@@ -5172,8 +5172,7 @@ FrameTree* WebContentsImpl::CreateNewWindow( if (delegate_ && delegate_->IsWebContentsCreationOverridden( opener, source_site_instance, params.window_container_type, diff --git a/patches/chromium/custom_protocols_plzserviceworker.patch b/patches/chromium/custom_protocols_plzserviceworker.patch index a3d61e14186ff..fb4b40f1cf3ff 100644 --- a/patches/chromium/custom_protocols_plzserviceworker.patch +++ b/patches/chromium/custom_protocols_plzserviceworker.patch @@ -8,10 +8,10 @@ Allow registering custom protocols to handle service worker main script fetching Refs https://bugs.chromium.org/p/chromium/issues/detail?id=996511 diff --git a/content/browser/service_worker/service_worker_context_wrapper.cc b/content/browser/service_worker/service_worker_context_wrapper.cc -index b4c984e0dd22f148a426ce0ea04988798ed95aaa..5fd099b6396fc51d29fce2843531d5fc89642d35 100644 +index bc49553c298d548a3c09a5e65a44cac1a42e893e..fd11dbf8117cc173fd8bb268b391ddbb8ad36f49 100644 --- a/content/browser/service_worker/service_worker_context_wrapper.cc +++ b/content/browser/service_worker/service_worker_context_wrapper.cc -@@ -1961,6 +1961,26 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -1972,6 +1972,26 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( loader_factory_bundle_info = context()->loader_factory_bundle_for_update_check()->Clone(); @@ -38,7 +38,7 @@ index b4c984e0dd22f148a426ce0ea04988798ed95aaa..5fd099b6396fc51d29fce2843531d5fc if (auto* config = content::WebUIConfigMap::GetInstance().GetConfig( browser_context(), scope)) { // If this is a Service Worker for a WebUI, the WebUI's URLDataSource -@@ -1980,9 +2000,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -1991,9 +2011,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( features::kEnableServiceWorkersForChromeScheme) && scope.scheme_piece() == kChromeUIScheme) { config->RegisterURLDataSource(browser_context()); @@ -49,7 +49,7 @@ index b4c984e0dd22f148a426ce0ea04988798ed95aaa..5fd099b6396fc51d29fce2843531d5fc .emplace(kChromeUIScheme, CreateWebUIServiceWorkerLoaderFactory( browser_context(), kChromeUIScheme, base::flat_set())); -@@ -1990,9 +2008,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -2001,9 +2019,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( features::kEnableServiceWorkersForChromeUntrusted) && scope.scheme_piece() == kChromeUIUntrustedScheme) { config->RegisterURLDataSource(browser_context()); diff --git a/patches/chromium/disable_hidden.patch b/patches/chromium/disable_hidden.patch index 72a1a92bcdd9c..ec069c6f8bdd3 100644 --- a/patches/chromium/disable_hidden.patch +++ b/patches/chromium/disable_hidden.patch @@ -6,7 +6,7 @@ Subject: disable_hidden.patch Electron uses this to disable background throttling for hidden windows. diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index 52f772876a8878a7dbc95bb8f243d1442d30977f..cdfdd322ffb2e61d5480ac7c88dba35a1cc1b5b9 100644 +index 252edf0bb40ba4c16061425013d9e4c559b91e78..624094ba6459f3663a12f868c4cb47dfa9f8dce1 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc @@ -833,6 +833,10 @@ void RenderWidgetHostImpl::WasHidden() { @@ -21,10 +21,10 @@ index 52f772876a8878a7dbc95bb8f243d1442d30977f..cdfdd322ffb2e61d5480ac7c88dba35a // Prompts should remain open and functional across tab switches. if (!delegate_ || !delegate_->IsWaitingForPointerLockPrompt(this)) { diff --git a/content/browser/renderer_host/render_widget_host_impl.h b/content/browser/renderer_host/render_widget_host_impl.h -index 0bc94f2246a9357915423d1954cb240fad602a22..4663f18c832c12e8704fbb99a5aea824cd44aa5b 100644 +index f24d02054c89c8bc6b75e127146cb97a72e3f94a..9b8919ab2d8c9432c5d908337e7a19bd055b440e 100644 --- a/content/browser/renderer_host/render_widget_host_impl.h +++ b/content/browser/renderer_host/render_widget_host_impl.h -@@ -1017,6 +1017,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl +@@ -1021,6 +1021,9 @@ class CONTENT_EXPORT RenderWidgetHostImpl // Requests a commit and forced redraw in the renderer compositor. void ForceRedrawForTesting(); diff --git a/patches/chromium/enable_reset_aspect_ratio.patch b/patches/chromium/enable_reset_aspect_ratio.patch index fc663286cd21c..7472302f6a410 100644 --- a/patches/chromium/enable_reset_aspect_ratio.patch +++ b/patches/chromium/enable_reset_aspect_ratio.patch @@ -6,7 +6,7 @@ Subject: feat: enable setting aspect ratio to 0 Make SetAspectRatio accept 0 as valid input, which would reset to null. diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc -index 18cd413e8780161d2c1d1993e12e8d87eb12a33f..b687c8505f1afc918fc4994dd6fbb8b6520e3e8a 100644 +index 93cede29651ef2fc0a77c6a7a569f9b8d1fe4ba9..cc9f13770da77d9522a48abeb9d831b7b8b742f9 100644 --- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc @@ -609,7 +609,7 @@ void DesktopWindowTreeHostWin::SetOpacity(float opacity) { @@ -19,7 +19,7 @@ index 18cd413e8780161d2c1d1993e12e8d87eb12a33f..b687c8505f1afc918fc4994dd6fbb8b6 excluded_margin); } diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index cb66f6e84abd95080a2051b39d86b1838a6df9bb..c38b58ed16b14ff765f24d0bb8bdf34b8de3a901 100644 +index 1a8943c86cb1bb79f83bfd867619b805aaa0c329..6df5e54cefe71393cb6189cc15240d21d2262059 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc @@ -993,8 +993,11 @@ void HWNDMessageHandler::SetFullscreen(bool fullscreen, diff --git a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch index 2f1b81e558628..3d39cd363c8ac 100644 --- a/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch +++ b/patches/chromium/feat_enable_offscreen_rendering_with_viz_compositor.patch @@ -597,7 +597,7 @@ index e063835e87f08e6a2359886a96d7b78954e3d5b2..34bcf67726f64466d11a56d7a315ce7e // Sends the created child window to the browser process so that it can be diff --git a/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom b/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom -index 4828bfcb0c221ce9de3f1fe9952849c542e7e3df..4d3667deff36216db4d51ae3f01f732d691f4866 100644 +index 3066550e422058eec23d5fe3e655625f5446d694..7358b05a646a2f80717a91182c4929776a404179 100644 --- a/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom +++ b/services/viz/privileged/mojom/compositing/frame_sink_manager.mojom @@ -39,6 +39,7 @@ struct RootCompositorFrameSinkParams { diff --git a/patches/chromium/fix_activate_background_material_on_windows.patch b/patches/chromium/fix_activate_background_material_on_windows.patch index 5dfab7478972f..3869ca7990f26 100644 --- a/patches/chromium/fix_activate_background_material_on_windows.patch +++ b/patches/chromium/fix_activate_background_material_on_windows.patch @@ -14,7 +14,7 @@ This patch likely can't be upstreamed as-is, as Chromium doesn't have this use case in mind currently. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 30399c8a81819a57f07702a97f85e3edd7df9d69..1559eb26fb86ac6172509785afff1e0bbd226ee7 100644 +index 1a10bd1a6c527633f97d6eee6525b1e45a3fcd3d..2b983ae3ec3e1d17951add818c2610582d586377 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc @@ -937,13 +937,13 @@ void HWNDMessageHandler::FrameTypeChanged() { diff --git a/patches/chromium/fix_aspect_ratio_with_max_size.patch b/patches/chromium/fix_aspect_ratio_with_max_size.patch index aea35450aad2d..9082b64ccb4c7 100644 --- a/patches/chromium/fix_aspect_ratio_with_max_size.patch +++ b/patches/chromium/fix_aspect_ratio_with_max_size.patch @@ -11,10 +11,10 @@ enlarge window above dimensions set during creation of the BrowserWindow. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index c38b58ed16b14ff765f24d0bb8bdf34b8de3a901..418dc47b6d4df097e8f0cfd61de8485af2a8d2c2 100644 +index 6df5e54cefe71393cb6189cc15240d21d2262059..011448d24c557059423f6901b7e1100e476f0c9f 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc -@@ -3775,15 +3775,30 @@ void HWNDMessageHandler::SizeWindowToAspectRatio(UINT param, +@@ -3765,15 +3765,30 @@ void HWNDMessageHandler::SizeWindowToAspectRatio(UINT param, delegate_->GetMinMaxSize(&min_window_size, &max_window_size); min_window_size = delegate_->DIPToScreenSize(min_window_size); max_window_size = delegate_->DIPToScreenSize(max_window_size); diff --git a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch index 1a74119031b3e..019258275bd6a 100644 --- a/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch +++ b/patches/chromium/fix_on-screen-keyboard_hides_on_input_blur_in_webview.patch @@ -87,10 +87,10 @@ index 75df43e3cd2721a92c90c18154d53d5c203e2465..ce42c75c8face36d21f53f44c0201ac4 // The view with active text input state, i.e., a focused element. // It will be nullptr if no such view exists. Note that the active view diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index eefecd6b3b9c940c3ae3e9ef40075c4a109878ef..fbe6b5d24185c0b0e664db05c7801434737d4d8d 100644 +index 374d5f1a1685229865d0f1f1032f36bbcd54e92e..0fba6e8b5f1f9ecde06b9d846b4ace984cdfc943 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10171,7 +10171,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( +@@ -10071,7 +10071,7 @@ void WebContentsImpl::OnFocusedElementChangedInFrame( "WebContentsImpl::OnFocusedElementChangedInFrame", "render_frame_host", frame); RenderWidgetHostViewBase* root_view = diff --git a/patches/chromium/fix_remove_caption-removing_style_call.patch b/patches/chromium/fix_remove_caption-removing_style_call.patch index 9ec10741fd494..06ca62ff53f02 100644 --- a/patches/chromium/fix_remove_caption-removing_style_call.patch +++ b/patches/chromium/fix_remove_caption-removing_style_call.patch @@ -18,7 +18,7 @@ or resizing, but Electron does not seem to run into that issue for opaque frameless windows even with that block commented out. diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 8c13b9db078e690240eca0a48a7c546dcdac3c11..30399c8a81819a57f07702a97f85e3edd7df9d69 100644 +index 06fc8190385139f165bad0c2da2fb22d7a2c3d76..1a10bd1a6c527633f97d6eee6525b1e45a3fcd3d 100644 --- a/ui/views/win/hwnd_message_handler.cc +++ b/ui/views/win/hwnd_message_handler.cc @@ -1800,7 +1800,23 @@ LRESULT HWNDMessageHandler::OnCreate(CREATESTRUCT* create_struct) { diff --git a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch index 7dbf4bee82036..da4242d32e2a8 100644 --- a/patches/chromium/fix_restore_original_resize_performance_on_macos.patch +++ b/patches/chromium/fix_restore_original_resize_performance_on_macos.patch @@ -11,10 +11,10 @@ This patch should be upstreamed as a conditional revert of the logic in desktop vs mobile runtimes. i.e. restore the old logic only on desktop platforms diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index a3cbb6cb369c2f250c702a0117e36e9aee04068c..05afca0c5560297b3fc4b993e872b6f296971615 100644 +index eed851d277c5efa2d5ca594e18eaf7dff3a5d11d..372c81bdfcf4d70dbd5b131a1b02af6b5c878cbe 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2134,9 +2134,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { +@@ -2135,9 +2135,8 @@ RenderWidgetHostImpl::GetWidgetInputHandler() { void RenderWidgetHostImpl::NotifyScreenInfoChanged() { // The resize message (which may not happen immediately) will carry with it // the screen info as well as the new size (if the screen has changed scale diff --git a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch index b4988630544a3..1c1f0bda21e16 100644 --- a/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch +++ b/patches/chromium/mas_avoid_private_macos_api_usage.patch.patch @@ -582,7 +582,7 @@ index d83f420d25e2c108ad400ebecae02b1ac327c058..77852c5c315ac09dddb7227adf3b840e return kAttributes; } diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 933abcca124aed9d1d621ff02533b2f7cc71c7d7..1f77801262614d36b7803837ce43ef2a499a7a97 100644 +index 6d414afa34803b997ccd363f45fab073c736a5ff..5e31cf33f58efe376396f8d178e0f9930832466a 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn @@ -342,6 +342,7 @@ source_set("browser") { diff --git a/patches/chromium/printing.patch b/patches/chromium/printing.patch index ea054be3fcf1c..8ae0dd18bc87b 100644 --- a/patches/chromium/printing.patch +++ b/patches/chromium/printing.patch @@ -887,10 +887,10 @@ index 97cb6458bc9eec767db89b56abfc5f4b4136ff7b..d9a0b343158b8464b5c9aa8e0e655c0b ScriptingThrottler scripting_throttler_; diff --git a/content/browser/BUILD.gn b/content/browser/BUILD.gn -index 1f77801262614d36b7803837ce43ef2a499a7a97..de5e27c2960ffd7253aa1dfae46dbc51ca57d2ce 100644 +index 5e31cf33f58efe376396f8d178e0f9930832466a..4468d19c0a2587dc678873aef949f54fdf4cb27f 100644 --- a/content/browser/BUILD.gn +++ b/content/browser/BUILD.gn -@@ -3171,8 +3171,9 @@ source_set("browser") { +@@ -3173,8 +3173,9 @@ source_set("browser") { "//ppapi/shared_impl", ] diff --git a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch index 2b3ac237b2556..733ee1e4ca6ca 100644 --- a/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch +++ b/patches/chromium/refactor_expose_cursor_changes_to_the_webcontentsobserver.patch @@ -8,7 +8,7 @@ Chrome moved the SetCursor IPC message to mojo, which we use to tell OSR about ` Refs: https://chromium-review.googlesource.com/c/chromium/src/+/2172779 diff --git a/content/browser/renderer_host/render_widget_host_delegate.h b/content/browser/renderer_host/render_widget_host_delegate.h -index a54a0dedf8ef1cfffa4e80a4707debed0e83d277..e66e71fdbabb40a5307b12cd8965e773e76c04fd 100644 +index 09eadc003aab03151a303b648a16e3ea50472f3e..c03ab618ca94e871558408f7bcf432ddc6fadc68 100644 --- a/content/browser/renderer_host/render_widget_host_delegate.h +++ b/content/browser/renderer_host/render_widget_host_delegate.h @@ -28,6 +28,7 @@ @@ -30,10 +30,10 @@ index a54a0dedf8ef1cfffa4e80a4707debed0e83d277..e66e71fdbabb40a5307b12cd8965e773 // RenderWidgetHost on the primary main frame, and false otherwise. virtual bool IsWidgetForPrimaryMainFrame(RenderWidgetHostImpl*); diff --git a/content/browser/renderer_host/render_widget_host_impl.cc b/content/browser/renderer_host/render_widget_host_impl.cc -index cdfdd322ffb2e61d5480ac7c88dba35a1cc1b5b9..a3cbb6cb369c2f250c702a0117e36e9aee04068c 100644 +index 624094ba6459f3663a12f868c4cb47dfa9f8dce1..eed851d277c5efa2d5ca594e18eaf7dff3a5d11d 100644 --- a/content/browser/renderer_host/render_widget_host_impl.cc +++ b/content/browser/renderer_host/render_widget_host_impl.cc -@@ -2068,6 +2068,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { +@@ -2069,6 +2069,9 @@ void RenderWidgetHostImpl::SetCursor(const ui::Cursor& cursor) { if (view_) { view_->UpdateCursor(cursor); } @@ -44,10 +44,10 @@ index cdfdd322ffb2e61d5480ac7c88dba35a1cc1b5b9..a3cbb6cb369c2f250c702a0117e36e9a void RenderWidgetHostImpl::ShowContextMenuAtPoint( diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 811d137c4b77d3347dc8de5bb6207646c952f23b..33abfcd326148f32eff2266a4545345e4a561a4e 100644 +index a45bf004f5096809b5fc7b70faa0b7fa7b257049..c034b546289ba069194ad65d3d3bc0703a3afe9c 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -6069,6 +6069,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { +@@ -6045,6 +6045,11 @@ TextInputManager* WebContentsImpl::GetTextInputManager() { return text_input_manager_.get(); } @@ -60,10 +60,10 @@ index 811d137c4b77d3347dc8de5bb6207646c952f23b..33abfcd326148f32eff2266a4545345e RenderWidgetHostImpl* render_widget_host) { return render_widget_host == GetPrimaryMainFrame()->GetRenderWidgetHost(); diff --git a/content/browser/web_contents/web_contents_impl.h b/content/browser/web_contents/web_contents_impl.h -index 478c9dfd9019e7acfa2ad63219a268aa5879670e..54c2a41b7ee21f1e6f022c5818e56e24a52ccbef 100644 +index 183643a2c6658a5821cb8699d5c8b5d33666a5e0..5117a762c0778f54f392b8ffbb400ef4dbd6a323 100644 --- a/content/browser/web_contents/web_contents_impl.h +++ b/content/browser/web_contents/web_contents_impl.h -@@ -1193,6 +1193,7 @@ class CONTENT_EXPORT WebContentsImpl +@@ -1191,6 +1191,7 @@ class CONTENT_EXPORT WebContentsImpl void SendScreenRects() override; void SendActiveState(bool active) override; TextInputManager* GetTextInputManager() override; diff --git a/patches/chromium/refactor_unfilter_unresponsive_events.patch b/patches/chromium/refactor_unfilter_unresponsive_events.patch index 7525fb4b186a9..429dc4371d97a 100644 --- a/patches/chromium/refactor_unfilter_unresponsive_events.patch +++ b/patches/chromium/refactor_unfilter_unresponsive_events.patch @@ -15,10 +15,10 @@ This CL removes these filters so the unresponsive event can still be accessed from our JS event. The filtering is moved into Electron's code. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 51798b8ceb81cf9d374cf594aa6afbcb366f4732..bacfca5b2f54e2db7700bb871fff4f66712f5c32 100644 +index b50e3c2ecb6f9f3322cfd16fc7bcbd8935f863a2..d7afac20523d2900cbefa5ab3ea9f0863780b704 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -10308,25 +10308,13 @@ void WebContentsImpl::RendererUnresponsive( +@@ -10208,25 +10208,13 @@ void WebContentsImpl::RendererUnresponsive( base::RepeatingClosure hang_monitor_restarter) { OPTIONAL_TRACE_EVENT1("content", "WebContentsImpl::RendererUnresponsive", "render_widget_host", render_widget_host); diff --git a/patches/chromium/web_contents.patch b/patches/chromium/web_contents.patch index c5101982d3ffd..b32c18f89d329 100644 --- a/patches/chromium/web_contents.patch +++ b/patches/chromium/web_contents.patch @@ -9,10 +9,10 @@ is needed for OSR. Originally landed in https://github.com/electron/libchromiumcontent/pull/226. diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index 4bb69438947fff73a6905a1ecc1b711986a89124..e745a26a4e877ace994be80c2134147500205d0b 100644 +index e603c0fddbf4efaeb225686c1791ffb581e9e6c0..88d7b948d57f53fcd681856587f79ece991ee8fa 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4103,6 +4103,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -4079,6 +4079,13 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, params.main_frame_name, GetOpener(), primary_main_frame_policy, base::UnguessableToken::Create()); @@ -26,7 +26,7 @@ index 4bb69438947fff73a6905a1ecc1b711986a89124..e745a26a4e877ace994be80c21341475 std::unique_ptr delegate = GetContentClient()->browser()->GetWebContentsViewDelegate(this); -@@ -4113,6 +4120,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, +@@ -4089,6 +4096,7 @@ void WebContentsImpl::Init(const WebContents::CreateParams& params, view_ = CreateWebContentsView(this, std::move(delegate), &render_view_host_delegate_view_); } diff --git a/patches/chromium/webview_fullscreen.patch b/patches/chromium/webview_fullscreen.patch index c0b5efc77afbd..14ea68c8b6f2a 100644 --- a/patches/chromium/webview_fullscreen.patch +++ b/patches/chromium/webview_fullscreen.patch @@ -37,10 +37,10 @@ index d8698f9f37eefa50bf4e29a164b2cc302c32ecdf..3a8dc82b882aa00e9a5430bc8b7ba409 if (had_fullscreen_token && !GetView()->HasFocus()) GetView()->Focus(); diff --git a/content/browser/web_contents/web_contents_impl.cc b/content/browser/web_contents/web_contents_impl.cc -index e745a26a4e877ace994be80c2134147500205d0b..eefecd6b3b9c940c3ae3e9ef40075c4a109878ef 100644 +index 88d7b948d57f53fcd681856587f79ece991ee8fa..374d5f1a1685229865d0f1f1032f36bbcd54e92e 100644 --- a/content/browser/web_contents/web_contents_impl.cc +++ b/content/browser/web_contents/web_contents_impl.cc -@@ -4393,21 +4393,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( +@@ -4369,21 +4369,25 @@ KeyboardEventProcessingResult WebContentsImpl::PreHandleKeyboardEvent( const input::NativeWebKeyboardEvent& event) { OPTIONAL_TRACE_EVENT0(TRACE_DISABLED_BY_DEFAULT("content.verbose"), "WebContentsImpl::PreHandleKeyboardEvent"); @@ -78,7 +78,7 @@ index e745a26a4e877ace994be80c2134147500205d0b..eefecd6b3b9c940c3ae3e9ef40075c4a } bool WebContentsImpl::HandleMouseEvent(const blink::WebMouseEvent& event) { -@@ -4566,7 +4570,7 @@ void WebContentsImpl::EnterFullscreenMode( +@@ -4542,7 +4546,7 @@ void WebContentsImpl::EnterFullscreenMode( OPTIONAL_TRACE_EVENT0("content", "WebContentsImpl::EnterFullscreenMode"); DCHECK(CanEnterFullscreenMode(requesting_frame)); DCHECK(requesting_frame->IsActive()); diff --git a/spec/api-desktop-capturer-spec.ts b/spec/api-desktop-capturer-spec.ts index af1567efe2a46..73124184c2194 100644 --- a/spec/api-desktop-capturer-spec.ts +++ b/spec/api-desktop-capturer-spec.ts @@ -8,18 +8,16 @@ import { setTimeout } from 'node:timers/promises'; import { ifdescribe, ifit } from './lib/spec-helpers'; import { closeAllWindows } from './lib/window-helpers'; -ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('desktopCapturer', () => { - let w: BrowserWindow; - - before(async () => { - w = new BrowserWindow({ show: false, webPreferences: { nodeIntegration: true, contextIsolation: false } }); - await w.loadURL('about:blank'); - }); - - after(closeAllWindows); +function getSourceTypes (): ('window' | 'screen')[] { + if (process.platform === 'linux') { + return ['screen']; + } + return ['window', 'screen']; +} +ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('desktopCapturer', () => { it('should return a non-empty array of sources', async () => { - const sources = await desktopCapturer.getSources({ types: ['window', 'screen'] }); + const sources = await desktopCapturer.getSources({ types: getSourceTypes() }); expect(sources).to.be.an('array').that.is.not.empty(); }); @@ -29,14 +27,15 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt }); it('does not throw an error when called more than once (regression)', async () => { - const sources1 = await desktopCapturer.getSources({ types: ['window', 'screen'] }); + const sources1 = await desktopCapturer.getSources({ types: getSourceTypes() }); expect(sources1).to.be.an('array').that.is.not.empty(); - const sources2 = await desktopCapturer.getSources({ types: ['window', 'screen'] }); + const sources2 = await desktopCapturer.getSources({ types: getSourceTypes() }); expect(sources2).to.be.an('array').that.is.not.empty(); }); - it('responds to subsequent calls of different options', async () => { + // Linux doesn't return any window sources. + ifit(process.platform !== 'linux')('responds to subsequent calls of different options', async () => { const promise1 = desktopCapturer.getSources({ types: ['window'] }); await expect(promise1).to.eventually.be.fulfilled(); @@ -46,11 +45,11 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt // Linux doesn't return any window sources. ifit(process.platform !== 'linux')('returns an empty display_id for window sources', async () => { - const w = new BrowserWindow({ width: 200, height: 200 }); - await w.loadURL('about:blank'); + const w2 = new BrowserWindow({ width: 200, height: 200 }); + await w2.loadURL('about:blank'); const sources = await desktopCapturer.getSources({ types: ['window'] }); - w.destroy(); + w2.destroy(); expect(sources).to.be.an('array').that.is.not.empty(); for (const { display_id: displayId } of sources) { expect(displayId).to.be.a('string').and.be.empty(); @@ -74,7 +73,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt await wShown; const isNonEmpties: boolean[] = (await desktopCapturer.getSources({ - types: ['window', 'screen'], + types: getSourceTypes(), thumbnailSize: { width: 100, height: 100 } })).map(s => s.thumbnail.constructor.name === 'NativeImage' && !s.thumbnail.isEmpty()); @@ -90,7 +89,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt await wShown; const isEmpties: boolean[] = (await desktopCapturer.getSources({ - types: ['window', 'screen'], + types: getSourceTypes(), thumbnailSize: { width: 0, height: 0 } })).map(s => s.thumbnail.constructor.name === 'NativeImage' && s.thumbnail.isEmpty()); @@ -99,29 +98,22 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt expect(isEmpties.every(e => e === true)).to.be.true(); }); - it('getMediaSourceId should match DesktopCapturerSource.id', async function () { - const w = new BrowserWindow({ show: false, width: 100, height: 100, webPreferences: { contextIsolation: false } }); - const wShown = once(w, 'show'); - const wFocused = once(w, 'focus'); - w.show(); - w.focus(); + // Linux doesn't return any window sources. + ifit(process.platform !== 'linux')('getMediaSourceId should match DesktopCapturerSource.id', async function () { + const w2 = new BrowserWindow({ show: false, width: 100, height: 100, webPreferences: { contextIsolation: false } }); + const wShown = once(w2, 'show'); + const wFocused = once(w2, 'focus'); + w2.show(); + w2.focus(); await wShown; await wFocused; - const mediaSourceId = w.getMediaSourceId(); + const mediaSourceId = w2.getMediaSourceId(); const sources = await desktopCapturer.getSources({ types: ['window'], thumbnailSize: { width: 0, height: 0 } }); - w.destroy(); - - // TODO(julien.isorce): investigate why |sources| is empty on the linux - // bots while it is not on my workstation, as expected, with and without - // the --ci parameter. - if (process.platform === 'linux' && sources.length === 0) { - this.skip(); - return; - } + w2.destroy(); expect(sources).to.be.an('array').that.is.not.empty(); const foundSource = sources.find((source) => { @@ -130,18 +122,19 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt expect(mediaSourceId).to.equal(foundSource!.id); }); - it('getSources should not incorrectly duplicate window_id', async function () { - const w = new BrowserWindow({ show: false, width: 100, height: 100, webPreferences: { contextIsolation: false } }); - const wShown = once(w, 'show'); - const wFocused = once(w, 'focus'); - w.show(); - w.focus(); + // Linux doesn't return any window sources. + ifit(process.platform !== 'linux')('getSources should not incorrectly duplicate window_id', async function () { + const w2 = new BrowserWindow({ show: false, width: 100, height: 100, webPreferences: { contextIsolation: false } }); + const wShown = once(w2, 'show'); + const wFocused = once(w2, 'focus'); + w2.show(); + w2.focus(); await wShown; await wFocused; // ensure window_id isn't duplicated in getMediaSourceId, // which uses a different method than getSources - const mediaSourceId = w.getMediaSourceId(); + const mediaSourceId = w2.getMediaSourceId(); const ids = mediaSourceId.split(':'); expect(ids[1]).to.not.equal(ids[2]); @@ -149,15 +142,7 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt types: ['window'], thumbnailSize: { width: 0, height: 0 } }); - w.destroy(); - - // TODO(julien.isorce): investigate why |sources| is empty on the linux - // bots while it is not on my workstation, as expected, with and without - // the --ci parameter. - if (process.platform === 'linux' && sources.length === 0) { - this.skip(); - return; - } + w2.destroy(); expect(sources).to.be.an('array').that.is.not.empty(); for (const source of sources) { @@ -168,19 +153,23 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt // Regression test - see https://github.com/electron/electron/issues/43002 it('does not affect window resizable state', async () => { + const w = new BrowserWindow({ show: false, webPreferences: { nodeIntegration: true, contextIsolation: false } }); + await w.loadURL('about:blank'); w.resizable = false; const wShown = once(w, 'show'); w.show(); await wShown; - const sources = await desktopCapturer.getSources({ types: ['window', 'screen'] }); + const sources = await desktopCapturer.getSources({ types: getSourceTypes() }); expect(sources).to.be.an('array').that.is.not.empty(); expect(w.resizable).to.be.false(); + await closeAllWindows(); }); - it('moveAbove should move the window at the requested place', async function () { + // Linux doesn't return any window sources. + ifit(process.platform !== 'linux')('moveAbove should move the window at the requested place', async function () { // DesktopCapturer.getSources() is guaranteed to return in the correct // z-order from foreground to background. const MAX_WIN = 4; @@ -220,15 +209,6 @@ ifdescribe(!process.arch.includes('arm') && process.platform !== 'win32')('deskt thumbnailSize: { width: 0, height: 0 } }); - // TODO(julien.isorce): investigate why |sources| is empty on the linux - // bots while it is not on my workstation, as expected, with and without - // the --ci parameter. - if (process.platform === 'linux' && sources.length === 0) { - destroyWindows(); - this.skip(); - return; - } - expect(sources).to.be.an('array').that.is.not.empty(); expect(sources.length).to.gte(MAX_WIN); From 3ea4c6c3e7a9b792bc12f42b5d871f7518dc3b7e Mon Sep 17 00:00:00 2001 From: Niklas Wenzel Date: Wed, 18 Jun 2025 04:01:50 +0200 Subject: [PATCH 107/186] fix: utilityProcess running user script after process.exit is called (#47492) fix: utilityProcess running user script after process.exit is called (#47469) * fix: utilityProcess running user script after process.exit is called * docs: update breaking changes * chore: update spec * chore: update spec/api-utility-process-spec.ts * chore: remove interface bound checks --------- Co-authored-by: Robo Co-authored-by: David Sanders --- docs/breaking-changes.md | 10 ++++++++++ shell/services/node/node_service.cc | 9 ++++----- spec/api-utility-process-spec.ts | 20 +++++++++++++++++++ .../api/utility-process/no-js-after-exit.js | 7 +++++++ 4 files changed, 41 insertions(+), 5 deletions(-) create mode 100644 spec/fixtures/api/utility-process/no-js-after-exit.js diff --git a/docs/breaking-changes.md b/docs/breaking-changes.md index 3a88ed3aee4f9..241702667f6ca 100644 --- a/docs/breaking-changes.md +++ b/docs/breaking-changes.md @@ -27,6 +27,16 @@ process.on('unhandledRejection', () => { }) ``` +### Behavior Changed: `process.exit()` kills utility process synchronously + +Calling `process.exit()` in a utility process will now kill the utility process synchronously. +This brings the behavior of `process.exit()` in line with Node.js behavior. + +Please refer to the +[Node.js docs](https://nodejs.org/docs/latest-v22.x/api/process.html#processexitcode) and +[PR #45690](https://github.com/electron/electron/pull/45690) to understand the potential +implications of that, e.g., when calling `console.log()` before `process.exit()`. + ### Behavior Changed: WebUSB and WebSerial Blocklist Support [WebUSB](https://developer.mozilla.org/en-US/docs/Web/API/WebUSB_API) and [Web Serial](https://developer.mozilla.org/en-US/docs/Web/API/Web_Serial_API) now support the [WebUSB Blocklist](https://wicg.github.io/webusb/#blocklist) and [Web Serial Blocklist](https://wicg.github.io/serial/#blocklist) used by Chromium and outlined in their respective specifications. diff --git a/shell/services/node/node_service.cc b/shell/services/node/node_service.cc index fd42dedad309d..7acca3c991ad6 100644 --- a/shell/services/node/node_service.cc +++ b/shell/services/node/node_service.cc @@ -9,6 +9,7 @@ #include "base/command_line.h" #include "base/no_destructor.h" +#include "base/process/process.h" #include "base/strings/utf_string_conversions.h" #include "electron/mas.h" #include "services/network/public/cpp/wrapper_shared_url_loader_factory.h" @@ -99,8 +100,6 @@ NodeService::~NodeService() { ParentPort::GetInstance()->Close(); js_env_->DestroyMicrotasksRunner(); node::Stop(node_env_.get(), node::StopFlags::kDoNotTerminateIsolate); - } - if (g_client_remote.is_bound()) { g_client_remote.reset(); } } @@ -147,12 +146,12 @@ void NodeService::Initialize( node::SetProcessExitHandler( node_env_.get(), [this](node::Environment* env, int exit_code) { // Destroy node platform. - env->set_trace_sync_io(false); + node_env_stopped_ = true; ParentPort::GetInstance()->Close(); js_env_->DestroyMicrotasksRunner(); - node::Stop(env, node::StopFlags::kDoNotTerminateIsolate); - node_env_stopped_ = true; + g_client_remote.reset(); receiver_.ResetWithReason(exit_code, "process_exit_termination"); + node::DefaultProcessExitHandler(env, exit_code); }); node_env_->set_trace_sync_io(node_env_->options()->trace_sync_io); diff --git a/spec/api-utility-process-spec.ts b/spec/api-utility-process-spec.ts index aa75aedda8671..dfd62945ec6ba 100644 --- a/spec/api-utility-process-spec.ts +++ b/spec/api-utility-process-spec.ts @@ -129,6 +129,26 @@ describe('utilityProcess module', () => { expect(code).to.equal(exitCode); }); + it('does not run JS after process.exit is called', async () => { + const file = path.join(os.tmpdir(), `no-js-after-exit-log-${Math.random()}`); + const child = utilityProcess.fork(path.join(fixturesPath, 'no-js-after-exit.js'), [`--testPath=${file}`]); + const [code] = await once(child, 'exit'); + expect(code).to.equal(1); + let handle = null; + const lines = []; + try { + handle = await fs.open(file); + for await (const line of handle.readLines()) { + lines.push(line); + } + } finally { + await handle?.close(); + await fs.rm(file, { force: true }); + } + expect(lines.length).to.equal(1); + expect(lines[0]).to.equal('before exit'); + }); + // 32-bit system will not have V8 Sandbox enabled. // WoA testing does not have VS toolchain configured to build native addons. ifit(process.arch !== 'ia32' && process.arch !== 'arm' && !isWindowsOnArm)('emits \'error\' when fatal error is triggered from V8', async () => { diff --git a/spec/fixtures/api/utility-process/no-js-after-exit.js b/spec/fixtures/api/utility-process/no-js-after-exit.js new file mode 100644 index 0000000000000..644019006b85f --- /dev/null +++ b/spec/fixtures/api/utility-process/no-js-after-exit.js @@ -0,0 +1,7 @@ +const { writeFileSync } = require('node:fs'); + +const arg = process.argv[2]; +const file = arg.split('=')[1]; +writeFileSync(file, 'before exit'); +process.exit(1); +writeFileSync(file, 'after exit'); From 2f1dfc73acb54b862361d3d23ccb4b30298f28d4 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 18 Jun 2025 20:47:06 +0200 Subject: [PATCH 108/186] feat: support `HIDDevice.collections` (#47483) * feat: support HIDDevice.collections Co-authored-by: Shelley Vohr * Update docs/api/structures/hid-device.md Co-authored-by: Erick Zhao Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- docs/api/structures/hid-device.md | 8 + shell/browser/hid/hid_chooser_context.cc | 178 +++++++++++++++++++++++ 2 files changed, 186 insertions(+) diff --git a/docs/api/structures/hid-device.md b/docs/api/structures/hid-device.md index a6a097061dc22..7c8712cd8605b 100644 --- a/docs/api/structures/hid-device.md +++ b/docs/api/structures/hid-device.md @@ -6,3 +6,11 @@ * `productId` Integer - The USB product ID. * `serialNumber` string (optional) - The USB device serial number. * `guid` string (optional) - Unique identifier for the HID interface. A device may have multiple HID interfaces. +* `collections` Object[] - an array of report formats. See [MDN documentation](https://developer.mozilla.org/en-US/docs/Web/API/HIDDevice/collections) for more. + * `usage` Integer - An integer representing the usage ID component of the HID usage associated with this collection. + * `usagePage` Integer - An integer representing the usage page component of the HID usage associated with this collection. + * `type` Integer - An 8-bit value representing the collection type, which describes a different relationship between the grouped items. + * `children` Object[] - An array of sub-collections which takes the same format as a top-level collection. + * `inputReports` Object[] - An array of inputReport items which represent individual input reports described in this collection. + * `outputReports` Object[] - An array of outputReport items which represent individual output reports described in this collection. + * `featureReports` Object[] - An array of featureReport items which represent individual feature reports described in this collection. diff --git a/shell/browser/hid/hid_chooser_context.cc b/shell/browser/hid/hid_chooser_context.cc index c1ad43c8f97f8..fa6ea210c0b40 100644 --- a/shell/browser/hid/hid_chooser_context.cc +++ b/shell/browser/hid/hid_chooser_context.cc @@ -36,6 +36,175 @@ #include "extensions/common/constants.h" #endif // BUILDFLAG(ENABLE_ELECTRON_EXTENSIONS) +namespace { + +// Adapted from third_party/blink/renderer/modules/hid/hid_device.cc. +enum HidUnitSystem { + // none: No unit system + kUnitSystemNone = 0x00, + // si-linear: Centimeter, Gram, Seconds, Kelvin, Ampere, Candela + kUnitSystemSILinear = 0x01, + // si-rotation: Radians, Gram, Seconds, Kelvin, Ampere, Candela + kUnitSystemSIRotation = 0x02, + // english-linear: Inch, Slug, Seconds, Fahrenheit, Ampere, Candela + kUnitSystemEnglishLinear = 0x03, + // english-linear: Degrees, Slug, Seconds, Fahrenheit, Ampere, Candela + kUnitSystemEnglishRotation = 0x04, + // vendor-defined unit system + kUnitSystemVendorDefined = 0x0f, +}; + +// Adapted from third_party/blink/renderer/modules/hid/hid_device.cc. +int ConvertHidUsageAndPageToInt(const device::mojom::HidUsageAndPage& usage) { + return static_cast((usage.usage_page) << 16 | usage.usage); +} + +// Adapted from third_party/blink/renderer/modules/hid/hid_device.cc. +int8_t UnitFactorExponentToInt(uint8_t unit_factor_exponent) { + DCHECK_LE(unit_factor_exponent, 0x0f); + // Values from 0x08 to 0x0f encode negative exponents. + if (unit_factor_exponent > 0x08) + return static_cast(unit_factor_exponent) - 16; + return unit_factor_exponent; +} + +// Adapted from third_party/blink/renderer/modules/hid/hid_device.cc. +std::string UnitSystemToString(uint8_t unit) { + DCHECK_LE(unit, 0x0f); + switch (unit) { + case kUnitSystemNone: + return "none"; + case kUnitSystemSILinear: + return "si-linear"; + case kUnitSystemSIRotation: + return "si-rotation"; + case kUnitSystemEnglishLinear: + return "english-linear"; + case kUnitSystemEnglishRotation: + return "english-rotation"; + case kUnitSystemVendorDefined: + return "vendor-defined"; + default: + break; + } + // Values other than those defined in HidUnitSystem are reserved by the spec. + return "reserved"; +} + +// Adapted from third_party/blink/renderer/modules/hid/hid_device.cc. +base::Value::Dict HidReportItemToValue( + const device::mojom::HidReportItem& item) { + base::Value::Dict dict; + + dict.Set("hasNull", item.has_null_position); + dict.Set("hasPreferredState", !item.no_preferred_state); + dict.Set("isAbsolute", !item.is_relative); + dict.Set("isArray", !item.is_variable); + dict.Set("isBufferedBytes", item.is_buffered_bytes); + dict.Set("isConstant", item.is_constant); + dict.Set("isLinear", !item.is_non_linear); + dict.Set("isRange", item.is_range); + dict.Set("isVolatile", item.is_volatile); + dict.Set("logicalMinimum", item.logical_minimum); + dict.Set("logicalMaximum", item.logical_maximum); + dict.Set("physicalMinimum", item.physical_minimum); + dict.Set("physicalMaximum", item.physical_maximum); + dict.Set("reportCount", static_cast(item.report_count)); + dict.Set("reportSize", static_cast(item.report_size)); + + dict.Set("unitExponent", UnitFactorExponentToInt(item.unit_exponent & 0x0f)); + dict.Set("unitFactorCurrentExponent", + UnitFactorExponentToInt((item.unit >> 20) & 0x0f)); + dict.Set("unitFactorLengthExponent", + UnitFactorExponentToInt((item.unit >> 4) & 0x0f)); + dict.Set("unitFactorLuminousIntensityExponent", + UnitFactorExponentToInt((item.unit >> 24) & 0x0f)); + dict.Set("unitFactorMassExponent", + UnitFactorExponentToInt((item.unit >> 8) & 0x0f)); + dict.Set("unitFactorTemperatureExponent", + UnitFactorExponentToInt((item.unit >> 16) & 0x0f)); + dict.Set("unitFactorTimeExponent", + UnitFactorExponentToInt((item.unit >> 12) & 0x0f)); + dict.Set("unitSystem", UnitSystemToString(item.unit & 0x0f)); + + if (item.is_range) { + dict.Set("usageMinimum", ConvertHidUsageAndPageToInt(*item.usage_minimum)); + dict.Set("usageMaximum", ConvertHidUsageAndPageToInt(*item.usage_maximum)); + } else { + base::Value::List usages_list; + for (const auto& usage : item.usages) { + usages_list.Append(ConvertHidUsageAndPageToInt(*usage)); + } + dict.Set("usages", std::move(usages_list)); + } + + dict.Set("wrap", item.wrap); + + return dict; +} + +// Adapted from third_party/blink/renderer/modules/hid/hid_device.cc. +base::Value::Dict HidReportDescriptionToValue( + const device::mojom::HidReportDescription& report) { + base::Value::Dict dict; + dict.Set("reportId", static_cast(report.report_id)); + + base::Value::List items_list; + for (const auto& item : report.items) { + items_list.Append(base::Value(HidReportItemToValue(*item))); + } + dict.Set("items", std::move(items_list)); + + return dict; +} + +// Adapted from third_party/blink/renderer/modules/hid/hid_device.cc. +base::Value::Dict HidCollectionInfoToValue( + const device::mojom::HidCollectionInfo& collection) { + base::Value::Dict dict; + + // Usage information + dict.Set("usage", collection.usage->usage); + dict.Set("usagePage", collection.usage->usage_page); + + // Collection type + dict.Set("collectionType", static_cast(collection.collection_type)); + + // Input reports + base::Value::List input_reports_list; + for (const auto& report : collection.input_reports) { + input_reports_list.Append( + base::Value(HidReportDescriptionToValue(*report))); + } + dict.Set("inputReports", std::move(input_reports_list)); + + // Output reports + base::Value::List output_reports_list; + for (const auto& report : collection.output_reports) { + output_reports_list.Append( + base::Value(HidReportDescriptionToValue(*report))); + } + dict.Set("outputReports", std::move(output_reports_list)); + + // Feature reports + base::Value::List feature_reports_list; + for (const auto& report : collection.feature_reports) { + feature_reports_list.Append( + base::Value(HidReportDescriptionToValue(*report))); + } + dict.Set("featureReports", std::move(feature_reports_list)); + + // Child collections (recursive) + base::Value::List children_list; + for (const auto& child : collection.children) { + children_list.Append(base::Value(HidCollectionInfoToValue(*child))); + } + dict.Set("children", std::move(children_list)); + + return dict; +} +} // namespace + namespace electron { HidChooserContext::HidChooserContext(ElectronBrowserContext* context) @@ -77,6 +246,7 @@ base::Value HidChooserContext::DeviceInfoToValue( base::UTF16ToUTF8(HidChooserContext::DisplayNameFromDeviceInfo(device))); value.Set(kDeviceVendorIdKey, device.vendor_id); value.Set(kDeviceProductIdKey, device.product_id); + if (HidChooserContext::CanStorePersistentEntry(device)) { // Use the USB serial number as a persistent identifier. If it is // unavailable, only ephemeral permissions may be granted. @@ -87,6 +257,14 @@ base::Value HidChooserContext::DeviceInfoToValue( // and must be granted again each time the device is connected. value.Set(kHidGuidKey, device.guid); } + + // Convert collections array + base::Value::List collections_list; + for (const auto& collection : device.collections) { + collections_list.Append(base::Value(HidCollectionInfoToValue(*collection))); + } + value.Set("collections", std::move(collections_list)); + return base::Value(std::move(value)); } From 221f5ee3d6777584ff0a6110bea29956d07d618e Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Thu, 19 Jun 2025 18:47:59 -0400 Subject: [PATCH 109/186] chore: bump chromium to 138.0.7204.35 (37-x-y) (#47504) * chore: bump chromium in DEPS to 138.0.7204.35 * chore: update patches --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- DEPS | 2 +- patches/chromium/custom_protocols_plzserviceworker.patch | 8 ++++---- ...eat_corner_smoothing_css_rule_and_blink_painting.patch | 2 +- .../feat_expose_raw_response_headers_from_urlloader.patch | 4 ++-- ...ect_the_first_menu_item_when_opened_via_keyboard.patch | 4 ++-- 5 files changed, 10 insertions(+), 10 deletions(-) diff --git a/DEPS b/DEPS index 2e5288ebd25b0..58432b0d9f170 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.23', + '138.0.7204.35', 'node_version': 'v22.16.0', 'nan_version': diff --git a/patches/chromium/custom_protocols_plzserviceworker.patch b/patches/chromium/custom_protocols_plzserviceworker.patch index fb4b40f1cf3ff..c55e91a0d7bd0 100644 --- a/patches/chromium/custom_protocols_plzserviceworker.patch +++ b/patches/chromium/custom_protocols_plzserviceworker.patch @@ -8,10 +8,10 @@ Allow registering custom protocols to handle service worker main script fetching Refs https://bugs.chromium.org/p/chromium/issues/detail?id=996511 diff --git a/content/browser/service_worker/service_worker_context_wrapper.cc b/content/browser/service_worker/service_worker_context_wrapper.cc -index bc49553c298d548a3c09a5e65a44cac1a42e893e..fd11dbf8117cc173fd8bb268b391ddbb8ad36f49 100644 +index 8d92bd66121e43992a1e26f7d5860b803ec8c3cb..edbf15cdbc45918d5ec86220cfe8c5398fa1af2c 100644 --- a/content/browser/service_worker/service_worker_context_wrapper.cc +++ b/content/browser/service_worker/service_worker_context_wrapper.cc -@@ -1972,6 +1972,26 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -1979,6 +1979,26 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( loader_factory_bundle_info = context()->loader_factory_bundle_for_update_check()->Clone(); @@ -38,7 +38,7 @@ index bc49553c298d548a3c09a5e65a44cac1a42e893e..fd11dbf8117cc173fd8bb268b391ddbb if (auto* config = content::WebUIConfigMap::GetInstance().GetConfig( browser_context(), scope)) { // If this is a Service Worker for a WebUI, the WebUI's URLDataSource -@@ -1991,9 +2011,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -1998,9 +2018,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( features::kEnableServiceWorkersForChromeScheme) && scope.scheme_piece() == kChromeUIScheme) { config->RegisterURLDataSource(browser_context()); @@ -49,7 +49,7 @@ index bc49553c298d548a3c09a5e65a44cac1a42e893e..fd11dbf8117cc173fd8bb268b391ddbb .emplace(kChromeUIScheme, CreateWebUIServiceWorkerLoaderFactory( browser_context(), kChromeUIScheme, base::flat_set())); -@@ -2001,9 +2019,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( +@@ -2008,9 +2026,7 @@ ServiceWorkerContextWrapper::GetLoaderFactoryForBrowserInitiatedRequest( features::kEnableServiceWorkersForChromeUntrusted) && scope.scheme_piece() == kChromeUIUntrustedScheme) { config->RegisterURLDataSource(browser_context()); diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index 448182b8d3b8a..0be7bdc58ffa5 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -307,7 +307,7 @@ index 2c2f4f405074e5baa4a26f255283404f86b40e21..ebeb7d6988ee9e6a4e78cb82fc01fdad ContouredRect PixelSnappedContouredBorderInternal( diff --git a/third_party/blink/renderer/platform/BUILD.gn b/third_party/blink/renderer/platform/BUILD.gn -index e8db5553065fd9a8ea03ec9d6cee136a8ea666dc..05eafec9e86846469e1877fe2a84b75a0dfe23ee 100644 +index 0b166b8dc52c87d41d4e0a9c7be04d10ef67ca97..67b634759de01995a99a2bb89eb20ad7e6651b42 100644 --- a/third_party/blink/renderer/platform/BUILD.gn +++ b/third_party/blink/renderer/platform/BUILD.gn @@ -1652,6 +1652,8 @@ component("platform") { diff --git a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch index 5d06ea2e34675..ac87b3d95c025 100644 --- a/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch +++ b/patches/chromium/feat_expose_raw_response_headers_from_urlloader.patch @@ -49,7 +49,7 @@ index df29c7cb739a488684c0c50bc5343df101911a31..86b5576c9c10e5544347117e4f6b09d7 mojo::PendingRemote trust_token_observer; mojo::PendingRemote diff --git a/services/network/public/cpp/url_request_mojom_traits.cc b/services/network/public/cpp/url_request_mojom_traits.cc -index 1fbe54bda8198423b42cb5eba291d7346a76873c..71b58ec4e11317a4da1c89d9407ab439ff1629c3 100644 +index 088517d1a9800de0d09c745bbe1ef2fe416c3425..2303ede53f1ee7a827befec560069d97601c2b80 100644 --- a/services/network/public/cpp/url_request_mojom_traits.cc +++ b/services/network/public/cpp/url_request_mojom_traits.cc @@ -50,6 +50,7 @@ bool StructTraits>(); out->trust_token_observer = data.TakeTrustTokenObserver< diff --git a/services/network/public/cpp/url_request_mojom_traits.h b/services/network/public/cpp/url_request_mojom_traits.h -index 1d6f7cb0347c2d1156052f43b82f22130c4750aa..ef6625a9148107772f94d2f62478914fc84d6b89 100644 +index 45defbfca47574ed002052a2ba2b1517a3ea89f4..a4f7a0cc7346b2e413cec1f56ec1d0484f94ed34 100644 --- a/services/network/public/cpp/url_request_mojom_traits.h +++ b/services/network/public/cpp/url_request_mojom_traits.h @@ -72,6 +72,10 @@ struct COMPONENT_EXPORT(NETWORK_CPP_BASE) diff --git a/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch b/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch index 347b6e6a2a01f..5ab66964901ef 100644 --- a/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch +++ b/patches/chromium/fix_select_the_first_menu_item_when_opened_via_keyboard.patch @@ -6,7 +6,7 @@ Subject: fix: select the first menu item when opened via keyboard This fixes an accessibility issue where the root view is 'focused' to the screen reader instead of the first menu item as with all other native menus. This patch will be upstreamed. diff --git a/ui/views/controls/menu/menu_controller.cc b/ui/views/controls/menu/menu_controller.cc -index 05dfc40b27072ee8f67930508e9005a9ba569348..9d5ad3940c1dd2228cc651d6d99cb52137626a7e 100644 +index d3e06148b22f06e6676bcda5fd8907595389887e..35f22b679494940ae1b1d64fa4eb17c41c0cc623 100644 --- a/ui/views/controls/menu/menu_controller.cc +++ b/ui/views/controls/menu/menu_controller.cc @@ -711,6 +711,16 @@ void MenuController::Run(Widget* parent, @@ -26,7 +26,7 @@ index 05dfc40b27072ee8f67930508e9005a9ba569348..9d5ad3940c1dd2228cc651d6d99cb521 if (button_controller) { pressed_lock_ = button_controller->TakeLock( false, ui::LocatedEvent::FromIfValid(event)); -@@ -2440,19 +2450,15 @@ void MenuController::OpenMenuImpl(MenuItemView* item, bool show) { +@@ -2426,19 +2436,15 @@ void MenuController::OpenMenuImpl(MenuItemView* item, bool show) { } item->GetSubmenu()->ShowAt(params); From cfa2efe0c27508dc48047181ec354ad3f9c2b05d Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 23 Jun 2025 12:21:38 +0200 Subject: [PATCH 110/186] feat: add support for --no-experimental-global-navigator (#47418) chore: add support for --no-experimental-global-navigator Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: deepak1556 --- docs/api/command-line-switches.md | 5 ++++ shell/common/node_bindings.cc | 1 + spec/api-utility-process-spec.ts | 28 +++++++++++++++++++ .../fixtures/api/utility-process/navigator.js | 1 + 4 files changed, 35 insertions(+) create mode 100644 spec/fixtures/api/utility-process/navigator.js diff --git a/docs/api/command-line-switches.md b/docs/api/command-line-switches.md index 8026d9351d375..e5ab9dcbe94d7 100644 --- a/docs/api/command-line-switches.md +++ b/docs/api/command-line-switches.md @@ -325,6 +325,10 @@ Set the directory to which all Node.js diagnostic output files are written. Defa Affects the default output directory of [v8.setHeapSnapshotNearHeapLimit](https://nodejs.org/docs/latest/api/v8.html#v8setheapsnapshotnearheaplimitlimit). +### `--no-experimental-global-navigator` + +Disable exposition of [Navigator API][] on the global scope from Node.js. + [app]: app.md [append-switch]: command-line.md#commandlineappendswitchswitch-value [debugging-main-process]: ../tutorial/debugging-main-process.md @@ -333,3 +337,4 @@ Affects the default output directory of [v8.setHeapSnapshotNearHeapLimit](https: [play-silent-audio]: https://github.com/atom/atom/pull/9485/files [ready]: app.md#event-ready [severities]: https://source.chromium.org/chromium/chromium/src/+/main:base/logging.h?q=logging::LogSeverity&ss=chromium +[Navigator API]: https://github.com/nodejs/node/blob/main/doc/api/globals.md#navigator diff --git a/shell/common/node_bindings.cc b/shell/common/node_bindings.cc index 4ff3fda19c1f8..c1b1b3e4ef624 100644 --- a/shell/common/node_bindings.cc +++ b/shell/common/node_bindings.cc @@ -375,6 +375,7 @@ bool IsAllowedOption(const std::string_view option) { "--throw-deprecation", "--trace-deprecation", "--trace-warnings", + "--no-experimental-global-navigator", }); if (debug_options.contains(option)) diff --git a/spec/api-utility-process-spec.ts b/spec/api-utility-process-spec.ts index dfd62945ec6ba..5a132a42ec913 100644 --- a/spec/api-utility-process-spec.ts +++ b/spec/api-utility-process-spec.ts @@ -800,5 +800,33 @@ describe('utilityProcess module', () => { expect(stat.size).to.be.greaterThan(0); await fs.rm(tmpDir, { recursive: true }); }); + + it('supports --no-experimental-global-navigator flag', async () => { + { + const child = utilityProcess.fork(path.join(fixturesPath, 'navigator.js'), [], { + stdio: 'ignore' + }); + await once(child, 'spawn'); + const [data] = await once(child, 'message'); + expect(data).to.be.true(); + const exit = once(child, 'exit'); + expect(child.kill()).to.be.true(); + await exit; + } + { + const child = utilityProcess.fork(path.join(fixturesPath, 'navigator.js'), [], { + stdio: 'ignore', + execArgv: [ + '--no-experimental-global-navigator' + ] + }); + await once(child, 'spawn'); + const [data] = await once(child, 'message'); + expect(data).to.be.false(); + const exit = once(child, 'exit'); + expect(child.kill()).to.be.true(); + await exit; + } + }); }); }); diff --git a/spec/fixtures/api/utility-process/navigator.js b/spec/fixtures/api/utility-process/navigator.js new file mode 100644 index 0000000000000..c7bfafb07c54c --- /dev/null +++ b/spec/fixtures/api/utility-process/navigator.js @@ -0,0 +1 @@ +process.parentPort.postMessage(typeof navigator === 'object'); From 6ce5f889406b29ac514c74ae2505d5cbfdeb6043 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 23 Jun 2025 14:39:56 +0200 Subject: [PATCH 111/186] build: update cache action to latest (#47520) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- .github/actions/checkout/action.yml | 2 +- .github/actions/install-dependencies/action.yml | 2 +- .github/actions/restore-cache-azcopy/action.yml | 6 +++--- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/actions/checkout/action.yml b/.github/actions/checkout/action.yml index 49a08eead649d..9edf46b877fa1 100644 --- a/.github/actions/checkout/action.yml +++ b/.github/actions/checkout/action.yml @@ -43,7 +43,7 @@ runs: curl --unix-socket /var/run/sas/sas.sock --fail "http://foo/$CACHE_FILE?platform=${{ inputs.target-platform }}" > sas-token - name: Save SAS Key if: ${{ inputs.generate-sas-token == 'true' }} - uses: actions/cache/save@d4323d4df104b026a6aa633fdb11d772146be0bf + uses: actions/cache/save@5a3ec84eff668545956fd18022155c47e93e2684 # v4.2.3 with: path: sas-token key: sas-key-${{ inputs.target-platform }}-${{ github.run_number }}-${{ github.run_attempt }} diff --git a/.github/actions/install-dependencies/action.yml b/.github/actions/install-dependencies/action.yml index 25f288c2a7fa1..ff0f5581472db 100644 --- a/.github/actions/install-dependencies/action.yml +++ b/.github/actions/install-dependencies/action.yml @@ -7,7 +7,7 @@ runs: shell: bash id: yarn-cache-dir-path run: echo "dir=$(node src/electron/script/yarn cache dir)" >> $GITHUB_OUTPUT - - uses: actions/cache@1bd1e32a3bdc45362d1e726936510720a7c30a57 + - uses: actions/cache@5a3ec84eff668545956fd18022155c47e93e2684 # v4.2.3 id: yarn-cache with: path: ${{ steps.yarn-cache-dir-path.outputs.dir }} diff --git a/.github/actions/restore-cache-azcopy/action.yml b/.github/actions/restore-cache-azcopy/action.yml index 4c34ba496340b..22e82e0f97843 100644 --- a/.github/actions/restore-cache-azcopy/action.yml +++ b/.github/actions/restore-cache-azcopy/action.yml @@ -8,14 +8,14 @@ runs: steps: - name: Obtain SAS Key continue-on-error: true - uses: actions/cache/restore@d4323d4df104b026a6aa633fdb11d772146be0bf + uses: actions/cache/restore@5a3ec84eff668545956fd18022155c47e93e2684 # v4.2.3 with: path: sas-token key: sas-key-${{ inputs.target-platform }}-${{ github.run_number }}-1 enableCrossOsArchive: true - name: Obtain SAS Key continue-on-error: true - uses: actions/cache/restore@d4323d4df104b026a6aa633fdb11d772146be0bf + uses: actions/cache/restore@5a3ec84eff668545956fd18022155c47e93e2684 # v4.2.3 with: path: sas-token key: sas-key-${{ inputs.target-platform }}-${{ github.run_number }}-${{ github.run_attempt }} @@ -32,7 +32,7 @@ runs: shell: bash command: | sas_token=$(cat sas-token) - if [ -z $sas-token ]; then + if [ -z "$sas_token" ]; then echo "SAS Token not found; exiting src cache download early..." exit 1 else From d4e22c97b26d7c42d16c8f27d6ec569439607b99 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 23 Jun 2025 14:40:04 +0200 Subject: [PATCH 112/186] build: combine dependent libc patch (#47521) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- patches/chromium/.patches | 1 - ...bcxx_abi_unstable_false_for_electron.patch | 8 +++++-- ...e_wrap_iter_in_string_view_and_array.patch | 22 ------------------- 3 files changed, 6 insertions(+), 25 deletions(-) delete mode 100644 patches/chromium/fix_enable_wrap_iter_in_string_view_and_array.patch diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 471d0813543ac..42ea65a667cc0 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -138,7 +138,6 @@ ignore_parse_errors_for_resolveshortcutproperties.patch feat_add_signals_when_embedder_cleanup_callbacks_run_for.patch feat_separate_content_settings_callback_for_sync_and_async_clipboard.patch fix_win32_synchronous_spellcheck.patch -fix_enable_wrap_iter_in_string_view_and_array.patch fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch diff --git a/patches/chromium/build_make_libcxx_abi_unstable_false_for_electron.patch b/patches/chromium/build_make_libcxx_abi_unstable_false_for_electron.patch index 172a0c2fe5a2c..fa9cab2791a46 100644 --- a/patches/chromium/build_make_libcxx_abi_unstable_false_for_electron.patch +++ b/patches/chromium/build_make_libcxx_abi_unstable_false_for_electron.patch @@ -5,16 +5,20 @@ Subject: build: make libcxx_abi_unstable false for electron https://nornagon.medium.com/a-libc-odyssey-973e51649063 +See also https://github.com/electron/electron/issues/45810#issuecomment-2691417213. + diff --git a/buildtools/third_party/libc++/__config_site b/buildtools/third_party/libc++/__config_site -index 67075bd8b4d42e6e6d651cb0988d64eccb64cc23..e240ff6fff94a6cebf8662996712fe7eb22e5fff 100644 +index 67075bd8b4d42e6e6d651cb0988d64eccb64cc23..ddf1693002aa171b3d91aa4ef08f5b360e4adddc 100644 --- a/buildtools/third_party/libc++/__config_site +++ b/buildtools/third_party/libc++/__config_site -@@ -18,7 +18,7 @@ +@@ -18,7 +18,9 @@ // _LIBCPP_ABI_NAMESPACE to a shorter value. #define _LIBCPP_ABI_NAMESPACE __Cr -#define _LIBCPP_ABI_VERSION 2 +#define _LIBCPP_ABI_VERSION 1 ++#define _LIBCPP_ABI_USE_WRAP_ITER_IN_STD_ARRAY ++#define _LIBCPP_ABI_USE_WRAP_ITER_IN_STD_STRING_VIEW #define _LIBCPP_ABI_FORCE_ITANIUM 0 #define _LIBCPP_ABI_FORCE_MICROSOFT 0 diff --git a/patches/chromium/fix_enable_wrap_iter_in_string_view_and_array.patch b/patches/chromium/fix_enable_wrap_iter_in_string_view_and_array.patch deleted file mode 100644 index 2c8066b61326a..0000000000000 --- a/patches/chromium/fix_enable_wrap_iter_in_string_view_and_array.patch +++ /dev/null @@ -1,22 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: deepak1556 -Date: Sat, 1 Mar 2025 05:11:41 +0900 -Subject: fix: enable __wrap_iter in string_view and array - -Refs https://github.com/electron/electron/issues/45810#issuecomment-2691417213 - -Patch can be removed when build_make_libcxx_abi_unstable_false_for_electron.patch is removed. - -diff --git a/buildtools/third_party/libc++/__config_site b/buildtools/third_party/libc++/__config_site -index e240ff6fff94a6cebf8662996712fe7eb22e5fff..ddf1693002aa171b3d91aa4ef08f5b360e4adddc 100644 ---- a/buildtools/third_party/libc++/__config_site -+++ b/buildtools/third_party/libc++/__config_site -@@ -19,6 +19,8 @@ - #define _LIBCPP_ABI_NAMESPACE __Cr - - #define _LIBCPP_ABI_VERSION 1 -+#define _LIBCPP_ABI_USE_WRAP_ITER_IN_STD_ARRAY -+#define _LIBCPP_ABI_USE_WRAP_ITER_IN_STD_STRING_VIEW - - #define _LIBCPP_ABI_FORCE_ITANIUM 0 - #define _LIBCPP_ABI_FORCE_MICROSOFT 0 From 9e453030aee78e761aa757f6f217393736dd6bb5 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 23 Jun 2025 08:32:58 -0700 Subject: [PATCH 113/186] docs: update timelines for E38 (#47526) Update electron-timelines.md Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Michaela Laurencin <35157522+mlaurencin@users.noreply.github.com> --- docs/tutorial/electron-timelines.md | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/docs/tutorial/electron-timelines.md b/docs/tutorial/electron-timelines.md index 893b7891a0fd4..9a445f08ab20b 100644 --- a/docs/tutorial/electron-timelines.md +++ b/docs/tutorial/electron-timelines.md @@ -9,10 +9,11 @@ check out our [Electron Versioning](./electron-versioning.md) doc. | Electron | Alpha | Beta | Stable | EOL | Chrome | Node | Supported | | ------- | ----- | ------- | ------ | ------ | ---- | ---- | ---- | -| 37.0.0 | 2025-May-01 | 2025-May-28 | 2025-Jun-24 | 2026-Jan-13 | M138 | TBD | āœ… | +| 38.0.0 | 2025-Jun-26 | 2025-Aug-06 | 2025-Sep-02 | 2026-Mar-10 | M140 | TBD | āœ… | +| 37.0.0 | 2025-May-01 | 2025-May-28 | 2025-Jun-24 | 2026-Jan-13 | M138 | v22.16 | āœ… | | 36.0.0 | 2025-Mar-06 | 2025-Apr-02 | 2025-Apr-29 | 2025-Oct-28 | M136 | v22.14 | āœ… | | 35.0.0 | 2025-Jan-16 | 2025-Feb-05 | 2025-Mar-04 | 2025-Sep-02 | M134 | v22.14 | āœ… | -| 34.0.0 | 2024-Oct-17 | 2024-Nov-13 | 2025-Jan-14 | 2025-Jun-24 | M132 | v20.18 | āœ… | +| 34.0.0 | 2024-Oct-17 | 2024-Nov-13 | 2025-Jan-14 | 2025-Jun-24 | M132 | v20.18 | 🚫 | | 33.0.0 | 2024-Aug-22 | 2024-Sep-18 | 2024-Oct-15 | 2025-Apr-29 | M130 | v20.18 | 🚫 | | 32.0.0 | 2024-Jun-14 | 2024-Jul-24 | 2024-Aug-20 | 2025-Mar-04 | M128 | v20.16 | 🚫 | | 31.0.0 | 2024-Apr-18 | 2024-May-15 | 2024-Jun-11 | 2025-Jan-14 | M126 | v20.14 | 🚫 | From 713030b21ac91eb24687739782ceae9260981e03 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 23 Jun 2025 19:54:53 -0400 Subject: [PATCH 114/186] feat: add menu item role `palette` and `header` (#47245) * feat: add menu item role `palette` and `header` Co-authored-by: Gellert Hegyi * adds comments Co-authored-by: Gellert Hegyi * refactors new role items to new item types Co-authored-by: Gellert Hegyi * docs: custom type Co-authored-by: Samuel Maddock * docs: note types only available on mac 14+ Co-authored-by: Samuel Maddock --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Gellert Hegyi Co-authored-by: Gellert Hegyi Co-authored-by: Samuel Maddock --- docs/api/menu-item.md | 15 ++++++++++--- lib/browser/api/menu-item.ts | 2 +- lib/browser/api/menu.ts | 5 +++++ shell/browser/api/electron_api_menu.cc | 5 +++++ shell/browser/api/electron_api_menu.h | 1 + .../ui/cocoa/electron_menu_controller.mm | 22 ++++++++++++++++--- shell/browser/ui/electron_menu_model.cc | 12 ++++++++++ shell/browser/ui/electron_menu_model.h | 4 ++++ typings/internal-ambient.d.ts | 2 +- typings/internal-electron.d.ts | 1 + 10 files changed, 61 insertions(+), 8 deletions(-) diff --git a/docs/api/menu-item.md b/docs/api/menu-item.md index 8ee760d1cb44a..980b27d2dee31 100644 --- a/docs/api/menu-item.md +++ b/docs/api/menu-item.md @@ -20,8 +20,14 @@ See [`Menu`](menu.md) for examples. * `event` [KeyboardEvent](structures/keyboard-event.md) * `role` string (optional) - Can be `undo`, `redo`, `cut`, `copy`, `paste`, `pasteAndMatchStyle`, `delete`, `selectAll`, `reload`, `forceReload`, `toggleDevTools`, `resetZoom`, `zoomIn`, `zoomOut`, `toggleSpellChecker`, `togglefullscreen`, `window`, `minimize`, `close`, `help`, `about`, `services`, `hide`, `hideOthers`, `unhide`, `quit`, `showSubstitutions`, `toggleSmartQuotes`, `toggleSmartDashes`, `toggleTextReplacement`, `startSpeaking`, `stopSpeaking`, `zoom`, `front`, `appMenu`, `fileMenu`, `editMenu`, `viewMenu`, `shareMenu`, `recentDocuments`, `toggleTabBar`, `selectNextTab`, `selectPreviousTab`, `showAllTabs`, `mergeAllWindows`, `clearRecentDocuments`, `moveTabToNewWindow` or `windowMenu` - Define the action of the menu item, when specified the `click` property will be ignored. See [roles](#roles). - * `type` string (optional) - Can be `normal`, `separator`, `submenu`, `checkbox` or - `radio`. + * `type` string (optional) + * `normal` + * `separator` + * `submenu` + * `checkbox` + * `radio` + * `header` - Only available on macOS 14 and up. + * `palette` - Only available on macOS 14 and up. * `label` string (optional) * `sublabel` string (optional) _macOS_ - Available in macOS >= 14.4 * `toolTip` string (optional) _macOS_ - Hover text for this menu item. @@ -162,7 +168,10 @@ item's submenu, if present. #### `menuItem.type` -A `string` indicating the type of the item. Can be `normal`, `separator`, `submenu`, `checkbox` or `radio`. +A `string` indicating the type of the item. Can be `normal`, `separator`, `submenu`, `checkbox`, `radio`, `header` or `palette`. + +> [!NOTE] +> `header` and `palette` are only available on macOS 14 and up. #### `menuItem.role` diff --git a/lib/browser/api/menu-item.ts b/lib/browser/api/menu-item.ts index 1ff4836caf303..6c58a80d33c6a 100644 --- a/lib/browser/api/menu-item.ts +++ b/lib/browser/api/menu-item.ts @@ -71,7 +71,7 @@ const MenuItem = function (this: any, options: any) { }; }; -MenuItem.types = ['normal', 'separator', 'submenu', 'checkbox', 'radio']; +MenuItem.types = ['normal', 'separator', 'submenu', 'checkbox', 'radio', 'header', 'palette']; MenuItem.prototype.getDefaultRoleAccelerator = function () { return roles.getDefaultAccelerator(this.role); diff --git a/lib/browser/api/menu.ts b/lib/browser/api/menu.ts index 8e0a63f764654..10cad67f10c43 100644 --- a/lib/browser/api/menu.ts +++ b/lib/browser/api/menu.ts @@ -143,6 +143,9 @@ Menu.prototype.insert = function (pos, item) { if (item.toolTip) this.setToolTip(pos, item.toolTip); if (item.icon) this.setIcon(pos, item.icon); if (item.role) this.setRole(pos, item.role); + if (item.type === 'palette' || item.type === 'header') { + this.setCustomType(pos, item.type); + } // Make menu accessible to items. item.overrideReadOnlyProperty('menu', this); @@ -264,9 +267,11 @@ function removeExtraSeparators (items: (MenuItemConstructorOptions | MenuItem)[] function insertItemByType (this: MenuType, item: MenuItem, pos: number) { const types = { normal: () => this.insertItem(pos, item.commandId, item.label), + header: () => this.insertItem(pos, item.commandId, item.label), checkbox: () => this.insertCheckItem(pos, item.commandId, item.label), separator: () => this.insertSeparator(pos), submenu: () => this.insertSubMenu(pos, item.commandId, item.label, item.submenu), + palette: () => this.insertSubMenu(pos, item.commandId, item.label, item.submenu), radio: () => { // Grouping radio menu items item.overrideReadOnlyProperty('groupId', generateGroupId(this.items, pos)); diff --git a/shell/browser/api/electron_api_menu.cc b/shell/browser/api/electron_api_menu.cc index 595a3513c499e..da093a8f4002d 100644 --- a/shell/browser/api/electron_api_menu.cc +++ b/shell/browser/api/electron_api_menu.cc @@ -213,6 +213,10 @@ void Menu::SetRole(int index, const std::u16string& role) { model_->SetRole(index, role); } +void Menu::SetCustomType(int index, const std::u16string& customType) { + model_->SetCustomType(index, customType); +} + void Menu::Clear() { model_->Clear(); } @@ -286,6 +290,7 @@ void Menu::FillObjectTemplate(v8::Isolate* isolate, .SetMethod("setSublabel", &Menu::SetSublabel) .SetMethod("setToolTip", &Menu::SetToolTip) .SetMethod("setRole", &Menu::SetRole) + .SetMethod("setCustomType", &Menu::SetCustomType) .SetMethod("clear", &Menu::Clear) .SetMethod("getIndexOfCommandId", &Menu::GetIndexOfCommandId) .SetMethod("getItemCount", &Menu::GetItemCount) diff --git a/shell/browser/api/electron_api_menu.h b/shell/browser/api/electron_api_menu.h index 6b5ee0635da30..06fb805c06da5 100644 --- a/shell/browser/api/electron_api_menu.h +++ b/shell/browser/api/electron_api_menu.h @@ -116,6 +116,7 @@ class Menu : public gin::Wrappable, void SetSublabel(int index, const std::u16string& sublabel); void SetToolTip(int index, const std::u16string& toolTip); void SetRole(int index, const std::u16string& role); + void SetCustomType(int index, const std::u16string& customType); void Clear(); int GetIndexOfCommandId(int command_id) const; int GetItemCount() const; diff --git a/shell/browser/ui/cocoa/electron_menu_controller.mm b/shell/browser/ui/cocoa/electron_menu_controller.mm index 71c9d8b49e863..1e78e57f01dc1 100644 --- a/shell/browser/ui/cocoa/electron_menu_controller.mm +++ b/shell/browser/ui/cocoa/electron_menu_controller.mm @@ -330,6 +330,17 @@ - (NSMenuItem*)makeMenuItemForIndex:(NSInteger)index } } + std::u16string role = model->GetRoleAt(index); + electron::ElectronMenuModel::ItemType type = model->GetTypeAt(index); + std::u16string customType = model->GetCustomTypeAt(index); + + // The sectionHeaderWithTitle menu item is only available in macOS 14.0+. + if (@available(macOS 14, *)) { + if (customType == u"header") { + item = [NSMenuItem sectionHeaderWithTitle:label]; + } + } + // If the menu item has an icon, set it. ui::ImageModel icon = model->GetIconAt(index); if (icon.IsImage()) @@ -338,9 +349,6 @@ - (NSMenuItem*)makeMenuItemForIndex:(NSInteger)index std::u16string toolTip = model->GetToolTipAt(index); [item setToolTip:base::SysUTF16ToNSString(toolTip)]; - std::u16string role = model->GetRoleAt(index); - electron::ElectronMenuModel::ItemType type = model->GetTypeAt(index); - if (role == u"services") { std::u16string title = u"Services"; NSString* sub_label = l10n_util::FixUpWindowsStyleLabel(title); @@ -372,6 +380,14 @@ - (NSMenuItem*)makeMenuItemForIndex:(NSInteger)index NSMenu* submenu = MenuHasVisibleItems(submenuModel) ? [self menuFromModel:submenuModel] : MakeEmptySubmenu(); + + // NSMenuPresentationStylePalette is only available in macOS 14.0+. + if (@available(macOS 14, *)) { + if (customType == u"palette") { + submenu.presentationStyle = NSMenuPresentationStylePalette; + } + } + [submenu setTitle:[item title]]; [item setSubmenu:submenu]; diff --git a/shell/browser/ui/electron_menu_model.cc b/shell/browser/ui/electron_menu_model.cc index fd854a6313bb3..5795514d3d63c 100644 --- a/shell/browser/ui/electron_menu_model.cc +++ b/shell/browser/ui/electron_menu_model.cc @@ -37,6 +37,18 @@ std::u16string ElectronMenuModel::GetToolTipAt(size_t index) { return iter == std::end(toolTips_) ? std::u16string() : iter->second; } +void ElectronMenuModel::SetCustomType(size_t index, + const std::u16string& customType) { + int command_id = GetCommandIdAt(index); + customTypes_[command_id] = customType; +} + +std::u16string ElectronMenuModel::GetCustomTypeAt(size_t index) { + const int command_id = GetCommandIdAt(index); + const auto iter = customTypes_.find(command_id); + return iter == std::end(customTypes_) ? std::u16string() : iter->second; +} + void ElectronMenuModel::SetRole(size_t index, const std::u16string& role) { int command_id = GetCommandIdAt(index); roles_[command_id] = role; diff --git a/shell/browser/ui/electron_menu_model.h b/shell/browser/ui/electron_menu_model.h index 943f335f41bdd..574d76ac639cc 100644 --- a/shell/browser/ui/electron_menu_model.h +++ b/shell/browser/ui/electron_menu_model.h @@ -84,6 +84,8 @@ class ElectronMenuModel : public ui::SimpleMenuModel { void SetToolTip(size_t index, const std::u16string& toolTip); std::u16string GetToolTipAt(size_t index); + void SetCustomType(size_t index, const std::u16string& customType); + std::u16string GetCustomTypeAt(size_t index); void SetRole(size_t index, const std::u16string& role); std::u16string GetRoleAt(size_t index); void SetSecondaryLabel(size_t index, const std::u16string& sublabel); @@ -125,6 +127,8 @@ class ElectronMenuModel : public ui::SimpleMenuModel { base::flat_map toolTips_; // command id -> tooltip base::flat_map roles_; // command id -> role base::flat_map sublabels_; // command id -> sublabel + base::flat_map + customTypes_; // command id -> custom type base::ObserverList observers_; base::WeakPtrFactory weak_factory_{this}; diff --git a/typings/internal-ambient.d.ts b/typings/internal-ambient.d.ts index 2f0e6b87f0e4d..df4f70a89e19c 100644 --- a/typings/internal-ambient.d.ts +++ b/typings/internal-ambient.d.ts @@ -279,7 +279,7 @@ declare module NodeJS { interface ContextMenuItem { id: number; label: string; - type: 'normal' | 'separator' | 'subMenu' | 'checkbox'; + type: 'normal' | 'separator' | 'subMenu' | 'checkbox' | 'header' | 'palette'; checked: boolean; enabled: boolean; subItems: ContextMenuItem[]; diff --git a/typings/internal-electron.d.ts b/typings/internal-electron.d.ts index 5d281261bb10d..09ae513f35078 100644 --- a/typings/internal-electron.d.ts +++ b/typings/internal-electron.d.ts @@ -172,6 +172,7 @@ declare namespace Electron { setToolTip(index: number, tooltip: string): void; setIcon(index: number, image: string | NativeImage): void; setRole(index: number, role: string): void; + setCustomType(index: number, customType: string): void; insertItem(index: number, commandId: number, label: string): void; insertCheckItem(index: number, commandId: number, label: string): void; insertRadioItem(index: number, commandId: number, label: string, groupId: number): void; From 285bbc560bc2078bd437660e076675b3ace840fe Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 24 Jun 2025 10:39:53 +0200 Subject: [PATCH 115/186] refactor: simplify titlebar overlay initialization (#47524) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/native_window.cc | 20 ++++++-------------- 1 file changed, 6 insertions(+), 14 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 4be8f95b23d73..36fff501b2047 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -109,20 +109,12 @@ NativeWindow::NativeWindow(const gin_helper::Dictionary& options, options.Get(options::kVibrancyType, &vibrancy_); #endif - v8::Local titlebar_overlay; - if (options.Get(options::ktitleBarOverlay, &titlebar_overlay)) { - if (titlebar_overlay->IsBoolean()) { - options.Get(options::ktitleBarOverlay, &titlebar_overlay_); - } else if (titlebar_overlay->IsObject()) { - titlebar_overlay_ = true; - - auto titlebar_overlay_dict = - gin_helper::Dictionary::CreateEmpty(options.isolate()); - options.Get(options::ktitleBarOverlay, &titlebar_overlay_dict); - int height; - if (titlebar_overlay_dict.Get(options::kOverlayHeight, &height)) - titlebar_overlay_height_ = height; - } + if (gin_helper::Dictionary dict; + options.Get(options::ktitleBarOverlay, &dict)) { + titlebar_overlay_ = true; + titlebar_overlay_height_ = dict.ValueOrDefault(options::kOverlayHeight, 0); + } else if (bool flag; options.Get(options::ktitleBarOverlay, &flag)) { + titlebar_overlay_ = flag; } if (parent) From 42325294ab104f3044b44f27e6378f412d2eb239 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 24 Jun 2025 11:55:24 +0200 Subject: [PATCH 116/186] build: rewrite push-patch to use the github API instead of local git commits to ensure commits are signed (#47530) * build: rewrite push-patch to use the github API instead of local git commits to ensure commits are signed Co-authored-by: Samuel Attard * again (cherry picked from commit a21afc3e45d15f88c1f754d5990908f248909b41) Co-authored-by: Samuel Attard * use pr head ref (cherry picked from commit 0edcc985fadcce64f01fb77b1c15653d5e66e864) Co-authored-by: Samuel Attard --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Samuel Attard Co-authored-by: Samuel Attard --- .github/actions/checkout/action.yml | 12 +-- script/patch-up.js | 128 ++++++++++++++++++++++++++++ script/push-patch.js | 38 --------- 3 files changed, 134 insertions(+), 44 deletions(-) create mode 100644 script/patch-up.js delete mode 100644 script/push-patch.js diff --git a/.github/actions/checkout/action.yml b/.github/actions/checkout/action.yml index 9edf46b877fa1..98fc18bb566b5 100644 --- a/.github/actions/checkout/action.yml +++ b/.github/actions/checkout/action.yml @@ -117,12 +117,7 @@ runs: git update-index --refresh || true if ! git diff-index --quiet HEAD --; then # There are changes to the patches. Make a git commit with the updated patches - git add patches - GIT_COMMITTER_NAME="PatchUp" GIT_COMMITTER_EMAIL="73610968+patchup[bot]@users.noreply.github.com" git commit -m "chore: update patches" --author="PatchUp <73610968+patchup[bot]@users.noreply.github.com>" - # Export it - mkdir -p ../../patches - git format-patch -1 --stdout --keep-subject --no-stat --full-index > ../../patches/update-patches.patch - if node ./script/push-patch.js; then + if node ./script/patch-up.js; then echo echo "======================================================================" echo "Changes to the patches when applying, we have auto-pushed the diff to the current branch" @@ -130,6 +125,11 @@ runs: echo "======================================================================" exit 1 else + git add patches + GIT_COMMITTER_NAME="PatchUp" GIT_COMMITTER_EMAIL="73610968+patchup[bot]@users.noreply.github.com" git commit -m "chore: update patches" --author="PatchUp <73610968+patchup[bot]@users.noreply.github.com>" + # Export it + mkdir -p ../../patches + git format-patch -1 --stdout --keep-subject --no-stat --full-index > ../../patches/update-patches.patch echo echo "======================================================================" echo "There were changes to the patches when applying." diff --git a/script/patch-up.js b/script/patch-up.js new file mode 100644 index 0000000000000..0b6d91a824c12 --- /dev/null +++ b/script/patch-up.js @@ -0,0 +1,128 @@ +const { appCredentialsFromString, getAuthOptionsForRepo } = require('@electron/github-app-auth'); + +const { Octokit } = require('@octokit/rest'); + +const fs = require('node:fs'); +const path = require('node:path'); + +const { PATCH_UP_APP_CREDS } = process.env; + +const REPO_OWNER = 'electron'; +const REPO_NAME = 'electron'; + +async function getAllPatchFiles (dir) { + const files = []; + + async function walkDir (currentDir) { + const entries = await fs.promises.readdir(currentDir, { withFileTypes: true }); + + for (const entry of entries) { + const fullPath = path.join(currentDir, entry.name); + + if (entry.isDirectory()) { + await walkDir(fullPath); + } else if (entry.isFile() && (entry.name.endsWith('.patch') || entry.name === 'README.md' || entry.name === 'config.json')) { + const relativePath = path.relative(process.cwd(), fullPath); + const content = await fs.promises.readFile(fullPath, 'utf8'); + files.push({ + path: relativePath, + content + }); + } + } + } + + await walkDir(dir); + return files; +} + +function getCurrentCommitSha () { + return process.env.GITHUB_SHA; +} + +function getCurrentBranch () { + return process.env.GITHUB_HEAD_REF; +} + +async function main () { + if (!PATCH_UP_APP_CREDS) { + throw new Error('PATCH_UP_APP_CREDS environment variable not set'); + } + + const currentBranch = getCurrentBranch(); + + if (!currentBranch) { + throw new Error('GITHUB_HEAD_REF environment variable not set. Patch Up only works in PR workflows currently.'); + } + + const octokit = new Octokit({ + ...await getAuthOptionsForRepo({ + name: REPO_OWNER, + owner: REPO_NAME + }, appCredentialsFromString(PATCH_UP_APP_CREDS)) + }); + + const patchesDir = path.join(process.cwd(), 'patches'); + + // Get current git state + const currentCommitSha = getCurrentCommitSha(); + + // Get the tree SHA from the current commit + const currentCommit = await octokit.git.getCommit({ + owner: REPO_OWNER, + repo: REPO_NAME, + commit_sha: currentCommitSha + }); + const baseTreeSha = currentCommit.data.tree.sha; + + // Find all patch files + const patchFiles = await getAllPatchFiles(patchesDir); + + if (patchFiles.length === 0) { + throw new Error('No patch files found'); + } + + console.log(`Found ${patchFiles.length} patch files`); + + // Create a new tree with the patch files + const tree = patchFiles.map(file => ({ + path: file.path, + mode: '100644', + type: 'blob', + content: file.content + })); + + const treeResponse = await octokit.git.createTree({ + owner: REPO_OWNER, + repo: REPO_NAME, + base_tree: baseTreeSha, + tree + }); + + // Create a new commit + const commitMessage = 'chore: update patches'; + const commitResponse = await octokit.git.createCommit({ + owner: REPO_OWNER, + repo: REPO_NAME, + message: commitMessage, + tree: treeResponse.data.sha, + parents: [currentCommitSha] + }); + + // Update the branch reference + await octokit.git.updateRef({ + owner: REPO_OWNER, + repo: REPO_NAME, + ref: `heads/${currentBranch}`, + sha: commitResponse.data.sha + }); + + console.log(`Successfully pushed commit ${commitResponse.data.sha} to ${currentBranch}`); +} + +if (require.main === module) { + main().catch((err) => { + console.error(err); + process.exit(1); + }); +} diff --git a/script/push-patch.js b/script/push-patch.js deleted file mode 100644 index 7265a10f59618..0000000000000 --- a/script/push-patch.js +++ /dev/null @@ -1,38 +0,0 @@ -const { appCredentialsFromString, getTokenForRepo } = require('@electron/github-app-auth'); - -const cp = require('node:child_process'); - -const { PATCH_UP_APP_CREDS } = process.env; - -async function main () { - if (!PATCH_UP_APP_CREDS) { - throw new Error('PATCH_UP_APP_CREDS environment variable not set'); - } - - const token = await getTokenForRepo( - { - name: 'electron', - owner: 'electron' - }, - appCredentialsFromString(PATCH_UP_APP_CREDS) - ); - - const remoteURL = `https://x-access-token:${token}@github.com/electron/electron.git`; - - // NEVER LOG THE OUTPUT OF THIS COMMAND - // GIT LEAKS THE ACCESS CREDENTIALS IN CONSOLE LOGS - const { status } = cp.spawnSync('git', ['push', '--set-upstream', remoteURL], { - stdio: 'ignore' - }); - - if (status !== 0) { - throw new Error('Failed to push to target branch'); - } -} - -if (require.main === module) { - main().catch((err) => { - console.error(err); - process.exit(1); - }); -} From 253d49b24f2deeafaf5aaa85be1e9b54562dff0f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 24 Jun 2025 21:12:21 +0200 Subject: [PATCH 117/186] fix: ensure `/dev/null` fd is closed on failure (#47543) * fix: ensure /dev/null fd is closed on failure Co-authored-by: Shelley Vohr * chore: ignore closehandle for windows Co-authored-by: Robo --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr Co-authored-by: Robo --- shell/browser/api/electron_api_utility_process.cc | 3 +++ 1 file changed, 3 insertions(+) diff --git a/shell/browser/api/electron_api_utility_process.cc b/shell/browser/api/electron_api_utility_process.cc index d9ff0996d91d8..b2eb975dacef5 100644 --- a/shell/browser/api/electron_api_utility_process.cc +++ b/shell/browser/api/electron_api_utility_process.cc @@ -78,6 +78,9 @@ UtilityProcessWrapper::UtilityProcessWrapper( base::FileHandleMappingVector fds_to_remap; #endif for (const auto& [io_handle, io_type] : stdio) { + if (io_handle == IOHandle::STDIN) + continue; + if (io_type == IOType::IO_PIPE) { #if BUILDFLAG(IS_WIN) HANDLE read = nullptr; From be53277b54d9ad42e39315a7a31def7a14150037 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 25 Jun 2025 09:34:09 -0400 Subject: [PATCH 118/186] docs: Add C++/Linux tutorial (#47550) * docs: Add C++/Linux tutorial Co-authored-by: Felix Rieseberg * Update docs/tutorial/native-code-and-electron-cpp-linux.md Co-authored-by: Kilian Valkhof Co-authored-by: Felix Rieseberg * Apply suggestions from code review Co-authored-by: Kilian Valkhof Co-authored-by: Erick Zhao Co-authored-by: Felix Rieseberg * Apply suggestions from code review Co-authored-by: Erick Zhao Co-authored-by: Felix Rieseberg * Apply suggestions from code review Co-authored-by: Erick Zhao Co-authored-by: Felix Rieseberg * Implement more feedback, lint Co-authored-by: Felix Rieseberg --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Felix Rieseberg Co-authored-by: Felix Rieseberg --- .../native-code-and-electron-cpp-linux.md | 1638 +++++++++++++++++ 1 file changed, 1638 insertions(+) create mode 100644 docs/tutorial/native-code-and-electron-cpp-linux.md diff --git a/docs/tutorial/native-code-and-electron-cpp-linux.md b/docs/tutorial/native-code-and-electron-cpp-linux.md new file mode 100644 index 0000000000000..b40fa8f6b4afc --- /dev/null +++ b/docs/tutorial/native-code-and-electron-cpp-linux.md @@ -0,0 +1,1638 @@ +# Native Code and Electron: C++ (Linux) + +This tutorial builds on the [general introduction to Native Code and Electron](./native-code-and-electron.md) and focuses on creating a native addon for Linux using C++ and GTK3. To illustrate how you can embed native Linux code in your Electron app, we'll be building a basic native GTK3 GUI that communicates with Electron's JavaScript. + +Specifically, we'll be using GTK3 for our GUI interface, which provides: + +* A comprehensive set of UI widgets like buttons, entry fields, and lists +* Cross-desktop compatibility across various Linux distributions +* Integration with the native theming and accessibility features of Linux desktops + +> [!NOTE] +> We specifically use GTK3 because that's what Chromium (and by extension, Electron) uses internally. Using GTK4 would cause runtime conflicts since both GTK3 and GTK4 would be loaded in the same process. If and when Chromium upgrades to GTK4, you will likely be able to easily upgrade your native code to GTK4, too. + +This tutorial will be most useful to those who already have some familiarity with GTK development on Linux. You should have experience with basic GTK concepts like widgets, signals, and the main event loop. In the interest of brevity, we're not spending too much time explaining the individual GTK elements we're using or the code we're writing for them. This allows this tutorial to be really helpful for those who already know GTK development and want to use their skills with Electron - without having to also be an entire GTK documentation. + +> [!NOTE] +> If you're not already familiar with these concepts, the [GTK3 documentation](https://docs.gtk.org/gtk3/) and [GTK3 tutorials](https://docs.gtk.org/gtk3/getting_started.html) are excellent resources to get started. The [GNOME Developer Documentation](https://developer.gnome.org/) also provides comprehensive guides for GTK development. + +## Requirements + +Just like our general introduction to Native Code and Electron, this tutorial assumes you have Node.js and npm installed, as well as the basic tools necessary for compiling native code. Since this tutorial discusses writing native code that interacts with GTK3, you'll need: + +* A Linux distribution with GTK3 development files installed +* The [pkg-config](https://www.freedesktop.org/wiki/Software/pkg-config/) tool +* G++ compiler and build tools + +On Ubuntu/Debian, you can install these with: + +```sh +sudo apt-get install build-essential pkg-config libgtk-3-dev +``` + +On Fedora/RHEL/CentOS: + +```sh +sudo dnf install gcc-c++ pkgconfig gtk3-devel +``` + +## 1) Creating a package + +You can re-use the package we created in our [Native Code and Electron](./native-code-and-electron.md) tutorial. This tutorial will not be repeating the steps described there. Let's first setup our basic addon folder structure: + +```txt +cpp-linux/ +ā”œā”€ā”€ binding.gyp # Configuration file for node-gyp to build the native addon +ā”œā”€ā”€ include/ +│ └── cpp_code.h # Header file with declarations for our C++ native code +ā”œā”€ā”€ js/ +│ └── index.js # JavaScript interface that loads and exposes our native addon +ā”œā”€ā”€ package.json # Node.js package configuration and dependencies +└── src/ + ā”œā”€ā”€ cpp_addon.cc # C++ code that bridges Node.js/Electron with our native code + └── cpp_code.cc # Implementation of our native C++ functionality using GTK3 +``` + +Our package.json should look like this: + +```json title='package.json' +{ + "name": "cpp-linux", + "version": "1.0.0", + "description": "A demo module that exposes C++ code to Electron", + "main": "js/index.js", + "scripts": { + "clean": "rm -rf build", + "build-electron": "electron-rebuild", + "build": "node-gyp configure && node-gyp build" + }, + "license": "MIT", + "dependencies": { + "node-addon-api": "^8.3.0", + "bindings": "^1.5.0" + } +} +``` + +## 2) Setting up the build configuration + +For a Linux-specific addon using GTK3, we need to configure our `binding.gyp` file correctly to ensure our addon is only compiled on Linux systems - doing ideally nothing on other platforms. This involves using conditional compilation flags, leveraging `pkg-config` to automatically locate and include the GTK3 libraries and header paths on the user's system, and setting appropriate compiler flags to enable features like exception handling and threading support. The configuration will ensure that our native code can properly interface with both the Node.js/Electron runtime and the GTK3 libraries that provide the native GUI capabilities. + +```json title='binding.gyp' +{ + "targets": [ + { + "target_name": "cpp_addon", + "conditions": [ + ['OS=="linux"', { + "sources": [ + "src/cpp_addon.cc", + "src/cpp_code.cc" + ], + "include_dirs": [ + " +#include + +namespace cpp_code { + +std::string hello_world(const std::string& input); +void hello_gui(); + +// Callback function types +using TodoCallback = std::function; + +// Callback setters +void setTodoAddedCallback(TodoCallback callback); +void setTodoUpdatedCallback(TodoCallback callback); +void setTodoDeletedCallback(TodoCallback callback); + +} // namespace cpp_code +``` + +This header defines: + +* A basic `hello_world` function +* A `hello_gui` function to create a GTK3 GUI +* Callback types for Todo operations (add, update, delete) +* Setter functions for the callback + +## 4) Implementing GTK3 GUI Code + +Now, let's implement our GTK3 GUI in `src/cpp_code.cc`. We'll break this into manageable sections. We'll start with a number of includes as well as the basic setup. + +### Basic Setup and Data Structures + +```cpp title='src/cpp_code.cc' +#include +#include +#include +#include +#include +#include +#include +#include +#include + +using TodoCallback = std::function; + +namespace cpp_code +{ + // Basic functions + std::string hello_world(const std::string &input) + { + return "Hello from C++! You said: " + input; + } + + // Data structures + struct TodoItem + { + uuid_t id; + std::string text; + int64_t date; + + std::string toJson() const + { + char uuid_str[37]; + uuid_unparse(id, uuid_str); + return "{" + "\"id\":\"" + + std::string(uuid_str) + "\"," + "\"text\":\"" + + text + "\"," + "\"date\":" + + std::to_string(date) + + "}"; + } + + static std::string formatDate(int64_t timestamp) + { + char date_str[64]; + time_t unix_time = timestamp / 1000; + strftime(date_str, sizeof(date_str), "%Y-%m-%d", localtime(&unix_time)); + return date_str; + } + }; +``` + +In this section: + +* We include necessary headers for GTK3, standard library components, and UUID generation. +* Define a `TodoCallback` type to handle communication back to JavaScript. +* Create a `TodoItem` struct to store our todo data with: + * A UUID for unique identification + * Text content and a timestamp + * A method to convert to JSON for sending to JavaScript + * A static helper to format dates for display + +The `toJson()` method is particularly important as it's what allows our C++ objects to be serialized for transmission to JavaScript. There are probably better ways to do that, but this tutorial is about combining C++ for native Linux UI development with Electron, so we'll give ourselves a pass for not writing better JSON serialization code here. There are many libraries to work with JSON in C++ with different trade-offs. See https://www.json.org/json-en.html for a list. + +Notably, we haven't actually added any user interface yet - which we'll do in the next step. GTK code tends to be verbose, so bear with us - despite the length. + +### Global state and forward declarations + +Below the code already in your `src/cpp_code.cc`, add the following: + +```cpp title='src/cpp_code.cc' + // Forward declarations + static void update_todo_row_label(GtkListBoxRow *row, const TodoItem &todo); + static GtkWidget *create_todo_dialog(GtkWindow *parent, const TodoItem *existing_todo); + + // Global state + namespace + { + TodoCallback g_todoAddedCallback; + TodoCallback g_todoUpdatedCallback; + TodoCallback g_todoDeletedCallback; + GMainContext *g_gtk_main_context = nullptr; + GMainLoop *g_main_loop = nullptr; + std::thread *g_gtk_thread = nullptr; + std::vector g_todos; + } +``` + +Here we: + +* Forward-declare helper functions we'll use later +* Set up global state in an anonymous namespace, including: + * Callbacks for the `add`, `update`, and `delete` todo operations + * GTK main context and loop pointers for thread management + * A pointer to the GTK thread itself + * A vector to store our todos + +These global variables keep track of application state and allow different parts of our code to interact with each other. The thread management variables (`g_gtk_main_context`, `g_main_loop`, and `g_gtk_thread`) are particularly important because GTK requires running in its own event loop. Since our code will be called from Node.js/Electron's main thread, we need to run GTK in a separate thread to avoid blocking the JavaScript event loop. This separation ensures that our native UI remains responsive while still allowing bidirectional communication with the Electron application. The callbacks enable us to send events back to JavaScript when the user interacts with our native GTK interface. + +### Helper Functions + +Moving on, we're adding more code below the code we've already written. In this section, we're adding three static helper methods - and also start setting up some actual native user interface. We'll add a helper function that'll notify a callback in a thread-safe way, a function to update a row label, and a function to create the whole "Add Todo" dialog. + +```cpp title='src/cpp_code.cc' + // Helper functions + static void notify_callback(const TodoCallback &callback, const std::string &json) + { + if (callback && g_gtk_main_context) + { + g_main_context_invoke(g_gtk_main_context, [](gpointer data) -> gboolean + { + auto* cb_data = static_cast*>(data); + cb_data->first(cb_data->second); + delete cb_data; + return G_SOURCE_REMOVE; }, new std::pair(callback, json)); + } + } + + static void update_todo_row_label(GtkListBoxRow *row, const TodoItem &todo) + { + auto *label = gtk_label_new((todo.text + " - " + TodoItem::formatDate(todo.date)).c_str()); + auto *old_label = GTK_WIDGET(gtk_container_get_children(GTK_CONTAINER(row))->data); + gtk_container_remove(GTK_CONTAINER(row), old_label); + gtk_container_add(GTK_CONTAINER(row), label); + gtk_widget_show_all(GTK_WIDGET(row)); + } + + static GtkWidget *create_todo_dialog(GtkWindow *parent, const TodoItem *existing_todo = nullptr) + { + auto *dialog = gtk_dialog_new_with_buttons( + existing_todo ? "Edit Todo" : "Add Todo", + parent, + GTK_DIALOG_MODAL, + "_Cancel", GTK_RESPONSE_CANCEL, + "_Save", GTK_RESPONSE_ACCEPT, + nullptr); + + auto *content_area = gtk_dialog_get_content_area(GTK_DIALOG(dialog)); + gtk_container_set_border_width(GTK_CONTAINER(content_area), 10); + + auto *entry = gtk_entry_new(); + if (existing_todo) + { + gtk_entry_set_text(GTK_ENTRY(entry), existing_todo->text.c_str()); + } + gtk_container_add(GTK_CONTAINER(content_area), entry); + + auto *calendar = gtk_calendar_new(); + if (existing_todo) + { + time_t unix_time = existing_todo->date / 1000; + struct tm *timeinfo = localtime(&unix_time); + gtk_calendar_select_month(GTK_CALENDAR(calendar), timeinfo->tm_mon, timeinfo->tm_year + 1900); + gtk_calendar_select_day(GTK_CALENDAR(calendar), timeinfo->tm_mday); + } + gtk_container_add(GTK_CONTAINER(content_area), calendar); + + gtk_widget_show_all(dialog); + return dialog; + } +``` + +These helper functions are crucial for our application: + +* `notify_callback`: Safely invokes JavaScript callbacks from the GTK thread using `g_main_context_invoke`, which schedules function execution in the GTK main context. As a reminder, the GTK main context is the environment where GTK operations must be performed to ensure thread safety, as GTK is not thread-safe and all UI operations must happen on the main thread. +* `update_todo_row_label`: Updates a row in the todo list with new text and formatted date. +* `create_todo_dialog`: Creates a dialog for adding or editing todos with: + * A text entry field for the todo text + * A calendar widget for selecting the date + * Appropriate buttons for saving or canceling + +### Event handlers + +Our native user interface has events - and those events must be handled. The only Electron-specific thing in this code is that we're notifying our JS callbacks. + +```cpp title='src/cpp_code.cc' + static void edit_action(GSimpleAction *action, GVariant *parameter, gpointer user_data) + { + auto *builder = static_cast(user_data); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + auto *row = gtk_list_box_get_selected_row(list); + if (!row) + return; + + gint index = gtk_list_box_row_get_index(row); + auto size = static_cast(g_todos.size()); + if (index < 0 || index >= size) + return; + + auto *dialog = create_todo_dialog( + GTK_WINDOW(gtk_builder_get_object(builder, "window")), + &g_todos[index]); + + if (gtk_dialog_run(GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) + { + auto *entry = GTK_ENTRY(gtk_container_get_children( + GTK_CONTAINER(gtk_dialog_get_content_area(GTK_DIALOG(dialog)))) + ->data); + auto *calendar = GTK_CALENDAR(gtk_container_get_children( + GTK_CONTAINER(gtk_dialog_get_content_area(GTK_DIALOG(dialog)))) + ->next->data); + + const char *new_text = gtk_entry_get_text(entry); + + guint year, month, day; + gtk_calendar_get_date(calendar, &year, &month, &day); + GDateTime *datetime = g_date_time_new_local(year, month + 1, day, 0, 0, 0); + gint64 new_date = g_date_time_to_unix(datetime) * 1000; + g_date_time_unref(datetime); + + g_todos[index].text = new_text; + g_todos[index].date = new_date; + + update_todo_row_label(row, g_todos[index]); + notify_callback(g_todoUpdatedCallback, g_todos[index].toJson()); + } + + gtk_widget_destroy(dialog); + } + + static void delete_action(GSimpleAction *action, GVariant *parameter, gpointer user_data) + { + auto *builder = static_cast(user_data); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + auto *row = gtk_list_box_get_selected_row(list); + if (!row) + return; + + gint index = gtk_list_box_row_get_index(row); + auto size = static_cast(g_todos.size()); + if (index < 0 || index >= size) + return; + + std::string json = g_todos[index].toJson(); + gtk_container_remove(GTK_CONTAINER(list), GTK_WIDGET(row)); + g_todos.erase(g_todos.begin() + index); + notify_callback(g_todoDeletedCallback, json); + } + + static void on_add_clicked(GtkButton *button, gpointer user_data) + { + auto *builder = static_cast(user_data); + auto *entry = GTK_ENTRY(gtk_builder_get_object(builder, "todo_entry")); + auto *calendar = GTK_CALENDAR(gtk_builder_get_object(builder, "todo_calendar")); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + + const char *text = gtk_entry_get_text(entry); + if (strlen(text) > 0) + { + TodoItem todo; + uuid_generate(todo.id); + todo.text = text; + + guint year, month, day; + gtk_calendar_get_date(calendar, &year, &month, &day); + GDateTime *datetime = g_date_time_new_local(year, month + 1, day, 0, 0, 0); + todo.date = g_date_time_to_unix(datetime) * 1000; + g_date_time_unref(datetime); + + g_todos.push_back(todo); + + auto *row = gtk_list_box_row_new(); + auto *label = gtk_label_new((todo.text + " - " + TodoItem::formatDate(todo.date)).c_str()); + gtk_container_add(GTK_CONTAINER(row), label); + gtk_container_add(GTK_CONTAINER(list), row); + gtk_widget_show_all(row); + + gtk_entry_set_text(entry, ""); + + notify_callback(g_todoAddedCallback, todo.toJson()); + } + } + + static void on_row_activated(GtkListBox *list_box, GtkListBoxRow *row, gpointer user_data) + { + GMenu *menu = g_menu_new(); + g_menu_append(menu, "Edit", "app.edit"); + g_menu_append(menu, "Delete", "app.delete"); + + auto *popover = gtk_popover_new_from_model(GTK_WIDGET(row), G_MENU_MODEL(menu)); + gtk_popover_set_position(GTK_POPOVER(popover), GTK_POS_RIGHT); + gtk_popover_popup(GTK_POPOVER(popover)); + + g_object_unref(menu); + } +``` + +These event handlers manage user interactions: + +`edit_action`: Handles editing a todo by: + +* Getting the selected row +* Creating a dialog with the current todo data +* Updating the todo if the user confirms +* Notifying JavaScript via callback + +`delete_action`: Removes a todo and notifies JavaScript. + +`on_add_clicked`: Adds a new todo when the user clicks the Add button: + +* Gets text and date from input fields +* Creates a new TodoItem with a unique ID +* Adds it to the list and the underlying data store +* Notifies JavaScript + +`on_row_activated`: Shows a popup menu when a todo is clicked, with options to edit or delete. + +### GTK application setup + +Now, we'll need to setup our GTK application. This might be counter-intuitive, given that we already have a GTK application running. The activation code here is necessary because this is native C++ code running alongside Electron, not within it. While Electron does have its own main process and renderer processes, this GTK application operates as a native OS window that's launched from the Electron application but runs in its own process or thread. The `hello_gui()` function specifically starts the GTK application with its own thread (`g_gtk_thread`), application loop, and UI context. + +```cpp title='src/cpp_code.cc' + static gboolean init_gtk_app(gpointer user_data) + { + auto *app = static_cast(user_data); + g_application_run(G_APPLICATION(app), 0, nullptr); + g_object_unref(app); + if (g_main_loop) + { + g_main_loop_quit(g_main_loop); + } + return G_SOURCE_REMOVE; + } + + static void activate_handler(GtkApplication *app, gpointer user_data) + { + auto *builder = gtk_builder_new(); + + const GActionEntry app_actions[] = { + {"edit", edit_action, nullptr, nullptr, nullptr, {0, 0, 0}}, + {"delete", delete_action, nullptr, nullptr, nullptr, {0, 0, 0}}}; + g_action_map_add_action_entries(G_ACTION_MAP(app), app_actions, + G_N_ELEMENTS(app_actions), builder); + + gtk_builder_add_from_string(builder, + "" + "" + " " + " Todo List" + " 400" + " 500" + " " + " " + " true" + " vertical" + " 6" + " 12" + " " + " " + " true" + " 6" + " " + " " + " true" + " true" + " Enter todo item..." + " " + " " + " " + " " + " true" + " " + " " + " " + " " + " true" + " Add" + " " + " " + " " + " " + " " + " " + " true" + " true" + " " + " " + " true" + " single" + " " + " " + " " + " " + " " + " " + " " + "", + -1, nullptr); + + auto *window = GTK_WINDOW(gtk_builder_get_object(builder, "window")); + auto *button = GTK_BUTTON(gtk_builder_get_object(builder, "add_button")); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + + gtk_window_set_application(window, app); + + g_signal_connect(button, "clicked", G_CALLBACK(on_add_clicked), builder); + g_signal_connect(list, "row-activated", G_CALLBACK(on_row_activated), nullptr); + + gtk_widget_show_all(GTK_WIDGET(window)); + } +``` + +Let's take a closer look at the code above: + +* `init_gtk_app`: Runs the GTK application main loop. +* `activate_handler`: Sets up the application UI when activated: + * Creates a GtkBuilder for loading the UI + * Registers edit and delete actions + * Defines the UI layout using GTK's XML markup language + * Connects signals to our event handlers + +The UI layout is defined inline using XML, which is a common pattern in GTK applications. It creates a main window, input controls (text entry, calendar, and add button), a list box for displaying todos, and proper layout containers and scrolling. + +### Main GUI function and thread management + +Now that we have everything wired, up, we can add our two core GUI functions: `hello_gui()` (which we'll call from JavaScript) and `cleanup_gui()` to get rid of everything. You'll be hopefully delighted to hear that our careful setup of GTK app, context, and threads makes this straightforward: + +```cpp title='src/cpp_code.cc' + void hello_gui() + { + if (g_gtk_thread != nullptr) + { + g_print("GTK application is already running.\n"); + return; + } + + if (!gtk_init_check(0, nullptr)) + { + g_print("Failed to initialize GTK.\n"); + return; + } + + g_gtk_main_context = g_main_context_new(); + g_main_loop = g_main_loop_new(g_gtk_main_context, FALSE); + + g_gtk_thread = new std::thread([]() + { + GtkApplication* app = gtk_application_new("com.example.todo", G_APPLICATION_NON_UNIQUE); + g_signal_connect(app, "activate", G_CALLBACK(activate_handler), nullptr); + + g_idle_add_full(G_PRIORITY_DEFAULT, init_gtk_app, app, nullptr); + + if (g_main_loop) { + g_main_loop_run(g_main_loop); + } }); + + g_gtk_thread->detach(); + } + + void cleanup_gui() + { + if (g_main_loop && g_main_loop_is_running(g_main_loop)) + { + g_main_loop_quit(g_main_loop); + } + + if (g_main_loop) + { + g_main_loop_unref(g_main_loop); + g_main_loop = nullptr; + } + + if (g_gtk_main_context) + { + g_main_context_unref(g_gtk_main_context); + g_gtk_main_context = nullptr; + } + + g_gtk_thread = nullptr; + } +``` + +These functions manage the GTK application lifecycle: + +* `hello_gui`: The entry point exposed to JavaScript that checks if GTK is already running, initializes GTK, creates a new main context and loop, launches a thread to run the GTK application, and detaches the thread so it runs independently. +* `cleanup_gui`: Properly cleans up GTK resources when the application closes. + +Running GTK in a separate thread is crucial for Electron integration, as it prevents the GTK main loop from blocking Node.js's event loop. + +### Callback management + +Previously, we setup global variables to hold our callbacks. Now, we'll add functions that assign those callbacks. These callbacks form the bridge between our native GTK code and JavaScript, allowing bidirectional communication. + +```cpp title='src/cpp_code.cc' + void setTodoAddedCallback(TodoCallback callback) + { + g_todoAddedCallback = callback; + } + + void setTodoUpdatedCallback(TodoCallback callback) + { + g_todoUpdatedCallback = callback; + } + + void setTodoDeletedCallback(TodoCallback callback) + { + g_todoDeletedCallback = callback; + } +``` + +### Putting `cpp_code.cc` together + +We've now finished the GTK and native part of our addon - that is, the code that's most concerned with interacting with the operating system (and by contrast, less so with bridging the native C++ and JavaScript worlds). After adding all the sections above, your `src/cpp_code.cc` should look like this: + +```cpp title='src/cpp_code.cc' +#include +#include +#include +#include +#include +#include +#include +#include +#include + +using TodoCallback = std::function; + +namespace cpp_code +{ + + // Basic functions + std::string hello_world(const std::string &input) + { + return "Hello from C++! You said: " + input; + } + + // Data structures + struct TodoItem + { + uuid_t id; + std::string text; + int64_t date; + + std::string toJson() const + { + char uuid_str[37]; + uuid_unparse(id, uuid_str); + return "{" + "\"id\":\"" + + std::string(uuid_str) + "\"," + "\"text\":\"" + + text + "\"," + "\"date\":" + + std::to_string(date) + + "}"; + } + + static std::string formatDate(int64_t timestamp) + { + char date_str[64]; + time_t unix_time = timestamp / 1000; + strftime(date_str, sizeof(date_str), "%Y-%m-%d", localtime(&unix_time)); + return date_str; + } + }; + + // Forward declarations + static void update_todo_row_label(GtkListBoxRow *row, const TodoItem &todo); + static GtkWidget *create_todo_dialog(GtkWindow *parent, const TodoItem *existing_todo); + + // Global state + namespace + { + TodoCallback g_todoAddedCallback; + TodoCallback g_todoUpdatedCallback; + TodoCallback g_todoDeletedCallback; + GMainContext *g_gtk_main_context = nullptr; + GMainLoop *g_main_loop = nullptr; + std::thread *g_gtk_thread = nullptr; + std::vector g_todos; + } + + // Helper functions + static void notify_callback(const TodoCallback &callback, const std::string &json) + { + if (callback && g_gtk_main_context) + { + g_main_context_invoke(g_gtk_main_context, [](gpointer data) -> gboolean + { + auto* cb_data = static_cast*>(data); + cb_data->first(cb_data->second); + delete cb_data; + return G_SOURCE_REMOVE; }, new std::pair(callback, json)); + } + } + + static void update_todo_row_label(GtkListBoxRow *row, const TodoItem &todo) + { + auto *label = gtk_label_new((todo.text + " - " + TodoItem::formatDate(todo.date)).c_str()); + auto *old_label = GTK_WIDGET(gtk_container_get_children(GTK_CONTAINER(row))->data); + gtk_container_remove(GTK_CONTAINER(row), old_label); + gtk_container_add(GTK_CONTAINER(row), label); + gtk_widget_show_all(GTK_WIDGET(row)); + } + + static GtkWidget *create_todo_dialog(GtkWindow *parent, const TodoItem *existing_todo = nullptr) + { + auto *dialog = gtk_dialog_new_with_buttons( + existing_todo ? "Edit Todo" : "Add Todo", + parent, + GTK_DIALOG_MODAL, + "_Cancel", GTK_RESPONSE_CANCEL, + "_Save", GTK_RESPONSE_ACCEPT, + nullptr); + + auto *content_area = gtk_dialog_get_content_area(GTK_DIALOG(dialog)); + gtk_container_set_border_width(GTK_CONTAINER(content_area), 10); + + auto *entry = gtk_entry_new(); + if (existing_todo) + { + gtk_entry_set_text(GTK_ENTRY(entry), existing_todo->text.c_str()); + } + gtk_container_add(GTK_CONTAINER(content_area), entry); + + auto *calendar = gtk_calendar_new(); + if (existing_todo) + { + time_t unix_time = existing_todo->date / 1000; + struct tm *timeinfo = localtime(&unix_time); + gtk_calendar_select_month(GTK_CALENDAR(calendar), timeinfo->tm_mon, timeinfo->tm_year + 1900); + gtk_calendar_select_day(GTK_CALENDAR(calendar), timeinfo->tm_mday); + } + gtk_container_add(GTK_CONTAINER(content_area), calendar); + + gtk_widget_show_all(dialog); + return dialog; + } + + static void edit_action(GSimpleAction *action, GVariant *parameter, gpointer user_data) + { + auto *builder = static_cast(user_data); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + auto *row = gtk_list_box_get_selected_row(list); + if (!row) + return; + + gint index = gtk_list_box_row_get_index(row); + auto size = static_cast(g_todos.size()); + if (index < 0 || index >= size) + return; + + auto *dialog = create_todo_dialog( + GTK_WINDOW(gtk_builder_get_object(builder, "window")), + &g_todos[index]); + + if (gtk_dialog_run(GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) + { + auto *entry = GTK_ENTRY(gtk_container_get_children( + GTK_CONTAINER(gtk_dialog_get_content_area(GTK_DIALOG(dialog)))) + ->data); + auto *calendar = GTK_CALENDAR(gtk_container_get_children( + GTK_CONTAINER(gtk_dialog_get_content_area(GTK_DIALOG(dialog)))) + ->next->data); + + const char *new_text = gtk_entry_get_text(entry); + + guint year, month, day; + gtk_calendar_get_date(calendar, &year, &month, &day); + GDateTime *datetime = g_date_time_new_local(year, month + 1, day, 0, 0, 0); + gint64 new_date = g_date_time_to_unix(datetime) * 1000; + g_date_time_unref(datetime); + + g_todos[index].text = new_text; + g_todos[index].date = new_date; + + update_todo_row_label(row, g_todos[index]); + notify_callback(g_todoUpdatedCallback, g_todos[index].toJson()); + } + + gtk_widget_destroy(dialog); + } + + static void delete_action(GSimpleAction *action, GVariant *parameter, gpointer user_data) + { + auto *builder = static_cast(user_data); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + auto *row = gtk_list_box_get_selected_row(list); + if (!row) + return; + + gint index = gtk_list_box_row_get_index(row); + auto size = static_cast(g_todos.size()); + if (index < 0 || index >= size) + return; + + std::string json = g_todos[index].toJson(); + gtk_container_remove(GTK_CONTAINER(list), GTK_WIDGET(row)); + g_todos.erase(g_todos.begin() + index); + notify_callback(g_todoDeletedCallback, json); + } + + static void on_add_clicked(GtkButton *button, gpointer user_data) + { + auto *builder = static_cast(user_data); + auto *entry = GTK_ENTRY(gtk_builder_get_object(builder, "todo_entry")); + auto *calendar = GTK_CALENDAR(gtk_builder_get_object(builder, "todo_calendar")); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + + const char *text = gtk_entry_get_text(entry); + if (strlen(text) > 0) + { + TodoItem todo; + uuid_generate(todo.id); + todo.text = text; + + guint year, month, day; + gtk_calendar_get_date(calendar, &year, &month, &day); + GDateTime *datetime = g_date_time_new_local(year, month + 1, day, 0, 0, 0); + todo.date = g_date_time_to_unix(datetime) * 1000; + g_date_time_unref(datetime); + + g_todos.push_back(todo); + + auto *row = gtk_list_box_row_new(); + auto *label = gtk_label_new((todo.text + " - " + TodoItem::formatDate(todo.date)).c_str()); + gtk_container_add(GTK_CONTAINER(row), label); + gtk_container_add(GTK_CONTAINER(list), row); + gtk_widget_show_all(row); + + gtk_entry_set_text(entry, ""); + + notify_callback(g_todoAddedCallback, todo.toJson()); + } + } + + static void on_row_activated(GtkListBox *list_box, GtkListBoxRow *row, gpointer user_data) + { + GMenu *menu = g_menu_new(); + g_menu_append(menu, "Edit", "app.edit"); + g_menu_append(menu, "Delete", "app.delete"); + + auto *popover = gtk_popover_new_from_model(GTK_WIDGET(row), G_MENU_MODEL(menu)); + gtk_popover_set_position(GTK_POPOVER(popover), GTK_POS_RIGHT); + gtk_popover_popup(GTK_POPOVER(popover)); + + g_object_unref(menu); + } + + static gboolean init_gtk_app(gpointer user_data) + { + auto *app = static_cast(user_data); + g_application_run(G_APPLICATION(app), 0, nullptr); + g_object_unref(app); + if (g_main_loop) + { + g_main_loop_quit(g_main_loop); + } + return G_SOURCE_REMOVE; + } + + static void activate_handler(GtkApplication *app, gpointer user_data) + { + auto *builder = gtk_builder_new(); + + const GActionEntry app_actions[] = { + {"edit", edit_action, nullptr, nullptr, nullptr, {0, 0, 0}}, + {"delete", delete_action, nullptr, nullptr, nullptr, {0, 0, 0}}}; + g_action_map_add_action_entries(G_ACTION_MAP(app), app_actions, + G_N_ELEMENTS(app_actions), builder); + + gtk_builder_add_from_string(builder, + "" + "" + " " + " Todo List" + " 400" + " 500" + " " + " " + " true" + " vertical" + " 6" + " 12" + " " + " " + " true" + " 6" + " " + " " + " true" + " true" + " Enter todo item..." + " " + " " + " " + " " + " true" + " " + " " + " " + " " + " true" + " Add" + " " + " " + " " + " " + " " + " " + " true" + " true" + " " + " " + " true" + " single" + " " + " " + " " + " " + " " + " " + " " + "", + -1, nullptr); + + auto *window = GTK_WINDOW(gtk_builder_get_object(builder, "window")); + auto *button = GTK_BUTTON(gtk_builder_get_object(builder, "add_button")); + auto *list = GTK_LIST_BOX(gtk_builder_get_object(builder, "todo_list")); + + gtk_window_set_application(window, app); + + g_signal_connect(button, "clicked", G_CALLBACK(on_add_clicked), builder); + g_signal_connect(list, "row-activated", G_CALLBACK(on_row_activated), nullptr); + + gtk_widget_show_all(GTK_WIDGET(window)); + } + + void hello_gui() + { + if (g_gtk_thread != nullptr) + { + g_print("GTK application is already running.\n"); + return; + } + + if (!gtk_init_check(0, nullptr)) + { + g_print("Failed to initialize GTK.\n"); + return; + } + + g_gtk_main_context = g_main_context_new(); + g_main_loop = g_main_loop_new(g_gtk_main_context, FALSE); + + g_gtk_thread = new std::thread([]() + { + GtkApplication* app = gtk_application_new("com.example.todo", G_APPLICATION_NON_UNIQUE); + g_signal_connect(app, "activate", G_CALLBACK(activate_handler), nullptr); + + g_idle_add_full(G_PRIORITY_DEFAULT, init_gtk_app, app, nullptr); + + if (g_main_loop) { + g_main_loop_run(g_main_loop); + } }); + + g_gtk_thread->detach(); + } + + void cleanup_gui() + { + if (g_main_loop && g_main_loop_is_running(g_main_loop)) + { + g_main_loop_quit(g_main_loop); + } + + if (g_main_loop) + { + g_main_loop_unref(g_main_loop); + g_main_loop = nullptr; + } + + if (g_gtk_main_context) + { + g_main_context_unref(g_gtk_main_context); + g_gtk_main_context = nullptr; + } + + g_gtk_thread = nullptr; + } + + void setTodoAddedCallback(TodoCallback callback) + { + g_todoAddedCallback = callback; + } + + void setTodoUpdatedCallback(TodoCallback callback) + { + g_todoUpdatedCallback = callback; + } + + void setTodoDeletedCallback(TodoCallback callback) + { + g_todoDeletedCallback = callback; + } + +} // namespace cpp_code +``` + +## 5) Creating the Node.js addon bridge + +Now let's implement the bridge between our C++ code and Node.js in `src/cpp_addon.cc`. Let's start by creating a basic skeleton for our addon: + +```cpp title='src/cpp_addon.cc' +#include +#include +#include "cpp_code.h" + +// Class to wrap our C++ code will go here + +Napi::Object Init(Napi::Env env, Napi::Object exports) { + // We'll add code here later + return exports; +} + +NODE_API_MODULE(cpp_addon, Init) +``` + +This is the minimal structure required for a Node.js addon using `node-addon-api`. The `Init` function is called when the addon is loaded, and the `NODE_API_MODULE` macro registers our initializer. This basic skeleton doesn't do anything yet, but it provides the entry point for Node.js to load our native code. + +### Create a class to wrap our C++ code + +Let's create a class that will wrap our C++ code and expose it to JavaScript. In our previous step, we've added a comment reading "Class to wrap our C++ code will go here" - replace it with the code below. + +```cpp title='src/cpp_addon.cc' +class CppAddon : public Napi::ObjectWrap +{ +public: + static Napi::Object Init(Napi::Env env, Napi::Object exports) + { + Napi::Function func = DefineClass(env, "CppLinuxAddon", { + InstanceMethod("helloWorld", &CppAddon::HelloWorld), + InstanceMethod("helloGui", &CppAddon::HelloGui), + InstanceMethod("on", &CppAddon::On) + }); + + Napi::FunctionReference *constructor = new Napi::FunctionReference(); + *constructor = Napi::Persistent(func); + env.SetInstanceData(constructor); + + exports.Set("CppLinuxAddon", func); + return exports; + } + + CppAddon(const Napi::CallbackInfo &info) + : Napi::ObjectWrap(info), + env_(info.Env()), + emitter(Napi::Persistent(Napi::Object::New(info.Env()))), + callbacks(Napi::Persistent(Napi::Object::New(info.Env()))), + tsfn_(nullptr) + { + // We'll implement the constructor together with a callback struct later + } + + ~CppAddon() + { + if (tsfn_ != nullptr) + { + napi_release_threadsafe_function(tsfn_, napi_tsfn_release); + tsfn_ = nullptr; + } + } + +private: + Napi::Env env_; + Napi::ObjectReference emitter; + Napi::ObjectReference callbacks; + napi_threadsafe_function tsfn_; + + // Method implementations will go here +}; +``` + +Here, we create a C++ class that inherits from `Napi::ObjectWrap`: + +`static Napi::Object Init` defines our JavaScript interface with three methods: + +* `helloWorld`: A simple function to test the bridge +* `helloGui`: The function to launch our GTK3 UI +* `on`: A method to register event callbacks + +The constructor initializes: + +* `emitter`: An object that will emit events to JavaScript +* `callbacks`: A map of registered JavaScript callback functions +* `tsfn_`: A thread-safe function handle (crucial for GTK3 thread communication) + +The destructor properly cleans up the thread-safe function when the object is garbage collected. + +### Implement basic functionality - HelloWorld + +Next, we'll add our two main methods, `HelloWorld()` and `HelloGui()`. We'll add these to our `private` scope, right where we have a comment reading "Method implementations will go here". + +```cpp title='src/cpp_addon.cc' +Napi::Value HelloWorld(const Napi::CallbackInfo &info) +{ + Napi::Env env = info.Env(); + + if (info.Length() < 1 || !info[0].IsString()) + { + Napi::TypeError::New(env, "Expected string argument").ThrowAsJavaScriptException(); + return env.Null(); + } + + std::string input = info[0].As(); + std::string result = cpp_code::hello_world(input); + + return Napi::String::New(env, result); +} + +void HelloGui(const Napi::CallbackInfo &info) +{ + cpp_code::hello_gui(); +} + +// On() method implementation will go here +``` + +`HelloWorld()`: + +* Validates the input argument (must be a string) +* Calls our C++ hello_world function +* Returns the result as a JavaScript string + +`HelloGui()`: + +* Simply calls our C++ hello_gui function without arguments +* Returns nothing (void) as the function just launches the UI +* These methods form the direct bridge between JavaScript calls and our native C++ functions. + +You might be wondering what `Napi::CallbackInfo` is or where it comes from. This is a class provided by the Node-API (N-API) C++ wrapper, specifically from the [`node-addon-api`](https://github.com/nodejs/node-addon-api) package. It encapsulates all the information about a JavaScript function call, including: + +* The arguments passed from JavaScript +* The JavaScript execution environment (via `info.Env()`) +* The `this` value of the function call +* The number of arguments (via `info.Length()`) + +This class is fundamental to the Node.js native addon development as it serves as the bridge between JavaScript function calls and C++ method implementations. Every native method that can be called from JavaScript receives a `CallbackInfo` object as its parameter, allowing the C++ code to access and validate the JavaScript arguments before processing them. You can see us using it in `HelloWorld()` to get function parameters and other information about the function call. Our `HelloGui()` function doesn't use it, but if it did, it'd follow the same pattern. + +### Setting up the event system + +Now we'll tackle the tricky part of native development: setting up the event system. Previously, we added native callbacks to our `cpp_code.cc` code - and in our bridge code in `cpp_addon.cc`, we'll need to find a way to have those callbacks ultimately trigger a JavaScript method. + +Let's start with the `On()` method, which we'll call from JavaScript. In our previously written code, you'll find a comment reading `On() method implementation will go here`. Replace it with the following method: + +```cpp title='src/cpp_addon.cc' +Napi::Value On(const Napi::CallbackInfo &info) +{ + Napi::Env env = info.Env(); + + if (info.Length() < 2 || !info[0].IsString() || !info[1].IsFunction()) + { + Napi::TypeError::New(env, "Expected (string, function) arguments").ThrowAsJavaScriptException(); + return env.Undefined(); + } + + callbacks.Value().Set(info[0].As(), info[1].As()); + return env.Undefined(); +} +``` + +This method allows JavaScript to register callbacks for different event types and stores the JavaScript function in our `callbacks` map for later use. So far, so good - but now we need to let `cpp_code.cc` know about these callbacks. We also need to figure out a way to coordinate our threads, because the actual `cpp_code.cc` will be doing most of its work on its own thread. + +In our code, find the section where we're declaring the constructor `CppAddon(const Napi::CallbackInfo &info)`, which you'll find in the `public` section. It should have a comment reading `We'll implement the constructor together with a callback struct later`. Then, replace that part with the following code: + +```cpp title='src/cpp_addon.cc' + struct CallbackData + { + std::string eventType; + std::string payload; + CppAddon *addon; + }; + + CppAddon(const Napi::CallbackInfo &info) + : Napi::ObjectWrap(info), + env_(info.Env()), + emitter(Napi::Persistent(Napi::Object::New(info.Env()))), + callbacks(Napi::Persistent(Napi::Object::New(info.Env()))), + tsfn_(nullptr) + { + napi_status status = napi_create_threadsafe_function( + env_, + nullptr, + nullptr, + Napi::String::New(env_, "CppCallback"), + 0, + 1, + nullptr, + nullptr, + this, + [](napi_env env, napi_value js_callback, void *context, void *data) + { + auto *callbackData = static_cast(data); + if (!callbackData) + return; + + Napi::Env napi_env(env); + Napi::HandleScope scope(napi_env); + + auto addon = static_cast(context); + if (!addon) + { + delete callbackData; + return; + } + + try + { + auto callback = addon->callbacks.Value().Get(callbackData->eventType).As(); + if (callback.IsFunction()) + { + callback.Call(addon->emitter.Value(), {Napi::String::New(napi_env, callbackData->payload)}); + } + } + catch (...) + { + } + + delete callbackData; + }, + &tsfn_); + + if (status != napi_ok) + { + Napi::Error::New(env_, "Failed to create threadsafe function").ThrowAsJavaScriptException(); + return; + } + + // Set up the callbacks here + auto makeCallback = [this](const std::string &eventType) + { + return [this, eventType](const std::string &payload) + { + if (tsfn_ != nullptr) + { + auto *data = new CallbackData{ + eventType, + payload, + this}; + napi_call_threadsafe_function(tsfn_, data, napi_tsfn_blocking); + } + }; + }; + + cpp_code::setTodoAddedCallback(makeCallback("todoAdded")); + cpp_code::setTodoUpdatedCallback(makeCallback("todoUpdated")); + cpp_code::setTodoDeletedCallback(makeCallback("todoDeleted")); + } +``` + +This is the most complex part of our bridge: implementing bidirectional communication. There are a few things worth noting going on here, so let's take them step by step: + +`CallbackData` struct: + +* Holds the event type, JSON payload, and a reference to our addon. + +In the constructor: + +* We create a thread-safe function (`napi_create_threadsafe_function`) which is crucial for calling into JavaScript from the GTK3 thread +* The thread-safe function callback unpacks the data and calls the appropriate JavaScript callback +* We create a lambda `makeCallback` that produces callback functions for different event types +* We register these callbacks with our C++ code using the setter functions + +Let's talk about `napi_create_threadsafe_function`. The orchestration of different threads is maybe the most difficult part about native addon development - and in our experience, the place where developers are most likely to give up. `napi_create_threadsafe_function` is provided by the N-API and allows you to safely call JavaScript functions from any thread. This is essential when working with GUI frameworks like GTK3 that run on their own thread. Here's why it's important: + +1. **Thread Safety**: JavaScript in Electron runs on a single thread (exceptions apply, but this is a generally useful rule). Without thread-safe functions, calling JavaScript from another thread would cause crashes or race conditions. +1. **Queue Management**: It automatically queues function calls and executes them on the JavaScript thread. +1. **Resource Management**: It handles proper reference counting to ensure objects aren't garbage collected while still needed. + +In our code, we're using it to bridge the gap between GTK3's event loop and Node.js's event loop, allowing events from our GUI to safely trigger JavaScript callbacks. + +For developers wanting to learn more, you can refer to the [official N-API documentation](https://nodejs.org/api/n-api.html#n_api_napi_create_threadsafe_function) for detailed information about thread-safe functions, the [node-addon-api wrapper documentation](https://github.com/nodejs/node-addon-api/blob/main/doc/threadsafe_function.md) for the C++ wrapper implementation, and the [Node.js Threading Model article](https://nodejs.org/en/docs/guides/dont-block-the-event-loop/) to understand how Node.js handles concurrency and why thread-safe functions are necessary. + +### Putting `cpp_addon.cc` together + +We've now finished the bridge part our addon - that is, the code that's most concerned with being the bridge between your JavaScript and C++ code (and by contrast, less so actually interacting with the operating system or GTK). After adding all the sections above, your `src/cpp_addon.cc` should look like this: + +```cpp title='src/cpp_addon.cc' +#include +#include +#include "cpp_code.h" + +class CppAddon : public Napi::ObjectWrap +{ +public: + static Napi::Object Init(Napi::Env env, Napi::Object exports) + { + Napi::Function func = DefineClass(env, "CppLinuxAddon", { + InstanceMethod("helloWorld", &CppAddon::HelloWorld), + InstanceMethod("helloGui", &CppAddon::HelloGui), + InstanceMethod("on", &CppAddon::On) + }); + + Napi::FunctionReference *constructor = new Napi::FunctionReference(); + *constructor = Napi::Persistent(func); + env.SetInstanceData(constructor); + + exports.Set("CppLinuxAddon", func); + return exports; + } + + struct CallbackData + { + std::string eventType; + std::string payload; + CppAddon *addon; + }; + + CppAddon(const Napi::CallbackInfo &info) + : Napi::ObjectWrap(info), + env_(info.Env()), + emitter(Napi::Persistent(Napi::Object::New(info.Env()))), + callbacks(Napi::Persistent(Napi::Object::New(info.Env()))), + tsfn_(nullptr) + { + napi_status status = napi_create_threadsafe_function( + env_, + nullptr, + nullptr, + Napi::String::New(env_, "CppCallback"), + 0, + 1, + nullptr, + nullptr, + this, + [](napi_env env, napi_value js_callback, void *context, void *data) + { + auto *callbackData = static_cast(data); + if (!callbackData) + return; + + Napi::Env napi_env(env); + Napi::HandleScope scope(napi_env); + + auto addon = static_cast(context); + if (!addon) + { + delete callbackData; + return; + } + + try + { + auto callback = addon->callbacks.Value().Get(callbackData->eventType).As(); + if (callback.IsFunction()) + { + callback.Call(addon->emitter.Value(), {Napi::String::New(napi_env, callbackData->payload)}); + } + } + catch (...) + { + } + + delete callbackData; + }, + &tsfn_); + + if (status != napi_ok) + { + Napi::Error::New(env_, "Failed to create threadsafe function").ThrowAsJavaScriptException(); + return; + } + + // Set up the callbacks here + auto makeCallback = [this](const std::string &eventType) + { + return [this, eventType](const std::string &payload) + { + if (tsfn_ != nullptr) + { + auto *data = new CallbackData{ + eventType, + payload, + this}; + napi_call_threadsafe_function(tsfn_, data, napi_tsfn_blocking); + } + }; + }; + + cpp_code::setTodoAddedCallback(makeCallback("todoAdded")); + cpp_code::setTodoUpdatedCallback(makeCallback("todoUpdated")); + cpp_code::setTodoDeletedCallback(makeCallback("todoDeleted")); + } + + ~CppAddon() + { + if (tsfn_ != nullptr) + { + napi_release_threadsafe_function(tsfn_, napi_tsfn_release); + tsfn_ = nullptr; + } + } + +private: + Napi::Env env_; + Napi::ObjectReference emitter; + Napi::ObjectReference callbacks; + napi_threadsafe_function tsfn_; + + Napi::Value HelloWorld(const Napi::CallbackInfo &info) + { + Napi::Env env = info.Env(); + + if (info.Length() < 1 || !info[0].IsString()) + { + Napi::TypeError::New(env, "Expected string argument").ThrowAsJavaScriptException(); + return env.Null(); + } + + std::string input = info[0].As(); + std::string result = cpp_code::hello_world(input); + + return Napi::String::New(env, result); + } + + void HelloGui(const Napi::CallbackInfo &info) + { + cpp_code::hello_gui(); + } + + Napi::Value On(const Napi::CallbackInfo &info) + { + Napi::Env env = info.Env(); + + if (info.Length() < 2 || !info[0].IsString() || !info[1].IsFunction()) + { + Napi::TypeError::New(env, "Expected (string, function) arguments").ThrowAsJavaScriptException(); + return env.Undefined(); + } + + callbacks.Value().Set(info[0].As(), info[1].As()); + return env.Undefined(); + } +}; + +Napi::Object Init(Napi::Env env, Napi::Object exports) +{ + return CppAddon::Init(env, exports); +} + +NODE_API_MODULE(cpp_addon, Init) +``` + +## 6) Creating a JavaScript wrapper + +Let's finish things off by adding a JavaScript wrapper in `js/index.js`. As we could all see, C++ requires a lot of boilerplate code that might be easier or faster to write in JavaScript - and you will find that many production applications end up transforming data or requests in JavaScript before invoking native code. We, for instance, turn our timestamp into a proper JavaScript date. + +```cpp title='js/index.js' +const EventEmitter = require('events'); + +class CppLinuxAddon extends EventEmitter { + constructor() { + super() + + if (process.platform !== 'linux') { + throw new Error('This module is only available on Linux'); + } + + const native = require('bindings')('cpp_addon') + this.addon = new native.CppLinuxAddon() + + // Set up event forwarding + this.addon.on('todoAdded', (payload) => { + this.emit('todoAdded', this.parse(payload)) + }); + + this.addon.on('todoUpdated', (payload) => { + this.emit('todoUpdated', this.parse(payload)) + }) + + this.addon.on('todoDeleted', (payload) => { + this.emit('todoDeleted', this.parse(payload)) + }) + } + + helloWorld(input = "") { + return this.addon.helloWorld(input) + } + + helloGui() { + return this.addon.helloGui() + } + + // Parse JSON and convert date to JavaScript Date object + parse(payload) { + const parsed = JSON.parse(payload) + + return { ...parsed, date: new Date(parsed.date) } + } +} + +if (process.platform === 'linux') { + module.exports = new CppLinuxAddon() +} else { + // Return empty object on non-Linux platforms + module.exports = {} +} +``` + +This wrapper: + +* Extends EventEmitter for native event handling +* Only loads on Linux platforms +* Forwards events from C++ to JavaScript +* Provides clean methods to call into C++ +* Converts JSON data into proper JavaScript objects + +## 7) Building and testing the addon + +With all files in place, you can build the addon: + +```sh +npm run build +``` + +If the build completes, you can now add the addon to your Electron app and `import` or `require` it there. + +## Usage Example + +Once you've built the addon, you can use it in your Electron application. Here's a complete example: + +```js @ts-expect-error=[2] +// In your Electron main process or renderer process +import cppLinux from 'cpp-linux' + +// Test the basic functionality +console.log(cppLinux.helloWorld('Hi!')) +// Output: "Hello from C++! You said: Hi!" + +// Set up event listeners for GTK GUI interactions +cppLinux.on('todoAdded', (todo) => { + console.log('New todo added:', todo) + // todo: { id: "uuid-string", text: "Todo text", date: Date object } +}) + +cppLinux.on('todoUpdated', (todo) => { + console.log('Todo updated:', todo) +}) + +cppLinux.on('todoDeleted', (todo) => { + console.log('Todo deleted:', todo) +}) + +// Launch the native GTK GUI +cppLinux.helloGui() +``` + +When you run this code: + +1. The `helloWorld()` call will return a greeting from C++ +2. The event listeners will be triggered when users interact with the GTK3 GUI +3. The `helloGui()` call will open a native GTK3 window with: + * A text entry field for todo items + * A calendar widget for selecting dates + * An "Add" button to create new todos + * A scrollable list showing all todos + * Right-click context menus for editing and deleting todos + +All interactions with the native GTK3 interface will trigger the corresponding JavaScript events, allowing your Electron application to respond to native GUI actions in real-time. + +## Conclusion + +You've now built a complete native Node.js addon for Linux using C++ and GTK3. This addon: + +1. Provides a bidirectional bridge between JavaScript and C++ +1. Creates a native GTK3 GUI that runs in its own thread +1. Implements a simple Todo application with add functionality +1. Uses GTK3, which is compatible with Electron's Chromium runtime +1. Handles callbacks from C++ to JavaScript safely + +This foundation can be extended to implement more complex Linux-specific features in your Electron applications. You can access system features, integrate with Linux-specific libraries, or create performant native UIs while maintaining the flexibility and ease of development that Electron provides. +For more information on GTK3 development, refer to the [GTK3 Documentation](https://docs.gtk.org/gtk3/) and the [GLib/GObject documentation](https://docs.gtk.org/gobject/). You may also find the [Node.js N-API documentation](https://nodejs.org/api/n-api.html) and [node-addon-api](https://github.com/nodejs/node-addon-api) helpful for extending your native addons. From 75cda9e16bcd0a7271385eb5a971cd9f760f15d4 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 25 Jun 2025 20:41:42 +0200 Subject: [PATCH 119/186] feat: support customizing window accent color on Windows (#47537) * fix: support window accent color in frameless windows Co-authored-by: Shelley Vohr * refactor: allow customization Co-authored-by: Shelley Vohr * Update docs/api/structures/base-window-options.md Co-authored-by: Will Anderson Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- docs/api/structures/base-window-options.md | 1 + shell/browser/native_window_views.cc | 11 +++ shell/browser/native_window_views.h | 3 + shell/browser/native_window_views_win.cc | 90 ++++++++++++++++++++++ shell/common/options_switches.h | 2 + 5 files changed, 107 insertions(+) diff --git a/docs/api/structures/base-window-options.md b/docs/api/structures/base-window-options.md index 0b451c7733a0e..375c6adc3b59b 100644 --- a/docs/api/structures/base-window-options.md +++ b/docs/api/structures/base-window-options.md @@ -95,6 +95,7 @@ * `color` String (optional) _Windows_ _Linux_ - The CSS color of the Window Controls Overlay when enabled. Default is the system color. * `symbolColor` String (optional) _Windows_ _Linux_ - The CSS color of the symbols on the Window Controls Overlay when enabled. Default is the system color. * `height` Integer (optional) - The height of the title bar and Window Controls Overlay in pixels. Default is system height. +* `accentColor` boolean | string (optional) _Windows_ - The accent color for the window. By default, follows user preference in System Settings. Set to `false` to explicitly disable, or set the color in Hex, RGB, RGBA, HSL, HSLA or named CSS color format. Alpha values will be ignored. * `trafficLightPosition` [Point](point.md) (optional) _macOS_ - Set a custom position for the traffic light buttons in frameless windows. * `roundedCorners` boolean (optional) _macOS_ _Windows_ - Whether frameless window diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 77250ef9e7272..fff2c9dd9a88c 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -79,6 +79,7 @@ #include "base/win/windows_version.h" #include "shell/browser/ui/views/win_frame_view.h" #include "shell/browser/ui/win/electron_desktop_native_widget_aura.h" +#include "shell/common/color_util.h" #include "skia/ext/skia_utils_win.h" #include "ui/display/win/screen_win.h" #include "ui/gfx/color_utils.h" @@ -214,6 +215,14 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, overlay_button_color_ = color_utils::GetSysSkColor(COLOR_BTNFACE); overlay_symbol_color_ = color_utils::GetSysSkColor(COLOR_BTNTEXT); + + bool accent_color = true; + std::string accent_color_string; + if (options.Get(options::kAccentColor, &accent_color_string)) { + accent_color_ = ParseCSSColor(accent_color_string); + } else if (options.Get(options::kAccentColor, &accent_color)) { + accent_color_ = accent_color; + } #endif v8::Local titlebar_overlay; @@ -430,6 +439,8 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, last_window_state_ = ui::mojom::WindowShowState::kFullscreen; else last_window_state_ = ui::mojom::WindowShowState::kNormal; + + UpdateWindowAccentColor(); #endif // Listen to mouse events. diff --git a/shell/browser/native_window_views.h b/shell/browser/native_window_views.h index b65221bcdba21..5554b8676e166 100644 --- a/shell/browser/native_window_views.h +++ b/shell/browser/native_window_views.h @@ -209,6 +209,7 @@ class NativeWindowViews : public NativeWindow, void ResetWindowControls(); void SetRoundedCorners(bool rounded); void SetForwardMouseMessages(bool forward); + void UpdateWindowAccentColor(); static LRESULT CALLBACK SubclassProc(HWND hwnd, UINT msg, WPARAM w_param, @@ -305,6 +306,8 @@ class NativeWindowViews : public NativeWindow, // Whether the window is currently being moved. bool is_moving_ = false; + std::variant accent_color_ = true; + std::optional pending_bounds_change_; // The message ID of the "TaskbarCreated" message, sent to us when we need to diff --git a/shell/browser/native_window_views_win.cc b/shell/browser/native_window_views_win.cc index 7202464f608d9..8a2876d4f69b4 100644 --- a/shell/browser/native_window_views_win.cc +++ b/shell/browser/native_window_views_win.cc @@ -7,6 +7,7 @@ #include #include "base/win/atl.h" // Must be before UIAutomationCore.h +#include "base/win/registry.h" #include "base/win/scoped_handle.h" #include "base/win/windows_version.h" #include "content/public/browser/browser_accessibility_state.h" @@ -28,6 +29,53 @@ namespace electron { namespace { +void SetWindowBorderAndCaptionColor(HWND hwnd, COLORREF color) { + if (base::win::GetVersion() < base::win::Version::WIN11) + return; + + HRESULT result = + DwmSetWindowAttribute(hwnd, DWMWA_CAPTION_COLOR, &color, sizeof(color)); + + if (FAILED(result)) + LOG(WARNING) << "Failed to set caption color"; + + result = + DwmSetWindowAttribute(hwnd, DWMWA_BORDER_COLOR, &color, sizeof(color)); + + if (FAILED(result)) + LOG(WARNING) << "Failed to set border color"; +} + +std::optional GetAccentColor() { + base::win::RegKey key; + if (key.Open(HKEY_CURRENT_USER, L"SOFTWARE\\Microsoft\\Windows\\DWM", + KEY_READ) != ERROR_SUCCESS) { + return std::nullopt; + } + + DWORD accent_color = 0; + if (key.ReadValueDW(L"AccentColor", &accent_color) != ERROR_SUCCESS) { + return std::nullopt; + } + + return accent_color; +} + +bool IsAccentColorOnTitleBarsEnabled() { + base::win::RegKey key; + if (key.Open(HKEY_CURRENT_USER, L"SOFTWARE\\Microsoft\\Windows\\DWM", + KEY_READ) != ERROR_SUCCESS) { + return false; + } + + DWORD enabled = 0; + if (key.ReadValueDW(L"ColorPrevalence", &enabled) != ERROR_SUCCESS) { + return false; + } + + return enabled != 0; +} + // Convert Win32 WM_QUERYENDSESSIONS to strings. const std::vector EndSessionToStringVec(LPARAM end_session_id) { std::vector params; @@ -450,6 +498,19 @@ bool NativeWindowViews::PreHandleMSG(UINT message, } return false; } + case WM_DWMCOLORIZATIONCOLORCHANGED: { + UpdateWindowAccentColor(); + return false; + } + case WM_SETTINGCHANGE: { + if (l_param) { + const wchar_t* setting_name = reinterpret_cast(l_param); + std::wstring setting_str(setting_name); + if (setting_str == L"ImmersiveColorSet") + UpdateWindowAccentColor(); + } + return false; + } default: { return false; } @@ -509,6 +570,35 @@ void NativeWindowViews::HandleSizeEvent(WPARAM w_param, LPARAM l_param) { } } +void NativeWindowViews::UpdateWindowAccentColor() { + if (base::win::GetVersion() < base::win::Version::WIN11) + return; + + if (!IsAccentColorOnTitleBarsEnabled()) + return; + + COLORREF border_color; + if (std::holds_alternative(accent_color_)) { + // Don't set accent color if the user has disabled it. + if (!std::get(accent_color_)) + return; + + std::optional accent_color = GetAccentColor(); + if (!accent_color.has_value()) + return; + + border_color = + RGB(GetRValue(accent_color.value()), GetGValue(accent_color.value()), + GetBValue(accent_color.value())); + } else { + SkColor color = std::get(accent_color_); + border_color = + RGB(SkColorGetR(color), SkColorGetG(color), SkColorGetB(color)); + } + + SetWindowBorderAndCaptionColor(GetAcceleratedWidget(), border_color); +} + void NativeWindowViews::ResetWindowControls() { // If a given window was minimized and has since been // unminimized (restored/maximized), ensure the WCO buttons diff --git a/shell/common/options_switches.h b/shell/common/options_switches.h index 7b86b734e5a21..1e2aad82727f3 100644 --- a/shell/common/options_switches.h +++ b/shell/common/options_switches.h @@ -123,6 +123,8 @@ inline constexpr std::string_view kRoundedCorners = "roundedCorners"; inline constexpr std::string_view ktitleBarOverlay = "titleBarOverlay"; +inline constexpr std::string_view kAccentColor = "accentColor"; + // The color to use as the theme and symbol colors respectively for Window // Controls Overlay if enabled on Windows. inline constexpr std::string_view kOverlayButtonColor = "color"; From e45eab5b3533d149bf9d9e0d2b78f152815247d6 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 25 Jun 2025 17:07:04 -0500 Subject: [PATCH 120/186] docs: update asar integrity fuse availability (#47567) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Niklas Wenzel --- docs/tutorial/fuses.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/tutorial/fuses.md b/docs/tutorial/fuses.md index 1afa53d6a7df3..c810d1af2a660 100644 --- a/docs/tutorial/fuses.md +++ b/docs/tutorial/fuses.md @@ -48,7 +48,7 @@ The nodeCliInspect fuse toggles whether the `--inspect`, `--inspect-brk`, etc. f **@electron/fuses:** `FuseV1Options.EnableEmbeddedAsarIntegrityValidation` -The embeddedAsarIntegrityValidation fuse toggles an experimental feature on macOS that validates the content of the `app.asar` file when it is loaded. This feature is designed to have a minimal performance impact but may marginally slow down file reads from inside the `app.asar` archive. +The embeddedAsarIntegrityValidation fuse toggles an experimental feature on macOS and Windows that validates the content of the `app.asar` file when it is loaded. This feature is designed to have a minimal performance impact but may marginally slow down file reads from inside the `app.asar` archive. For more information on how to use asar integrity validation please read the [Asar Integrity](asar-integrity.md) documentation. From 1eb8f7e705eafdd21f7dae69d80b1f48c55c6f86 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 26 Jun 2025 08:18:06 -0500 Subject: [PATCH 121/186] refactor: remove stray `.c_str()` calls for `absl::StrFormat()` (#47577) refactor: remove stray .c_str() calls for absl::StrFormat() StrFormat() understands std::string, std::string_view Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_session.cc | 5 ++--- .../electron_management_api_delegate.cc | 5 ++--- .../extensions/api/scripting/scripting_api.cc | 8 +++---- shell/browser/hid/hid_chooser_controller.cc | 7 +++---- .../net/proxying_url_loader_factory.cc | 2 +- shell/browser/net/proxying_websocket.cc | 3 +-- shell/browser/ui/inspectable_web_contents.cc | 21 ++++++++----------- shell/browser/ui/views/global_menu_bar_x11.cc | 4 ++-- shell/common/application_info.cc | 2 +- shell/renderer/renderer_client_base.cc | 4 ++-- 10 files changed, 27 insertions(+), 34 deletions(-) diff --git a/shell/browser/api/electron_api_session.cc b/shell/browser/api/electron_api_session.cc index 563d63aa95e7d..08d4861b93e24 100644 --- a/shell/browser/api/electron_api_session.cc +++ b/shell/browser/api/electron_api_session.cc @@ -1499,9 +1499,8 @@ v8::Local Session::ClearData(gin_helper::ErrorThrower thrower, // Opaque origins cannot be used with this API if (origin.opaque()) { - thrower.ThrowError( - absl::StrFormat("Invalid origin: '%s'", - origin_url.possibly_invalid_spec().c_str())); + thrower.ThrowError(absl::StrFormat( + "Invalid origin: '%s'", origin_url.possibly_invalid_spec())); return v8::Undefined(isolate); } diff --git a/shell/browser/extensions/api/management/electron_management_api_delegate.cc b/shell/browser/extensions/api/management/electron_management_api_delegate.cc index 258dc7851c92e..f555460588f8b 100644 --- a/shell/browser/extensions/api/management/electron_management_api_delegate.cc +++ b/shell/browser/extensions/api/management/electron_management_api_delegate.cc @@ -199,9 +199,8 @@ GURL ElectronManagementAPIDelegate::GetIconURL( ExtensionIconSet::Match match, bool grayscale) const { GURL icon_url(absl::StrFormat( - "%s%s/%d/%d%s", chrome::kChromeUIExtensionIconURL, - extension->id().c_str(), icon_size, static_cast(match), - grayscale ? "?grayscale=true" : "")); + "%s%s/%d/%d%s", chrome::kChromeUIExtensionIconURL, extension->id(), + icon_size, static_cast(match), grayscale ? "?grayscale=true" : "")); CHECK(icon_url.is_valid()); return icon_url; } diff --git a/shell/browser/extensions/api/scripting/scripting_api.cc b/shell/browser/extensions/api/scripting/scripting_api.cc index b140bd69b6064..33e2591bbde9a 100644 --- a/shell/browser/extensions/api/scripting/scripting_api.cc +++ b/shell/browser/extensions/api/scripting/scripting_api.cc @@ -215,7 +215,7 @@ bool CollectFramesForInjection(const api::scripting::InjectionTarget& target, ExtensionApiFrameIdMap::DocumentIdFromString(id); if (!document_id) { - *error_out = absl::StrFormat("Invalid document id %s", id.c_str()); + *error_out = absl::StrFormat("Invalid document id %s", id); return false; } @@ -227,7 +227,7 @@ bool CollectFramesForInjection(const api::scripting::InjectionTarget& target, // request. if (!frame || content::WebContents::FromRenderFrameHost(frame) != tab) { *error_out = absl::StrFormat("No document with id %s in tab with id %d", - id.c_str(), target.tab_id); + id, target.tab_id); return false; } @@ -499,8 +499,8 @@ ExtensionFunction::ResponseAction ScriptingExecuteScriptFunction::Run() { args_expression = base::JoinString(string_args, ","); } - std::string code_to_execute = absl::StrFormat( - "(%s)(%s)", injection_.func->c_str(), args_expression.c_str()); + std::string code_to_execute = + absl::StrFormat("(%s)(%s)", *injection_.func, args_expression); std::vector sources; sources.push_back(mojom::JSSource::New(std::move(code_to_execute), GURL())); diff --git a/shell/browser/hid/hid_chooser_controller.cc b/shell/browser/hid/hid_chooser_controller.cc index e1d6ed06b7a70..6cf1b0a9107f1 100644 --- a/shell/browser/hid/hid_chooser_controller.cc +++ b/shell/browser/hid/hid_chooser_controller.cc @@ -280,8 +280,8 @@ bool HidChooserController::DisplayDevice( absl::StrFormat( "Chooser dialog is not displaying a FIDO HID device: vendorId=%d, " "productId=%d, name='%s', serial='%s'", - device.vendor_id, device.product_id, device.product_name.c_str(), - device.serial_number.c_str())); + device.vendor_id, device.product_id, device.product_name, + device.serial_number)); return false; } @@ -292,8 +292,7 @@ bool HidChooserController::DisplayDevice( "the HID blocklist: vendorId=%d, " "productId=%d, name='%s', serial='%s'", device.vendor_id, device.product_id, - device.product_name.c_str(), - device.serial_number.c_str())); + device.product_name, device.serial_number)); return false; } diff --git a/shell/browser/net/proxying_url_loader_factory.cc b/shell/browser/net/proxying_url_loader_factory.cc index 572e5e4ae6ded..1bbb15b669cfc 100644 --- a/shell/browser/net/proxying_url_loader_factory.cc +++ b/shell/browser/net/proxying_url_loader_factory.cc @@ -394,7 +394,7 @@ void ProxyingURLLoaderFactory::InProgressRequest:: "HTTP/1.1 %i Internal Redirect\n" "Location: %s\n" "Non-Authoritative-Reason: WebRequest API\n\n", - kInternalRedirectStatusCode, redirect_url_.spec().c_str()); + kInternalRedirectStatusCode, redirect_url_.spec()); // Cross-origin requests need to modify the Origin header to 'null'. Since // CorsURLLoader sets |request_initiator| to the Origin request header in diff --git a/shell/browser/net/proxying_websocket.cc b/shell/browser/net/proxying_websocket.cc index 75f922fa5e40f..02ae781d0bb74 100644 --- a/shell/browser/net/proxying_websocket.cc +++ b/shell/browser/net/proxying_websocket.cc @@ -142,8 +142,7 @@ void ProxyingWebSocket::OnConnectionEstablished( base::MakeRefCounted(absl::StrFormat( "HTTP/%d.%d %d %s", handshake_response_->http_version.major_value(), handshake_response_->http_version.minor_value(), - handshake_response_->status_code, - handshake_response_->status_text.c_str())); + handshake_response_->status_code, handshake_response_->status_text)); for (const auto& header : handshake_response_->headers) response_->headers->AddHeader(header->name, header->value); diff --git a/shell/browser/ui/inspectable_web_contents.cc b/shell/browser/ui/inspectable_web_contents.cc index e80d6a6d7662d..f05476527bd73 100644 --- a/shell/browser/ui/inspectable_web_contents.cc +++ b/shell/browser/ui/inspectable_web_contents.cc @@ -139,16 +139,14 @@ double GetNextZoomLevel(double level, bool out) { } GURL GetRemoteBaseURL() { - return GURL( - absl::StrFormat("%s%s/%s/", kChromeUIDevToolsRemoteFrontendBase, - kChromeUIDevToolsRemoteFrontendPath, - embedder_support::GetChromiumGitRevision().c_str())); + return GURL(absl::StrFormat("%s%s/%s/", kChromeUIDevToolsRemoteFrontendBase, + kChromeUIDevToolsRemoteFrontendPath, + embedder_support::GetChromiumGitRevision())); } GURL GetDevToolsURL(bool can_dock) { - auto url_string = - absl::StrFormat(kChromeUIDevToolsURL, GetRemoteBaseURL().spec().c_str(), - can_dock ? "true" : ""); + auto url_string = absl::StrFormat( + kChromeUIDevToolsURL, GetRemoteBaseURL().spec(), can_dock ? "true" : ""); return GURL(url_string); } @@ -630,8 +628,7 @@ void InspectableWebContents::SetInspectedPageBounds(const gfx::Rect& rect) { void InspectableWebContents::InspectedURLChanged(const std::string& url) { if (managed_devtools_web_contents_) { if (devtools_title_.empty()) { - view_->SetTitle( - base::UTF8ToUTF16(absl::StrFormat(kTitleFormat, url.c_str()))); + view_->SetTitle(base::UTF8ToUTF16(absl::StrFormat(kTitleFormat, url))); } } } @@ -1023,9 +1020,9 @@ void InspectableWebContents::DidFinishNavigation( // most likely bug in chromium. base::ReplaceFirstSubstringAfterOffset(&it->second, 0, "var chrome", "var chrome = window.chrome "); - auto script = absl::StrFormat( - "%s(\"%s\")", it->second.c_str(), - base::Uuid::GenerateRandomV4().AsLowercaseString().c_str()); + auto script = + absl::StrFormat("%s(\"%s\")", it->second, + base::Uuid::GenerateRandomV4().AsLowercaseString()); // Invoking content::DevToolsFrontendHost::SetupExtensionsAPI(frame, script); // should be enough, but it seems to be a noop currently. frame->ExecuteJavaScriptForTests(base::UTF8ToUTF16(script), diff --git a/shell/browser/ui/views/global_menu_bar_x11.cc b/shell/browser/ui/views/global_menu_bar_x11.cc index 53e51db0857e1..feb1d9472770a 100644 --- a/shell/browser/ui/views/global_menu_bar_x11.cc +++ b/shell/browser/ui/views/global_menu_bar_x11.cc @@ -164,8 +164,8 @@ std::string GetMenuModelStatus(ElectronMenuModel* model) { int status = model->GetTypeAt(i) | (model->IsVisibleAt(i) << 3) | (model->IsEnabledAt(i) << 4) | (model->IsItemCheckedAt(i) << 5); - ret += absl::StrFormat( - "%s-%X\n", base::UTF16ToUTF8(model->GetLabelAt(i)).c_str(), status); + ret += absl::StrFormat("%s-%X\n", base::UTF16ToUTF8(model->GetLabelAt(i)), + status); } return ret; } diff --git a/shell/common/application_info.cc b/shell/common/application_info.cc index f7b04a2d04ac2..acba56d544ad0 100644 --- a/shell/common/application_info.cc +++ b/shell/common/application_info.cc @@ -44,7 +44,7 @@ std::string GetApplicationUserAgent() { } else { user_agent = absl::StrFormat( "%s/%s Chrome/%s " ELECTRON_PRODUCT_NAME "/" ELECTRON_VERSION_STRING, - name.c_str(), browser->GetVersion().c_str(), CHROME_VERSION_STRING); + name, browser->GetVersion(), CHROME_VERSION_STRING); } return embedder_support::BuildUserAgentFromProduct(user_agent); } diff --git a/shell/renderer/renderer_client_base.cc b/shell/renderer/renderer_client_base.cc index 5eb0fe04fc6e1..cc971f7b65a55 100644 --- a/shell/renderer/renderer_client_base.cc +++ b/shell/renderer/renderer_client_base.cc @@ -185,8 +185,8 @@ RendererClientBase* RendererClientBase::Get() { void RendererClientBase::BindProcess(v8::Isolate* isolate, gin_helper::Dictionary* process, content::RenderFrame* render_frame) { - auto context_id = absl::StrFormat("%s-%" PRId64, renderer_client_id_.c_str(), - ++next_context_id_); + auto context_id = + absl::StrFormat("%s-%" PRId64, renderer_client_id_, ++next_context_id_); process->SetReadOnly("isMainFrame", render_frame->IsMainFrame()); process->SetReadOnly("contextIsolated", From 1754c55c0528794ef343fd113c80e3aed6f56782 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 26 Jun 2025 16:38:14 +0200 Subject: [PATCH 122/186] docs: fix `--experimental-network-inspection` spelling (#47573) doc: fix `--experimental-network-inspection` spelling Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Niklas Wenzel --- docs/api/command-line-switches.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/api/command-line-switches.md b/docs/api/command-line-switches.md index e5ab9dcbe94d7..413d7143a6c58 100644 --- a/docs/api/command-line-switches.md +++ b/docs/api/command-line-switches.md @@ -290,7 +290,7 @@ Specify ways of the inspector web socket url exposure. By default inspector websocket url is available in stderr and under /json/list endpoint on `http://host:port/json/list`. -### `--experimental-network-inspector` +### `--experimental-network-inspection` Enable support for devtools network inspector events, for visibility into requests made by the nodejs `http` and `https` modules. From 99a224e45be94aaec154d3c06beea7af483be45c Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 27 Jun 2025 14:38:49 -0500 Subject: [PATCH 123/186] refactor: make context bridge's private keys hidden, constexpr string_views (#47586) * refactor: local functions GetPrivate(), SetPrivate() now take std::string_views Co-authored-by: Charles Kerr * refactor: make local keys std::string_views instead of C-style char arrays Co-authored-by: Charles Kerr * refactor: make local keys constexpr Co-authored-by: Charles Kerr * refactor: move local keys into local anonymous namespace Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- .../api/electron_api_context_bridge.cc | 45 +++++++++---------- 1 file changed, 20 insertions(+), 25 deletions(-) diff --git a/shell/renderer/api/electron_api_context_bridge.cc b/shell/renderer/api/electron_api_context_bridge.cc index ff91fee761af8..da6bf279544b2 100644 --- a/shell/renderer/api/electron_api_context_bridge.cc +++ b/shell/renderer/api/electron_api_context_bridge.cc @@ -42,18 +42,16 @@ content::RenderFrame* GetRenderFrame(v8::Local value); namespace api { -namespace context_bridge { +namespace { -const char kProxyFunctionPrivateKey[] = "electron_contextBridge_proxy_fn"; -const char kProxyFunctionReceiverPrivateKey[] = +constexpr std::string_view kProxyFunctionPrivateKey = + "electron_contextBridge_proxy_fn"; +constexpr std::string_view kProxyFunctionReceiverPrivateKey = "electron_contextBridge_proxy_fn_receiver"; -const char kSupportsDynamicPropertiesPrivateKey[] = +constexpr std::string_view kSupportsDynamicPropertiesPrivateKey = "electron_contextBridge_supportsDynamicProperties"; -const char kOriginalFunctionPrivateKey[] = "electron_contextBridge_original_fn"; - -} // namespace context_bridge - -namespace { +constexpr std::string_view kOriginalFunctionPrivateKey = + "electron_contextBridge_original_fn"; static int kMaxRecursion = 1000; @@ -115,7 +113,7 @@ bool IsPlainArray(const v8::Local& arr) { void SetPrivate(v8::Local context, v8::Local target, - const std::string& key, + const std::string_view key, v8::Local value) { target ->SetPrivate( @@ -128,7 +126,7 @@ void SetPrivate(v8::Local context, v8::MaybeLocal GetPrivate(v8::Local context, v8::Local target, - const std::string& key) { + const std::string_view key) { return target->GetPrivate( context, v8::Private::ForApi(context->GetIsolate(), @@ -192,8 +190,8 @@ v8::MaybeLocal PassValueToOtherContextInner( // the global handle at the right time. if (value->IsFunction()) { auto func = value.As(); - v8::MaybeLocal maybe_original_fn = GetPrivate( - source_context, func, context_bridge::kOriginalFunctionPrivateKey); + v8::MaybeLocal maybe_original_fn = + GetPrivate(source_context, func, kOriginalFunctionPrivateKey); { v8::Context::Scope destination_scope(destination_context); @@ -214,13 +212,11 @@ v8::MaybeLocal PassValueToOtherContextInner( v8::Local state = v8::Object::New(destination_context->GetIsolate()); - SetPrivate(destination_context, state, - context_bridge::kProxyFunctionPrivateKey, func); - SetPrivate(destination_context, state, - context_bridge::kProxyFunctionReceiverPrivateKey, + SetPrivate(destination_context, state, kProxyFunctionPrivateKey, func); + SetPrivate(destination_context, state, kProxyFunctionReceiverPrivateKey, parent_value); SetPrivate(destination_context, state, - context_bridge::kSupportsDynamicPropertiesPrivateKey, + kSupportsDynamicPropertiesPrivateKey, gin::ConvertToV8(destination_context->GetIsolate(), support_dynamic_properties)); @@ -228,7 +224,7 @@ v8::MaybeLocal PassValueToOtherContextInner( .ToLocal(&proxy_func)) return {}; SetPrivate(destination_context, proxy_func.As(), - context_bridge::kOriginalFunctionPrivateKey, func); + kOriginalFunctionPrivateKey, func); object_cache->CacheProxiedObject(value, proxy_func); return v8::MaybeLocal(proxy_func); } @@ -486,12 +482,11 @@ void ProxyFunctionWrapper(const v8::FunctionCallbackInfo& info) { // Pull the original function and its context off of the data private key v8::MaybeLocal sdp_value = - GetPrivate(calling_context, data, - context_bridge::kSupportsDynamicPropertiesPrivateKey); - v8::MaybeLocal maybe_func = GetPrivate( - calling_context, data, context_bridge::kProxyFunctionPrivateKey); - v8::MaybeLocal maybe_recv = GetPrivate( - calling_context, data, context_bridge::kProxyFunctionReceiverPrivateKey); + GetPrivate(calling_context, data, kSupportsDynamicPropertiesPrivateKey); + v8::MaybeLocal maybe_func = + GetPrivate(calling_context, data, kProxyFunctionPrivateKey); + v8::MaybeLocal maybe_recv = + GetPrivate(calling_context, data, kProxyFunctionReceiverPrivateKey); v8::Local func_value; if (sdp_value.IsEmpty() || maybe_func.IsEmpty() || maybe_recv.IsEmpty() || !gin::ConvertFromV8(args.isolate(), sdp_value.ToLocalChecked(), From e73d57cc082a24d0fc004b51fc1c10a8e034fd77 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sun, 29 Jun 2025 21:58:08 +0200 Subject: [PATCH 124/186] docs: update example apps (#47600) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Erick Zhao --- docs/tutorial/electron-versioning.md | 2 +- docs/why-electron.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/tutorial/electron-versioning.md b/docs/tutorial/electron-versioning.md index bfba4e2b0d22d..17504280ba3c7 100644 --- a/docs/tutorial/electron-versioning.md +++ b/docs/tutorial/electron-versioning.md @@ -143,7 +143,7 @@ The `electron/electron` repository also enforces squash merging, so you only nee ## Historical versioning (Electron 1.X) -Electron versions _< 2.0_ did not conform to the [SemVer](https://semver.org) spec: major versions corresponded to end-user API changes, minor versions corresponded to Chromium major releases, and patch versions corresponded to new features and bug fixes. While convenient for developers merging features, it creates problems for developers of client-facing applications. The QA testing cycles of major apps like Slack, Teams, Skype, VS Code, and GitHub Desktop can be lengthy and stability is a highly desired outcome. There is a high risk in adopting new features while trying to absorb bug fixes. +Electron versions _< 2.0_ did not conform to the [SemVer](https://semver.org) spec: major versions corresponded to end-user API changes, minor versions corresponded to Chromium major releases, and patch versions corresponded to new features and bug fixes. While convenient for developers merging features, it creates problems for developers of client-facing applications. The QA testing cycles of major apps like Slack, Teams, VS Code, and GitHub Desktop can be lengthy and stability is a highly desired outcome. There is a high risk in adopting new features while trying to absorb bug fixes. Here is an example of the 1.x strategy: diff --git a/docs/why-electron.md b/docs/why-electron.md index 4da202ee84fdf..51b81641f1142 100644 --- a/docs/why-electron.md +++ b/docs/why-electron.md @@ -44,7 +44,7 @@ Electron combines Chromium, Node.js, and the ability to write custom native code ### Enterprise-grade -Electron is reliable, secure, stable, and mature. It is the premier choice for companies building their flagship product. We have a list of some of those companies on our homepage, but just among chat apps, Slack, Discord, and Skype are built with Electron. Among AI applications, both OpenAI’s ChatGPT and Anthropic’s Claude use Electron. Visual Studio Code, Loom, Canva, Notion, Docker, and countless other leading developers of software bet on Electron. +Electron is reliable, secure, stable, and mature. It is the premier choice for companies building their flagship product. We have a list of some of those companies on our homepage, but just among chat apps, Slack, Discord, and Signal are built with Electron. Among AI applications, both OpenAI’s ChatGPT and Anthropic’s Claude use Electron. Visual Studio Code, Loom, Canva, Notion, Docker, and countless other leading developers of software bet on Electron. We did make it a priority to make Electron easy to work with and a delight for developers. That’s likely the main reason why Electron became as popular as it is today — but what keeps Electron alive and thriving is the maintainer’s focus on making Electron as stable, secure, performant, and capable of mission-critical use cases for end users as possible. We’re building an Electron that is ready to be used in scenarios where unfixable bugs, unpatched security holes, and outages of any kind are worst-case scenarios. From 47e927ac2b3282c2e13dd4bcd34a21e185b0bf94 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 30 Jun 2025 10:28:55 +0200 Subject: [PATCH 125/186] refactor: avoid copies of large objects in range based for loops (#47605) * Avoid copies of large objects in range-based for-loops. Xref: https://chromium-review.googlesource.com/c/chromium/src/+/6527689 Co-authored-by: Charles Kerr * Avoid copies of large objects in range-based for-loops in Browser::ShowAboutPanel() Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/browser_win.cc | 2 +- shell/browser/ui/webui/accessibility_ui.cc | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/shell/browser/browser_win.cc b/shell/browser/browser_win.cc index da035a79099fe..fb75895404eb2 100644 --- a/shell/browser/browser_win.cc +++ b/shell/browser/browser_win.cc @@ -754,7 +754,7 @@ void Browser::ShowAboutPanel() { "applicationName", "applicationVersion", "copyright", "credits"}; const std::string* str; - for (std::string opt : stringOptions) { + for (const std::string& opt : stringOptions) { if ((str = dict.FindString(opt))) { aboutMessage.append(*str).append("\r\n"); } diff --git a/shell/browser/ui/webui/accessibility_ui.cc b/shell/browser/ui/webui/accessibility_ui.cc index 05424f8182fd8..e774909aa3891 100644 --- a/shell/browser/ui/webui/accessibility_ui.cc +++ b/shell/browser/ui/webui/accessibility_ui.cc @@ -268,7 +268,7 @@ std::string RecursiveDumpAXPlatformNodeAsString( std::string line = node->GetDelegate()->GetData().ToString(); std::vector attributes = base::SplitString( line, " ", base::KEEP_WHITESPACE, base::SPLIT_WANT_NONEMPTY); - for (std::string attribute : attributes) { + for (const std::string& attribute : attributes) { if (ui::AXTreeFormatter::MatchesPropertyFilters(property_filters, attribute, false)) { str += attribute + " "; From 9aedb9c1f462bdfecade4a7c1952e68ffde8dc29 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 30 Jun 2025 10:29:14 +0200 Subject: [PATCH 126/186] perf: avoid copying a vector when calling ConvertToWeakPtrVector() (#47601) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/window_list.cc | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/shell/browser/window_list.cc b/shell/browser/window_list.cc index 188402d0e6bb1..f945dfa2270bf 100644 --- a/shell/browser/window_list.cc +++ b/shell/browser/window_list.cc @@ -6,20 +6,18 @@ #include +#include "base/containers/to_vector.h" #include "base/no_destructor.h" #include "shell/browser/native_window.h" #include "shell/browser/window_list_observer.h" namespace { + template -std::vector> ConvertToWeakPtrVector(std::vector raw_ptrs) { - std::vector> converted_to_weak; - converted_to_weak.reserve(raw_ptrs.size()); - for (auto* raw_ptr : raw_ptrs) { - converted_to_weak.push_back(raw_ptr->GetWeakPtr()); - } - return converted_to_weak; +auto ConvertToWeakPtrVector(const std::vector& raw_ptrs) { + return base::ToVector(raw_ptrs, [](T* t) { return t->GetWeakPtr(); }); } + } // namespace namespace electron { From bbf8003f0f9af80fb3504ab501c3bc7ad8389bb5 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 30 Jun 2025 10:59:18 +0200 Subject: [PATCH 127/186] test: fix nan tests on macOS (#47607) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- script/nan-spec-runner.js | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-) diff --git a/script/nan-spec-runner.js b/script/nan-spec-runner.js index 031062f4b3552..2abdfe85e91f4 100644 --- a/script/nan-spec-runner.js +++ b/script/nan-spec-runner.js @@ -46,20 +46,23 @@ async function main () { const platformFlags = []; if (process.platform === 'darwin') { const sdkPath = path.resolve(BASE, 'out', outDir, 'sdk', 'xcode_links'); - const sdks = (await fs.promises.readdir(sdkPath)).filter(fileName => fileName.endsWith('.sdk')); - const sdkToUse = sdks[0]; - if (!sdkToUse) { + const sdks = (await fs.promises.readdir(sdkPath)).filter(f => f.endsWith('.sdk')); + + if (!sdks.length) { console.error('Could not find an SDK to use for the NAN tests'); process.exit(1); } - if (sdks.length) { - console.warn(`Multiple SDKs found in the xcode_links directory - using ${sdkToUse}`); + const sdkToUse = sdks.sort((a, b) => { + const getVer = s => s.match(/(\d+)\.?(\d*)/)?.[0] || '0'; + return getVer(b).localeCompare(getVer(a), undefined, { numeric: true }); + })[0]; + + if (sdks.length > 1) { + console.warn(`Multiple SDKs found - using ${sdkToUse}`); } - platformFlags.push( - `-isysroot ${path.resolve(sdkPath, sdkToUse)}` - ); + platformFlags.push(`-isysroot ${path.resolve(sdkPath, sdkToUse)}`); } // TODO(ckerr) this is cribbed from read obj/electron/electron_app.ninja. From abba00867357cfbbce9db34ae0fb959e968e14c6 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Mon, 30 Jun 2025 11:00:22 +0200 Subject: [PATCH 128/186] chore: bump chromium to 138.0.7204.49 (37-x-y) (#47558) chore: bump chromium in DEPS to 138.0.7204.49 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> --- DEPS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DEPS b/DEPS index 58432b0d9f170..18cd2a59f660f 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.35', + '138.0.7204.49', 'node_version': 'v22.16.0', 'nan_version': From 2856008e52cd1b41030cbce610832c0a6ee9c506 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 30 Jun 2025 11:17:04 +0200 Subject: [PATCH 129/186] refactor: sync IsKillURL() with upstream impl in extension_tab_util.cc (#47595) Use base::MakeFixedFlatSet() Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/extensions/api/tabs/tabs_api.cc | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/shell/browser/extensions/api/tabs/tabs_api.cc b/shell/browser/extensions/api/tabs/tabs_api.cc index 50a8e2c371e97..29dd10e761eba 100644 --- a/shell/browser/extensions/api/tabs/tabs_api.cc +++ b/shell/browser/extensions/api/tabs/tabs_api.cc @@ -11,7 +11,7 @@ #include #include "base/command_line.h" -#include "base/containers/contains.h" +#include "base/containers/fixed_flat_set.h" #include "base/strings/pattern.h" #include "base/types/expected_macros.h" #include "chrome/common/url_constants.h" @@ -497,13 +497,16 @@ bool IsKillURL(const GURL& url) { } // Also disallow a few more hosts which are not covered by the check above. - static const char* const kKillHosts[] = { - chrome::kChromeUIDelayedHangUIHost, chrome::kChromeUIHangUIHost, - chrome::kChromeUIQuitHost, chrome::kChromeUIRestartHost, - content::kChromeUIBrowserCrashHost, content::kChromeUIMemoryExhaustHost, - }; + constexpr auto kKillHosts = base::MakeFixedFlatSet({ + chrome::kChromeUIDelayedHangUIHost, + chrome::kChromeUIHangUIHost, + chrome::kChromeUIQuitHost, + chrome::kChromeUIRestartHost, + content::kChromeUIBrowserCrashHost, + content::kChromeUIMemoryExhaustHost, + }); - return base::Contains(kKillHosts, url.host_piece()); + return kKillHosts.contains(url.host_piece()); } GURL ResolvePossiblyRelativeURL(const std::string& url_string, From fc55862138c270adbff4aa1ff1982d1671a2af03 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 30 Jun 2025 11:17:19 +0200 Subject: [PATCH 130/186] fix: Reland "[accessibility] Platform node lifetime cleanups" (#47611) Reland "[accessibility] Platform node lifetime cleanups" https://chromium-review.googlesource.com/c/chromium/src/+/6462552 Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/ui/webui/accessibility_ui.cc | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/shell/browser/ui/webui/accessibility_ui.cc b/shell/browser/ui/webui/accessibility_ui.cc index e774909aa3891..1caed7bd4e2f6 100644 --- a/shell/browser/ui/webui/accessibility_ui.cc +++ b/shell/browser/ui/webui/accessibility_ui.cc @@ -265,7 +265,8 @@ std::string RecursiveDumpAXPlatformNodeAsString( return ""; } std::string str(2 * indent, '+'); - std::string line = node->GetDelegate()->GetData().ToString(); + ui::AXPlatformNodeDelegate* const node_delegate = node->GetDelegate(); + std::string line = node_delegate->GetData().ToString(); std::vector attributes = base::SplitString( line, " ", base::KEEP_WHITESPACE, base::SPLIT_WANT_NONEMPTY); for (const std::string& attribute : attributes) { @@ -275,8 +276,9 @@ std::string RecursiveDumpAXPlatformNodeAsString( } } str += "\n"; - for (size_t i = 0; i < node->GetDelegate()->GetChildCount(); i++) { - gfx::NativeViewAccessible child = node->GetDelegate()->ChildAtIndex(i); + for (size_t i = 0, child_count = node_delegate->GetChildCount(); + i < child_count; i++) { + gfx::NativeViewAccessible child = node_delegate->ChildAtIndex(i); ui::AXPlatformNode* child_node = ui::AXPlatformNode::FromNativeViewAccessible(child); str += RecursiveDumpAXPlatformNodeAsString(child_node, indent + 1, From 65c062d3f9d686b17eb731aaa6385777f7a2163b Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Mon, 30 Jun 2025 14:49:16 +0200 Subject: [PATCH 131/186] chore: bump node to v22.17.0 (37-x-y) (#47555) * chore: bump node in DEPS to v22.17.0 * build: use //third_party/simdutf by default in GN https://github.com/nodejs/node/pull/58115 * chore: adjust crypto specs: - https://github.com/nodejs/node/pull/58117 - https://github.com/nodejs/node/pull/58387 * deps: update libuv to 1.51.0 https://github.com/nodejs/node/pull/58124 * test: fix test-buffer-tostring-range on allocation failure https://github.com/nodejs/node/pull/58416 * build: use FILE_OFFSET_BITS=64 esp. on 32-bit arch https://github.com/nodejs/node/pull/58090 * build: use //third_party/simdutf by default in GN https://github.com/nodejs/node/pull/58115 * inspector: add protocol method Network.dataReceived https://github.com/nodejs/node/pull/58001 * test: force slow JSON.stringify path for overflow https://github.com/nodejs/node/pull/58181 * chore: fixup patch indices * 6049967: Remove protocol::Maybe and roll inspector_protocol https://chromium-review.googlesource.com/c/chromium/src/+/6049967 * chore: fixup crypto test patch * src: fix module buffer allocation https://github.com/nodejs/node/pull/57738 * crypto: expose process.features.openssl_is_boringssl https://github.com/nodejs/node/pull/58387 * util: add internal assignFunctionName() function https://github.com/nodejs/node/pull/57916 * build: fix pointer compression builds https://github.com/nodejs/node/pull/58171 * chore: put back config options * fixup! deps: update libuv to 1.51.0 * chore: update patches --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr Co-authored-by: patchup[bot] <73610968+patchup[bot]@users.noreply.github.com> --- DEPS | 2 +- lib/node/asar-fs-wrapper.ts | 11 +- patches/node/.patches | 5 +- patches/node/build_add_gn_build_files.patch | 25 +- ...etraits_signatures_to_avoid_conflict.patch | 18 +- .../build_compile_with_c_20_support.patch | 6 +- patches/node/build_enable_perfetto.patch | 6 +- ...compilation_fails_if_not_using_a_new.patch | 18 +- ...f_original-fs_and_custom_embedder_js.patch | 2 +- ...o_use_custom_inspector_protocol_path.patch | 26 -- ...e_clang_as_default_compiler_on_macos.patch | 4 +- .../node/build_use_third_party_simdutf.patch | 20 - ...deprecation_ftbfs_in_simdjson_header.patch | 8 +- ...e_expose_importmoduledynamically_and.patch | 14 +- ...move_protocol_maybe_from_node_string.patch | 33 ++ ...cli_move_--trace-atomics-wait_to_eol.patch | 14 +- .../node/cli_remove_deprecated_v8_flag.patch | 8 +- ...enable_crashpad_linux_node_processes.patch | 10 +- .../expose_get_builtin_module_function.patch | 8 +- ...o_change_option_to_uv_loop_configure.patch | 92 ++-- ...matched-new-delete_in_debug_utils_cc.patch | 31 ++ ..._values_for_variables_in_common_gypi.patch | 4 +- ...g_fileexists_fn_to_legacymainresolve.patch | 10 +- ...ssert_module_in_the_renderer_process.patch | 4 +- .../node/fix_cppgc_initializing_twice.patch | 4 +- .../fix_crypto_tests_to_run_with_bssl.patch | 401 ++++-------------- ..._do_not_resolve_electron_entrypoints.patch | 2 +- ...se_readfilesync_override_for_modules.patch | 4 +- ...n_electron_module_via_the_esm_loader.patch | 4 +- ...ingssl_and_openssl_incompatibilities.patch | 29 +- ...in_esm_loaders_to_apply_asar_patches.patch | 2 +- ...ix_remove_deprecated_errno_constants.patch | 10 +- .../fix_remove_fastapitypedarray_usage.patch | 8 +- ...rmony-import-assertions_from_node_cc.patch | 4 +- ...pwritev64_before_preadv_pwritev_4683.patch | 51 --- .../pass_all_globals_through_require.patch | 2 +- ...dder_overriding_of_internal_fs_calls.patch | 2 +- ...ch_cppgc_heap_on_v8_isolate_creation.patch | 10 +- ..._on_wrapper-descriptor-based_cppheap.patch | 6 +- ...ted_fields_of_fastapicallbackoptions.patch | 4 +- .../node/support_v8_sandboxed_pointers.patch | 17 +- ...low_json_stringify_path_for_overflow.patch | 38 -- ...st_formally_mark_some_tests_as_flaky.patch | 2 +- 43 files changed, 359 insertions(+), 620 deletions(-) delete mode 100644 patches/node/build_use_third_party_simdutf.patch create mode 100644 patches/node/chore_remove_protocol_maybe_from_node_string.patch create mode 100644 patches/node/fix_-wmismatched-new-delete_in_debug_utils_cc.patch delete mode 100644 patches/node/linux_try_preadv64_pwritev64_before_preadv_pwritev_4683.patch delete mode 100644 patches/node/test_force_slow_json_stringify_path_for_overflow.patch diff --git a/DEPS b/DEPS index 18cd2a59f660f..ec3ebdcc5c512 100644 --- a/DEPS +++ b/DEPS @@ -4,7 +4,7 @@ vars = { 'chromium_version': '138.0.7204.49', 'node_version': - 'v22.16.0', + 'v22.17.0', 'nan_version': 'e14bdcd1f72d62bca1d541b66da43130384ec213', 'squirrel.mac_version': diff --git a/lib/node/asar-fs-wrapper.ts b/lib/node/asar-fs-wrapper.ts index 6ecaa0ac785b5..90d256342a060 100644 --- a/lib/node/asar-fs-wrapper.ts +++ b/lib/node/asar-fs-wrapper.ts @@ -54,6 +54,10 @@ const { getDirent } = __non_webpack_require__('internal/fs/utils'); +const { + assignFunctionName +} = __non_webpack_require__('internal/util'); + const { validateBoolean, validateFunction @@ -235,7 +239,10 @@ const overrideAPI = function (module: Record, name: string, pathArg }; if (old[util.promisify.custom]) { - module[name][util.promisify.custom] = makePromiseFunction(old[util.promisify.custom], pathArgumentIndex); + module[name][util.promisify.custom] = assignFunctionName( + name, + makePromiseFunction(old[util.promisify.custom], pathArgumentIndex) + ); } if (module.promises && module.promises[name]) { @@ -1238,7 +1245,7 @@ export const wrapFsWithAsar = (fs: Record) => { // command as a single path to an archive. const { exec, execSync } = childProcess; childProcess.exec = invokeWithNoAsar(exec); - childProcess.exec[util.promisify.custom] = invokeWithNoAsar(exec[util.promisify.custom]); + childProcess.exec[util.promisify.custom] = assignFunctionName('exec', invokeWithNoAsar(exec[util.promisify.custom])); childProcess.execSync = invokeWithNoAsar(execSync); overrideAPI(childProcess, 'execFile'); diff --git a/patches/node/.patches b/patches/node/.patches index d6d0530bffd23..ecbe186e500f9 100644 --- a/patches/node/.patches +++ b/patches/node/.patches @@ -34,10 +34,8 @@ fix_remove_harmony-import-assertions_from_node_cc.patch chore_disable_deprecation_ftbfs_in_simdjson_header.patch build_allow_unbundling_of_node_js_dependencies.patch test_use_static_method_names_in_call_stacks.patch -build_use_third_party_simdutf.patch fix_remove_fastapitypedarray_usage.patch test_handle_explicit_resource_management_globals.patch -linux_try_preadv64_pwritev64_before_preadv_pwritev_4683.patch build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch build_option_to_use_custom_inspector_protocol_path.patch fix_adjust_wpt_and_webidl_tests_for_enabled_float16array.patch @@ -48,4 +46,5 @@ cli_move_--trace-atomics-wait_to_eol.patch fix_cppgc_initializing_twice.patch fix_task_starvation_in_inspector_context_test.patch fix_expose_readfilesync_override_for_modules.patch -test_force_slow_json_stringify_path_for_overflow.patch +chore_remove_protocol_maybe_from_node_string.patch +fix_-wmismatched-new-delete_in_debug_utils_cc.patch diff --git a/patches/node/build_add_gn_build_files.patch b/patches/node/build_add_gn_build_files.patch index 6f6e1a48a0662..28ee7c05fe8b0 100644 --- a/patches/node/build_add_gn_build_files.patch +++ b/patches/node/build_add_gn_build_files.patch @@ -10,8 +10,21 @@ however those files were cherry-picked from main branch and do not really in 20/21. We have to wait until 22 is released to be able to build with upstream GN files. +diff --git a/configure.py b/configure.py +index 4560bac7b8e3c707ecea5a425f642efb9de9ed36..e9c2a4391f4058a21a259cacaac4fde5d199288e 100755 +--- a/configure.py ++++ b/configure.py +@@ -1722,7 +1722,7 @@ def configure_v8(o, configs): + # Until we manage to get rid of all those, v8_enable_sandbox cannot be used. + # Note that enabling pointer compression without enabling sandbox is unsupported by V8, + # so this can be broken at any time. +- o['variables']['v8_enable_sandbox'] = 0 ++ o['variables']['v8_enable_sandbox'] = 1 if options.enable_pointer_compression else 0 + o['variables']['v8_enable_pointer_compression_shared_cage'] = 1 if options.enable_pointer_compression else 0 + o['variables']['v8_enable_external_code_space'] = 1 if options.enable_pointer_compression else 0 + o['variables']['v8_enable_31bit_smis_on_64bit_arch'] = 1 if options.enable_pointer_compression else 0 diff --git a/node.gni b/node.gni -index a2123cc6c6d21c53fafc8934203b3720393e7b11..245a43920c7baf000ba63192a84a4c3fd219be7d 100644 +index 35ccd0487f20cece033d58827ecb7ed016908ee4..b4450e3dd17994d1eaf59eb5cff5912545e89793 100644 --- a/node.gni +++ b/node.gni @@ -5,10 +5,10 @@ @@ -55,10 +68,10 @@ index a2123cc6c6d21c53fafc8934203b3720393e7b11..245a43920c7baf000ba63192a84a4c3f assert(!node_enable_inspector || node_use_openssl, diff --git a/src/node_builtins.cc b/src/node_builtins.cc -index defb657a62a0316224a02b68505ac1142fd89d03..d637faac88875bfa110e2b8d1f53962061d98279 100644 +index 092341dbfbabe15b15ed43057d399f754505f6fd..f14b45850e42585f5686b7201e2b8281ed8c24e1 100644 --- a/src/node_builtins.cc +++ b/src/node_builtins.cc -@@ -785,6 +785,7 @@ void BuiltinLoader::RegisterExternalReferences( +@@ -788,6 +788,7 @@ void BuiltinLoader::RegisterExternalReferences( registry->Register(GetNatives); RegisterExternalReferencesForInternalizedBuiltinCode(registry); @@ -80,10 +93,10 @@ index f9426599f2d5dc6ad061407f0c4eb2c9203a4433..302030f610965f07dd6998d282275c1b // Handles compilation and caching of built-in JavaScript modules and // bootstrap scripts, whose source are bundled into the binary as static data. diff --git a/tools/install.py b/tools/install.py -index 17515720ba9c85d533465365188021074a8d30f4..92f83a83be67aafc9ead6923b868dbb0de39db34 100755 +index 8797b59e59c85a8877b977fa3281e50165e6f6b2..0af01e075616195f38fb242626dcab770ec1eb57 100755 --- a/tools/install.py +++ b/tools/install.py -@@ -212,6 +212,7 @@ def headers(options, action): +@@ -222,6 +222,7 @@ def headers(options, action): 'include/cppgc/internal/caged-heap-local-data.h', 'include/cppgc/internal/caged-heap.h', 'include/cppgc/internal/compiler-specific.h', @@ -91,7 +104,7 @@ index 17515720ba9c85d533465365188021074a8d30f4..92f83a83be67aafc9ead6923b868dbb0 'include/cppgc/internal/finalizer-trait.h', 'include/cppgc/internal/gc-info.h', 'include/cppgc/internal/logging.h', -@@ -291,6 +292,7 @@ def headers(options, action): +@@ -301,6 +302,7 @@ def headers(options, action): 'include/v8-promise.h', 'include/v8-proxy.h', 'include/v8-regexp.h', diff --git a/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch b/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch index 68cbb15ef5eaa..3054af71962d5 100644 --- a/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch +++ b/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch @@ -1,6 +1,6 @@ From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 From: Shelley Vohr -Date: Wed, 12 Feb 2025 15:31:07 +0100 +Date: Thu, 26 Jun 2025 09:25:24 +0000 Subject: build: change crdtp::ProtocolTypeTraits signatures to avoid conflict After https://github.com/nodejs/node/pull/56649 we see conflicts with the @@ -14,7 +14,7 @@ error: duplicate symbol: crdtp::ProtocolTypeTraitstokenizer()->TokenTag() == cbor::CBORTokenTag::STRING8) { span cbor_span = state->tokenizer()->GetString8(); value->assign(reinterpret_cast(cbor_span.data()), -@@ -24,12 +25,13 @@ bool ProtocolTypeTraits::Deserialize(DeserializerState* state, +@@ -24,7 +25,8 @@ bool ProtocolTypeTraits::Deserialize(DeserializerState* state, } void ProtocolTypeTraits::Serialize(const std::string& value, @@ -36,18 +36,12 @@ index 6db4bee1072bfe911a4179c3edb2bbaf18f1a182..c603f95f1f93438bd55bce3ff7f5bb31 + void* extra) { cbor::EncodeString8(SpanFrom(value), bytes); } -- - } // namespace crdtp -+ - namespace node { - namespace inspector { - namespace protocol { diff --git a/src/inspector/node_string.h b/src/inspector/node_string.h -index 38cf96e874dcc49cde87137b2737c35a84f418d0..b2f67c224acc7b3a3b867867e251a7c62833f46e 100644 +index 94ec9b2301998c4c5aad9ca3dae72ecf323fa0bb..a0d19a592d7bf9b00d6b98ef1ae931626ebb945c 100644 --- a/src/inspector/node_string.h +++ b/src/inspector/node_string.h -@@ -15,8 +15,8 @@ namespace crdtp { +@@ -19,8 +19,8 @@ namespace crdtp { template <> struct ProtocolTypeTraits { @@ -57,4 +51,4 @@ index 38cf96e874dcc49cde87137b2737c35a84f418d0..b2f67c224acc7b3a3b867867e251a7c6 + static void Serialize(const std::string& value, std::vector* bytes, void* extra = nullptr); }; - } // namespace crdtp + template <> diff --git a/patches/node/build_compile_with_c_20_support.patch b/patches/node/build_compile_with_c_20_support.patch index 10aec30f9fc6c..83862862dcd55 100644 --- a/patches/node/build_compile_with_c_20_support.patch +++ b/patches/node/build_compile_with_c_20_support.patch @@ -10,10 +10,10 @@ V8 requires C++20 support as of https://chromium-review.googlesource.com/c/v8/v8 This can be removed when Electron upgrades to a version of Node.js containing the required V8 version. diff --git a/common.gypi b/common.gypi -index f3476a91e4c3cda7cecf49e07bb594a167ac46ef..de73f6c18131f43e6fe3107c866599aa3398cf10 100644 +index 03fefab4b0a9727925411b95310831ffdc33e8d9..f9b5e47f1d67807435529c99d12f419d0fd4269f 100644 --- a/common.gypi +++ b/common.gypi -@@ -530,7 +530,7 @@ +@@ -538,7 +538,7 @@ '-fno-rtti', '-fno-exceptions', '-fno-strict-aliasing', @@ -22,7 +22,7 @@ index f3476a91e4c3cda7cecf49e07bb594a167ac46ef..de73f6c18131f43e6fe3107c866599aa ], 'defines': [ '__STDC_FORMAT_MACROS' ], 'ldflags': [ '-rdynamic' ], -@@ -700,7 +700,7 @@ +@@ -708,7 +708,7 @@ ['clang==1', { 'xcode_settings': { 'GCC_VERSION': 'com.apple.compilers.llvm.clang.1_0', diff --git a/patches/node/build_enable_perfetto.patch b/patches/node/build_enable_perfetto.patch index f0b97e2c4acae..1e2e8823fe0cb 100644 --- a/patches/node/build_enable_perfetto.patch +++ b/patches/node/build_enable_perfetto.patch @@ -64,10 +64,10 @@ index 251f51ec454f9cba4023b8b6729241ee753aac13..1de8cac6e3953ce9cab9db03530da327 module.exports = { diff --git a/node.gyp b/node.gyp -index ad010a8d99cf08013b7202eddce66e5b3885652d..d735b887d05ddfadec8e56dd8eae09646890aa84 100644 +index 0434887c363a586cbfa0438765fc8800d4237057..20fbf03cee24e66f9ad0d394dbcfa3ad03348890 100644 --- a/node.gyp +++ b/node.gyp -@@ -176,7 +176,6 @@ +@@ -175,7 +175,6 @@ 'src/timers.cc', 'src/timer_wrap.cc', 'src/tracing/agent.cc', @@ -75,7 +75,7 @@ index ad010a8d99cf08013b7202eddce66e5b3885652d..d735b887d05ddfadec8e56dd8eae0964 'src/tracing/node_trace_writer.cc', 'src/tracing/trace_event.cc', 'src/tracing/traced_value.cc', -@@ -305,7 +304,6 @@ +@@ -302,7 +301,6 @@ 'src/tcp_wrap.h', 'src/timers.h', 'src/tracing/agent.h', diff --git a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch index 0527e9476f670..259c40e0aeb53 100644 --- a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch +++ b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch @@ -7,10 +7,10 @@ Subject: build: ensure native module compilation fails if not using a new This should not be upstreamed, it is a quality-of-life patch for downstream module builders. diff --git a/common.gypi b/common.gypi -index d9c0b721fe0a629a30efb3c4e04905176ca0a7f5..f3476a91e4c3cda7cecf49e07bb594a167ac46ef 100644 +index bfe567e016cf102d2087f7647e64cc051116ab8d..03fefab4b0a9727925411b95310831ffdc33e8d9 100644 --- a/common.gypi +++ b/common.gypi -@@ -88,6 +88,8 @@ +@@ -89,6 +89,8 @@ 'v8_use_perfetto': 0, 'tsan%': 0, @@ -19,15 +19,17 @@ index d9c0b721fe0a629a30efb3c4e04905176ca0a7f5..f3476a91e4c3cda7cecf49e07bb594a1 ##### end V8 defaults ##### # When building native modules using 'npm install' with the system npm, -@@ -293,6 +295,7 @@ - # Defines these mostly for node-gyp to pickup. - 'defines': [ +@@ -297,7 +299,8 @@ '_GLIBCXX_USE_CXX11_ABI=1', + # This help forks when building Node.js on a 32-bit arch as + # libuv is always compiled with _FILE_OFFSET_BITS=64 +- '_FILE_OFFSET_BITS=64' ++ '_FILE_OFFSET_BITS=64', + 'ELECTRON_ENSURE_CONFIG_GYPI', ], # Forcibly disable -Werror. We support a wide range of compilers, it's -@@ -449,6 +452,11 @@ +@@ -454,6 +457,11 @@ }], ], }], @@ -40,10 +42,10 @@ index d9c0b721fe0a629a30efb3c4e04905176ca0a7f5..f3476a91e4c3cda7cecf49e07bb594a1 # list in v8/BUILD.gn. ['v8_enable_v8_checks == 1', { diff --git a/configure.py b/configure.py -index 932484674e5b15b765b8bfe307bdf99b49b5039f..befaa85527b9ebebad226e603586e23d04ec1e51 100755 +index e9c2a4391f4058a21a259cacaac4fde5d199288e..7821a0d3a7179a9e7fa9e48a062c2b0e7705ca6f 100755 --- a/configure.py +++ b/configure.py -@@ -1698,6 +1698,7 @@ def configure_library(lib, output, pkgname=None): +@@ -1704,6 +1704,7 @@ def configure_library(lib, output, pkgname=None): def configure_v8(o, configs): set_configuration_variable(configs, 'v8_enable_v8_checks', release=1, debug=0) diff --git a/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch b/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch index c4c54c21fdfe0..025e06ca2388a 100644 --- a/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch +++ b/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch @@ -34,7 +34,7 @@ index 411eab8136d5957ae8a491bc38ffbdc88e59f5da..63c93b5be09692d0d4b6bfbb214b173b let kResistStopPropagation; diff --git a/src/node_builtins.cc b/src/node_builtins.cc -index d637faac88875bfa110e2b8d1f53962061d98279..e0b58c4d0ac5640a677c22d710f88f1b318378d7 100644 +index f14b45850e42585f5686b7201e2b8281ed8c24e1..915b8cba6d512096e6090272ab3fbc63d5c61ce8 100644 --- a/src/node_builtins.cc +++ b/src/node_builtins.cc @@ -35,6 +35,7 @@ using v8::Value; diff --git a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch b/patches/node/build_option_to_use_custom_inspector_protocol_path.patch index 8e3aa3dbea37a..5b00462181125 100644 --- a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch +++ b/patches/node/build_option_to_use_custom_inspector_protocol_path.patch @@ -25,32 +25,6 @@ index 203b4abbc44df9e58083c819f61f9025104abdc6..73bf3839866a2652ca660f1117e8f249 # The NODE_MODULE_VERSION defined in node_version.h. node_module_version = exec_script("$node_path/tools/getmoduleversion.py", [], "value") -diff --git a/src/inspector/node_json.cc b/src/inspector/node_json.cc -index d8aacbdf1a8fc858c792ad3ce17ca2f46baebe7e..4625008c048532c2c3340130670647d2877430bd 100644 ---- a/src/inspector/node_json.cc -+++ b/src/inspector/node_json.cc -@@ -72,7 +72,7 @@ class ValueParserHandler : public ParserHandler { - - void HandleBinary(span bytes) override { - AddValueToParent( -- BinaryValue::create(Binary::fromSpan(bytes.data(), bytes.size()))); -+ BinaryValue::create(Binary::fromSpan(bytes))); - } - - void HandleDouble(double value) override { -diff --git a/src/inspector/node_string.h b/src/inspector/node_string.h -index b2f67c224acc7b3a3b867867e251a7c62833f46e..33e93ce5bf7dda7e30b7b1b198ff3b53ccfac22a 100644 ---- a/src/inspector/node_string.h -+++ b/src/inspector/node_string.h -@@ -66,7 +66,7 @@ class Binary { - static Binary fromBase64(const std::string_view base64, bool* success) { - UNREACHABLE(); - } -- static Binary fromSpan(const uint8_t* data, size_t size) { UNREACHABLE(); } -+ static Binary fromSpan(crdtp::span data) { UNREACHABLE(); } - }; - - } // namespace protocol diff --git a/src/inspector/unofficial.gni b/src/inspector/unofficial.gni index 3d7aa148678b2646b88fa7c32abec91791b02b82..4810d93eb971b253f7dadff7011a632f6dbe6a2b 100644 --- a/src/inspector/unofficial.gni diff --git a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch index 73e7e840edf73..d7262f8fc5c5a 100644 --- a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch +++ b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch @@ -11,10 +11,10 @@ node-gyp will use the result of `process.config` that reflects the environment in which the binary got built. diff --git a/common.gypi b/common.gypi -index de73f6c18131f43e6fe3107c866599aa3398cf10..e2171e14b9e29dfc3c629f8164545d56d5e9057e 100644 +index f9b5e47f1d67807435529c99d12f419d0fd4269f..c99f583d3674347dd6eb9a5eea1ed5588e376d31 100644 --- a/common.gypi +++ b/common.gypi -@@ -127,6 +127,7 @@ +@@ -128,6 +128,7 @@ 'v8_base': '<(PRODUCT_DIR)/obj.target/tools/v8_gypfiles/libv8_snapshot.a', }], ['OS=="mac"', { diff --git a/patches/node/build_use_third_party_simdutf.patch b/patches/node/build_use_third_party_simdutf.patch deleted file mode 100644 index 07d50bf3a9e44..0000000000000 --- a/patches/node/build_use_third_party_simdutf.patch +++ /dev/null @@ -1,20 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Charles Kerr -Date: Mon, 9 Dec 2024 11:18:51 -0600 -Subject: build: use third_party/simdutf - -use the Chromium version of simdutf to avoid duplicate symbols - -diff --git a/node.gni b/node.gni -index 56a554175b805c1703f13d62041f8c80d6e94dd9..203b4abbc44df9e58083c819f61f9025104abdc6 100644 ---- a/node.gni -+++ b/node.gni -@@ -14,7 +14,7 @@ declare_args() { - node_openssl_path = "//third_party/boringssl" - - # The location of simdutf - use the one from node's deps by default. -- node_simdutf_path = "$node_path/deps/simdutf" -+ node_simdutf_path = "//third_party/simdutf" - - # The NODE_MODULE_VERSION defined in node_version.h. - node_module_version = exec_script("$node_path/tools/getmoduleversion.py", [], "value") diff --git a/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch b/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch index a51aa2f27749d..0bde5d3fc9c81 100644 --- a/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch +++ b/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch @@ -11,10 +11,10 @@ Without this patch, building with simdjson fails with This patch can be removed once this is fixed upstream in simdjson. diff --git a/deps/simdjson/simdjson.h b/deps/simdjson/simdjson.h -index c1535ee81300b9cb93eb9ee6e769246793f936c3..3350287401e181e1d4ee432b8bd16081d0d7a73e 100644 +index a0d449975224a3e0db5c05de79b290763d6e390c..e77e47f972b4609e38aa8b68ab0d81ed1575effb 100644 --- a/deps/simdjson/simdjson.h +++ b/deps/simdjson/simdjson.h -@@ -3837,12 +3837,17 @@ inline std::ostream& operator<<(std::ostream& out, simdjson_result padded_string::load(std::string_view filen +@@ -4273,6 +4278,9 @@ inline simdjson_result padded_string::load(std::string_view filen } // namespace simdjson @@ -42,7 +42,7 @@ index c1535ee81300b9cb93eb9ee6e769246793f936c3..3350287401e181e1d4ee432b8bd16081 inline simdjson::padded_string operator ""_padded(const char *str, size_t len) { return simdjson::padded_string(str, len); } -@@ -4250,6 +4258,8 @@ inline simdjson::padded_string operator ""_padded(const char8_t *str, size_t len +@@ -4281,6 +4289,8 @@ inline simdjson::padded_string operator ""_padded(const char8_t *str, size_t len return simdjson::padded_string(reinterpret_cast(str), len); } #endif diff --git a/patches/node/chore_expose_importmoduledynamically_and.patch b/patches/node/chore_expose_importmoduledynamically_and.patch index 5e9f79e6ff54d..497ea5842d984 100644 --- a/patches/node/chore_expose_importmoduledynamically_and.patch +++ b/patches/node/chore_expose_importmoduledynamically_and.patch @@ -11,7 +11,7 @@ its own blended handler between Node and Blink. Not upstreamable. diff --git a/lib/internal/modules/esm/utils.js b/lib/internal/modules/esm/utils.js -index fd17ce8695c55f8f38ed19d59960acc1a7692bc8..96754db3277b3a0445b69275368602166c6d5423 100644 +index 9d6f850f667c5186efe6855bc3d5f5af332bdaa7..8521759e20adf53024e5893dbf3cb36e1752085e 100644 --- a/lib/internal/modules/esm/utils.js +++ b/lib/internal/modules/esm/utils.js @@ -30,7 +30,7 @@ const { @@ -40,10 +40,10 @@ index fd17ce8695c55f8f38ed19d59960acc1a7692bc8..96754db3277b3a0445b6927536860216 /** diff --git a/src/module_wrap.cc b/src/module_wrap.cc -index 912acc8da815405531d8b527383f19c3731be100..8d48f4693c3b5f0d1d94d3edadc48c4f36d1bf97 100644 +index cdd0ba00eb0cafbc79b816017423f9021ca2979d..6916497f6feb14e482cf5080b57d639ae7292d20 100644 --- a/src/module_wrap.cc +++ b/src/module_wrap.cc -@@ -858,7 +858,7 @@ MaybeLocal ModuleWrap::ResolveModuleCallback( +@@ -875,7 +875,7 @@ MaybeLocal ModuleWrap::ResolveModuleCallback( return module->module_.Get(isolate); } @@ -52,7 +52,7 @@ index 912acc8da815405531d8b527383f19c3731be100..8d48f4693c3b5f0d1d94d3edadc48c4f Local context, Local host_defined_options, Local resource_name, -@@ -923,12 +923,13 @@ void ModuleWrap::SetImportModuleDynamicallyCallback( +@@ -947,12 +947,13 @@ void ModuleWrap::SetImportModuleDynamicallyCallback( Realm* realm = Realm::GetCurrent(args); HandleScope handle_scope(isolate); @@ -68,7 +68,7 @@ index 912acc8da815405531d8b527383f19c3731be100..8d48f4693c3b5f0d1d94d3edadc48c4f } void ModuleWrap::HostInitializeImportMetaObjectCallback( -@@ -970,13 +971,14 @@ void ModuleWrap::SetInitializeImportMetaObjectCallback( +@@ -994,13 +995,14 @@ void ModuleWrap::SetInitializeImportMetaObjectCallback( Realm* realm = Realm::GetCurrent(args); Isolate* isolate = realm->isolate(); @@ -87,7 +87,7 @@ index 912acc8da815405531d8b527383f19c3731be100..8d48f4693c3b5f0d1d94d3edadc48c4f MaybeLocal ModuleWrap::SyntheticModuleEvaluationStepsCallback( diff --git a/src/module_wrap.h b/src/module_wrap.h -index 83b5793013cbc453cf92c0a006fc7be3c06ad276..90353954bc497cb4ae413dc134850f8abb4efc7c 100644 +index ef4dfd1d6b091d2b0f71b946904a47415b6435ba..862f946a75f2a2949d7eeb7f97e96289beab8078 100644 --- a/src/module_wrap.h +++ b/src/module_wrap.h @@ -8,6 +8,7 @@ @@ -123,7 +123,7 @@ index 83b5793013cbc453cf92c0a006fc7be3c06ad276..90353954bc497cb4ae413dc134850f8a private: ModuleWrap(Realm* realm, v8::Local object, -@@ -129,7 +139,6 @@ class ModuleWrap : public BaseObject { +@@ -130,7 +140,6 @@ class ModuleWrap : public BaseObject { v8::Local specifier, v8::Local import_attributes, v8::Local referrer); diff --git a/patches/node/chore_remove_protocol_maybe_from_node_string.patch b/patches/node/chore_remove_protocol_maybe_from_node_string.patch new file mode 100644 index 0000000000000..12352945185c9 --- /dev/null +++ b/patches/node/chore_remove_protocol_maybe_from_node_string.patch @@ -0,0 +1,33 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Shelley Vohr +Date: Thu, 26 Jun 2025 09:20:43 +0000 +Subject: chore: remove protocol::Maybe from node_string + +It was removed upstream in https://chromium-review.googlesource.com/c/chromium/src/+/6049967. + +This should be upstreamed. + +diff --git a/src/inspector/node_string.h b/src/inspector/node_string.h +index a0d19a592d7bf9b00d6b98ef1ae931626ebb945c..ddedca4a5b9b35258050f8b4cb446ceeba956896 100644 +--- a/src/inspector/node_string.h ++++ b/src/inspector/node_string.h +@@ -6,7 +6,6 @@ + #include + #include + #include +-#include "crdtp/maybe.h" + #include "crdtp/protocol_core.h" + #include "util.h" + #include "v8-inspector.h" +@@ -31,11 +30,6 @@ struct ProtocolTypeTraits { + std::vector* bytes); + }; + +-template <> +-struct detail::MaybeTypedef { +- typedef ValueMaybe type; +-}; +- + } // namespace crdtp + + namespace node { diff --git a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch index 6eec17ed7bf01..681ea40add6e0 100644 --- a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch +++ b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch @@ -15,10 +15,10 @@ Reviewed-By: Benjamin Gruenbaum Reviewed-By: Yagiz Nizipli diff --git a/doc/api/cli.md b/doc/api/cli.md -index 121d8f2bbd2b1d93067a06a902b1e7b986bcdb49..3460ad33c6186dcc3aa3281d80b723a1cc1d50dd 100644 +index d924287df3ca29681cf71e2fbd402314ce8edd97..f2f4d25a838b9758234cd667b0fb537d0d0fcced 100644 --- a/doc/api/cli.md +++ b/doc/api/cli.md -@@ -3367,7 +3367,6 @@ one is included in the list below. +@@ -3386,7 +3386,6 @@ one is included in the list below. * `--tls-min-v1.1` * `--tls-min-v1.2` * `--tls-min-v1.3` @@ -43,7 +43,7 @@ index 663d123ac728f097e8a76c94cf10c53d059983d7..497f5a61182beafbaa26b94518105635 Print stack traces for deprecations. . diff --git a/src/node.cc b/src/node.cc -index 6f8f6386d0db8aef1e2e0126cc9064101cbe6112..bc670a6c8b5027417cdc35e1cd94a60f63fd342d 100644 +index 0c2a4d344c991c2ca0d9d90934cf7921abf2a629..19d9fb77f1aaf003e43b7d7016f45e6c35df06b3 100644 --- a/src/node.cc +++ b/src/node.cc @@ -232,44 +232,6 @@ void Environment::WaitForInspectorFrontendByOptions() { @@ -110,10 +110,10 @@ index 6f8f6386d0db8aef1e2e0126cc9064101cbe6112..bc670a6c8b5027417cdc35e1cd94a60f isolate_->SetPromiseHook(TracePromises); } diff --git a/src/node_options.cc b/src/node_options.cc -index a9500716f2a955fc591628a969c5fba40783a2e7..b153d2c6a771e80bcdf5ed6adbc1cd225b3bf97e 100644 +index 9829b0b2b2d013b93ac14d3ec6d46c35abcc4635..5fb2e713a50185b997935cb15fddd7b8b65a5b82 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -770,10 +770,6 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() { +@@ -773,10 +773,6 @@ EnvironmentOptionsParser::EnvironmentOptionsParser() { "throw an exception on deprecations", &EnvironmentOptions::throw_deprecation, kAllowedInEnvvar); @@ -125,10 +125,10 @@ index a9500716f2a955fc591628a969c5fba40783a2e7..b153d2c6a771e80bcdf5ed6adbc1cd22 "show stack traces on deprecations", &EnvironmentOptions::trace_deprecation, diff --git a/src/node_options.h b/src/node_options.h -index 60068b008b2e2a034c3f0c58b947a8d04d55e3b2..d821bc6a9adf28ea312a9c446f8acfc8ed586ae3 100644 +index eb18fdd617fd19e5b97cd67f351e70c28fee3e75..216c0f92167bd131e5ef2ea96ad47425ff51c3f7 100644 --- a/src/node_options.h +++ b/src/node_options.h -@@ -203,7 +203,6 @@ class EnvironmentOptions : public Options { +@@ -204,7 +204,6 @@ class EnvironmentOptions : public Options { std::vector coverage_include_pattern; std::vector coverage_exclude_pattern; bool throw_deprecation = false; diff --git a/patches/node/cli_remove_deprecated_v8_flag.patch b/patches/node/cli_remove_deprecated_v8_flag.patch index 70a46ac99e195..f4525f0ae0d24 100644 --- a/patches/node/cli_remove_deprecated_v8_flag.patch +++ b/patches/node/cli_remove_deprecated_v8_flag.patch @@ -18,10 +18,10 @@ Reviewed-By: MichaĆ«l Zasso Reviewed-By: Yagiz Nizipli diff --git a/doc/api/cli.md b/doc/api/cli.md -index 6f984926a62973ba36bd3c27cc39b01f2bcac819..121d8f2bbd2b1d93067a06a902b1e7b986bcdb49 100644 +index cc311472678108f21eed70281e91b0d40c5fe7b6..d924287df3ca29681cf71e2fbd402314ce8edd97 100644 --- a/doc/api/cli.md +++ b/doc/api/cli.md -@@ -3404,7 +3404,6 @@ V8 options that are allowed are: +@@ -3423,7 +3423,6 @@ V8 options that are allowed are: * `--disallow-code-generation-from-strings` * `--enable-etw-stack-walking` * `--expose-gc` @@ -30,10 +30,10 @@ index 6f984926a62973ba36bd3c27cc39b01f2bcac819..121d8f2bbd2b1d93067a06a902b1e7b9 * `--jitless` * `--max-old-space-size` diff --git a/src/node_options.cc b/src/node_options.cc -index bb1e80ece4158dfed1b8bab7dc6d00dd56505aac..a9500716f2a955fc591628a969c5fba40783a2e7 100644 +index d2e945b1d6ef6729709cc73c238cfae46d4e56b6..9829b0b2b2d013b93ac14d3ec6d46c35abcc4635 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -992,11 +992,6 @@ PerIsolateOptionsParser::PerIsolateOptionsParser( +@@ -995,11 +995,6 @@ PerIsolateOptionsParser::PerIsolateOptionsParser( "disallow eval and friends", V8Option{}, kAllowedInEnvvar); diff --git a/patches/node/enable_crashpad_linux_node_processes.patch b/patches/node/enable_crashpad_linux_node_processes.patch index 4204092a3ea56..158a8bdeff2da 100644 --- a/patches/node/enable_crashpad_linux_node_processes.patch +++ b/patches/node/enable_crashpad_linux_node_processes.patch @@ -8,10 +8,10 @@ to child processes spawned with `ELECTRON_RUN_AS_NODE` which is used by the crashpad client to connect with the handler process. diff --git a/lib/child_process.js b/lib/child_process.js -index bb27670112c1ea42c7ff00883fe4b684544d9cd4..4d4da798ce59ce42e42d1f05fccf07699c033d46 100644 +index e848b3d5ee9b13ea3ea303eb3b57ef47ef951580..5b89c420f1a917526ab311fed52bff01637a86fe 100644 --- a/lib/child_process.js +++ b/lib/child_process.js -@@ -61,6 +61,7 @@ let debug = require('internal/util/debuglog').debuglog( +@@ -62,6 +62,7 @@ let debug = require('internal/util/debuglog').debuglog( ); const { Buffer } = require('buffer'); const { Pipe, constants: PipeConstants } = internalBinding('pipe_wrap'); @@ -19,7 +19,7 @@ index bb27670112c1ea42c7ff00883fe4b684544d9cd4..4d4da798ce59ce42e42d1f05fccf0769 const { AbortError, -@@ -153,7 +154,6 @@ function fork(modulePath, args = [], options) { +@@ -154,7 +155,6 @@ function fork(modulePath, args = [], options) { ArrayPrototypeSplice(execArgv, index - 1, 2); } } @@ -27,7 +27,7 @@ index bb27670112c1ea42c7ff00883fe4b684544d9cd4..4d4da798ce59ce42e42d1f05fccf0769 args = [...execArgv, modulePath, ...args]; if (typeof options.stdio === 'string') { -@@ -609,6 +609,22 @@ function normalizeSpawnArguments(file, args, options) { +@@ -610,6 +610,22 @@ function normalizeSpawnArguments(file, args, options) { 'options.windowsVerbatimArguments'); } @@ -50,7 +50,7 @@ index bb27670112c1ea42c7ff00883fe4b684544d9cd4..4d4da798ce59ce42e42d1f05fccf0769 if (options.shell) { validateArgumentNullCheck(options.shell, 'options.shell'); const command = ArrayPrototypeJoin([file, ...args], ' '); -@@ -642,7 +658,6 @@ function normalizeSpawnArguments(file, args, options) { +@@ -643,7 +659,6 @@ function normalizeSpawnArguments(file, args, options) { ArrayPrototypeUnshift(args, file); } diff --git a/patches/node/expose_get_builtin_module_function.patch b/patches/node/expose_get_builtin_module_function.patch index bee428c167591..8b95ccbe3290c 100644 --- a/patches/node/expose_get_builtin_module_function.patch +++ b/patches/node/expose_get_builtin_module_function.patch @@ -9,10 +9,10 @@ modules to sandboxed renderers. TODO(codebytere): remove and replace with a public facing API. diff --git a/src/node_binding.cc b/src/node_binding.cc -index 6c337232149ccb8bdb1188e72d59a052b1cb79c1..44ad4a480a33a2c39494a7d961318270a25620d8 100644 +index aa4213c3622eab077fa8d764775c1f95c6313e34..11f722d2d7c21079cbc65033429086231a786ca7 100644 --- a/src/node_binding.cc +++ b/src/node_binding.cc -@@ -653,6 +653,10 @@ void GetInternalBinding(const FunctionCallbackInfo& args) { +@@ -652,6 +652,10 @@ void GetInternalBinding(const FunctionCallbackInfo& args) { args.GetReturnValue().Set(exports); } @@ -24,10 +24,10 @@ index 6c337232149ccb8bdb1188e72d59a052b1cb79c1..44ad4a480a33a2c39494a7d961318270 Environment* env = Environment::GetCurrent(args); diff --git a/src/node_binding.h b/src/node_binding.h -index eb1364cb01a2bea52bce768056e73b0f3a86ae35..d421a2773403e7b22fcca2fcf8275ef2d9654c55 100644 +index 611f38ef5e21cc303127326d50c648fbb557b4da..3d95ad2733dc83d0b7d37d57c337732c8a0e83d7 100644 --- a/src/node_binding.h +++ b/src/node_binding.h -@@ -146,6 +146,8 @@ void GetInternalBinding(const v8::FunctionCallbackInfo& args); +@@ -154,6 +154,8 @@ void GetInternalBinding(const v8::FunctionCallbackInfo& args); void GetLinkedBinding(const v8::FunctionCallbackInfo& args); void DLOpen(const v8::FunctionCallbackInfo& args); diff --git a/patches/node/feat_add_uv_loop_interrupt_on_io_change_option_to_uv_loop_configure.patch b/patches/node/feat_add_uv_loop_interrupt_on_io_change_option_to_uv_loop_configure.patch index 5fd144ea0a870..32992b2832354 100644 --- a/patches/node/feat_add_uv_loop_interrupt_on_io_change_option_to_uv_loop_configure.patch +++ b/patches/node/feat_add_uv_loop_interrupt_on_io_change_option_to_uv_loop_configure.patch @@ -23,10 +23,10 @@ index d1f41e1c9f44838410326df23b1b175fa16ba199..dcf69093469b611a6f9db2bb84530456 asynchronous file system operations. diff --git a/deps/uv/include/uv.h b/deps/uv/include/uv.h -index 9e450c5110fe57117b686bf683cc6631f37efaeb..f75a496071ac3396cbc6dec819eaab7294609deb 100644 +index 938e998fdc54d17c8d0d4b1949087b968044829f..0295eeddbb4eb1cffd9dbcd02e037907fadc1b7e 100644 --- a/deps/uv/include/uv.h +++ b/deps/uv/include/uv.h -@@ -261,6 +261,7 @@ typedef struct uv_metrics_s uv_metrics_t; +@@ -263,6 +263,7 @@ typedef struct uv_metrics_s uv_metrics_t; typedef enum { UV_LOOP_BLOCK_SIGNAL = 0, UV_METRICS_IDLE_TIME, @@ -35,18 +35,27 @@ index 9e450c5110fe57117b686bf683cc6631f37efaeb..f75a496071ac3396cbc6dec819eaab72 #define UV_LOOP_USE_IO_URING_SQPOLL UV_LOOP_USE_IO_URING_SQPOLL } uv_loop_option; diff --git a/deps/uv/src/unix/async.c b/deps/uv/src/unix/async.c -index 0ff2669e30a628dbb2df9e28ba14b38cf14114e5..117190ef26338944b78dbed7380c631de8057223 100644 +index 538ae7876f2b2463716459b179d74843383295be..6ce53f12834c7a34241ea0865bda99af0541ea5f 100644 --- a/deps/uv/src/unix/async.c +++ b/deps/uv/src/unix/async.c -@@ -38,7 +38,6 @@ - #include +@@ -40,7 +40,7 @@ + + #if UV__KQUEUE_EVFILT_USER + static uv_once_t kqueue_runtime_detection_guard = UV_ONCE_INIT; +-static int kqueue_evfilt_user_support = 1; ++int kqueue_evfilt_user_support = 1; + + + static void uv__kqueue_runtime_detection(void) { +@@ -66,7 +66,6 @@ static void uv__kqueue_runtime_detection(void) { + } #endif -static void uv__async_send(uv_loop_t* loop); static int uv__async_start(uv_loop_t* loop); static void uv__cpu_relax(void); -@@ -78,7 +77,7 @@ int uv_async_send(uv_async_t* handle) { +@@ -106,7 +105,7 @@ int uv_async_send(uv_async_t* handle) { /* Wake up the other thread's event loop. */ if (atomic_exchange(pending, 1) == 0) @@ -55,7 +64,7 @@ index 0ff2669e30a628dbb2df9e28ba14b38cf14114e5..117190ef26338944b78dbed7380c631d /* Set the loop to not-busy. */ atomic_fetch_add(busy, -1); -@@ -178,39 +177,6 @@ static void uv__async_io(uv_loop_t* loop, uv__io_t* w, unsigned int events) { +@@ -210,50 +209,6 @@ static void uv__async_io(uv_loop_t* loop, uv__io_t* w, unsigned int events) { } @@ -76,6 +85,17 @@ index 0ff2669e30a628dbb2df9e28ba14b38cf14114e5..117190ef26338944b78dbed7380c631d - len = sizeof(val); - fd = loop->async_io_watcher.fd; /* eventfd */ - } +-#elif UV__KQUEUE_EVFILT_USER +- struct kevent ev; +- +- if (kqueue_evfilt_user_support) { +- fd = loop->async_io_watcher.fd; /* magic number for EVFILT_USER */ +- EV_SET(&ev, fd, EVFILT_USER, 0, NOTE_TRIGGER, 0, 0); +- r = kevent(loop->backend_fd, &ev, 1, NULL, 0, NULL); +- if (r == 0) +- return; +- abort(); +- } -#endif - - do @@ -96,20 +116,20 @@ index 0ff2669e30a628dbb2df9e28ba14b38cf14114e5..117190ef26338944b78dbed7380c631d static int uv__async_start(uv_loop_t* loop) { int pipefd[2]; diff --git a/deps/uv/src/unix/core.c b/deps/uv/src/unix/core.c -index 0c52ccf2ad7b2dcae77a7bc4b3af9d1a1346ce18..13cd33a7d3031c5e19c9418a18217d1e4158c82e 100644 +index bd51b69b8120e878f3342c2812fb1f4c0fd35071..4c005360c8d83955b727bde3c0ff0bc3e32061a4 100644 --- a/deps/uv/src/unix/core.c +++ b/deps/uv/src/unix/core.c -@@ -937,6 +937,9 @@ void uv__io_start(uv_loop_t* loop, uv__io_t* w, unsigned int events) { - loop->watchers[w->fd] = w; +@@ -944,6 +944,9 @@ int uv__io_start(uv_loop_t* loop, uv__io_t* w, unsigned int events) { loop->nfds++; } -+ + + if (uv__get_internal_fields(loop)->flags & UV_LOOP_INTERRUPT_ON_IO_CHANGE) + uv__loop_interrupt(loop); ++ + return 0; } - -@@ -968,6 +971,9 @@ void uv__io_stop(uv_loop_t* loop, uv__io_t* w, unsigned int events) { +@@ -993,6 +996,9 @@ void uv__io_stop(uv_loop_t* loop, uv__io_t* w, unsigned int events) { } else if (uv__queue_empty(&w->watcher_queue)) uv__queue_insert_tail(&loop->watcher_queue, &w->watcher_queue); @@ -119,7 +139,7 @@ index 0c52ccf2ad7b2dcae77a7bc4b3af9d1a1346ce18..13cd33a7d3031c5e19c9418a18217d1e } -@@ -984,6 +990,9 @@ void uv__io_close(uv_loop_t* loop, uv__io_t* w) { +@@ -1009,6 +1015,9 @@ void uv__io_close(uv_loop_t* loop, uv__io_t* w) { void uv__io_feed(uv_loop_t* loop, uv__io_t* w) { if (uv__queue_empty(&w->pending_queue)) uv__queue_insert_tail(&loop->pending_queue, &w->pending_queue); @@ -129,11 +149,24 @@ index 0c52ccf2ad7b2dcae77a7bc4b3af9d1a1346ce18..13cd33a7d3031c5e19c9418a18217d1e } +diff --git a/deps/uv/src/unix/internal.h b/deps/uv/src/unix/internal.h +index a1d7d4366308acb6ba8d2b84b7a2be4b89abe2ce..a86505eba1243a8c89d77a1d036d16ac8313a785 100644 +--- a/deps/uv/src/unix/internal.h ++++ b/deps/uv/src/unix/internal.h +@@ -523,6 +523,8 @@ int uv__get_constrained_cpu(long long* quota); + * people will be directed here if this number gets printed due to some + * kqueue error and they google for help. */ + #define UV__KQUEUE_EVFILT_USER_IDENT 0x1e7e7711 ++/* Global variable to cache kqueue EVFILT_USER support detection result */ ++extern int kqueue_evfilt_user_support; + #else + #define UV__KQUEUE_EVFILT_USER 0 + #endif diff --git a/deps/uv/src/unix/loop.c b/deps/uv/src/unix/loop.c -index 179ee999d8052e779dc692aeb5b673d210aaa997..03cca2c491015e5ef958f61a0167d29dfc56e247 100644 +index 5d3f0c7a348b334e5651bf8682fe29b355ec0cb9..d0b8686783d009365e89731366afee1878a6757b 100644 --- a/deps/uv/src/unix/loop.c +++ b/deps/uv/src/unix/loop.c -@@ -224,6 +224,10 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap) { +@@ -228,6 +228,10 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap) { } #endif @@ -144,7 +177,7 @@ index 179ee999d8052e779dc692aeb5b673d210aaa997..03cca2c491015e5ef958f61a0167d29d if (option != UV_LOOP_BLOCK_SIGNAL) return UV_ENOSYS; -@@ -234,3 +238,40 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap) { +@@ -238,3 +242,51 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap) { loop->flags |= UV_LOOP_BLOCK_SIGPROF; return 0; } @@ -167,6 +200,17 @@ index 179ee999d8052e779dc692aeb5b673d210aaa997..03cca2c491015e5ef958f61a0167d29d + len = sizeof(val); + fd = loop->async_io_watcher.fd; /* eventfd */ + } ++#elif UV__KQUEUE_EVFILT_USER ++ struct kevent ev; ++ ++ if (kqueue_evfilt_user_support) { ++ fd = loop->async_io_watcher.fd; /* magic number for EVFILT_USER */ ++ EV_SET(&ev, fd, EVFILT_USER, 0, NOTE_TRIGGER, 0, 0); ++ r = kevent(loop->backend_fd, &ev, 1, NULL, 0, NULL); ++ if (r == 0) ++ return; ++ abort(); ++ } +#endif + + do @@ -186,10 +230,10 @@ index 179ee999d8052e779dc692aeb5b673d210aaa997..03cca2c491015e5ef958f61a0167d29d + abort(); +} diff --git a/deps/uv/src/uv-common.h b/deps/uv/src/uv-common.h -index 4baede2e506ee1787d554a0ec75bc9eb346fc8f2..385d4f420b50bfd2dc23f119d535c0442a3ce4e7 100644 +index b9a8e976eefdd62cfad31f6d3ed9b6179776eaa4..985b8fa3f2594f729af1845334b4afade3e054ee 100644 --- a/deps/uv/src/uv-common.h +++ b/deps/uv/src/uv-common.h -@@ -144,6 +144,8 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap); +@@ -149,6 +149,8 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap); void uv__loop_close(uv_loop_t* loop); @@ -198,7 +242,7 @@ index 4baede2e506ee1787d554a0ec75bc9eb346fc8f2..385d4f420b50bfd2dc23f119d535c044 int uv__read_start(uv_stream_t* stream, uv_alloc_cb alloc_cb, uv_read_cb read_cb); -@@ -280,6 +282,10 @@ void uv__threadpool_cleanup(void); +@@ -291,6 +293,10 @@ void uv__threadpool_cleanup(void); if (((h)->flags & UV_HANDLE_ACTIVE) != 0) break; \ (h)->flags |= UV_HANDLE_ACTIVE; \ if (((h)->flags & UV_HANDLE_REF) != 0) uv__active_handle_add(h); \ @@ -210,7 +254,7 @@ index 4baede2e506ee1787d554a0ec75bc9eb346fc8f2..385d4f420b50bfd2dc23f119d535c044 while (0) diff --git a/deps/uv/src/win/core.c b/deps/uv/src/win/core.c -index e9885a0f1ff3890a8d957c8793e22b01cedc0e97..ae3d09878253fe7169ad7b74b3faea0223f89de5 100644 +index 5f41c87ad5ed137c51b43e4941414c89ddff5216..73f26c68e5734d340fe210b4418f0161dc172182 100644 --- a/deps/uv/src/win/core.c +++ b/deps/uv/src/win/core.c @@ -384,10 +384,20 @@ int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap) { @@ -459,10 +503,10 @@ index 6e9917239aa5626dd56fffd6eb2469d3e63224bf..b0da9d1cddc69428e9fb3379d1338cf8 MAKE_VALGRIND_HAPPY(loop); return 0; diff --git a/deps/uv/test/test-list.h b/deps/uv/test/test-list.h -index e07bd61ecf73c122a553d5d8232a7478980751a5..21cf8c09edac15ba5ea010d54d3e158e0d1b7e5b 100644 +index 0dea544699d75fcf11d4a8b6a7f0d5f4242f892a..6f8c70bc8b6cb2d2ffc1f63fe60920f8fb8a1abe 100644 --- a/deps/uv/test/test-list.h +++ b/deps/uv/test/test-list.h -@@ -279,6 +279,7 @@ TEST_DECLARE (process_priority) +@@ -281,6 +281,7 @@ TEST_DECLARE (process_priority) TEST_DECLARE (has_ref) TEST_DECLARE (active) TEST_DECLARE (embed) @@ -470,7 +514,7 @@ index e07bd61ecf73c122a553d5d8232a7478980751a5..21cf8c09edac15ba5ea010d54d3e158e TEST_DECLARE (async) TEST_DECLARE (async_null_cb) TEST_DECLARE (eintr_handling) -@@ -919,6 +920,7 @@ TASK_LIST_START +@@ -929,6 +930,7 @@ TASK_LIST_START TEST_ENTRY (active) TEST_ENTRY (embed) diff --git a/patches/node/fix_-wmismatched-new-delete_in_debug_utils_cc.patch b/patches/node/fix_-wmismatched-new-delete_in_debug_utils_cc.patch new file mode 100644 index 0000000000000..f06d854cdddb4 --- /dev/null +++ b/patches/node/fix_-wmismatched-new-delete_in_debug_utils_cc.patch @@ -0,0 +1,31 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Shelley Vohr +Date: Thu, 26 Jun 2025 12:46:41 +0000 +Subject: fix: -Wmismatched-new-delete in debug_utils.cc + +Fixes the following error: + +Error: ../../third_party/electron_node/src/debug_utils.cc(491,11): error: 'delete' applied to a pointer that was allocated with 'new[]'; did you mean 'delete[]'? [-Werror,-Wmismatched-new-delete] + 491 | delete str; + | ^ + | [] +../../third_party/electron_node/src/debug_utils.cc(487,23): note: allocated with 'new[]' here + 487 | char* str = new char[size]; + | ^ +1 error generated. + +Upstreamed in https://github.com/nodejs/node/pull/58844. + +diff --git a/src/debug_utils.cc b/src/debug_utils.cc +index 97884b9a0f8d6d88e36da06b05642505c767338d..65283ef31da35d0f08fcff7a5e79bf960d861126 100644 +--- a/src/debug_utils.cc ++++ b/src/debug_utils.cc +@@ -488,7 +488,7 @@ std::vector NativeSymbolDebuggingContext::GetLoadedLibraries() { + WideCharToMultiByte( + CP_UTF8, 0, module_name, -1, str, size, nullptr, nullptr); + list.emplace_back(str); +- delete str; ++ delete[] str; + } + } + } diff --git a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch index f21f31edd6765..e2f7f19bc3655 100644 --- a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch +++ b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch @@ -7,10 +7,10 @@ common.gypi is a file that's included in the node header bundle, despite the fact that we do not build node with gyp. diff --git a/common.gypi b/common.gypi -index 393fe32765794fbc5e92690e968e3c18f0d749fa..d9c0b721fe0a629a30efb3c4e04905176ca0a7f5 100644 +index a73d4401f26d8493802d3ecec3e015a77717720a..bfe567e016cf102d2087f7647e64cc051116ab8d 100644 --- a/common.gypi +++ b/common.gypi -@@ -90,6 +90,23 @@ +@@ -91,6 +91,23 @@ ##### end V8 defaults ##### diff --git a/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch b/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch index 6ca8291f2b3e6..ffd52bf513310 100644 --- a/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch +++ b/patches/node/fix_allow_passing_fileexists_fn_to_legacymainresolve.patch @@ -53,10 +53,10 @@ index 2879e5cf541fb4d226cfd7cc0fe367ca448fb926..03082f0ec4f91382933eec48e77331cd const maybeMain = resolvedOption <= legacyMainResolveExtensionsIndexes.kResolvedByMainIndexNode ? packageConfig.main || './' : ''; diff --git a/src/node_file.cc b/src/node_file.cc -index 49816349d8bab37fea1d84e5326ee5a11acad7a2..5aea65d6800494def62829432ee48f9c06e65d63 100644 +index fe28c340c9b50384e79fe14263d8b3807f49e0b3..37172158d318d6569194fd3c5441d107e155e54c 100644 --- a/src/node_file.cc +++ b/src/node_file.cc -@@ -3237,13 +3237,25 @@ static void CpSyncCheckPaths(const FunctionCallbackInfo& args) { +@@ -3523,13 +3523,25 @@ static void CpSyncCopyDir(const FunctionCallbackInfo& args) { } BindingData::FilePathIsFileReturnType BindingData::FilePathIsFile( @@ -83,7 +83,7 @@ index 49816349d8bab37fea1d84e5326ee5a11acad7a2..5aea65d6800494def62829432ee48f9c uv_fs_t req; int rc = uv_fs_stat(env->event_loop(), &req, file_path.c_str(), nullptr); -@@ -3301,6 +3313,11 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { +@@ -3587,6 +3599,11 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { std::optional initial_file_path; std::string file_path; @@ -95,7 +95,7 @@ index 49816349d8bab37fea1d84e5326ee5a11acad7a2..5aea65d6800494def62829432ee48f9c if (args.Length() >= 2 && args[1]->IsString()) { auto package_config_main = Utf8Value(isolate, args[1]).ToString(); -@@ -3321,7 +3338,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { +@@ -3607,7 +3624,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { BufferValue buff_file_path(isolate, local_file_path); ToNamespacedPath(env, &buff_file_path); @@ -104,7 +104,7 @@ index 49816349d8bab37fea1d84e5326ee5a11acad7a2..5aea65d6800494def62829432ee48f9c case BindingData::FilePathIsFileReturnType::kIsFile: return args.GetReturnValue().Set(i); case BindingData::FilePathIsFileReturnType::kIsNotFile: -@@ -3358,7 +3375,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { +@@ -3644,7 +3661,7 @@ void BindingData::LegacyMainResolve(const FunctionCallbackInfo& args) { BufferValue buff_file_path(isolate, local_file_path); ToNamespacedPath(env, &buff_file_path); diff --git a/patches/node/fix_assert_module_in_the_renderer_process.patch b/patches/node/fix_assert_module_in_the_renderer_process.patch index 63191d23c70b6..3ab6d454f6e8c 100644 --- a/patches/node/fix_assert_module_in_the_renderer_process.patch +++ b/patches/node/fix_assert_module_in_the_renderer_process.patch @@ -44,10 +44,10 @@ index 59b5a16f1309a5e4055bccfdb7a529045ad30402..bfdaf6211466a01b64b7942f7b16c480 let filename = call.getFileName(); const line = call.getLineNumber() - 1; diff --git a/src/node_options.cc b/src/node_options.cc -index 8be78889e8234eb3100f309829bf7470db544dcd..bb1e80ece4158dfed1b8bab7dc6d00dd56505aac 100644 +index 14f7764c995e8de6582faf58c9b98a9cbe4fab73..d2e945b1d6ef6729709cc73c238cfae46d4e56b6 100644 --- a/src/node_options.cc +++ b/src/node_options.cc -@@ -1557,14 +1557,16 @@ void GetEmbedderOptions(const FunctionCallbackInfo& args) { +@@ -1560,14 +1560,16 @@ void GetEmbedderOptions(const FunctionCallbackInfo& args) { } Isolate* isolate = args.GetIsolate(); diff --git a/patches/node/fix_cppgc_initializing_twice.patch b/patches/node/fix_cppgc_initializing_twice.patch index 432dce585764e..475bd2830be6a 100644 --- a/patches/node/fix_cppgc_initializing_twice.patch +++ b/patches/node/fix_cppgc_initializing_twice.patch @@ -12,10 +12,10 @@ This can be removed/refactored once Node.js upgrades to a version of V8 containing the above CL. diff --git a/src/node.cc b/src/node.cc -index bc670a6c8b5027417cdc35e1cd94a60f63fd342d..49a9670de72c222d6b4a681be001efb4a2651ea3 100644 +index 19d9fb77f1aaf003e43b7d7016f45e6c35df06b3..9fad3198757ce639eb491eb628c6264a17002bf2 100644 --- a/src/node.cc +++ b/src/node.cc -@@ -1209,7 +1209,7 @@ InitializeOncePerProcessInternal(const std::vector& args, +@@ -1208,7 +1208,7 @@ InitializeOncePerProcessInternal(const std::vector& args, result->platform_ = per_process::v8_platform.Platform(); } diff --git a/patches/node/fix_crypto_tests_to_run_with_bssl.patch b/patches/node/fix_crypto_tests_to_run_with_bssl.patch index 5e27975c22151..a46f89cb41230 100644 --- a/patches/node/fix_crypto_tests_to_run_with_bssl.patch +++ b/patches/node/fix_crypto_tests_to_run_with_bssl.patch @@ -10,50 +10,15 @@ This should be upstreamed in some form, though it may need to be tweaked before it's acceptable to upstream, as this patch comments out a couple of tests that upstream probably cares about. -diff --git a/test/common/index.js b/test/common/index.js -index 8f5af57a83dc6b426f1b11bd2e3a8c6c0f2d9a85..f6e00c9f3f3ac4b42662eed6c8d190586f92ab99 100644 ---- a/test/common/index.js -+++ b/test/common/index.js -@@ -56,6 +56,8 @@ const hasCrypto = Boolean(process.versions.openssl) && - - const hasQuic = hasCrypto && !!process.config.variables.openssl_quic; - -+const openSSLIsBoringSSL = process.versions.openssl === '0.0.0'; -+ - function parseTestFlags(filename = process.argv[1]) { - // The copyright notice is relatively big and the flags could come afterwards. - const bytesToRead = 1500; -@@ -901,6 +903,7 @@ const common = { - mustNotMutateObjectDeep, - mustSucceed, - nodeProcessAborted, -+ openSSLIsBoringSSL, - PIPE, - parseTestFlags, - platformTimeout, -diff --git a/test/parallel/test-buffer-tostring-range.js b/test/parallel/test-buffer-tostring-range.js -index d033cd204b3200cdd736b581abe027d6e46e4ff3..73fec107a36c3db4af6f492137d0ca174f2d0547 100644 ---- a/test/parallel/test-buffer-tostring-range.js -+++ b/test/parallel/test-buffer-tostring-range.js -@@ -102,7 +102,8 @@ assert.throws(() => { - // Must not throw when start and end are within kMaxLength - // Cannot test on 32bit machine as we are testing the case - // when start and end are above the threshold --common.skipIf32Bits(); -+if (!common.openSSLIsBoringSSL) { - const threshold = 0xFFFFFFFF; - const largeBuffer = Buffer.alloc(threshold + 20); - largeBuffer.toString('utf8', threshold, threshold + 20); -+} diff --git a/test/parallel/test-crypto-async-sign-verify.js b/test/parallel/test-crypto-async-sign-verify.js -index b35dd08e6c49796418cd9d10eb5cc9d02b39961e..a49fdde82ea4cbadd60307cdc99439be892ef5a6 100644 +index b35dd08e6c49796418cd9d10eb5cc9d02b39961e..97bcd79b331db140d157e6b1faf92625597edc98 100644 --- a/test/parallel/test-crypto-async-sign-verify.js +++ b/test/parallel/test-crypto-async-sign-verify.js @@ -89,6 +89,7 @@ test('rsa_public.pem', 'rsa_private.pem', 'sha256', false, // ED25519 test('ed25519_public.pem', 'ed25519_private.pem', undefined, true); // ED448 -+if (!common.openSSLIsBoringSSL) { ++if (!process.features.openssl_is_boringssl) { test('ed448_public.pem', 'ed448_private.pem', undefined, true); // ECDSA w/ der signature encoding @@ -72,7 +37,7 @@ index b35dd08e6c49796418cd9d10eb5cc9d02b39961e..a49fdde82ea4cbadd60307cdc99439be - const expected = hasOpenSSL3 ? - /operation not supported for this keytype/ : /no default digest/; + let expected = /no default digest/; -+ if (hasOpenSSL3 || common.openSSLIsBoringSSL) { ++ if (hasOpenSSL3 || process.features.openssl_is_boringssl) { + expected = /operation[\s_]not[\s_]supported[\s_]for[\s_]this[\s_]keytype/i; + } @@ -144,23 +109,29 @@ index 81a469c226c261564dee1e0b06b6571b18a41f1f..58b66045dba4201b7ebedd78b129420f const availableCurves = new Set(crypto.getCurves()); diff --git a/test/parallel/test-crypto-dh-errors.js b/test/parallel/test-crypto-dh-errors.js -index 0af4db0310750cea9350ecff7fc44404c6df6c83..85ab03f6019989ad4fe93b779c3b4772ce1f5130 100644 +index 0af4db0310750cea9350ecff7fc44404c6df6c83..b14b4bbf88b902b6de916b92e3d48335c01df911 100644 --- a/test/parallel/test-crypto-dh-errors.js +++ b/test/parallel/test-crypto-dh-errors.js -@@ -33,9 +33,9 @@ for (const bits of [-1, 0, 1]) { +@@ -27,7 +27,7 @@ assert.throws(() => crypto.createDiffieHellman('abcdef', 13.37), { + for (const bits of [-1, 0, 1]) { + if (hasOpenSSL3) { + assert.throws(() => crypto.createDiffieHellman(bits), { +- code: 'ERR_OSSL_DH_MODULUS_TOO_SMALL', ++ code: 'ERR_OSSL_BN_BITS_TOO_SMALL', + name: 'Error', + message: /modulus too small/, }); - } else { +@@ -35,7 +35,7 @@ for (const bits of [-1, 0, 1]) { assert.throws(() => crypto.createDiffieHellman(bits), { -- code: 'ERR_OSSL_BN_BITS_TOO_SMALL', -+ code: /ERR_OSSL_BN_BITS_TOO_SMALL|ERR_OSSL_DH_MODULUS_TOO_LARGE/, + code: 'ERR_OSSL_BN_BITS_TOO_SMALL', name: 'Error', - message: /bits too small/, -+ message: /bits too small|BITS_TOO_SMALL|MODULUS_TOO_LARGE/, ++ message: /bits[\s_]too[\s_]small/i, }); } } diff --git a/test/parallel/test-crypto-dh.js b/test/parallel/test-crypto-dh.js -index d7ffbe5eca92734aa2380f482c7f9bfe7e2a36c7..21ab2333431ea70bdf98dde43624e0b712566395 100644 +index d7ffbe5eca92734aa2380f482c7f9bfe7e2a36c7..b4e7002d862907d2af3b4f8e985700bd03300809 100644 --- a/test/parallel/test-crypto-dh.js +++ b/test/parallel/test-crypto-dh.js @@ -60,18 +60,17 @@ const { @@ -171,10 +142,10 @@ index d7ffbe5eca92734aa2380f482c7f9bfe7e2a36c7..21ab2333431ea70bdf98dde43624e0b7 - code: 'ERR_OSSL_WRONG_FINAL_BLOCK_LENGTH', - library: 'Provider routines', - reason: 'wrong final block length' -+ message: /error:1C80006B:Provider routines::wrong final block length|error:1e00007b:Cipher functions:OPENSSL_internal:WRONG_FINAL_BLOCK_LENGTH/, ++ message: /wrong[\s_]final[\s_]block[\s_]length/i, + code: /ERR_OSSL_(EVP_)?WRONG_FINAL_BLOCK_LENGTH/, -+ library: /digital envelope routines|Cipher functions/, -+ reason: /wrong final block length|WRONG_FINAL_BLOCK_LENGTH/ ++ library: /Provider routines|Cipher functions/, ++ reason: /wrong[\s_]final[\s_]block[\s_]length/i, }; } else { wrongBlockLength = { @@ -183,10 +154,10 @@ index d7ffbe5eca92734aa2380f482c7f9bfe7e2a36c7..21ab2333431ea70bdf98dde43624e0b7 - code: 'ERR_OSSL_EVP_WRONG_FINAL_BLOCK_LENGTH', - library: 'digital envelope routines', - reason: 'wrong final block length' -+ message: /error:0606506D:digital envelope routines:EVP_DecryptFinal_ex:wrong final block length|error:1e00007b:Cipher functions:OPENSSL_internal:WRONG_FINAL_BLOCK_LENGTH/, ++ message: /wrong[\s_]final[\s_]block[\s_]length/i, + code: /ERR_OSSL_(EVP_)?WRONG_FINAL_BLOCK_LENGTH/, + library: /digital envelope routines|Cipher functions/, -+ reason: /wrong final block length|WRONG_FINAL_BLOCK_LENGTH/ ++ reason: /wrong[\s_]final[\s_]block[\s_]length/i, }; } @@ -217,25 +188,6 @@ index d7ffbe5eca92734aa2380f482c7f9bfe7e2a36c7..21ab2333431ea70bdf98dde43624e0b7 + name: 'Error' + }); } -diff --git a/test/parallel/test-crypto-getcipherinfo.js b/test/parallel/test-crypto-getcipherinfo.js -index 64b79fc36ccf4d38f763fcd8c1930473c82cefd7..1c6717ebd46497384b9b13174b65894ca89e7f2d 100644 ---- a/test/parallel/test-crypto-getcipherinfo.js -+++ b/test/parallel/test-crypto-getcipherinfo.js -@@ -62,9 +62,13 @@ assert(getCipherInfo('aes-128-cbc', { ivLength: 16 })); - - assert(!getCipherInfo('aes-128-ccm', { ivLength: 1 })); - assert(!getCipherInfo('aes-128-ccm', { ivLength: 14 })); -+if (!common.openSSLIsBoringSSL) { - for (let n = 7; n <= 13; n++) - assert(getCipherInfo('aes-128-ccm', { ivLength: n })); -+} - - assert(!getCipherInfo('aes-128-ocb', { ivLength: 16 })); -+if (!common.openSSLIsBoringSSL) { - for (let n = 1; n < 16; n++) - assert(getCipherInfo('aes-128-ocb', { ivLength: n })); -+} -\ No newline at end of file diff --git a/test/parallel/test-crypto-hash-stream-pipe.js b/test/parallel/test-crypto-hash-stream-pipe.js index d22281abbd5c3cab3aaa3ac494301fa6b4a8a968..5f0c6a4aed2e868a1a1049212edf218791cd6868 100644 --- a/test/parallel/test-crypto-hash-stream-pipe.js @@ -258,7 +210,7 @@ index d22281abbd5c3cab3aaa3ac494301fa6b4a8a968..5f0c6a4aed2e868a1a1049212edf2187 s.pipe(h).on('data', common.mustCall(function(c) { assert.strictEqual(c, expect); diff --git a/test/parallel/test-crypto-hash.js b/test/parallel/test-crypto-hash.js -index 61145aee0727fbe0b9781acdb3eeb641e7010729..fd7d4bd7d3f86caa30ffd03ea880eeac023bbcbb 100644 +index 61145aee0727fbe0b9781acdb3eeb641e7010729..51693e637b310981f76f23c2f35d43e4d2d9c4ef 100644 --- a/test/parallel/test-crypto-hash.js +++ b/test/parallel/test-crypto-hash.js @@ -183,7 +183,7 @@ assert.throws( @@ -266,57 +218,57 @@ index 61145aee0727fbe0b9781acdb3eeb641e7010729..fd7d4bd7d3f86caa30ffd03ea880eeac // Test XOF hash functions and the outputLength option. -{ -+if (!common.openSSLIsBoringSSL) { ++if (!process.features.openssl_is_boringssl) { // Default outputLengths. Since OpenSSL 3.4 an outputLength is mandatory if (!hasOpenSSL(3, 4)) { assert.strictEqual(crypto.createHash('shake128').digest('hex'), -diff --git a/test/parallel/test-crypto-hkdf.js b/test/parallel/test-crypto-hkdf.js -index 3f7e61e9b2ebc0ca7c367d7c229afe9ab87762b8..36bd78105d153b75b42e4736f11d80a257916607 100644 ---- a/test/parallel/test-crypto-hkdf.js -+++ b/test/parallel/test-crypto-hkdf.js -@@ -125,7 +125,7 @@ const algorithms = [ - ['sha256', '', 'salt', '', 10], - ['sha512', 'secret', 'salt', '', 15], - ]; --if (!hasOpenSSL3) -+if (!hasOpenSSL3 && !common.openSSLIsBoringSSL) - algorithms.push(['whirlpool', 'secret', '', 'info', 20]); - - algorithms.forEach(([ hash, secret, salt, info, length ]) => { diff --git a/test/parallel/test-crypto-padding.js b/test/parallel/test-crypto-padding.js -index 48cd1ed4df61aaddeee8785cb90f83bdd9628187..a18aeb2bdffcc7a7e9ef12328b849994e39d6c27 100644 +index 48cd1ed4df61aaddeee8785cb90f83bdd9628187..d09e01712c617597833bb1320a32a967bcf1d318 100644 --- a/test/parallel/test-crypto-padding.js +++ b/test/parallel/test-crypto-padding.js -@@ -88,10 +88,9 @@ assert.throws(function() { - code: 'ERR_OSSL_WRONG_FINAL_BLOCK_LENGTH', - reason: 'wrong final block length', +@@ -84,14 +84,13 @@ assert.throws(function() { + // Input must have block length %. + enc(ODD_LENGTH_PLAIN, false); + }, hasOpenSSL3 ? { +- message: 'error:1C80006B:Provider routines::wrong final block length', +- code: 'ERR_OSSL_WRONG_FINAL_BLOCK_LENGTH', +- reason: 'wrong final block length', ++ message: /wrong[\s_]final[\s_]block[\s_]length/i, ++ code: /ERR_OSSL(_EVP)?_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH/, ++ message: /wrong[\s_]final[\s_]block[\s_]length/i, } : { - message: 'error:0607F08A:digital envelope routines:EVP_EncryptFinal_ex:' + - 'data not multiple of block length', - code: 'ERR_OSSL_EVP_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH', - reason: 'data not multiple of block length', -+ message: /error:0607F08A:digital envelope routines:EVP_EncryptFinal_ex:data not multiple of block length|error:1e00006a:Cipher functions:OPENSSL_internal:DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH/, ++ message: /data[\s_]not[\s_]multiple[\s_]of[\s_]block[\s_]length/i, + code: /ERR_OSSL(_EVP)?_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH/, -+ reason: /data not multiple of block length|DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH/, ++ reason: /data[\s_]not[\s_]multiple[\s_]of[\s_]block[\s_]length/i, } ); -@@ -115,10 +114,9 @@ assert.throws(function() { - reason: 'bad decrypt', - code: 'ERR_OSSL_BAD_DECRYPT', - } : { +@@ -110,15 +109,10 @@ assert.strictEqual(dec(EVEN_LENGTH_ENCRYPTED, false).length, 48); + assert.throws(function() { + // Must have at least 1 byte of padding (PKCS): + assert.strictEqual(dec(EVEN_LENGTH_ENCRYPTED_NOPAD, true), EVEN_LENGTH_PLAIN); +-}, hasOpenSSL3 ? { +- message: 'error:1C800064:Provider routines::bad decrypt', +- reason: 'bad decrypt', +- code: 'ERR_OSSL_BAD_DECRYPT', +-} : { - message: 'error:06065064:digital envelope routines:EVP_DecryptFinal_ex:' + - 'bad decrypt', - reason: 'bad decrypt', - code: 'ERR_OSSL_EVP_BAD_DECRYPT', -+ message: /error:06065064:digital envelope routines:EVP_DecryptFinal_ex:bad decrypt|error:1e000065:Cipher functions:OPENSSL_internal:BAD_DECRYPT/, -+ reason: /bad decrypt|BAD_DECRYPT/, ++}, { ++ message: /bad[\s_]decrypt/i, ++ reason: /bad[\s_]decrypt/i, + code: /ERR_OSSL(_EVP)?_BAD_DECRYPT/, }); // No-pad encrypted string should return the same: diff --git a/test/parallel/test-crypto-rsa-dsa.js b/test/parallel/test-crypto-rsa-dsa.js -index dcd5045daaf58c60e27c1e2f7941033302241339..6ac75565792b92a97c622baba73f821d754b8d01 100644 +index dcd5045daaf58c60e27c1e2f7941033302241339..b52ec0e2cd5d6b1c9a0fee3064f2f8ff3b6e4308 100644 --- a/test/parallel/test-crypto-rsa-dsa.js +++ b/test/parallel/test-crypto-rsa-dsa.js @@ -29,12 +29,11 @@ const dsaPkcs8KeyPem = fixtures.readKey('dsa_private_pkcs8.pem'); @@ -342,7 +294,7 @@ index dcd5045daaf58c60e27c1e2f7941033302241339..6ac75565792b92a97c622baba73f821d - if (padding === constants.RSA_PKCS1_PADDING) { -+ if (!common.openSSLIsBoringSSL) { ++ if (!process.features.openssl_is_boringssl) { if (!process.config.variables.node_shared_openssl) { assert.throws(() => { crypto.privateDecrypt({ @@ -351,7 +303,7 @@ index dcd5045daaf58c60e27c1e2f7941033302241339..6ac75565792b92a97c622baba73f821d // Test DSA signing and verification // -{ -+if (!common.openSSLIsBoringSSL) { ++if (!process.features.openssl_is_boringssl) { const input = 'I AM THE WALRUS'; // DSA signatures vary across runs so there is no static string to verify @@ -369,7 +321,7 @@ index 03a18c7522531c7317f12705550117dc389a0245..2f0f46f2c6ddc62de89877cfa0ca8094 }; assert.throws(() => crypto.scrypt('pass', 'salt', 1, options, () => {}), diff --git a/test/parallel/test-crypto-sign-verify.js b/test/parallel/test-crypto-sign-verify.js -index 0589d60736e377f24dc8550f87a6b7624173fc44..547f22cdc130cf0c68d117f92068e3ac53a0efc2 100644 +index 0589d60736e377f24dc8550f87a6b7624173fc44..113003826fc47a589cf2334f7345e33d3e189d0a 100644 --- a/test/parallel/test-crypto-sign-verify.js +++ b/test/parallel/test-crypto-sign-verify.js @@ -33,7 +33,7 @@ const keySize = 2048; @@ -377,7 +329,7 @@ index 0589d60736e377f24dc8550f87a6b7624173fc44..547f22cdc130cf0c68d117f92068e3ac // Test handling of exceptional conditions -{ -+if (!common.openSSLIsBoringSSL) { ++if (!process.features.openssl_is_boringssl) { const library = { configurable: true, set() { @@ -426,77 +378,24 @@ index 0589d60736e377f24dc8550f87a6b7624173fc44..547f22cdc130cf0c68d117f92068e3ac for (const [file, length] of keys) { const privKey = fixtures.readKey(file); diff --git a/test/parallel/test-crypto-stream.js b/test/parallel/test-crypto-stream.js -index 62be4eaf6edfb01ce275e7db3e56b51d09ac66ce..3fb6cd833d959d1c3c8522ebacc8f18352672628 100644 +index 747af780469c22eb8e4c6c35424043e868f75c3d..ed0916b036a9af23d805007ebd609973ee954473 100644 --- a/test/parallel/test-crypto-stream.js +++ b/test/parallel/test-crypto-stream.js -@@ -78,10 +78,10 @@ cipher.pipe(decipher) - library: 'Provider routines', - reason: 'bad decrypt', +@@ -73,9 +73,9 @@ const cipher = crypto.createCipheriv('aes-128-cbc', key, iv); + const decipher = crypto.createDecipheriv('aes-128-cbc', badkey, iv); + + cipher.pipe(decipher) +- .on('error', common.expectsError(hasOpenSSL3 ? { +- message: /bad[\s_]decrypt/, +- library: 'Provider routines', ++ .on('error', common.expectsError((hasOpenSSL3 || process.features.openssl_is_boringssl) ? { ++ message: /bad[\s_]decrypt/i, ++ library: /Provider routines|Cipher functions/, + reason: /bad[\s_]decrypt/i, } : { -- message: /bad decrypt/, -- function: 'EVP_DecryptFinal_ex', -- library: 'digital envelope routines', -- reason: 'bad decrypt', -+ message: /bad decrypt|BAD_DECRYPT/, -+ function: /EVP_DecryptFinal_ex|OPENSSL_internal/, -+ library: /digital envelope routines|Cipher functions/, -+ reason: /bad decrypt|BAD_DECRYPT/, - })); - - cipher.end('Papaya!'); // Should not cause an unhandled exception. -diff --git a/test/parallel/test-crypto-x509.js b/test/parallel/test-crypto-x509.js -index f75e1d63470bfb7ce7fb354118b87a1a6fe5e4cc..5c0852e83a466ab4b255e8c9c9a33aca1beb9b94 100644 ---- a/test/parallel/test-crypto-x509.js -+++ b/test/parallel/test-crypto-x509.js -@@ -97,8 +97,10 @@ const der = Buffer.from( - assert.strictEqual(x509.infoAccess, infoAccessCheck); - assert.strictEqual(x509.validFrom, 'Sep 3 21:40:37 2022 GMT'); - assert.strictEqual(x509.validTo, 'Jun 17 21:40:37 2296 GMT'); -+ if (!common.openSSLIsBoringSSL) { - assert.deepStrictEqual(x509.validFromDate, new Date('2022-09-03T21:40:37Z')); - assert.deepStrictEqual(x509.validToDate, new Date('2296-06-17T21:40:37Z')); -+ } - assert.strictEqual( - x509.fingerprint, - '8B:89:16:C4:99:87:D2:13:1A:64:94:36:38:A5:32:01:F0:95:3B:53'); -@@ -326,6 +328,7 @@ oans248kpal88CGqsN2so/wZKxVnpiXlPHMdiNL7hRSUqlHkUi07FrP2Htg8kjI= - legacyObjectCheck.serialNumberPattern); - } - -+if (!common.openSSLIsBoringSSL) { - { - // This X.509 Certificate can be parsed by OpenSSL because it contains a - // structurally sound TBSCertificate structure. However, the SPKI field of the -@@ -364,6 +367,7 @@ UcXd/5qu2GhokrKU2cPttU+XAN2Om6a0 - - assert.strictEqual(cert.checkIssued(cert), false); - } -+} - - { - // Test date parsing of `validFromDate` and `validToDate` fields, according to RFC 5280. -@@ -401,8 +405,10 @@ UidvpWWipVLZgK+oDks+bKTobcoXGW9oXobiIYqslXPy - -----END CERTIFICATE-----`.trim(); - const c1 = new X509Certificate(certPemUTCTime); - -+ if (!common.openSSLIsBoringSSL) { - assert.deepStrictEqual(c1.validFromDate, new Date('1949-12-25T23:59:58Z')); - assert.deepStrictEqual(c1.validToDate, new Date('1950-01-01T23:59:58Z')); -+ } - - // The GeneralizedTime format is used for dates in 2050 or later. - const certPemGeneralizedTime = `-----BEGIN CERTIFICATE----- -@@ -436,6 +442,8 @@ CWwQO8JZjJqFtqtuzy2n+gLCvqePgG/gmSqHOPm2ZbLW - -----END CERTIFICATE-----`.trim(); - const c2 = new X509Certificate(certPemGeneralizedTime); - -+ if (!common.openSSLIsBoringSSL) { - assert.deepStrictEqual(c2.validFromDate, new Date('2049-12-26T00:00:01Z')); - assert.deepStrictEqual(c2.validToDate, new Date('2050-01-02T00:00:01Z')); -+ } - } + message: /bad[\s_]decrypt/i, diff --git a/test/parallel/test-crypto.js b/test/parallel/test-crypto.js -index 93644e016de447d2aadc519123f18cd72b7a5750..8b16c83cd47bd8969654242296c987ecc97ccaeb 100644 +index 84111740cd9ef6425b747e24e984e66e46b0b2ef..b1621d310536fae3fdec91a6a9d275ec8fc99a98 100644 --- a/test/parallel/test-crypto.js +++ b/test/parallel/test-crypto.js @@ -62,7 +62,7 @@ assert.throws(() => { @@ -539,25 +438,10 @@ index 93644e016de447d2aadc519123f18cd72b7a5750..8b16c83cd47bd8969654242296c987ec } ); -+if (!common.openSSLIsBoringSSL) { ++if (!process.features.openssl_is_boringssl) { assert.throws(() => { const priv = [ '-----BEGIN RSA PRIVATE KEY-----', -@@ -217,10 +216,10 @@ assert.throws(() => { - library: 'rsa routines', - } : { - name: 'Error', -- message: /routines:RSA_sign:digest too big for rsa key$/, -- library: 'rsa routines', -- function: 'RSA_sign', -- reason: 'digest too big for rsa key', -+ message: /routines:RSA_sign:digest too big for rsa key$|routines:OPENSSL_internal:DIGEST_TOO_BIG_FOR_RSA_KEY$/, -+ library: /rsa routines|RSA routines/, -+ function: /RSA_sign|OPENSSL_internal/, -+ reason: /digest too big for rsa key|DIGEST_TOO_BIG_FOR_RSA_KEY/, - code: 'ERR_OSSL_RSA_DIGEST_TOO_BIG_FOR_RSA_KEY' - }); - return true; @@ -253,7 +252,7 @@ if (!hasOpenSSL3) { return true; }); @@ -567,162 +451,29 @@ index 93644e016de447d2aadc519123f18cd72b7a5750..8b16c83cd47bd8969654242296c987ec // Make sure memory isn't released before being returned console.log(crypto.randomBytes(16)); -diff --git a/test/parallel/test-https-agent-additional-options.js b/test/parallel/test-https-agent-additional-options.js -index 543ee176fb6af38874fee9f14be76f3fdda11060..fef9f1bc2f9fc6c220cf47847e86e03882b51b1d 100644 ---- a/test/parallel/test-https-agent-additional-options.js -+++ b/test/parallel/test-https-agent-additional-options.js -@@ -13,7 +13,7 @@ const options = { - cert: fixtures.readKey('agent1-cert.pem'), - ca: fixtures.readKey('ca1-cert.pem'), - minVersion: 'TLSv1.1', -- ciphers: 'ALL@SECLEVEL=0' -+ // ciphers: 'ALL@SECLEVEL=0' - }; - - const server = https.Server(options, (req, res) => { -@@ -28,7 +28,7 @@ function getBaseOptions(port) { - ca: options.ca, - rejectUnauthorized: true, - servername: 'agent1', -- ciphers: 'ALL@SECLEVEL=0' -+ // ciphers: 'ALL@SECLEVEL=0' - }; - } - -diff --git a/test/parallel/test-https-agent-session-eviction.js b/test/parallel/test-https-agent-session-eviction.js -index 6f88e81e9ff29defe73800fc038b0d96d1ebd846..c0b92e2bdf86d3d2638c973f8be3110d5ae31f78 100644 ---- a/test/parallel/test-https-agent-session-eviction.js -+++ b/test/parallel/test-https-agent-session-eviction.js -@@ -17,7 +17,7 @@ const options = { - key: readKey('agent1-key.pem'), - cert: readKey('agent1-cert.pem'), - secureOptions: SSL_OP_NO_TICKET, -- ciphers: 'RSA@SECLEVEL=0' -+ // ciphers: 'RSA@SECLEVEL=0' - }; - - // Create TLS1.2 server diff --git a/test/parallel/test-tls-alert-handling.js b/test/parallel/test-tls-alert-handling.js -index cba5bebaa29b6f8ac4fd0fcedaadb2f7bb3eb321..019d95df499892b14ab088f99013ee32c432779c 100644 +index 7bd42bbe721c4c9442410d524c5ca740078fc72c..de49dbdc2b75517f497af353a6b24b1beb11ed69 100644 --- a/test/parallel/test-tls-alert-handling.js +++ b/test/parallel/test-tls-alert-handling.js -@@ -35,7 +35,7 @@ let iter = 0; - - const errorHandler = common.mustCall((err) => { - let expectedErrorCode = 'ERR_SSL_WRONG_VERSION_NUMBER'; -- let expectedErrorReason = 'wrong version number'; -+ let expectedErrorReason = /wrong[\s_]version[\s_]number/i; - if (hasOpenSSL(3, 2)) { - expectedErrorCode = 'ERR_SSL_PACKET_LENGTH_TOO_LONG'; - expectedErrorReason = 'packet length too long'; -@@ -43,8 +43,8 @@ const errorHandler = common.mustCall((err) => { +@@ -43,7 +43,8 @@ const errorHandler = common.mustCall((err) => { assert.strictEqual(err.code, expectedErrorCode); assert.strictEqual(err.library, 'SSL routines'); - if (!hasOpenSSL3) assert.strictEqual(err.function, 'ssl3_get_record'); -- assert.strictEqual(err.reason, expectedErrorReason); -+ if (!hasOpenSSL3 && !common.openSSLIsBoringSSL) assert.strictEqual(err.function, 'ssl3_get_record'); -+ assert.match(err.reason, expectedErrorReason); ++ if (!hasOpenSSL3 && !process.features.openssl_is_boringssl) ++ assert.strictEqual(err.function, 'ssl3_get_record'); + assert.match(err.reason, expectedErrorReason); errorReceived = true; if (canCloseServer()) - server.close(); -@@ -98,15 +98,15 @@ function sendBADTLSRecord() { - })); - client.on('error', common.mustCall((err) => { - let expectedErrorCode = 'ERR_SSL_TLSV1_ALERT_PROTOCOL_VERSION'; -- let expectedErrorReason = 'tlsv1 alert protocol version'; -+ let expectedErrorReason = /tlsv1[\s_]alert[\s_]protocol[\s_]version/i; - if (hasOpenSSL(3, 2)) { - expectedErrorCode = 'ERR_SSL_TLSV1_ALERT_RECORD_OVERFLOW'; - expectedErrorReason = 'tlsv1 alert record overflow'; +@@ -105,7 +106,7 @@ function sendBADTLSRecord() { } assert.strictEqual(err.code, expectedErrorCode); assert.strictEqual(err.library, 'SSL routines'); - if (!hasOpenSSL3) -+ if (!hasOpenSSL3 && !common.openSSLIsBoringSSL) ++ if (!hasOpenSSL3 && !process.features.openssl_is_boringssl) assert.strictEqual(err.function, 'ssl3_read_bytes'); -- assert.strictEqual(err.reason, expectedErrorReason); -+ assert.match(err.reason, expectedErrorReason); + assert.match(err.reason, expectedErrorReason); })); - } -diff --git a/test/parallel/test-tls-getprotocol.js b/test/parallel/test-tls-getprotocol.js -index b1eab88fd6517e3698934dea17752ef2bb8d8d54..3ad6db20316baa8490e3787dd55903b58a54ad06 100644 ---- a/test/parallel/test-tls-getprotocol.js -+++ b/test/parallel/test-tls-getprotocol.js -@@ -29,7 +29,7 @@ const clientConfigs = [ - - const serverConfig = { - secureProtocol: 'TLS_method', -- ciphers: 'RSA@SECLEVEL=0', -+ // ciphers: 'RSA@SECLEVEL=0', - key: fixtures.readKey('agent2-key.pem'), - cert: fixtures.readKey('agent2-cert.pem') - }; -diff --git a/test/parallel/test-tls-write-error.js b/test/parallel/test-tls-write-error.js -index b06f2fa2c53ea72f9a66f0d002dd9281d0259a0f..864fffeebfad75d95416fd47efdea7f222c507a2 100644 ---- a/test/parallel/test-tls-write-error.js -+++ b/test/parallel/test-tls-write-error.js -@@ -17,7 +17,7 @@ const server_cert = fixtures.readKey('agent1-cert.pem'); - const opts = { - key: server_key, - cert: server_cert, -- ciphers: 'ALL@SECLEVEL=0' -+ // ciphers: 'ALL@SECLEVEL=0' - }; - - const server = https.createServer(opts, (req, res) => { -diff --git a/test/parallel/test-webcrypto-derivebits.js b/test/parallel/test-webcrypto-derivebits.js -index eb09bc24f0cb8244b05987e3a7c1d203360d3a38..8c251ff2371fb59bf679160574e1c5dc1b4b2665 100644 ---- a/test/parallel/test-webcrypto-derivebits.js -+++ b/test/parallel/test-webcrypto-derivebits.js -@@ -101,8 +101,9 @@ const { subtle } = globalThis.crypto; - tests.then(common.mustCall()); - } - -+ - // Test X25519 and X448 bit derivation --{ -+if (!common.openSSLIsBoringSSL) { - async function test(name) { - const [alice, bob] = await Promise.all([ - subtle.generateKey({ name }, true, ['deriveBits']), -diff --git a/test/parallel/test-webcrypto-derivekey.js b/test/parallel/test-webcrypto-derivekey.js -index 558d37d90d5796b30101d1b512c9df3e7661d0db..f42bf8f4be0b439dd7e7c8d0f6f8a41e01588870 100644 ---- a/test/parallel/test-webcrypto-derivekey.js -+++ b/test/parallel/test-webcrypto-derivekey.js -@@ -176,7 +176,7 @@ const { KeyObject } = require('crypto'); - } - - // Test X25519 and X448 key derivation --{ -+if (!common.openSSLIsBoringSSL) { - async function test(name) { - const [alice, bob] = await Promise.all([ - subtle.generateKey({ name }, true, ['deriveKey']), -diff --git a/test/parallel/test-webcrypto-sign-verify.js b/test/parallel/test-webcrypto-sign-verify.js -index de736102bdcb71a5560c95f7041537f25026aed4..12d7fa39446c196bdf1479dbe74c9ee8ab02f949 100644 ---- a/test/parallel/test-webcrypto-sign-verify.js -+++ b/test/parallel/test-webcrypto-sign-verify.js -@@ -105,8 +105,9 @@ const { subtle } = globalThis.crypto; - test('hello world').then(common.mustCall()); - } - -+ - // Test Sign/Verify Ed25519 --{ -+if (!common.openSSLIsBoringSSL) { - async function test(data) { - const ec = new TextEncoder(); - const { publicKey, privateKey } = await subtle.generateKey({ -@@ -126,7 +127,7 @@ const { subtle } = globalThis.crypto; - } - - // Test Sign/Verify Ed448 --{ -+if (!common.openSSLIsBoringSSL) { - async function test(data) { - const ec = new TextEncoder(); - const { publicKey, privateKey } = await subtle.generateKey({ diff --git a/test/parallel/test-webcrypto-wrap-unwrap.js b/test/parallel/test-webcrypto-wrap-unwrap.js index d1ca571af4be713082d32093bfb8a65f2aef9800..57b8df2ce18df58ff54b2d828af67e3c2e082fe0 100644 --- a/test/parallel/test-webcrypto-wrap-unwrap.js diff --git a/patches/node/fix_do_not_resolve_electron_entrypoints.patch b/patches/node/fix_do_not_resolve_electron_entrypoints.patch index a489cf55632f5..a55af942e64b7 100644 --- a/patches/node/fix_do_not_resolve_electron_entrypoints.patch +++ b/patches/node/fix_do_not_resolve_electron_entrypoints.patch @@ -6,7 +6,7 @@ Subject: fix: do not resolve electron entrypoints This wastes fs cycles and can result in strange behavior if this path actually exists on disk diff --git a/lib/internal/modules/esm/translators.js b/lib/internal/modules/esm/translators.js -index 49aacb6262502ced54e817f99dd596db85b9659c..f9f065bb743275e9b2ce71375e6a9f06e00c0f36 100644 +index bbd3085cfbf14aefd611954fa836f6c96d7e402c..9e71d2d0b79656e212fb21efdb3efcf988529f5e 100644 --- a/lib/internal/modules/esm/translators.js +++ b/lib/internal/modules/esm/translators.js @@ -291,6 +291,9 @@ function cjsPreparseModuleExports(filename, source, isMain, format) { diff --git a/patches/node/fix_expose_readfilesync_override_for_modules.patch b/patches/node/fix_expose_readfilesync_override_for_modules.patch index c2b377ee140aa..9fb45295e340a 100644 --- a/patches/node/fix_expose_readfilesync_override_for_modules.patch +++ b/patches/node/fix_expose_readfilesync_override_for_modules.patch @@ -8,10 +8,10 @@ an API override to replace the native `ReadFileSync` in the `modules` binding. diff --git a/src/env_properties.h b/src/env_properties.h -index cbb7eab2df0416087cd3e6fb80eef2079143d9c8..7e9f5e977506149d69c6015e85d031770325e1da 100644 +index 3df4e303e05105b43a542456546cbc050d0445fa..4f7aee6cb64b4c1d25e98b43d13e747c4546adaa 100644 --- a/src/env_properties.h +++ b/src/env_properties.h -@@ -501,6 +501,7 @@ +@@ -502,6 +502,7 @@ V(maybe_cache_generated_source_map, v8::Function) \ V(messaging_deserialize_create_object, v8::Function) \ V(message_port, v8::Object) \ diff --git a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch index dec3592cbdc61..181b24add48b2 100644 --- a/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch +++ b/patches/node/fix_expose_the_built-in_electron_module_via_the_esm_loader.patch @@ -64,7 +64,7 @@ index 5ba13096b98047ff33e4d44167c2a069ccc5e69d..09a332c0999086b30fd952d9456f7889 } } diff --git a/lib/internal/modules/esm/loader.js b/lib/internal/modules/esm/loader.js -index aff686577df3c366f06f90666e23a03fc376cf53..e8857a151428acd6f8ece74d92774a18accc1e13 100644 +index 5a817ed0434b8bc08f9b9bd260c978bbe5ddc664..f9dba42cddb08f69e02834f76d6d80c5e47a637d 100644 --- a/lib/internal/modules/esm/loader.js +++ b/lib/internal/modules/esm/loader.js @@ -492,7 +492,7 @@ class ModuleLoader { @@ -101,7 +101,7 @@ index bfd9bd3d127404de1cbb6f30c43ab0342590759d..9e7d8ef0adef3b68a3ec186e4b218f59 const packageConfig = packageJsonReader.read(packageJSONPath, { __proto__: null, specifier, base, isESM: true }); diff --git a/lib/internal/modules/esm/translators.js b/lib/internal/modules/esm/translators.js -index 7dcd7afe8ce3c25ceb314cdf15c330f3d66eb84f..4445bcc4c4c6c6f87ac45e693012a18a93739f9b 100644 +index 0695b47a8a8f78451c20c025a3d9dac7cadab686..1db58d31dad24cd2da6bdc5e45e9dd4f0b899a23 100644 --- a/lib/internal/modules/esm/translators.js +++ b/lib/internal/modules/esm/translators.js @@ -186,7 +186,7 @@ function createCJSModuleWrap(url, source, isMain, format, loadCJS = loadCJSModul diff --git a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch index 709e710e07aa5..134bd2a779163 100644 --- a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch +++ b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch @@ -172,7 +172,7 @@ index e5bf2b529bf23914677e25d7468aad58a4684557..9a3c6029ff3319cce58c79782a7bd5d1 }; // Check to see if the given public key is suitable for this DH instance. diff --git a/node.gni b/node.gni -index 245a43920c7baf000ba63192a84a4c3fd219be7d..56a554175b805c1703f13d62041f8c80d6e94dd9 100644 +index b4450e3dd17994d1eaf59eb5cff5912545e89793..203b4abbc44df9e58083c819f61f9025104abdc6 100644 --- a/node.gni +++ b/node.gni @@ -11,7 +11,7 @@ declare_args() { @@ -183,7 +183,7 @@ index 245a43920c7baf000ba63192a84a4c3fd219be7d..56a554175b805c1703f13d62041f8c80 + node_openssl_path = "//third_party/boringssl" # The location of simdutf - use the one from node's deps by default. - node_simdutf_path = "$node_path/deps/simdutf" + node_simdutf_path = "//third_party/simdutf" diff --git a/src/crypto/crypto_cipher.cc b/src/crypto/crypto_cipher.cc index 2176fb6982484e2c42538478eeb4dd81c9d50ee1..c00d3616e08b00b1e0a3a29b2dbb5278e1e14fcc 100644 --- a/src/crypto/crypto_cipher.cc @@ -520,7 +520,7 @@ index 7c548d32b40365343f0e208c3aa856a1c847f4c3..6346f8f7199cf7b7d3736c59571606ff } // namespace diff --git a/src/env.h b/src/env.h -index b6bdff9b8580d2588a39f00b594c4c480157d78a..cfe917c797a6e4bb0f0284ec56be82637f840129 100644 +index c42493ad958508f650917bf5ca92088714a5056c..07accfbcca491966c6c8ad9c20e146dbd22347f0 100644 --- a/src/env.h +++ b/src/env.h @@ -50,7 +50,7 @@ @@ -532,7 +532,7 @@ index b6bdff9b8580d2588a39f00b594c4c480157d78a..cfe917c797a6e4bb0f0284ec56be8263 #include #endif -@@ -1073,7 +1073,7 @@ class Environment final : public MemoryRetainer { +@@ -1076,7 +1076,7 @@ class Environment final : public MemoryRetainer { kExitInfoFieldCount }; @@ -541,8 +541,23 @@ index b6bdff9b8580d2588a39f00b594c4c480157d78a..cfe917c797a6e4bb0f0284ec56be8263 #if OPENSSL_VERSION_MAJOR >= 3 // We declare another alias here to avoid having to include crypto_util.h using EVPMDPointer = DeleteFnPtr; +diff --git a/src/node_config.cc b/src/node_config.cc +index 6032bbd10f41da7bae44828a8e908c1bec0ea0b6..2013de54f0f6a036e8378deefbff8d7cb5f7cfb2 100644 +--- a/src/node_config.cc ++++ b/src/node_config.cc +@@ -7,6 +7,10 @@ + #include "node_options.h" + #include "util-inl.h" + ++#if HAVE_OPENSSL ++#include ++#endif ++ + namespace node { + + using v8::Context; diff --git a/src/node_metadata.h b/src/node_metadata.h -index 6f8cb433ff8059c63d5cf16c8783139ae92fbf61..603ac3dde7d1a1109afbc451b69c8d0935b81641 100644 +index 7b2072ad39c3f1a7c73101b25b69beb781141e26..d23536d88d21255d348175425a59e2424332cd19 100644 --- a/src/node_metadata.h +++ b/src/node_metadata.h @@ -6,7 +6,7 @@ @@ -555,7 +570,7 @@ index 6f8cb433ff8059c63d5cf16c8783139ae92fbf61..603ac3dde7d1a1109afbc451b69c8d09 #if NODE_OPENSSL_HAS_QUIC #include diff --git a/src/node_options.cc b/src/node_options.cc -index 3fc8194475ec0e8a9047c1f3da5d120f25d66190..8be78889e8234eb3100f309829bf7470db544dcd 100644 +index da39abf79c53fcc3d83d3431deda9dbdf3b0621e..14f7764c995e8de6582faf58c9b98a9cbe4fab73 100644 --- a/src/node_options.cc +++ b/src/node_options.cc @@ -7,7 +7,7 @@ @@ -568,7 +583,7 @@ index 3fc8194475ec0e8a9047c1f3da5d120f25d66190..8be78889e8234eb3100f309829bf7470 #endif diff --git a/src/node_options.h b/src/node_options.h -index 7d14f06370d936a3866f0d988123de9fe614ce09..60068b008b2e2a034c3f0c58b947a8d04d55e3b2 100644 +index 165950c207ca752ec942ef27a671af66cbd2b938..eb18fdd617fd19e5b97cd67f351e70c28fee3e75 100644 --- a/src/node_options.h +++ b/src/node_options.h @@ -11,7 +11,7 @@ diff --git a/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch b/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch index 3eb241ca1eb19..c672873f6622d 100644 --- a/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch +++ b/patches/node/fix_lazyload_fs_in_esm_loaders_to_apply_asar_patches.patch @@ -60,7 +60,7 @@ index 9e7d8ef0adef3b68a3ec186e4b218f591aa69266..2879e5cf541fb4d226cfd7cc0fe367ca }); const { search, hash } = resolved; diff --git a/lib/internal/modules/esm/translators.js b/lib/internal/modules/esm/translators.js -index 4445bcc4c4c6c6f87ac45e693012a18a93739f9b..49aacb6262502ced54e817f99dd596db85b9659c 100644 +index 1db58d31dad24cd2da6bdc5e45e9dd4f0b899a23..bbd3085cfbf14aefd611954fa836f6c96d7e402c 100644 --- a/lib/internal/modules/esm/translators.js +++ b/lib/internal/modules/esm/translators.js @@ -24,7 +24,7 @@ const { diff --git a/patches/node/fix_remove_deprecated_errno_constants.patch b/patches/node/fix_remove_deprecated_errno_constants.patch index 0e9ce33bc3b42..55ac88fa57cd0 100644 --- a/patches/node/fix_remove_deprecated_errno_constants.patch +++ b/patches/node/fix_remove_deprecated_errno_constants.patch @@ -10,19 +10,19 @@ This change removes the usage of these constants to fix a compilation failure du See: https://github.com/llvm/llvm-project/pull/80542 diff --git a/deps/uv/include/uv.h b/deps/uv/include/uv.h -index f75a496071ac3396cbc6dec819eaab7294609deb..30f9a05f2f508b55a7d7ae036612660068c8400e 100644 +index 0295eeddbb4eb1cffd9dbcd02e037907fadc1b7e..7c2f9d2a8b13584ff6b33cd3ff4745e9fb3c4170 100644 --- a/deps/uv/include/uv.h +++ b/deps/uv/include/uv.h -@@ -155,7 +155,6 @@ struct uv__queue { +@@ -156,7 +156,6 @@ struct uv__queue { XX(EFTYPE, "inappropriate file type or format") \ XX(EILSEQ, "illegal byte sequence") \ XX(ESOCKTNOSUPPORT, "socket type not supported") \ - XX(ENODATA, "no data available") \ XX(EUNATCH, "protocol driver not attached") \ + XX(ENOEXEC, "exec format error") \ - #define UV_HANDLE_TYPE_MAP(XX) \ diff --git a/deps/uv/include/uv/errno.h b/deps/uv/include/uv/errno.h -index 127278ef916161a96e23e645927d16bedfdaca5b..b36da3daa5744e6f994e32d9d82aaef689008a5f 100644 +index ac00778cfc59fb55e361b24fc81a965a5e8f97e7..f0c4d6dfc9f03bee59e656b2da9ac325bced7b69 100644 --- a/deps/uv/include/uv/errno.h +++ b/deps/uv/include/uv/errno.h @@ -456,18 +456,6 @@ @@ -45,7 +45,7 @@ index 127278ef916161a96e23e645927d16bedfdaca5b..b36da3daa5744e6f994e32d9d82aaef6 # define UV__EUNATCH UV__ERR(EUNATCH) #else diff --git a/src/node_constants.cc b/src/node_constants.cc -index 13263149c111beede83b7063fa54f56655aea54c..99068098e1867af4846e18a5d039a25689722a4a 100644 +index 8c44e32381a44675792ca0922e47df1adda48e41..d193725ea9a3270ed9affea12d11467fb14efdf8 100644 --- a/src/node_constants.cc +++ b/src/node_constants.cc @@ -241,10 +241,6 @@ void DefineErrnoConstants(Local target) { diff --git a/patches/node/fix_remove_fastapitypedarray_usage.patch b/patches/node/fix_remove_fastapitypedarray_usage.patch index 1d5b56cbe1fea..29a42af4b16cf 100644 --- a/patches/node/fix_remove_fastapitypedarray_usage.patch +++ b/patches/node/fix_remove_fastapitypedarray_usage.patch @@ -48,7 +48,7 @@ index 867a1c4aca54b9d41490d23a5eb55088b7e941cc..09f4c65a18efea262b1f854f993c6f18 static v8::CFunction fast_equal(v8::CFunction::Make(FastTimingSafeEqual)); diff --git a/src/node_buffer.cc b/src/node_buffer.cc -index 5bdffc0a4d7f8f643343593a543f2064b670c1b9..6931404b75dbe17bf3c7b561430b8d7c0921d085 100644 +index b8021c079ca6b141ea99a4abbc828430da9d3093..98ade40ec7a6bc805acb579c8a51dcd5468c2893 100644 --- a/src/node_buffer.cc +++ b/src/node_buffer.cc @@ -44,6 +44,14 @@ @@ -194,7 +194,7 @@ index 5bdffc0a4d7f8f643343593a543f2064b670c1b9..6931404b75dbe17bf3c7b561430b8d7c static const v8::CFunction fast_write_string_ascii( diff --git a/src/node_external_reference.h b/src/node_external_reference.h -index bb007dbdcce486659afeed07b78103e44b00307b..314a4ded6908a94107de1ae1e550b7d46afdce75 100644 +index 3bc7b2cab5a12e281058b79a7d0f734eb527986c..4218eaf365c739a4c04ca94e29d6d2a33a637d44 100644 --- a/src/node_external_reference.h +++ b/src/node_external_reference.h @@ -43,16 +43,16 @@ using CFunctionCallbackWithStrings = @@ -219,7 +219,7 @@ index bb007dbdcce486659afeed07b78103e44b00307b..314a4ded6908a94107de1ae1e550b7d4 uint32_t, int64_t, bool); -@@ -71,18 +71,20 @@ using CFunctionWithBool = void (*)(v8::Local, +@@ -73,18 +73,20 @@ using CFunctionWithBool = void (*)(v8::Local, using CFunctionWriteString = uint32_t (*)(v8::Local receiver, @@ -246,7 +246,7 @@ index bb007dbdcce486659afeed07b78103e44b00307b..314a4ded6908a94107de1ae1e550b7d4 // This class manages the external references from the V8 heap // to the C++ addresses in Node.js. diff --git a/src/util.h b/src/util.h -index a77332f583402af956cc886fd5b9771390cc4827..f0d7571caa458a3f9a9c252a95f72eb5fbddd06d 100644 +index 6376cf4f81113cdb2e3c179b800f1c79b51ab762..cc7ad99f981f564fba0395159d9d8b39901050ff 100644 --- a/src/util.h +++ b/src/util.h @@ -60,6 +60,7 @@ diff --git a/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch b/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch index 81346e984b9a8..eb48a5a18140f 100644 --- a/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch +++ b/patches/node/fix_remove_harmony-import-assertions_from_node_cc.patch @@ -11,10 +11,10 @@ This patch can be removed when we upgrade to a V8 version that contains the above CL. diff --git a/src/node.cc b/src/node.cc -index 0fbcd55d674b1d0cae88f04fe337cfcca702255f..092b1c525c7d4d50a09f99dc088d0698afcaf8a6 100644 +index c0d0b734edfa729c91a8112189c480e3f2382988..a43d36c731693b9d2ed1ba13f6b4bb33bf6c4ca4 100644 --- a/src/node.cc +++ b/src/node.cc -@@ -814,7 +814,7 @@ static ExitCode ProcessGlobalArgsInternal(std::vector* args, +@@ -816,7 +816,7 @@ static ExitCode ProcessGlobalArgsInternal(std::vector* args, } // TODO(nicolo-ribaudo): remove this once V8 doesn't enable it by default // anymore. diff --git a/patches/node/linux_try_preadv64_pwritev64_before_preadv_pwritev_4683.patch b/patches/node/linux_try_preadv64_pwritev64_before_preadv_pwritev_4683.patch deleted file mode 100644 index 06bb2affd320e..0000000000000 --- a/patches/node/linux_try_preadv64_pwritev64_before_preadv_pwritev_4683.patch +++ /dev/null @@ -1,51 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Ben Noordhuis -Date: Tue, 28 Jan 2025 09:27:58 +0100 -Subject: linux: try preadv64/pwritev64 before preadv/pwritev (#4683) - -Fixes: https://github.com/libuv/libuv/issues/4678 -Refs: https://github.com/libuv/libuv/issues/4532 - -diff --git a/deps/uv/src/unix/fs.c b/deps/uv/src/unix/fs.c -index 239ecda16a7eb9b40453502cf0362ae66366cf72..1631d9340bc10c2ac4c3d53a63ed9bc10f3e1c7c 100644 ---- a/deps/uv/src/unix/fs.c -+++ b/deps/uv/src/unix/fs.c -@@ -461,12 +461,7 @@ static ssize_t uv__pwritev_emul(int fd, - - /* The function pointer cache is an uintptr_t because _Atomic void* - * doesn't work on macos/ios/etc... -- * Disable optimization on armv7 to work around the bug described in -- * https://github.com/libuv/libuv/issues/4532 - */ --#if defined(__arm__) && (__ARM_ARCH == 7) --__attribute__((optimize("O0"))) --#endif - static ssize_t uv__preadv_or_pwritev(int fd, - const struct iovec* bufs, - size_t nbufs, -@@ -479,7 +474,12 @@ static ssize_t uv__preadv_or_pwritev(int fd, - p = (void*) atomic_load_explicit(cache, memory_order_relaxed); - if (p == NULL) { - #ifdef RTLD_DEFAULT -- p = dlsym(RTLD_DEFAULT, is_pread ? "preadv" : "pwritev"); -+ /* Try _LARGEFILE_SOURCE version of preadv/pwritev first, -+ * then fall back to the plain version, for libcs like musl. -+ */ -+ p = dlsym(RTLD_DEFAULT, is_pread ? "preadv64" : "pwritev64"); -+ if (p == NULL) -+ p = dlsym(RTLD_DEFAULT, is_pread ? "preadv" : "pwritev"); - dlerror(); /* Clear errors. */ - #endif /* RTLD_DEFAULT */ - if (p == NULL) -@@ -487,10 +487,7 @@ static ssize_t uv__preadv_or_pwritev(int fd, - atomic_store_explicit(cache, (uintptr_t) p, memory_order_relaxed); - } - -- /* Use memcpy instead of `f = p` to work around a compiler bug, -- * see https://github.com/libuv/libuv/issues/4532 -- */ -- memcpy(&f, &p, sizeof(p)); -+ f = p; - return f(fd, bufs, nbufs, off); - } - diff --git a/patches/node/pass_all_globals_through_require.patch b/patches/node/pass_all_globals_through_require.patch index 918c6d2aac4f2..7d2b862278233 100644 --- a/patches/node/pass_all_globals_through_require.patch +++ b/patches/node/pass_all_globals_through_require.patch @@ -6,7 +6,7 @@ Subject: Pass all globals through "require" (cherry picked from commit 7d015419cb7a0ecfe6728431a4ed2056cd411d62) diff --git a/lib/internal/modules/cjs/loader.js b/lib/internal/modules/cjs/loader.js -index ccd2b4ced3134d81ddd37b8b5b90218457633421..a19fc5e52109bf2ad63fbe554c02a458c3096081 100644 +index d90476addb3f7cc2d0b8d8686386873894e75c25..e647bdda4624317615490cedd8d4edbcebbca8bc 100644 --- a/lib/internal/modules/cjs/loader.js +++ b/lib/internal/modules/cjs/loader.js @@ -200,6 +200,13 @@ const { diff --git a/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch b/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch index e7344756b3855..dbbf389088cd5 100644 --- a/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch +++ b/patches/node/refactor_allow_embedder_overriding_of_internal_fs_calls.patch @@ -7,7 +7,7 @@ We use this to allow node's 'fs' module to read from ASAR files as if they were a real filesystem. diff --git a/lib/internal/bootstrap/node.js b/lib/internal/bootstrap/node.js -index 4fd535f730e6382672b853bf2098b3fefc1f83b4..bd6724de52ee1f01fa42084c7652c71054f0a9c6 100644 +index dd9e3e58d72fb9ada1528212f80e0e911292a266..5758c74f6139dbe4fbeeae9d1e9b078688261257 100644 --- a/lib/internal/bootstrap/node.js +++ b/lib/internal/bootstrap/node.js @@ -132,6 +132,10 @@ process.domain = null; diff --git a/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch b/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch index a526b752d46d3..f6eff26f8203a 100644 --- a/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch +++ b/patches/node/refactor_attach_cppgc_heap_on_v8_isolate_creation.patch @@ -47,7 +47,7 @@ index 5b7f6e0609c8414c686d2d5ca603ea5c8bc484d0..6c9c81ff3c08fc28dc35578229a78552 event_loop, platform, diff --git a/src/env.cc b/src/env.cc -index ddf82c8a18c29c355641e33974c1e5e67867379d..ae43803d8c2de90fb191a8e10605f6f3b18816ed 100644 +index 400ff494f4e153408a2fce343d7b156d7ccefc7b..cac2d97323d131451eab4ca68ce771cb936447e4 100644 --- a/src/env.cc +++ b/src/env.cc @@ -577,14 +577,6 @@ IsolateData::IsolateData(Isolate* isolate, @@ -82,7 +82,7 @@ index ddf82c8a18c29c355641e33974c1e5e67867379d..ae43803d8c2de90fb191a8e10605f6f3 void SetCppgcReference(Isolate* isolate, Local object, diff --git a/src/env.h b/src/env.h -index 9f1c7ef45b6df10f811936a78ea6d9fcc13fef4f..c429eecd937d1df32a2ff90bc0a22a2e58df3a3d 100644 +index 1079e3beb02e5f5d71a15fd2db65cb93ebd175d6..a7be609c3ab9093cec5145367b95ae6859936a24 100644 --- a/src/env.h +++ b/src/env.h @@ -155,7 +155,6 @@ class NODE_EXTERN_PRIVATE IsolateData : public MemoryRetainer { @@ -102,10 +102,10 @@ index 9f1c7ef45b6df10f811936a78ea6d9fcc13fef4f..c429eecd937d1df32a2ff90bc0a22a2e worker::Worker* worker_context_ = nullptr; PerIsolateWrapperData* wrapper_data_; diff --git a/src/node.cc b/src/node.cc -index 092b1c525c7d4d50a09f99dc088d0698afcaf8a6..6f8f6386d0db8aef1e2e0126cc9064101cbe6112 100644 +index a43d36c731693b9d2ed1ba13f6b4bb33bf6c4ca4..0c2a4d344c991c2ca0d9d90934cf7921abf2a629 100644 --- a/src/node.cc +++ b/src/node.cc -@@ -1258,6 +1258,14 @@ InitializeOncePerProcessInternal(const std::vector& args, +@@ -1257,6 +1257,14 @@ InitializeOncePerProcessInternal(const std::vector& args, result->platform_ = per_process::v8_platform.Platform(); } @@ -120,7 +120,7 @@ index 092b1c525c7d4d50a09f99dc088d0698afcaf8a6..6f8f6386d0db8aef1e2e0126cc906410 if (!(flags & ProcessInitializationFlags::kNoInitializeV8)) { V8::Initialize(); -@@ -1267,14 +1275,6 @@ InitializeOncePerProcessInternal(const std::vector& args, +@@ -1266,14 +1274,6 @@ InitializeOncePerProcessInternal(const std::vector& args, absl::SetMutexDeadlockDetectionMode(absl::OnDeadlockCycle::kIgnore); } diff --git a/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch b/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch index 3936c9bc7017a..76a7169955aec 100644 --- a/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch +++ b/patches/node/src_remove_dependency_on_wrapper-descriptor-based_cppheap.patch @@ -16,7 +16,7 @@ patch: (cherry picked from commit 30329d06235a9f9733b1d4da479b403462d1b326) diff --git a/src/env-inl.h b/src/env-inl.h -index d4b211dfb2f77a65f311701d95365e66d92f8875..4c1a5f2b92d7fdddb8c2e7bbfd6788fdff3645b9 100644 +index 0d32d9f5a55da257a5e5a895a2ff002b780f96fe..9567d9499c62ea44cca651e87ab912ad55e2d90b 100644 --- a/src/env-inl.h +++ b/src/env-inl.h @@ -62,31 +62,6 @@ inline uv_loop_t* IsolateData::event_loop() const { @@ -52,7 +52,7 @@ index d4b211dfb2f77a65f311701d95365e66d92f8875..4c1a5f2b92d7fdddb8c2e7bbfd6788fd return &(wrapper_data_->cppgc_id); } diff --git a/src/env.cc b/src/env.cc -index f8c24e422756d5101a258175a2f28a96648bea47..ddf82c8a18c29c355641e33974c1e5e67867379d 100644 +index 99bd3e37853f99ecb2e45df373f17c10b3bd1561..400ff494f4e153408a2fce343d7b156d7ccefc7b 100644 --- a/src/env.cc +++ b/src/env.cc @@ -23,6 +23,7 @@ @@ -146,7 +146,7 @@ index f8c24e422756d5101a258175a2f28a96648bea47..ddf82c8a18c29c355641e33974c1e5e6 void IsolateData::MemoryInfo(MemoryTracker* tracker) const { diff --git a/src/env.h b/src/env.h -index cfe917c797a6e4bb0f0284ec56be82637f840129..9f1c7ef45b6df10f811936a78ea6d9fcc13fef4f 100644 +index 07accfbcca491966c6c8ad9c20e146dbd22347f0..1079e3beb02e5f5d71a15fd2db65cb93ebd175d6 100644 --- a/src/env.h +++ b/src/env.h @@ -175,10 +175,6 @@ class NODE_EXTERN_PRIVATE IsolateData : public MemoryRetainer { diff --git a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch index 4a6e3d5147779..ae9a03f622734 100644 --- a/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch +++ b/patches/node/src_stop_using_deprecated_fields_of_fastapicallbackoptions.patch @@ -40,10 +40,10 @@ index 5641990e0bac455c33ddf7b9a865deba871516e7..bd757f42e02391abbeec007d9c4cea60 } HistogramBase* histogram; diff --git a/src/node_file.cc b/src/node_file.cc -index 5aea65d6800494def62829432ee48f9c06e65d63..80cf6648ed99241eea8c176c5c958d76fe33aa14 100644 +index 37172158d318d6569194fd3c5441d107e155e54c..41498615a37945111348e22b18214c3bcc9533a0 100644 --- a/src/node_file.cc +++ b/src/node_file.cc -@@ -1071,13 +1071,8 @@ static int32_t FastInternalModuleStat( +@@ -1074,13 +1074,8 @@ static int32_t FastInternalModuleStat( // NOLINTNEXTLINE(runtime/references) This is V8 api. FastApiCallbackOptions& options) { // This needs a HandleScope which needs an isolate. diff --git a/patches/node/support_v8_sandboxed_pointers.patch b/patches/node/support_v8_sandboxed_pointers.patch index 2aedd3ceeae9a..e0c48e287c723 100644 --- a/patches/node/support_v8_sandboxed_pointers.patch +++ b/patches/node/support_v8_sandboxed_pointers.patch @@ -189,7 +189,7 @@ index f616223cfb0f6e10f7cf57ada9704316bde2797e..eb6dad44a49d997097c8fb5009eeb60a Local ret; if (!Buffer::New(env, ab, 0, ab->ByteLength()).ToLocal(&ret)) return {}; diff --git a/src/node_i18n.cc b/src/node_i18n.cc -index ea7810e41e2667713a896250dc1b904b0a7cf198..865b3128c1edfe7074769f25a0b87878ca094f31 100644 +index 61b6ecd240c9500f21f683065a2f920af3afb502..ad2b1c76325cb5c8f18a618c5a85ae87b6a7bbe7 100644 --- a/src/node_i18n.cc +++ b/src/node_i18n.cc @@ -104,7 +104,7 @@ namespace { @@ -384,18 +384,3 @@ index 9787b14352753c5e0f8dc2b90093680e7cd10f1a..31af9e62396368af1b81f8841a705fd3 auto ab = ArrayBuffer::New(isolate, std::move(bs)); v8::Local u8 = v8::Uint8Array::New(ab, 0, 1); -diff --git a/test/parallel/test-buffer-tostring-range.js b/test/parallel/test-buffer-tostring-range.js -index 73fec107a36c3db4af6f492137d0ca174f2d0547..a1153ec381f7b12a1640b611073f6997e1ec5696 100644 ---- a/test/parallel/test-buffer-tostring-range.js -+++ b/test/parallel/test-buffer-tostring-range.js -@@ -102,8 +102,8 @@ assert.throws(() => { - // Must not throw when start and end are within kMaxLength - // Cannot test on 32bit machine as we are testing the case - // when start and end are above the threshold --if (!common.openSSLIsBoringSSL) { -+/* - const threshold = 0xFFFFFFFF; - const largeBuffer = Buffer.alloc(threshold + 20); - largeBuffer.toString('utf8', threshold, threshold + 20); --} -+*/ diff --git a/patches/node/test_force_slow_json_stringify_path_for_overflow.patch b/patches/node/test_force_slow_json_stringify_path_for_overflow.patch deleted file mode 100644 index 7d57385f74f11..0000000000000 --- a/patches/node/test_force_slow_json_stringify_path_for_overflow.patch +++ /dev/null @@ -1,38 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Shelley Vohr -Date: Mon, 5 May 2025 13:04:14 +0000 -Subject: test: force slow JSON.stringify path for overflow - -Refs https://chromium-review.googlesource.com/c/v8/v8/+/6011806 - -The V8 team just enabled the JSON.stringify fast path by default, -which is iterative and won't throw. Pre-emptively preserve test -functionality by forcing the slow path. See above linked PR for -approach this is borrowed from. - -Upstreamed in https://github.com/nodejs/node/pull/58181. - -diff --git a/test/fixtures/console/stack_overflow.js b/test/fixtures/console/stack_overflow.js -index 565692b6d6e4ba4c439a38250407004c5aa21df9..14bceef878b5cf27609b29c8cc7852cab4dd63ff 100644 ---- a/test/fixtures/console/stack_overflow.js -+++ b/test/fixtures/console/stack_overflow.js -@@ -26,11 +26,15 @@ Error.stackTraceLimit = 0; - - console.error('before'); - -+// Invalidate elements protector to force slow-path. -+// The fast-path of JSON.stringify is iterative and won't throw. -+Array.prototype[2] = 'foo'; -+ - // Trigger stack overflow by stringifying a deeply nested array. --let array = []; --for (let i = 0; i < 100000; i++) { -- array = [ array ]; --} -+// eslint-disable-next-line no-sparse-arrays -+let array = [,]; -+for (let i = 0; i < 10000; i++) -+ array = [array]; - - JSON.stringify(array); - diff --git a/patches/node/test_formally_mark_some_tests_as_flaky.patch b/patches/node/test_formally_mark_some_tests_as_flaky.patch index 5dd4584847450..c137995d960c0 100644 --- a/patches/node/test_formally_mark_some_tests_as_flaky.patch +++ b/patches/node/test_formally_mark_some_tests_as_flaky.patch @@ -7,7 +7,7 @@ Instead of disabling the tests, flag them as flaky so they still run but don't cause CI failures on flakes. diff --git a/test/parallel/parallel.status b/test/parallel/parallel.status -index cc99efd7a743d683d5210ad83e258560c28cbd16..b2f0f7fb49665f0dc924cdd3e344c2579d617fbf 100644 +index 8b9a4e80a08031085dde8a6952224e6ca3ca052e..2e83f166a34930083e697aaf06271e79cefe3f23 100644 --- a/test/parallel/parallel.status +++ b/test/parallel/parallel.status @@ -5,6 +5,16 @@ prefix parallel From cc05e5f40eac80c658000524223cc2657ca643d2 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Wed, 2 Jul 2025 12:12:01 +0200 Subject: [PATCH 132/186] chore: bump chromium to 138.0.7204.97 (37-x-y) (#47619) * chore: bump chromium in DEPS to 138.0.7204.51 * chore: bump chromium in DEPS to 138.0.7204.97 * Revert "Reland "FSA: Only normalize the hardcoded rules once during initialization"" https://chromium-review.googlesource.com/c/chromium/src/+/6687843 --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- DEPS | 2 +- ..._expose_file_system_access_blocklist.patch | 601 ++++++++---------- .../file_system_access_permission_context.cc | 148 ++--- .../file_system_access_permission_context.h | 24 +- 4 files changed, 297 insertions(+), 478 deletions(-) diff --git a/DEPS b/DEPS index ec3ebdcc5c512..efc27b9309385 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.49', + '138.0.7204.97', 'node_version': 'v22.17.0', 'nan_version': diff --git a/patches/chromium/refactor_expose_file_system_access_blocklist.patch b/patches/chromium/refactor_expose_file_system_access_blocklist.patch index 20dba82debd12..3d349fdf3f994 100644 --- a/patches/chromium/refactor_expose_file_system_access_blocklist.patch +++ b/patches/chromium/refactor_expose_file_system_access_blocklist.patch @@ -8,10 +8,18 @@ it in Electron and prevent drift from Chrome's blocklist. We should look for a w to upstream this change to Chrome. diff --git a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc -index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255cab529c646 100644 +index 3514864559de0d2f2f36fda9b0add0b7b88f3b2a..44318ce3bed67e6f83f3687d11500ddfecd4aef4 100644 --- a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc +++ b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.cc -@@ -82,11 +82,13 @@ +@@ -45,7 +45,6 @@ + #include "chrome/browser/ui/file_system_access/file_system_access_dangerous_file_dialog.h" + #include "chrome/browser/ui/file_system_access/file_system_access_dialogs.h" + #include "chrome/browser/ui/file_system_access/file_system_access_restricted_directory_dialog.h" +-#include "chrome/common/chrome_paths.h" + #include "chrome/grit/generated_resources.h" + #include "components/content_settings/core/browser/host_content_settings_map.h" + #include "components/content_settings/core/common/content_settings.h" +@@ -81,11 +80,13 @@ #include "chrome/browser/ui/browser_window.h" #include "chrome/browser/ui/tabs/public/tab_features.h" #include "chrome/browser/ui/views/file_system_access/file_system_access_page_action_controller.h" @@ -25,7 +33,7 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca #include "components/tabs/public/tab_interface.h" #if BUILDFLAG(ENABLE_PLATFORM_APPS) #include "extensions/browser/extension_registry.h" // nogncheck -@@ -262,182 +264,10 @@ bool MaybeIsLocalUNCPath(const base::FilePath& path) { +@@ -261,129 +262,10 @@ bool MaybeIsLocalUNCPath(const base::FilePath& path) { } #endif @@ -33,6 +41,111 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca -// the struct below. -constexpr const int kNoBasePathKey = -1; - +-using BlockType = ChromeFileSystemAccessPermissionContext::BlockType; +- +-std::vector +-GenerateBlockedPath() { +- return { +- // Don't allow users to share their entire home directory, entire desktop +- // or entire documents folder, but do allow sharing anything inside those +- // directories not otherwise blocked. +- {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, +- {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, +- {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, +- // Similar restrictions for the downloads directory. +- {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, BlockType::kDontBlockChildren}, +- {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, +- BlockType::kDontBlockChildren}, +- // The Chrome installation itself should not be modified by the web. +- {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, +- // And neither should the configuration of at least the currently running +- // Chrome instance (note that this does not take --user-data-dir command +- // line overrides into account). +- {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, +- // ~/.ssh is pretty sensitive on all platforms, so block access to that. +- {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), BlockType::kBlockAllChildren}, +- // And limit access to ~/.gnupg as well. +- {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), +- BlockType::kBlockAllChildren}, +-#if BUILDFLAG(IS_WIN) +- // Some Windows specific directories to block, basically all apps, the +- // operating system itself, as well as configuration data for apps. +- {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- // Opening a file from an MTP device, such as a smartphone or a camera, is +- // implemented by Windows as opening a file in the temporary internet +- // files directory. To support that, allow opening files in that +- // directory, but not whole directories. +- {base::DIR_IE_INTERNET_CACHE, nullptr, +- BlockType::kBlockNestedDirectories}, +-#endif +-#if BUILDFLAG(IS_MAC) +- // Similar Mac specific blocks. +- {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- // Block access to the current bundle directory. +- {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, +- // Block access to the user's Applications directory. +- {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), +- BlockType::kBlockAllChildren}, +- // Block access to the root Applications directory. +- {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), +- BlockType::kBlockAllChildren}, +- {base::DIR_HOME, FILE_PATH_LITERAL("Library"), +- BlockType::kBlockAllChildren}, +- // Allow access to other cloud files, such as Google Drive. +- {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), +- BlockType::kDontBlockChildren}, +- // Allow the site to interact with data from its corresponding natively +- // installed (sandboxed) application. It would be nice to limit a site to +- // access only _its_ corresponding natively installed application, but +- // unfortunately there's no straightforward way to do that. See +- // https://crbug.com/984641#c22. +- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), +- BlockType::kDontBlockChildren}, +- // Allow access to iCloud files... +- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), +- BlockType::kDontBlockChildren}, +- // ... which may also appear at this directory. +- {base::DIR_HOME, +- FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), +- BlockType::kDontBlockChildren}, +-#endif +-#if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_ANDROID) +- // On Linux also block access to devices via /dev. +- {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), BlockType::kBlockAllChildren}, +- // And security sensitive data in /proc and /sys. +- {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), +- BlockType::kBlockAllChildren}, +- {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), BlockType::kBlockAllChildren}, +- // And system files in /boot and /etc. +- {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), +- BlockType::kBlockAllChildren}, +- {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), BlockType::kBlockAllChildren}, +- // And block all of ~/.config, matching the similar restrictions on mac +- // and windows. +- {base::DIR_HOME, FILE_PATH_LITERAL(".config"), +- BlockType::kBlockAllChildren}, +- // Block ~/.dbus as well, just in case, although there probably isn't much +- // a website can do with access to that directory and its contents. +- {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), +- BlockType::kBlockAllChildren}, +-#endif +-#if BUILDFLAG(IS_ANDROID) +- {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, +- {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, +-#endif +- // TODO(crbug.com/40095723): Refine this list, for example add +- // XDG_CONFIG_HOME when it is not set ~/.config? +- }; +-} +- -// A wrapper around `base::NormalizeFilePath` that returns its result instead of -// using an out parameter. -base::FilePath NormalizeFilePath(const base::FilePath& path) { @@ -47,164 +160,6 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca - CHECK_EQ(path.empty(), normalized_path.empty()); - return normalized_path; -} -- --using BlockType = ChromeFileSystemAccessPermissionContext::BlockType; -- --std::unique_ptr --GenerateBlockPaths(bool should_normalize_file_path) { -- static constexpr ChromeFileSystemAccessPermissionContext::BlockPath -- kBlockPaths[] = { -- // Don't allow users to share their entire home directory, entire -- // desktop or entire documents folder, but do allow sharing anything -- // inside those directories not otherwise blocked. -- {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, -- {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, -- {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, -- // Similar restrictions for the downloads directory. -- {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, -- BlockType::kDontBlockChildren}, -- {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, -- BlockType::kDontBlockChildren}, -- // The Chrome installation itself should not be modified by the web. -- {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, -- // And neither should the configuration of at least the currently -- // running -- // Chrome instance (note that this does not take --user-data-dir -- // command -- // line overrides into account). -- {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, -- // ~/.ssh is pretty sensitive on all platforms, so block access to -- // that. -- {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), -- BlockType::kBlockAllChildren}, -- // And limit access to ~/.gnupg as well. -- {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), -- BlockType::kBlockAllChildren}, --#if BUILDFLAG(IS_WIN) -- // Some Windows specific directories to block, basically all apps, the -- // operating system itself, as well as configuration data for apps. -- {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- // Opening a file from an MTP device, such as a smartphone or a -- // camera, is -- // implemented by Windows as opening a file in the temporary internet -- // files directory. To support that, allow opening files in that -- // directory, but not whole directories. -- {base::DIR_IE_INTERNET_CACHE, nullptr, -- BlockType::kBlockNestedDirectories}, --#endif --#if BUILDFLAG(IS_MAC) -- // Similar Mac specific blocks. -- {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- // Block access to the current bundle directory. -- {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, -- // Block access to the user's Applications directory. -- {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), -- BlockType::kBlockAllChildren}, -- // Block access to the root Applications directory. -- {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), -- BlockType::kBlockAllChildren}, -- {base::DIR_HOME, FILE_PATH_LITERAL("Library"), -- BlockType::kBlockAllChildren}, -- // Allow access to other cloud files, such as Google Drive. -- {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), -- BlockType::kDontBlockChildren}, -- // Allow the site to interact with data from its corresponding -- // natively -- // installed (sandboxed) application. It would be nice to limit a site -- // to -- // access only _its_ corresponding natively installed application, but -- // unfortunately there's no straightforward way to do that. See -- // https://crbug.com/984641#c22. -- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), -- BlockType::kDontBlockChildren}, -- // Allow access to iCloud files... -- {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), -- BlockType::kDontBlockChildren}, -- // ... which may also appear at this directory. -- {base::DIR_HOME, -- FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), -- BlockType::kDontBlockChildren}, --#endif --#if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_ANDROID) -- // On Linux also block access to devices via /dev. -- {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), -- BlockType::kBlockAllChildren}, -- // And security sensitive data in /proc and /sys. -- {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), -- BlockType::kBlockAllChildren}, -- {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), -- BlockType::kBlockAllChildren}, -- // And system files in /boot and /etc. -- {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), -- BlockType::kBlockAllChildren}, -- {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), -- BlockType::kBlockAllChildren}, -- // And block all of ~/.config, matching the similar restrictions on -- // mac -- // and windows. -- {base::DIR_HOME, FILE_PATH_LITERAL(".config"), -- BlockType::kBlockAllChildren}, -- // Block ~/.dbus as well, just in case, although there probably isn't -- // much -- // a website can do with access to that directory and its contents. -- {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), -- BlockType::kBlockAllChildren}, --#endif --#if BUILDFLAG(IS_ANDROID) -- {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -- {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, --#endif -- // TODO(crbug.com/40095723): Refine this list, for example add -- // XDG_CONFIG_HOME when it is not set ~/.config? -- }; -- -- // ChromeOS supports multi-user sign-in. base::DIR_HOME only returns the -- // profile path for the primary user, the first user to sign in. We want to -- // use the `profile_path` instead since that's associated with user that -- // initiated this blocklist check. -- // -- // TODO(crbug.com/375490221): Improve the ChromeOS blocklist logic. -- constexpr bool kUseProfilePathForDirHome = BUILDFLAG(IS_CHROMEOS); -- // Populate the hard-coded rules. -- auto block_path_rules = std::make_unique< -- ChromeFileSystemAccessPermissionContext::BlockPathRules>(); -- -- for (const auto& blocked_path : kBlockPaths) { -- base::FilePath path; -- if (blocked_path.base_path_key != kNoBasePathKey) { -- if (kUseProfilePathForDirHome && -- blocked_path.base_path_key == base::DIR_HOME) { -- block_path_rules->profile_based_block_path_rules_.emplace_back( -- blocked_path.path, blocked_path.type); -- continue; -- } -- -- if (!base::PathService::Get(blocked_path.base_path_key, &path)) { -- continue; -- } -- -- if (blocked_path.path) { -- path = path.Append(blocked_path.path); -- } -- } else { -- DCHECK(blocked_path.path); -- path = base::FilePath(blocked_path.path); -- } -- block_path_rules->block_path_rules_.emplace_back( -- should_normalize_file_path ? NormalizeFilePath(path) : path, -- blocked_path.type); -- } -- -- return block_path_rules; --} +// This patch moves the deleted content from this file over to +// chrome/browser/file_system_access/chrome_file_system_access_permission_context.h. +// NOTE IF THERE IS A CONFLICT ABOVE, you will need to copy the changes in the @@ -212,24 +167,7 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca // Checks if `path` should be blocked by the `rules`. // The BlockType of the nearest ancestor of a path to check is what -@@ -1261,16 +1091,6 @@ struct ChromeFileSystemAccessPermissionContext::OriginState { - std::unique_ptr cleanup_timer; - }; - --ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules() = -- default; --ChromeFileSystemAccessPermissionContext::BlockPathRules::~BlockPathRules() = -- default; --ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules( -- const BlockPathRules& other) = default; --ChromeFileSystemAccessPermissionContext::BlockPathRules& --ChromeFileSystemAccessPermissionContext::BlockPathRules::operator=( -- const BlockPathRules& other) = default; -- - ChromeFileSystemAccessPermissionContext:: - ChromeFileSystemAccessPermissionContext(content::BrowserContext* context, - const base::Clock* clock) -@@ -1289,7 +1109,7 @@ ChromeFileSystemAccessPermissionContext:: +@@ -1237,7 +1119,7 @@ ChromeFileSystemAccessPermissionContext:: #if BUILDFLAG(IS_ANDROID) one_time_permissions_tracker_.Observe( OneTimePermissionsTrackerFactory::GetForBrowserContext(context)); @@ -238,7 +176,7 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca auto* provider = web_app::WebAppProvider::GetForWebApps( Profile::FromBrowserContext(profile_)); if (provider) { -@@ -2551,7 +2371,7 @@ void ChromeFileSystemAccessPermissionContext::OnShutdown() { +@@ -2443,7 +2325,7 @@ void ChromeFileSystemAccessPermissionContext::OnShutdown() { one_time_permissions_tracker_.Reset(); } @@ -247,7 +185,7 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca void ChromeFileSystemAccessPermissionContext::OnWebAppInstalled( const webapps::AppId& app_id) { if (!base::FeatureList::IsEnabled( -@@ -3108,11 +2928,7 @@ bool ChromeFileSystemAccessPermissionContext::OriginHasExtendedPermission( +@@ -3000,11 +2882,7 @@ bool ChromeFileSystemAccessPermissionContext::OriginHasExtendedPermission( const url::Origin& origin) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); @@ -260,7 +198,7 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca if (!base::FeatureList::IsEnabled( features::kFileSystemAccessPersistentPermissions)) { return false; -@@ -3156,6 +2972,7 @@ bool ChromeFileSystemAccessPermissionContext::OriginHasExtendedPermission( +@@ -3048,6 +2926,7 @@ bool ChromeFileSystemAccessPermissionContext::OriginHasExtendedPermission( : WebAppInstallStatus::kUninstalled; return app_has_os_integration; #endif // BUILDFLAG(IS_ANDROID) @@ -269,10 +207,10 @@ index 5b543e82abb17cbb91bf37fa6bac016b6053eb93..117b6b05b3a1c39183a45830b97255ca void ChromeFileSystemAccessPermissionContext::SetOriginExtendedPermissionByUser( diff --git a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h -index f647100981fd98d8511d07a6d7e100910e38a0f2..14e1b3c8ec78429f5a845f54cc973e7c77ea8bc4 100644 +index 46a2019587b534add3c89f464cdf7261a67e7cce..57e3f7c966a45114b17701a851b191be88d72e7c 100644 --- a/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h +++ b/chrome/browser/file_system_access/chrome_file_system_access_permission_context.h -@@ -9,10 +9,13 @@ +@@ -9,9 +9,12 @@ #include #include "base/auto_reset.h" @@ -281,200 +219,165 @@ index f647100981fd98d8511d07a6d7e100910e38a0f2..14e1b3c8ec78429f5a845f54cc973e7c #include "base/files/file_path.h" +#include "base/files/file_util.h" #include "base/memory/raw_ptr.h" - #include "base/memory/weak_ptr.h" +#include "base/path_service.h" #include "base/scoped_observation.h" #include "base/sequence_checker.h" #include "base/time/clock.h" -@@ -22,6 +25,7 @@ +@@ -21,7 +24,7 @@ #include "chrome/browser/file_system_access/file_system_access_permission_request_manager.h" #include "chrome/browser/permissions/one_time_permissions_tracker.h" #include "chrome/browser/permissions/one_time_permissions_tracker_observer.h" +-#include "components/enterprise/buildflags/buildflags.h" +#include "chrome/common/chrome_paths.h" - #include "components/enterprise/buildflags/buildflags.h" #include "components/permissions/features.h" #include "components/permissions/object_permission_context_base.h" -@@ -403,6 +407,183 @@ class ChromeFileSystemAccessPermissionContext - return is_block_path_rules_init_complete_; - } + #include "content/public/browser/file_system_access_permission_context.h" +@@ -31,7 +34,7 @@ + #include "chrome/browser/web_applications/web_app_install_manager_observer.h" + #endif + +-#if BUILDFLAG(ENTERPRISE_CLOUD_CONTENT_ANALYSIS) ++#if 0 + #include "components/enterprise/common/files_scan_data.h" + #endif + +@@ -371,6 +374,130 @@ class ChromeFileSystemAccessPermissionContext + // KeyedService: + void Shutdown() override; + // Sentinel used to indicate that no PathService key is specified for a path in + // the struct below. + static constexpr const int kNoBasePathKey = -1; + -+ // A wrapper around `base::NormalizeFilePath` that returns its result instead of -+ // using an out parameter. -+ static base::FilePath NormalizeFilePath(const base::FilePath& path) { -+ CHECK(path.IsAbsolute()); -+ // TODO(crbug.com/368130513O): On Windows, this call will fail if the target -+ // file path is greater than MAX_PATH. We should decide how to handle this -+ // scenario. -+ base::FilePath normalized_path; -+ if (!base::NormalizeFilePath(path, &normalized_path)) { -+ return path; -+ } -+ CHECK_EQ(path.empty(), normalized_path.empty()); -+ return normalized_path; -+ } -+ + using BlockType = ChromeFileSystemAccessPermissionContext::BlockType; + -+ static std::unique_ptr -+ GenerateBlockPaths(bool should_normalize_file_path) { -+ static constexpr ChromeFileSystemAccessPermissionContext::BlockPath -+ kBlockPaths[] = { -+ // Don't allow users to share their entire home directory, entire -+ // desktop or entire documents folder, but do allow sharing anything -+ // inside those directories not otherwise blocked. -+ {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, -+ {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, -+ {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, -+ // Similar restrictions for the downloads directory. -+ {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, -+ BlockType::kDontBlockChildren}, -+ {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, -+ BlockType::kDontBlockChildren}, -+ // The Chrome installation itself should not be modified by the web. -+ {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, -+ // And neither should the configuration of at least the currently -+ // running -+ // Chrome instance (note that this does not take --user-data-dir -+ // command -+ // line overrides into account). -+ {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, -+ // ~/.ssh is pretty sensitive on all platforms, so block access to -+ // that. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), -+ BlockType::kBlockAllChildren}, -+ // And limit access to ~/.gnupg as well. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), -+ BlockType::kBlockAllChildren}, ++ static std::vector ++ GenerateBlockedPath() { ++ return { ++ // Don't allow users to share their entire home directory, entire desktop ++ // or entire documents folder, but do allow sharing anything inside those ++ // directories not otherwise blocked. ++ {base::DIR_HOME, nullptr, BlockType::kDontBlockChildren}, ++ {base::DIR_USER_DESKTOP, nullptr, BlockType::kDontBlockChildren}, ++ {chrome::DIR_USER_DOCUMENTS, nullptr, BlockType::kDontBlockChildren}, ++ // Similar restrictions for the downloads directory. ++ {chrome::DIR_DEFAULT_DOWNLOADS, nullptr, BlockType::kDontBlockChildren}, ++ {chrome::DIR_DEFAULT_DOWNLOADS_SAFE, nullptr, ++ BlockType::kDontBlockChildren}, ++ // The Chrome installation itself should not be modified by the web. ++ {base::DIR_EXE, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_MODULE, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_ASSETS, nullptr, BlockType::kBlockAllChildren}, ++ // And neither should the configuration of at least the currently running ++ // Chrome instance (note that this does not take --user-data-dir command ++ // line overrides into account). ++ {chrome::DIR_USER_DATA, nullptr, BlockType::kBlockAllChildren}, ++ // ~/.ssh is pretty sensitive on all platforms, so block access to that. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".ssh"), BlockType::kBlockAllChildren}, ++ // And limit access to ~/.gnupg as well. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".gnupg"), ++ BlockType::kBlockAllChildren}, + #if BUILDFLAG(IS_WIN) -+ // Some Windows specific directories to block, basically all apps, the -+ // operating system itself, as well as configuration data for apps. -+ {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ // Opening a file from an MTP device, such as a smartphone or a -+ // camera, is -+ // implemented by Windows as opening a file in the temporary internet -+ // files directory. To support that, allow opening files in that -+ // directory, but not whole directories. -+ {base::DIR_IE_INTERNET_CACHE, nullptr, -+ BlockType::kBlockNestedDirectories}, ++ // Some Windows specific directories to block, basically all apps, the ++ // operating system itself, as well as configuration data for apps. ++ {base::DIR_PROGRAM_FILES, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_PROGRAM_FILESX86, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_PROGRAM_FILES6432, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_WINDOWS, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_ROAMING_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_LOCAL_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_COMMON_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ // Opening a file from an MTP device, such as a smartphone or a camera, is ++ // implemented by Windows as opening a file in the temporary internet ++ // files directory. To support that, allow opening files in that ++ // directory, but not whole directories. ++ {base::DIR_IE_INTERNET_CACHE, nullptr, ++ BlockType::kBlockNestedDirectories}, + #endif + #if BUILDFLAG(IS_MAC) -+ // Similar Mac specific blocks. -+ {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ // Block access to the current bundle directory. -+ {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, -+ // Block access to the user's Applications directory. -+ {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), -+ BlockType::kBlockAllChildren}, -+ // Block access to the root Applications directory. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), -+ BlockType::kBlockAllChildren}, -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library"), -+ BlockType::kBlockAllChildren}, -+ // Allow access to other cloud files, such as Google Drive. -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), -+ BlockType::kDontBlockChildren}, -+ // Allow the site to interact with data from its corresponding -+ // natively -+ // installed (sandboxed) application. It would be nice to limit a site -+ // to -+ // access only _its_ corresponding natively installed application, but -+ // unfortunately there's no straightforward way to do that. See -+ // https://crbug.com/984641#c22. -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), -+ BlockType::kDontBlockChildren}, -+ // Allow access to iCloud files... -+ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), -+ BlockType::kDontBlockChildren}, -+ // ... which may also appear at this directory. -+ {base::DIR_HOME, -+ FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), -+ BlockType::kDontBlockChildren}, ++ // Similar Mac specific blocks. ++ {base::DIR_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ // Block access to the current bundle directory. ++ {chrome::DIR_OUTER_BUNDLE, nullptr, BlockType::kBlockAllChildren}, ++ // Block access to the user's Applications directory. ++ {base::DIR_HOME, FILE_PATH_LITERAL("Applications"), ++ BlockType::kBlockAllChildren}, ++ // Block access to the root Applications directory. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/Applications"), ++ BlockType::kBlockAllChildren}, ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library"), ++ BlockType::kBlockAllChildren}, ++ // Allow access to other cloud files, such as Google Drive. ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library/CloudStorage"), ++ BlockType::kDontBlockChildren}, ++ // Allow the site to interact with data from its corresponding natively ++ // installed (sandboxed) application. It would be nice to limit a site to ++ // access only _its_ corresponding natively installed application, but ++ // unfortunately there's no straightforward way to do that. See ++ // https://crbug.com/984641#c22. ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Containers"), ++ BlockType::kDontBlockChildren}, ++ // Allow access to iCloud files... ++ {base::DIR_HOME, FILE_PATH_LITERAL("Library/Mobile Documents"), ++ BlockType::kDontBlockChildren}, ++ // ... which may also appear at this directory. ++ {base::DIR_HOME, ++ FILE_PATH_LITERAL("Library/Mobile Documents/com~apple~CloudDocs"), ++ BlockType::kDontBlockChildren}, + #endif + #if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_ANDROID) -+ // On Linux also block access to devices via /dev. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), -+ BlockType::kBlockAllChildren}, -+ // And security sensitive data in /proc and /sys. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), -+ BlockType::kBlockAllChildren}, -+ {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), -+ BlockType::kBlockAllChildren}, -+ // And system files in /boot and /etc. -+ {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), -+ BlockType::kBlockAllChildren}, -+ {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), -+ BlockType::kBlockAllChildren}, -+ // And block all of ~/.config, matching the similar restrictions on -+ // mac -+ // and windows. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".config"), -+ BlockType::kBlockAllChildren}, -+ // Block ~/.dbus as well, just in case, although there probably isn't -+ // much -+ // a website can do with access to that directory and its contents. -+ {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), -+ BlockType::kBlockAllChildren}, ++ // On Linux also block access to devices via /dev. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/dev"), BlockType::kBlockAllChildren}, ++ // And security sensitive data in /proc and /sys. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/proc"), ++ BlockType::kBlockAllChildren}, ++ {kNoBasePathKey, FILE_PATH_LITERAL("/sys"), BlockType::kBlockAllChildren}, ++ // And system files in /boot and /etc. ++ {kNoBasePathKey, FILE_PATH_LITERAL("/boot"), ++ BlockType::kBlockAllChildren}, ++ {kNoBasePathKey, FILE_PATH_LITERAL("/etc"), BlockType::kBlockAllChildren}, ++ // And block all of ~/.config, matching the similar restrictions on mac ++ // and windows. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".config"), ++ BlockType::kBlockAllChildren}, ++ // Block ~/.dbus as well, just in case, although there probably isn't much ++ // a website can do with access to that directory and its contents. ++ {base::DIR_HOME, FILE_PATH_LITERAL(".dbus"), ++ BlockType::kBlockAllChildren}, + #endif + #if BUILDFLAG(IS_ANDROID) -+ {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, -+ {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_ANDROID_APP_DATA, nullptr, BlockType::kBlockAllChildren}, ++ {base::DIR_CACHE, nullptr, BlockType::kBlockAllChildren}, + #endif -+ // TODO(crbug.com/40095723): Refine this list, for example add -+ // XDG_CONFIG_HOME when it is not set ~/.config? -+ }; -+ -+ // ChromeOS supports multi-user sign-in. base::DIR_HOME only returns the -+ // profile path for the primary user, the first user to sign in. We want to -+ // use the `profile_path` instead since that's associated with user that -+ // initiated this blocklist check. -+ // -+ // TODO(crbug.com/375490221): Improve the ChromeOS blocklist logic. -+ constexpr bool kUseProfilePathForDirHome = BUILDFLAG(IS_CHROMEOS); -+ // Populate the hard-coded rules. -+ auto block_path_rules = std::make_unique< -+ ChromeFileSystemAccessPermissionContext::BlockPathRules>(); -+ -+ for (const auto& blocked_path : kBlockPaths) { -+ base::FilePath path; -+ if (blocked_path.base_path_key != kNoBasePathKey) { -+ if (kUseProfilePathForDirHome && -+ blocked_path.base_path_key == base::DIR_HOME) { -+ block_path_rules->profile_based_block_path_rules_.emplace_back( -+ blocked_path.path, blocked_path.type); -+ continue; -+ } -+ -+ if (!base::PathService::Get(blocked_path.base_path_key, &path)) { -+ continue; -+ } ++ // TODO(crbug.com/40095723): Refine this list, for example add ++ // XDG_CONFIG_HOME when it is not set ~/.config? ++ }; ++ } + -+ if (blocked_path.path) { -+ path = path.Append(blocked_path.path); -+ } -+ } else { -+ DCHECK(blocked_path.path); -+ path = base::FilePath(blocked_path.path); -+ } -+ block_path_rules->block_path_rules_.emplace_back( -+ should_normalize_file_path ? NormalizeFilePath(path) : path, -+ blocked_path.type); ++ // A wrapper around `base::NormalizeFilePath` that returns its result instead of ++ // using an out parameter. ++ base::FilePath NormalizeFilePath(const base::FilePath& path) { ++ CHECK(path.IsAbsolute()); ++ // TODO(crbug.com/368130513O): On Windows, this call will fail if the target ++ // file path is greater than MAX_PATH. We should decide how to handle this ++ // scenario. ++ base::FilePath normalized_path; ++ if (!base::NormalizeFilePath(path, &normalized_path)) { ++ return path; + } -+ -+ return block_path_rules; ++ CHECK_EQ(path.empty(), normalized_path.empty()); ++ return normalized_path; + } + protected: SEQUENCE_CHECKER(sequence_checker_); +@@ -390,7 +517,7 @@ class ChromeFileSystemAccessPermissionContext + + void PermissionGrantDestroyed(PermissionGrantImpl* grant); + +-#if BUILDFLAG(ENTERPRISE_CLOUD_CONTENT_ANALYSIS) ++#if 0 + void OnContentAnalysisComplete( + std::vector entries, + EntriesAllowedByEnterprisePolicyCallback callback, diff --git a/shell/browser/file_system_access/file_system_access_permission_context.cc b/shell/browser/file_system_access/file_system_access_permission_context.cc index 383d9a5b67898..1fb8c1d4a57aa 100644 --- a/shell/browser/file_system_access/file_system_access_permission_context.cc +++ b/shell/browser/file_system_access/file_system_access_permission_context.cc @@ -10,7 +10,6 @@ #include "base/base_paths.h" #include "base/files/file_path.h" -#include "base/files/file_util.h" #include "base/json/values_util.h" #include "base/path_service.h" #include "base/task/bind_post_task.h" @@ -40,16 +39,6 @@ #include "ui/base/l10n/l10n_util.h" #include "url/origin.h" -ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules() = - default; -ChromeFileSystemAccessPermissionContext::BlockPathRules::~BlockPathRules() = - default; -ChromeFileSystemAccessPermissionContext::BlockPathRules::BlockPathRules( - const BlockPathRules& other) = default; -ChromeFileSystemAccessPermissionContext::BlockPathRules& -ChromeFileSystemAccessPermissionContext::BlockPathRules::operator=( - const BlockPathRules& other) = default; - namespace gin { template <> @@ -152,53 +141,51 @@ bool MaybeIsLocalUNCPath(const base::FilePath& path) { } #endif // BUILDFLAG(IS_WIN) -bool ShouldBlockAccessToPath( - base::FilePath path, - HandleType handle_type, - std::vector - extra_rules, - ChromeFileSystemAccessPermissionContext::BlockPathRules block_path_rules) { +// Describes a rule for blocking a directory, which can be constructed +// dynamically (based on state) or statically (from kBlockedPaths). +struct BlockPathRule { + base::FilePath path; + BlockType type; +}; + +bool ShouldBlockAccessToPath(const base::FilePath& path, + HandleType handle_type, + std::vector rules) { DCHECK(!path.empty()); DCHECK(path.IsAbsolute()); - path = ChromeFileSystemAccessPermissionContext::NormalizeFilePath(path); - for (auto& rule : extra_rules) { - rule.path = - ChromeFileSystemAccessPermissionContext::NormalizeFilePath(rule.path); - } - #if BUILDFLAG(IS_WIN) // On Windows, local UNC paths are rejected, as UNC path can be written in a // way that can bypass the blocklist. - if (MaybeIsLocalUNCPath(path)) { + if (MaybeIsLocalUNCPath(path)) return true; +#endif // BUILDFLAG(IS_WIN) + + // Add the hard-coded rules to the dynamic rules. + for (auto const& [key, rule_path, type] : + ChromeFileSystemAccessPermissionContext::GenerateBlockedPath()) { + if (key == ChromeFileSystemAccessPermissionContext::kNoBasePathKey) { + rules.emplace_back(base::FilePath{rule_path}, type); + } else if (base::FilePath block_path; + base::PathService::Get(key, &block_path)) { + rules.emplace_back(rule_path ? block_path.Append(rule_path) : block_path, + type); + } } -#endif base::FilePath nearest_ancestor; BlockType nearest_ancestor_block_type = BlockType::kDontBlockChildren; - auto should_block_with_rule = [&](const base::FilePath& block_path, - BlockType block_type) -> bool { - if (path == block_path || path.IsParent(block_path)) { - VLOG(1) << "Blocking access to " << path << " because it is a parent of " - << block_path; + for (const auto& block : rules) { + if (path == block.path || path.IsParent(block.path)) { + DLOG(INFO) << "Blocking access to " << path + << " because it is a parent of " << block.path; return true; } - if (block_path.IsParent(path) && - (nearest_ancestor.empty() || nearest_ancestor.IsParent(block_path))) { - nearest_ancestor = block_path; - nearest_ancestor_block_type = block_type; - } - return false; - }; - - for (const auto* block_rules_ptr : - {&extra_rules, &block_path_rules.block_path_rules_}) { - for (const auto& block : *block_rules_ptr) { - if (should_block_with_rule(block.path, block.type)) { - return true; - } + if (block.path.IsParent(path) && + (nearest_ancestor.empty() || nearest_ancestor.IsParent(block.path))) { + nearest_ancestor = block.path; + nearest_ancestor_block_type = block.type; } } @@ -206,8 +193,6 @@ bool ShouldBlockAccessToPath( // nearest ancestor does not block access to its children. Grant access. if (nearest_ancestor.empty() || nearest_ancestor_block_type == BlockType::kDontBlockChildren) { - VLOG(1) << "Not blocking access to " << path << " because it is inside " - << nearest_ancestor << " and it's kDontBlockChildren"; return false; } @@ -215,14 +200,12 @@ bool ShouldBlockAccessToPath( // access to directories. Grant access. if (handle_type == HandleType::kFile && nearest_ancestor_block_type == BlockType::kBlockNestedDirectories) { - VLOG(1) << "Not blocking access to " << path << " because it is inside " - << nearest_ancestor << " and it's kBlockNestedDirectories"; return false; } // The nearest ancestor blocks access to its children, so block access. - VLOG(1) << "Blocking access to " << path << " because it is inside " - << nearest_ancestor << " and it's kBlockAllChildren"; + DLOG(INFO) << "Blocking access to " << path << " because it is inside " + << nearest_ancestor; return true; } @@ -463,30 +446,11 @@ FileSystemAccessPermissionContext::FileSystemAccessPermissionContext( const base::Clock* clock) : browser_context_(browser_context), clock_(clock) { DETACH_FROM_SEQUENCE(sequence_checker_); - ResetBlockPaths(); } FileSystemAccessPermissionContext::~FileSystemAccessPermissionContext() = default; -void FileSystemAccessPermissionContext::ResetBlockPaths() { - is_block_path_rules_init_complete_ = false; - base::ThreadPool::PostTaskAndReplyWithResult( - FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE}, - base::BindOnce( - &ChromeFileSystemAccessPermissionContext::GenerateBlockPaths, true), - base::BindOnce(&FileSystemAccessPermissionContext::UpdateBlockPaths, - weak_factory_.GetWeakPtr())); -} - -void FileSystemAccessPermissionContext::UpdateBlockPaths( - std::unique_ptr - block_path_rules) { - block_path_rules_ = std::move(block_path_rules); - is_block_path_rules_init_complete_ = true; - block_rules_check_callbacks_.Notify(*block_path_rules_.get()); -} - scoped_refptr FileSystemAccessPermissionContext::GetReadPermissionGrant( const url::Origin& origin, @@ -640,26 +604,12 @@ void FileSystemAccessPermissionContext::ConfirmSensitiveEntryAccess( std::move(after_blocklist_check_callback)); } -void FileSystemAccessPermissionContext::CheckShouldBlockAccessToPathAndReply( - base::FilePath path, - HandleType handle_type, - std::vector - extra_rules, - base::OnceCallback callback, - ChromeFileSystemAccessPermissionContext::BlockPathRules block_path_rules) { - base::ThreadPool::PostTaskAndReplyWithResult( - FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE}, - base::BindOnce(&ShouldBlockAccessToPath, path, handle_type, extra_rules, - block_path_rules), - std::move(callback)); -} - void FileSystemAccessPermissionContext::CheckPathAgainstBlocklist( const content::PathInfo& path_info, HandleType handle_type, base::OnceCallback callback) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - // TODO(crbug.com/40101272): Figure out what external paths should be + // TODO(https://crbug.com/1009970): Figure out what external paths should be // blocked. We could resolve the external path to a local path, and check for // blocked directories based on that, but that doesn't work well. Instead we // should have a separate Chrome OS only code path to block for example the @@ -669,27 +619,15 @@ void FileSystemAccessPermissionContext::CheckPathAgainstBlocklist( return; } - // Unlike the DIR_USER_DATA check, this handles the --user-data-dir override. - // We check for the user data dir in two different ways: directly, via the - // profile manager, where it exists (it does not in unit tests), and via the - // profile's directory, assuming the profile dir is a child of the user data - // dir. - std::vector - extra_rules; - if (is_block_path_rules_init_complete_) { - // The rules initialization is completed, we can just post the task to a - // anonymous blocking traits. - CheckShouldBlockAccessToPathAndReply(path_info.path, handle_type, - extra_rules, std::move(callback), - *block_path_rules_.get()); - return; - } - // The check must be performed after the rules initialization is done. - block_rules_check_subscription_.push_back(block_rules_check_callbacks_.Add( - base::BindOnce(&FileSystemAccessPermissionContext:: - CheckShouldBlockAccessToPathAndReply, - weak_factory_.GetWeakPtr(), path_info.path, handle_type, - extra_rules, std::move(callback)))); + std::vector extra_rules; + extra_rules.emplace_back(browser_context_->GetPath().DirName(), + BlockType::kBlockAllChildren); + + base::ThreadPool::PostTaskAndReplyWithResult( + FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE}, + base::BindOnce(&ShouldBlockAccessToPath, path_info.path, handle_type, + extra_rules), + std::move(callback)); } void FileSystemAccessPermissionContext::PerformAfterWriteChecks( diff --git a/shell/browser/file_system_access/file_system_access_permission_context.h b/shell/browser/file_system_access/file_system_access_permission_context.h index 591c1288e2dda..18d55ad477100 100644 --- a/shell/browser/file_system_access/file_system_access_permission_context.h +++ b/shell/browser/file_system_access/file_system_access_permission_context.h @@ -12,14 +12,13 @@ #include #include -#include "base/callback_list.h" #include "base/functional/callback_forward.h" #include "base/memory/weak_ptr.h" #include "base/time/clock.h" #include "base/time/default_clock.h" #include "base/values.h" -#include "chrome/browser/file_system_access/chrome_file_system_access_permission_context.h" // nogncheck #include "components/keyed_service/core/keyed_service.h" +#include "content/public/browser/file_system_access_permission_context.h" class GURL; @@ -136,14 +135,6 @@ class FileSystemAccessPermissionContext void PermissionGrantDestroyed(PermissionGrantImpl* grant); - void CheckShouldBlockAccessToPathAndReply( - base::FilePath path, - HandleType handle_type, - std::vector - extra_rules, - base::OnceCallback callback, - ChromeFileSystemAccessPermissionContext::BlockPathRules block_path_rules); - void CheckPathAgainstBlocklist(const content::PathInfo& path, HandleType handle_type, base::OnceCallback callback); @@ -168,11 +159,6 @@ class FileSystemAccessPermissionContext const base::FilePath& path, GrantType grant_type) const; - void ResetBlockPaths(); - void UpdateBlockPaths( - std::unique_ptr - block_path_rules); - base::WeakPtr GetWeakPtr(); const raw_ptr browser_context_; @@ -190,14 +176,6 @@ class FileSystemAccessPermissionContext std::map> callback_map_; - std::unique_ptr - block_path_rules_; - bool is_block_path_rules_init_complete_ = false; - std::vector block_rules_check_subscription_; - base::OnceCallbackList - block_rules_check_callbacks_; - base::WeakPtrFactory weak_factory_{this}; }; From 841a770c6ccfc8ddb4b380c086c14629c14c58e4 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 3 Jul 2025 14:41:59 +0200 Subject: [PATCH 133/186] build: update yarn to 1.22.22 (#47638) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Samuel Attard --- DEPS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DEPS b/DEPS index efc27b9309385..b4fd1eb8ba5be 100644 --- a/DEPS +++ b/DEPS @@ -31,7 +31,7 @@ vars = { 'sysroots_json_path': 'electron/script/sysroots.json', # KEEP IN SYNC WITH utils.js FILE - 'yarn_version': '1.15.2', + 'yarn_version': '1.22.22', # To be able to build clean Chromium from sources. 'apply_patches': True, From 90a0f81302d3e6a84365462af7ab2d8605f8e917 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 3 Jul 2025 19:19:22 +0200 Subject: [PATCH 134/186] fix: crash on source capture with empty thumbnail size (#47653) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/api/electron_api_desktop_capturer.cc | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/shell/browser/api/electron_api_desktop_capturer.cc b/shell/browser/api/electron_api_desktop_capturer.cc index d0b3f40b5dcc0..a5453ff8cd0f5 100644 --- a/shell/browser/api/electron_api_desktop_capturer.cc +++ b/shell/browser/api/electron_api_desktop_capturer.cc @@ -233,7 +233,8 @@ DesktopCapturer::DesktopListListener::~DesktopListListener() = default; void DesktopCapturer::DesktopListListener::OnDelegatedSourceListSelection() { if (have_thumbnail_) { - std::move(update_callback_).Run(); + content::GetUIThreadTaskRunner({})->PostTask(FROM_HERE, + std::move(update_callback_)); } else { have_selection_ = true; } @@ -246,7 +247,8 @@ void DesktopCapturer::DesktopListListener::OnSourceThumbnailChanged(int index) { have_selection_ = false; // PipeWire returns a single source, so index is not relevant. - std::move(update_callback_).Run(); + content::GetUIThreadTaskRunner({})->PostTask(FROM_HERE, + std::move(update_callback_)); } else { have_thumbnail_ = true; } From 549c73a8b470811d740f2f2580d201b80210b166 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 3 Jul 2025 22:19:26 +0200 Subject: [PATCH 135/186] fix: accent color should reflect system settings without restart (#47656) fix: accentColor should reflect system settings without restart Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/native_window_views.h | 2 +- shell/browser/native_window_views_win.cc | 44 ++++++++++++++++-------- 2 files changed, 30 insertions(+), 16 deletions(-) diff --git a/shell/browser/native_window_views.h b/shell/browser/native_window_views.h index 5554b8676e166..fb66b981ce474 100644 --- a/shell/browser/native_window_views.h +++ b/shell/browser/native_window_views.h @@ -306,7 +306,7 @@ class NativeWindowViews : public NativeWindow, // Whether the window is currently being moved. bool is_moving_ = false; - std::variant accent_color_ = true; + std::variant accent_color_; std::optional pending_bounds_change_; diff --git a/shell/browser/native_window_views_win.cc b/shell/browser/native_window_views_win.cc index 8a2876d4f69b4..c7f3456f2f208 100644 --- a/shell/browser/native_window_views_win.cc +++ b/shell/browser/native_window_views_win.cc @@ -574,28 +574,42 @@ void NativeWindowViews::UpdateWindowAccentColor() { if (base::win::GetVersion() < base::win::Version::WIN11) return; - if (!IsAccentColorOnTitleBarsEnabled()) - return; - COLORREF border_color; - if (std::holds_alternative(accent_color_)) { - // Don't set accent color if the user has disabled it. - if (!std::get(accent_color_)) - return; + bool should_apply_accent = false; - std::optional accent_color = GetAccentColor(); - if (!accent_color.has_value()) - return; - - border_color = - RGB(GetRValue(accent_color.value()), GetGValue(accent_color.value()), - GetBValue(accent_color.value())); - } else { + if (std::holds_alternative(accent_color_)) { + bool force_accent = std::get(accent_color_); + if (!force_accent) { + should_apply_accent = false; + } else { + std::optional accent_color = GetAccentColor(); + if (accent_color.has_value()) { + border_color = RGB(GetRValue(accent_color.value()), + GetGValue(accent_color.value()), + GetBValue(accent_color.value())); + should_apply_accent = true; + } + } + } else if (std::holds_alternative(accent_color_)) { SkColor color = std::get(accent_color_); border_color = RGB(SkColorGetR(color), SkColorGetG(color), SkColorGetB(color)); + should_apply_accent = true; + } else if (std::holds_alternative(accent_color_)) { + if (IsAccentColorOnTitleBarsEnabled()) { + std::optional accent_color = GetAccentColor(); + if (accent_color.has_value()) { + border_color = RGB(GetRValue(accent_color.value()), + GetGValue(accent_color.value()), + GetBValue(accent_color.value())); + should_apply_accent = true; + } + } } + // Reset to default system colors when accent color should not be applied. + if (!should_apply_accent) + border_color = DWMWA_COLOR_DEFAULT; SetWindowBorderAndCaptionColor(GetAcceleratedWidget(), border_color); } From f4e709c47e72c8dc89ec137b628e5924ee36ba30 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 4 Jul 2025 10:58:45 +0200 Subject: [PATCH 136/186] refactor: avoid a few unnecessary strings (#47654) * perf: replace string temporary with string_view in GetXdgAppId() Co-authored-by: Charles Kerr * perf: replace string temporary with string_view in ToV8(WindowOpenDisposition) Co-authored-by: Charles Kerr * perf: replace string temporary with string_view in ToV8(electron::api::WebContents::Type) Co-authored-by: Charles Kerr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Charles Kerr --- shell/browser/api/electron_api_web_contents.cc | 4 ++-- shell/common/platform_util_linux.cc | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index d25171ea116ff..e062b7a1aff80 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -242,7 +242,7 @@ template <> struct Converter { static v8::Local ToV8(v8::Isolate* isolate, WindowOpenDisposition val) { - std::string disposition = "other"; + std::string_view disposition = "other"; switch (val) { case WindowOpenDisposition::CURRENT_TAB: disposition = "default"; @@ -303,7 +303,7 @@ struct Converter { static v8::Local ToV8(v8::Isolate* isolate, electron::api::WebContents::Type val) { using Type = electron::api::WebContents::Type; - std::string type; + std::string_view type; switch (val) { case Type::kBackgroundPage: type = "backgroundPage"; diff --git a/shell/common/platform_util_linux.cc b/shell/common/platform_util_linux.cc index dea72f7a370b5..87c3d6fbda339 100644 --- a/shell/common/platform_util_linux.cc +++ b/shell/common/platform_util_linux.cc @@ -430,7 +430,7 @@ std::optional GetDesktopName() { std::string GetXdgAppId() { if (std::optional desktop_file_name = GetDesktopName()) { - const std::string kDesktopExtension{".desktop"}; + constexpr std::string_view kDesktopExtension = ".desktop"; if (base::EndsWith(*desktop_file_name, kDesktopExtension, base::CompareCase::INSENSITIVE_ASCII)) { desktop_file_name->resize(desktop_file_name->size() - From 6e9a46042da30cbec7ec8f961e3030b5e047ebce Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 8 Jul 2025 15:22:52 +0200 Subject: [PATCH 137/186] fix: fullscreen for windows without rounded corners (#47682) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/native_window_mac.h | 2 + shell/browser/native_window_mac.mm | 17 ++++--- shell/browser/ui/cocoa/electron_ns_window.mm | 3 -- .../ui/cocoa/electron_ns_window_delegate.h | 2 + .../ui/cocoa/electron_ns_window_delegate.mm | 5 ++ spec/api-browser-window-spec.ts | 48 +++++++++++++++++++ 6 files changed, 67 insertions(+), 10 deletions(-) diff --git a/shell/browser/native_window_mac.h b/shell/browser/native_window_mac.h index 5420e14aecd7d..9eb4df3c22d7c 100644 --- a/shell/browser/native_window_mac.h +++ b/shell/browser/native_window_mac.h @@ -175,6 +175,8 @@ class NativeWindowMac : public NativeWindow, // cleanup in destructor. void Cleanup(); + void SetBorderless(bool borderless); + void UpdateVibrancyRadii(bool fullscreen); void UpdateWindowOriginalFrame(); diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 9278ece8ea14b..4e3c14b399eb3 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -158,13 +158,6 @@ static bool FromV8(v8::Isolate* isolate, NSUInteger styleMask = NSWindowStyleMaskTitled; - // The NSWindowStyleMaskFullSizeContentView style removes rounded corners - // for frameless window. - const bool rounded_corner = - options.ValueOrDefault(options::kRoundedCorners, true); - if (!rounded_corner && !has_frame()) - styleMask = NSWindowStyleMaskBorderless; - if (minimizable) styleMask |= NSWindowStyleMaskMiniaturizable; if (closable) @@ -224,6 +217,11 @@ static bool FromV8(v8::Isolate* isolate, SetParentWindow(parent); } + const bool rounded_corner = + options.ValueOrDefault(options::kRoundedCorners, true); + if (!rounded_corner && !has_frame()) + SetBorderless(!rounded_corner); + if (transparent()) { // Setting the background color to clear will also hide the shadow. [window_ setBackgroundColor:[NSColor clearColor]]; @@ -775,6 +773,11 @@ static bool FromV8(v8::Isolate* isolate, [window_ orderWindowByShuffling:NSWindowAbove relativeTo:0]; } +void NativeWindowMac::SetBorderless(bool borderless) { + SetStyleMask(!borderless, NSWindowStyleMaskTitled); + SetStyleMask(borderless, NSWindowStyleMaskBorderless); +} + void NativeWindowMac::SetResizable(bool resizable) { ScopedDisableResize disable_resize; SetStyleMask(resizable, NSWindowStyleMaskResizable); diff --git a/shell/browser/ui/cocoa/electron_ns_window.mm b/shell/browser/ui/cocoa/electron_ns_window.mm index cf9d479b93fc5..3d5daec5df2d2 100644 --- a/shell/browser/ui/cocoa/electron_ns_window.mm +++ b/shell/browser/ui/cocoa/electron_ns_window.mm @@ -375,9 +375,6 @@ - (void)performClose:(id)sender { } - (BOOL)toggleFullScreenMode:(id)sender { - if (!shell_->has_frame() && !shell_->HasStyleMask(NSWindowStyleMaskTitled)) - return NO; - bool is_simple_fs = shell_->IsSimpleFullScreen(); bool always_simple_fs = shell_->always_simple_fullscreen(); diff --git a/shell/browser/ui/cocoa/electron_ns_window_delegate.h b/shell/browser/ui/cocoa/electron_ns_window_delegate.h index f65d78a095d1b..1035f9e049e60 100644 --- a/shell/browser/ui/cocoa/electron_ns_window_delegate.h +++ b/shell/browser/ui/cocoa/electron_ns_window_delegate.h @@ -24,6 +24,8 @@ class NativeWindowMac; int level_; bool is_resizable_; + bool is_borderless_; + // Whether the window is currently minimized. Used to work // around a macOS bug with child window minimization. bool is_minimized_; diff --git a/shell/browser/ui/cocoa/electron_ns_window_delegate.mm b/shell/browser/ui/cocoa/electron_ns_window_delegate.mm index d2a64514f12e3..df7b7b66eadb4 100644 --- a/shell/browser/ui/cocoa/electron_ns_window_delegate.mm +++ b/shell/browser/ui/cocoa/electron_ns_window_delegate.mm @@ -299,6 +299,8 @@ - (void)windowDidEndLiveResize:(NSNotification*)notification { - (void)windowWillEnterFullScreen:(NSNotification*)notification { // Store resizable mask so it can be restored after exiting fullscreen. is_resizable_ = shell_->HasStyleMask(NSWindowStyleMaskResizable); + // Store borderless mask so it can be restored after exiting fullscreen. + is_borderless_ = !shell_->HasStyleMask(NSWindowStyleMaskTitled); shell_->set_is_transitioning_fullscreen(true); @@ -306,6 +308,8 @@ - (void)windowWillEnterFullScreen:(NSNotification*)notification { // Set resizable to true before entering fullscreen. shell_->SetResizable(true); + // Set borderless to false before entering fullscreen. + shell_->SetBorderless(false); } - (void)windowDidEnterFullScreen:(NSNotification*)notification { @@ -341,6 +345,7 @@ - (void)windowDidExitFullScreen:(NSNotification*)notification { shell_->set_is_transitioning_fullscreen(false); shell_->SetResizable(is_resizable_); + shell_->SetBorderless(is_borderless_); shell_->NotifyWindowLeaveFullScreen(); if (shell_->HandleDeferredClose()) diff --git a/spec/api-browser-window-spec.ts b/spec/api-browser-window-spec.ts index a54992049afda..71b62eeb77faa 100755 --- a/spec/api-browser-window-spec.ts +++ b/spec/api-browser-window-spec.ts @@ -5993,6 +5993,54 @@ describe('BrowserWindow module', () => { await leaveFullScreen; }); + it('should not crash if rounded corners are disabled', async () => { + const w = new BrowserWindow({ + frame: false, + roundedCorners: false + }); + + const enterFullScreen = once(w, 'enter-full-screen'); + w.setFullScreen(true); + await enterFullScreen; + + await setTimeout(); + + const leaveFullScreen = once(w, 'leave-full-screen'); + w.setFullScreen(false); + await leaveFullScreen; + }); + + it('should not crash if opening a borderless child window from fullscreen parent', async () => { + const parent = new BrowserWindow(); + + const parentFS = once(parent, 'enter-full-screen'); + parent.setFullScreen(true); + await parentFS; + + await setTimeout(); + + const child = new BrowserWindow({ + width: 400, + height: 300, + show: false, + parent, + frame: false, + roundedCorners: false + }); + + await setTimeout(); + + const childFS = once(child, 'enter-full-screen'); + child.show(); + await childFS; + + await setTimeout(); + + const leaveFullScreen = once(child, 'leave-full-screen'); + child.setFullScreen(false); + await leaveFullScreen; + }); + it('should be able to load a URL while transitioning to fullscreen', async () => { const w = new BrowserWindow({ fullscreen: true }); w.loadFile(path.join(fixtures, 'pages', 'c.html')); From 93d70103aa5e0f775ef70559d62ae5f5cab6aed3 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 9 Jul 2025 12:31:48 +0200 Subject: [PATCH 138/186] docs: update build prerequisites (#47698) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- docs/development/build-instructions-linux.md | 7 ++----- docs/development/build-instructions-macos.md | 4 ++-- docs/development/build-instructions-windows.md | 2 +- 3 files changed, 5 insertions(+), 8 deletions(-) diff --git a/docs/development/build-instructions-linux.md b/docs/development/build-instructions-linux.md index 8bfd6349a511a..07cd2c49d091a 100644 --- a/docs/development/build-instructions-linux.md +++ b/docs/development/build-instructions-linux.md @@ -7,11 +7,8 @@ Follow the guidelines below for building **Electron itself** on Linux, for the p ## Prerequisites * At least 25GB disk space and 8GB RAM. -* Python >= 3.7. -* Node.js. There are various ways to install Node. You can download - source code from [nodejs.org](https://nodejs.org) and compile it. - Doing so permits installing Node on your own home directory as a standard user. - Or try repositories such as [NodeSource](https://nodesource.com/blog/nodejs-v012-iojs-and-the-nodesource-linux-repositories). +* Python >= 3.9. +* [Node.js](https://nodejs.org/download/) >= 22.12.0 * [clang](https://clang.llvm.org/get_started.html) 3.4 or later. * Development headers of GTK 3 and libnotify. diff --git a/docs/development/build-instructions-macos.md b/docs/development/build-instructions-macos.md index 8ab4670d1971c..cc3ab4fc8a7dc 100644 --- a/docs/development/build-instructions-macos.md +++ b/docs/development/build-instructions-macos.md @@ -10,8 +10,8 @@ Follow the guidelines below for building **Electron itself** on macOS, for the p * [Xcode](https://developer.apple.com/technologies/tools/). The exact version needed depends on what branch you are building, but the latest version of Xcode is generally a good bet for building `main`. -* [node.js](https://nodejs.org) (external) -* Python >= 3.7 +* Python >= 3.9 +* [Node.js](https://nodejs.org/download/) >= 22.12.0 ### Arm64-specific prerequisites diff --git a/docs/development/build-instructions-windows.md b/docs/development/build-instructions-windows.md index 0d1a079c5d705..3ff011c45e04e 100644 --- a/docs/development/build-instructions-windows.md +++ b/docs/development/build-instructions-windows.md @@ -14,7 +14,7 @@ Follow the guidelines below for building **Electron itself** on Windows, for the set a few environment variables to point the toolchains to your installation path. * `vs2022_install = DRIVE:\path\to\Microsoft Visual Studio\2022\Community`, replacing `2022` and `Community` with your installed versions and replacing `DRIVE:` with the drive that Visual Studio is on. Often, this will be `C:`. * `WINDOWSSDKDIR = DRIVE:\path\to\Windows Kits\10`, replacing `DRIVE:` with the drive that Windows Kits is on. Often, this will be `C:`. -* [Node.js](https://nodejs.org/download/) +* [Node.js](https://nodejs.org/download/) >= 22.12.0 * [Git](https://git-scm.com) * Debugging Tools for Windows of Windows SDK 10.0.15063.468 if you plan on creating a full distribution since `symstore.exe` is used for creating a symbol From e93c4a34190ece56a9f94021ffe6b7adef99023a Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Fri, 11 Jul 2025 10:39:48 +0200 Subject: [PATCH 139/186] chore: bump chromium to 138.0.7204.100 (37-x-y) (#47701) chore: bump chromium in DEPS to 138.0.7204.100 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> --- DEPS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DEPS b/DEPS index b4fd1eb8ba5be..75b990c16b8c1 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.97', + '138.0.7204.100', 'node_version': 'v22.17.0', 'nan_version': From 6e1650af1284ff0113c0153d7aeaa703ae5fa469 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sat, 12 Jul 2025 09:52:21 +0200 Subject: [PATCH 140/186] build: cleanup symlinks in cache (#47731) * build: cleanup symlinks in cache Co-authored-by: John Kleinschmidt * build: ignore broken links Co-authored-by: John Kleinschmidt * try --ignore-failed-read Co-authored-by: John Kleinschmidt * build: dont deref symlinks Co-authored-by: John Kleinschmidt * build: add flag to 7zip to resolve symlink error Needed to ignore Dangerous symbolic link path was ignored errors Co-authored-by: John Kleinschmidt * Revert "build: cleanup symlinks in cache" This reverts commit 69e53cdc8850a62af3cb8cb1d4b6246b1e378c29. Co-authored-by: John Kleinschmidt --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- .github/actions/restore-cache-azcopy/action.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/actions/restore-cache-azcopy/action.yml b/.github/actions/restore-cache-azcopy/action.yml index 22e82e0f97843..2272ee6e76876 100644 --- a/.github/actions/restore-cache-azcopy/action.yml +++ b/.github/actions/restore-cache-azcopy/action.yml @@ -96,7 +96,7 @@ runs: $TEMP_DIR=New-Item -ItemType Directory -Path temp-cache $TEMP_DIR_PATH = $TEMP_DIR.FullName - C:\ProgramData\Chocolatey\bin\7z.exe -y x $src_cache -o"$TEMP_DIR_PATH" + C:\ProgramData\Chocolatey\bin\7z.exe -y -snld x $src_cache -o"$TEMP_DIR_PATH" - name: Move Src Cache (Windows) if: ${{ inputs.target-platform == 'win' }} From 8164a0b1f9ec568e4ca9101b3081db5433c2a089 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Sat, 12 Jul 2025 09:54:14 +0200 Subject: [PATCH 141/186] ci: set git `core.longpaths` to true (#47713) ci: set git core.longpaths to true Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .github/actions/install-build-tools/action.yml | 1 + .github/workflows/pipeline-segment-electron-test.yml | 1 + 2 files changed, 2 insertions(+) diff --git a/.github/actions/install-build-tools/action.yml b/.github/actions/install-build-tools/action.yml index 54aa56a42a05a..982ebbe89e253 100644 --- a/.github/actions/install-build-tools/action.yml +++ b/.github/actions/install-build-tools/action.yml @@ -11,6 +11,7 @@ runs: git config --global core.autocrlf false git config --global branch.autosetuprebase always git config --global core.fscache true + git config --global core.longpaths true git config --global core.preloadindex true fi export BUILD_TOOLS_SHA=f2a960b4d82e6b5c9dbbd437378a39489f399c50 diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index 17cf3f2398b98..54543f5dd4e22 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -135,6 +135,7 @@ jobs: git config --global core.autocrlf false git config --global branch.autosetuprebase always git config --global core.fscache true + git config --global core.longpaths true git config --global core.preloadindex true git clone --filter=tree:0 https://chromium.googlesource.com/chromium/tools/depot_tools.git # Ensure depot_tools does not update. From cbec5f7a5ac738b281e47108bf703dffe616dc9a Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 14 Jul 2025 10:02:30 +0200 Subject: [PATCH 142/186] ci: add `kTCCServiceAppleEvents` perm override to fix AppleScript errors (#47735) ci: add kTCCServiceAppleEvents perm override to fix AppleScript errors Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .github/workflows/pipeline-segment-electron-test.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index 54543f5dd4e22..ae2a19b30ae9d 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -103,6 +103,7 @@ jobs: "'kTCCServiceMicrophone','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" "'kTCCServiceCamera','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" "'kTCCServiceBluetoothAlways','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" + "'kTCCServiceAppleEvents','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" ) for values in "${userValuesArray[@]}"; do # Sonoma and higher have a few extra values From ca563d5464fb91d069a11dff55ab74b3c4dd283b Mon Sep 17 00:00:00 2001 From: David Sanders Date: Mon, 14 Jul 2025 01:06:55 -0700 Subject: [PATCH 143/186] build: drop eslint-plugin-unicorn (#47687) build: drop eslint-plugin-unicorn (#47676) --- build/.eslintrc.json | 4 +- default_app/.eslintrc.json | 4 +- package.json | 3 +- script/.eslintrc.json | 4 +- spec/.eslintrc.json | 6 +- spec/fixtures/module/preload-sandbox.js | 6 +- yarn.lock | 988 +++++++++++++++++++----- 7 files changed, 789 insertions(+), 226 deletions(-) diff --git a/build/.eslintrc.json b/build/.eslintrc.json index dc7dde78dc189..35c8df531937d 100644 --- a/build/.eslintrc.json +++ b/build/.eslintrc.json @@ -1,8 +1,8 @@ { "plugins": [ - "unicorn" + "import" ], "rules": { - "unicorn/prefer-node-protocol": "error" + "import/enforce-node-protocol-usage": ["error", "always"] } } diff --git a/default_app/.eslintrc.json b/default_app/.eslintrc.json index dc7dde78dc189..35c8df531937d 100644 --- a/default_app/.eslintrc.json +++ b/default_app/.eslintrc.json @@ -1,8 +1,8 @@ { "plugins": [ - "unicorn" + "import" ], "rules": { - "unicorn/prefer-node-protocol": "error" + "import/enforce-node-protocol-usage": ["error", "always"] } } diff --git a/package.json b/package.json index d2bfd9bfa718f..8f6c837ddfa47 100644 --- a/package.json +++ b/package.json @@ -28,13 +28,12 @@ "dugite": "^2.7.1", "eslint": "^8.57.1", "eslint-config-standard": "^17.1.0", - "eslint-plugin-import": "^2.30.0", + "eslint-plugin-import": "^2.32.0", "eslint-plugin-mocha": "^10.5.0", "eslint-plugin-n": "^16.6.2", "eslint-plugin-node": "^11.1.0", "eslint-plugin-promise": "^6.6.0", "eslint-plugin-standard": "^5.0.0", - "eslint-plugin-unicorn": "^55.0.0", "events": "^3.2.0", "folder-hash": "^2.1.1", "got": "^11.8.5", diff --git a/script/.eslintrc.json b/script/.eslintrc.json index dc7dde78dc189..35c8df531937d 100644 --- a/script/.eslintrc.json +++ b/script/.eslintrc.json @@ -1,8 +1,8 @@ { "plugins": [ - "unicorn" + "import" ], "rules": { - "unicorn/prefer-node-protocol": "error" + "import/enforce-node-protocol-usage": ["error", "always"] } } diff --git a/spec/.eslintrc.json b/spec/.eslintrc.json index 364b1639cbaef..83b471f885996 100644 --- a/spec/.eslintrc.json +++ b/spec/.eslintrc.json @@ -11,11 +11,11 @@ "WebView": true }, "plugins": [ - "mocha", - "unicorn" + "import", + "mocha" ], "rules": { "mocha/no-exclusive-tests": "error", - "unicorn/prefer-node-protocol": "error" + "import/enforce-node-protocol-usage": ["error", "always"] } } diff --git a/spec/fixtures/module/preload-sandbox.js b/spec/fixtures/module/preload-sandbox.js index ce0b0d3d816a2..f6a4d55e55b7a 100644 --- a/spec/fixtures/module/preload-sandbox.js +++ b/spec/fixtures/module/preload-sandbox.js @@ -33,11 +33,11 @@ systemVersion: invoke(() => process.getSystemVersion()), cpuUsage: invoke(() => process.getCPUUsage()), uptime: invoke(() => process.uptime()), - // eslint-disable-next-line unicorn/prefer-node-protocol + // eslint-disable-next-line import/enforce-node-protocol-usage nodeEvents: invoke(() => require('events') === require('node:events')), - // eslint-disable-next-line unicorn/prefer-node-protocol + // eslint-disable-next-line import/enforce-node-protocol-usage nodeTimers: invoke(() => require('timers') === require('node:timers')), - // eslint-disable-next-line unicorn/prefer-node-protocol + // eslint-disable-next-line import/enforce-node-protocol-usage nodeUrl: invoke(() => require('url') === require('node:url')), env: process.env, execPath: process.execPath, diff --git a/yarn.lock b/yarn.lock index ad0ed30e207f1..4ff9dd5afc01d 100644 --- a/yarn.lock +++ b/yarn.lock @@ -156,11 +156,6 @@ "@babel/highlight" "^7.25.7" picocolors "^1.0.0" -"@babel/helper-validator-identifier@^7.24.5": - version "7.24.7" - resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.24.7.tgz#75b889cfaf9e35c2aaf42cf0d72c8e91719251db" - integrity sha512-rR+PBcQ1SMQDDyF6X0wxtG8QyLCgUB0eRAGguqRLfkCA87l7yAP7ehq8SNj96OOGTO8OBV70KhuFYcIkHXOg0w== - "@babel/helper-validator-identifier@^7.25.7": version "7.25.7" resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.25.7.tgz#77b7f60c40b15c97df735b38a66ba1d7c3e93da5" @@ -999,11 +994,6 @@ dependencies: undici-types "~6.19.2" -"@types/normalize-package-data@^2.4.0": - version "2.4.1" - resolved "https://registry.yarnpkg.com/@types/normalize-package-data/-/normalize-package-data-2.4.1.tgz#d3357479a0fdfdd5907fe67e17e0a85c906e1301" - integrity sha512-Gj7cI7z+98M282Tqmp2K5EIsoouUEzbBJhQQzDE3jSIRk6r9gsz0oUokqIUR4u1R3dMHo0pDHM7sNOHyhulypw== - "@types/parse-json@^4.0.0": version "4.0.0" resolved "https://registry.yarnpkg.com/@types/parse-json/-/parse-json-4.0.0.tgz#2f8bb441434d163b35fb8ffdccd7138927ffb8c0" @@ -1472,6 +1462,14 @@ array-buffer-byte-length@^1.0.1: call-bind "^1.0.5" is-array-buffer "^3.0.4" +array-buffer-byte-length@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/array-buffer-byte-length/-/array-buffer-byte-length-1.0.2.tgz#384d12a37295aec3769ab022ad323a18a51ccf8b" + integrity sha512-LHE+8BuR7RYGDKvnrmcuSq3tDcKv9OFEXQt/HpbZhY7V6h0zlUXutnAD82GiFx9rdieCMjkvtcsPqBwgUl1Iiw== + dependencies: + call-bound "^1.0.3" + is-array-buffer "^3.0.5" + array-includes@^3.1.5, array-includes@^3.1.6: version "3.1.6" resolved "https://registry.yarnpkg.com/array-includes/-/array-includes-3.1.6.tgz#9e9e720e194f198266ba9e18c29e6a9b0e4b225f" @@ -1483,34 +1481,37 @@ array-includes@^3.1.5, array-includes@^3.1.6: get-intrinsic "^1.1.3" is-string "^1.0.7" -array-includes@^3.1.8: - version "3.1.8" - resolved "https://registry.yarnpkg.com/array-includes/-/array-includes-3.1.8.tgz#5e370cbe172fdd5dd6530c1d4aadda25281ba97d" - integrity sha512-itaWrbYbqpGXkGhZPGUulwnhVf5Hpy1xiCFsGqyIGglbBxmG5vSjxQen3/WGOjPpNEv1RtBLKxbmVXm8HpJStQ== +array-includes@^3.1.9: + version "3.1.9" + resolved "https://registry.yarnpkg.com/array-includes/-/array-includes-3.1.9.tgz#1f0ccaa08e90cdbc3eb433210f903ad0f17c3f3a" + integrity sha512-FmeCCAenzH0KH381SPT5FZmiA/TmpndpcaShhfgEN9eCVjnFBqq3l1xrI42y8+PPLI6hypzou4GXw00WHmPBLQ== dependencies: - call-bind "^1.0.7" + call-bind "^1.0.8" + call-bound "^1.0.4" define-properties "^1.2.1" - es-abstract "^1.23.2" - es-object-atoms "^1.0.0" - get-intrinsic "^1.2.4" - is-string "^1.0.7" + es-abstract "^1.24.0" + es-object-atoms "^1.1.1" + get-intrinsic "^1.3.0" + is-string "^1.1.1" + math-intrinsics "^1.1.0" array-unique@^0.3.2: version "0.3.2" resolved "https://registry.yarnpkg.com/array-unique/-/array-unique-0.3.2.tgz#a894b75d4bc4f6cd679ef3244a9fd8f46ae2d428" integrity sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg= -array.prototype.findlastindex@^1.2.5: - version "1.2.5" - resolved "https://registry.yarnpkg.com/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.5.tgz#8c35a755c72908719453f87145ca011e39334d0d" - integrity sha512-zfETvRFA8o7EiNn++N5f/kaCw221hrpGsDmcpndVupkPzEc1Wuf3VgC0qby1BbHs7f5DVYjgtEU2LLh5bqeGfQ== +array.prototype.findlastindex@^1.2.6: + version "1.2.6" + resolved "https://registry.yarnpkg.com/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.6.tgz#cfa1065c81dcb64e34557c9b81d012f6a421c564" + integrity sha512-F/TKATkzseUExPlfvmwQKGITM3DGTK+vkAsCZoDc5daVygbJBnjEUCbgkAvVFsgfXfX4YIqZ/27G3k3tdXrTxQ== dependencies: - call-bind "^1.0.7" + call-bind "^1.0.8" + call-bound "^1.0.4" define-properties "^1.2.1" - es-abstract "^1.23.2" + es-abstract "^1.23.9" es-errors "^1.3.0" - es-object-atoms "^1.0.0" - es-shim-unscopables "^1.0.2" + es-object-atoms "^1.1.1" + es-shim-unscopables "^1.1.0" array.prototype.flat@^1.3.1: version "1.3.1" @@ -1522,15 +1523,15 @@ array.prototype.flat@^1.3.1: es-abstract "^1.20.4" es-shim-unscopables "^1.0.0" -array.prototype.flat@^1.3.2: - version "1.3.2" - resolved "https://registry.yarnpkg.com/array.prototype.flat/-/array.prototype.flat-1.3.2.tgz#1476217df8cff17d72ee8f3ba06738db5b387d18" - integrity sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA== +array.prototype.flat@^1.3.3: + version "1.3.3" + resolved "https://registry.yarnpkg.com/array.prototype.flat/-/array.prototype.flat-1.3.3.tgz#534aaf9e6e8dd79fb6b9a9917f839ef1ec63afe5" + integrity sha512-rwG/ja1neyLqCuGZ5YYrznA62D4mZXg0i1cIskIUKSiqF3Cje9/wXAls9B9s1Wa2fomMsIv8czB8jZcPmxCXFg== dependencies: - call-bind "^1.0.2" - define-properties "^1.2.0" - es-abstract "^1.22.1" - es-shim-unscopables "^1.0.0" + call-bind "^1.0.8" + define-properties "^1.2.1" + es-abstract "^1.23.5" + es-shim-unscopables "^1.0.2" array.prototype.flatmap@^1.3.1: version "1.3.1" @@ -1542,15 +1543,15 @@ array.prototype.flatmap@^1.3.1: es-abstract "^1.20.4" es-shim-unscopables "^1.0.0" -array.prototype.flatmap@^1.3.2: - version "1.3.2" - resolved "https://registry.yarnpkg.com/array.prototype.flatmap/-/array.prototype.flatmap-1.3.2.tgz#c9a7c6831db8e719d6ce639190146c24bbd3e527" - integrity sha512-Ewyx0c9PmpcsByhSW4r+9zDU7sGjFc86qf/kKtuSCRdhfbk0SNLLkaT5qvcHnRGgc5NP/ly/y+qkXkqONX54CQ== +array.prototype.flatmap@^1.3.3: + version "1.3.3" + resolved "https://registry.yarnpkg.com/array.prototype.flatmap/-/array.prototype.flatmap-1.3.3.tgz#712cc792ae70370ae40586264629e33aab5dd38b" + integrity sha512-Y7Wt51eKJSyi80hFrJCePGGNo5ktJCslFuboqJsbf57CCPcm5zztluPlc4/aD8sWsKvlwatezpV4U1efk8kpjg== dependencies: - call-bind "^1.0.2" - define-properties "^1.2.0" - es-abstract "^1.22.1" - es-shim-unscopables "^1.0.0" + call-bind "^1.0.8" + define-properties "^1.2.1" + es-abstract "^1.23.5" + es-shim-unscopables "^1.0.2" array.prototype.tosorted@^1.1.1: version "1.1.1" @@ -1577,6 +1578,19 @@ arraybuffer.prototype.slice@^1.0.3: is-array-buffer "^3.0.4" is-shared-array-buffer "^1.0.2" +arraybuffer.prototype.slice@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.4.tgz#9d760d84dbdd06d0cbf92c8849615a1a7ab3183c" + integrity sha512-BNoCY6SXXPQ7gF2opIP4GBE+Xw7U+pHMYKuzjgCN3GwiaIR09UUeKfheyIry77QtrCBlC0KK0q5/TER/tYh3PQ== + dependencies: + array-buffer-byte-length "^1.0.1" + call-bind "^1.0.8" + define-properties "^1.2.1" + es-abstract "^1.23.5" + es-errors "^1.3.0" + get-intrinsic "^1.2.6" + is-array-buffer "^3.0.4" + arrify@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/arrify/-/arrify-1.0.1.tgz#898508da2226f380df904728456849c1501a4b0d" @@ -1592,6 +1606,11 @@ astral-regex@^2.0.0: resolved "https://registry.yarnpkg.com/astral-regex/-/astral-regex-2.0.0.tgz#483143c567aeed4785759c0865786dc77d7d2e31" integrity sha512-Z7tMw1ytTXt5jqMcOP+OQteU1VuNK9Y02uuJtKQ1Sv69jXQKKg5cibLwGJow8yzZP+eAc18EmLGPal0bp36rvQ== +async-function@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/async-function/-/async-function-1.0.0.tgz#509c9fca60eaf85034c6829838188e4e4c8ffb2b" + integrity sha512-hsU18Ae8CDTR6Kgu9DYf0EbCr/a5iGL0rytQDobUcdpYOKokk8LEjVphnXkDkgpi0wYVsqrXuP0bZxJaTqdgoA== + async@^3.2.0: version "3.2.4" resolved "https://registry.yarnpkg.com/async/-/async-3.2.4.tgz#2d22e00f8cddeb5fde5dd33522b56d1cf569a81c" @@ -1671,7 +1690,7 @@ braces@^3.0.3, braces@~3.0.2: dependencies: fill-range "^7.1.1" -browserslist@^4.21.10, browserslist@^4.23.3: +browserslist@^4.21.10: version "4.23.3" resolved "https://registry.yarnpkg.com/browserslist/-/browserslist-4.23.3.tgz#debb029d3c93ebc97ffbc8d9cbb03403e227c800" integrity sha512-btwCFJVjI4YWDNfau8RhZ+B1Q/VLoUITrm3RlP6y1tYGWIOa+InuYiRGXUBXo8nA1qKmHMyLB/iVQg5TT4eFoA== @@ -1744,6 +1763,14 @@ cacheable-request@^7.0.2: normalize-url "^6.0.1" responselike "^2.0.0" +call-bind-apply-helpers@^1.0.0, call-bind-apply-helpers@^1.0.1, call-bind-apply-helpers@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz#4b5428c222be985d79c3d82657479dbe0b59b2d6" + integrity sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ== + dependencies: + es-errors "^1.3.0" + function-bind "^1.1.2" + call-bind@^1.0.0, call-bind@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/call-bind/-/call-bind-1.0.2.tgz#b1d4e89e688119c3c9a903ad30abb2f6a919be3c" @@ -1763,6 +1790,24 @@ call-bind@^1.0.5, call-bind@^1.0.6, call-bind@^1.0.7: get-intrinsic "^1.2.4" set-function-length "^1.2.1" +call-bind@^1.0.8: + version "1.0.8" + resolved "https://registry.yarnpkg.com/call-bind/-/call-bind-1.0.8.tgz#0736a9660f537e3388826f440d5ec45f744eaa4c" + integrity sha512-oKlSFMcMwpUg2ednkhQ454wfWiU/ul3CkJe/PEHcTKuiX6RpbehUiFMXu13HalGZxfUwCQzZG747YXBn1im9ww== + dependencies: + call-bind-apply-helpers "^1.0.0" + es-define-property "^1.0.0" + get-intrinsic "^1.2.4" + set-function-length "^1.2.2" + +call-bound@^1.0.2, call-bound@^1.0.3, call-bound@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/call-bound/-/call-bound-1.0.4.tgz#238de935d2a2a692928c538c7ccfa91067fd062a" + integrity sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg== + dependencies: + call-bind-apply-helpers "^1.0.2" + get-intrinsic "^1.3.0" + callsites@^3.0.0: version "3.1.0" resolved "https://registry.yarnpkg.com/callsites/-/callsites-3.1.0.tgz#b3630abd8943432f54b3f0519238e33cd7df2f73" @@ -1876,13 +1921,6 @@ ci-info@^4.0.0: resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-4.0.0.tgz#65466f8b280fc019b9f50a5388115d17a63a44f2" integrity sha512-TdHqgGf9odd8SXNuxtUBVx8Nv+qZOejE6qyqiy5NtbYYQOeFa6zmHkxlPzmaLxWWHsU6nJmB7AETdVPi+2NBUg== -clean-regexp@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/clean-regexp/-/clean-regexp-1.0.0.tgz#8df7c7aae51fd36874e8f8d05b9180bc11a3fed7" - integrity sha512-GfisEZEJvzKrmGWkvfhgzcz/BllN1USeqD2V6tg14OAOgaCD2Z/PUEuxnAZ/nPvmaHRG7a8y77p1T/IRQ4D1Hw== - dependencies: - escape-string-regexp "^1.0.5" - clean-stack@^2.0.0: version "2.2.0" resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b" @@ -2013,13 +2051,6 @@ concat-stream@^2.0.0: readable-stream "^3.0.2" typedarray "^0.0.6" -core-js-compat@^3.37.0: - version "3.38.1" - resolved "https://registry.yarnpkg.com/core-js-compat/-/core-js-compat-3.38.1.tgz#2bc7a298746ca5a7bcb9c164bcb120f2ebc09a09" - integrity sha512-JRH6gfXxGmrzF3tZ57lFx97YARxCXPaMzPo6jELZhv88pBH5VXpQ+y0znKGlFnzuaihqhLbefxSJxWJMPtfDzw== - dependencies: - browserslist "^4.23.3" - core-util-is@~1.0.0: version "1.0.2" resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.2.tgz#b5fd54220aa2bc5ab57aab7140c940754503c1a7" @@ -2054,6 +2085,15 @@ data-view-buffer@^1.0.1: es-errors "^1.3.0" is-data-view "^1.0.1" +data-view-buffer@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/data-view-buffer/-/data-view-buffer-1.0.2.tgz#211a03ba95ecaf7798a8c7198d79536211f88570" + integrity sha512-EmKO5V3OLXh1rtK2wgXRansaK1/mtVdTUEiEI0W8RkvgT05kfxaH29PliLnpLP73yYO6142Q72QNa8Wx/A5CqQ== + dependencies: + call-bound "^1.0.3" + es-errors "^1.3.0" + is-data-view "^1.0.2" + data-view-byte-length@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/data-view-byte-length/-/data-view-byte-length-1.0.1.tgz#90721ca95ff280677eb793749fce1011347669e2" @@ -2063,6 +2103,15 @@ data-view-byte-length@^1.0.1: es-errors "^1.3.0" is-data-view "^1.0.1" +data-view-byte-length@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/data-view-byte-length/-/data-view-byte-length-1.0.2.tgz#9e80f7ca52453ce3e93d25a35318767ea7704735" + integrity sha512-tuhGbE6CfTM9+5ANGf+oQb72Ky/0+s3xKUpHvShfiz2RxMFgFPjsXuRLBVMtvMs15awe45SRb83D6wH4ew6wlQ== + dependencies: + call-bound "^1.0.3" + es-errors "^1.3.0" + is-data-view "^1.0.2" + data-view-byte-offset@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/data-view-byte-offset/-/data-view-byte-offset-1.0.0.tgz#5e0bbfb4828ed2d1b9b400cd8a7d119bca0ff18a" @@ -2072,6 +2121,15 @@ data-view-byte-offset@^1.0.0: es-errors "^1.3.0" is-data-view "^1.0.1" +data-view-byte-offset@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/data-view-byte-offset/-/data-view-byte-offset-1.0.1.tgz#068307f9b71ab76dbbe10291389e020856606191" + integrity sha512-BS8PfmtDGnrgYdOonGZQdLZslWIeCGFP9tpan0hi1Co2Zr2NKADsvGYA8XxuG/4UWgJ6Cjtv+YJnB6MM69QGlQ== + dependencies: + call-bound "^1.0.2" + es-errors "^1.3.0" + is-data-view "^1.0.1" + debug@4, debug@^4.0.0, debug@^4.1.0, debug@^4.1.1, debug@^4.3.1, debug@^4.3.2, debug@^4.3.3, debug@^4.3.4, debug@^4.3.7: version "4.3.7" resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.7.tgz#87945b4151a011d76d95a198d7111c865c360a52" @@ -2195,6 +2253,15 @@ dugite@^2.7.1: progress "^2.0.3" tar "^6.1.11" +dunder-proto@^1.0.0, dunder-proto@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/dunder-proto/-/dunder-proto-1.0.1.tgz#d7ae667e1dc83482f8b70fd0f6eefc50da30f58a" + integrity sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A== + dependencies: + call-bind-apply-helpers "^1.0.1" + es-errors "^1.3.0" + gopd "^1.2.0" + duplexer@~0.1.1: version "0.1.1" resolved "https://registry.yarnpkg.com/duplexer/-/duplexer-0.1.1.tgz#ace6ff808c1ce66b57d1ebf97977acb02334cfc1" @@ -2399,6 +2466,66 @@ es-abstract@^1.22.1, es-abstract@^1.22.3, es-abstract@^1.23.0, es-abstract@^1.23 unbox-primitive "^1.0.2" which-typed-array "^1.1.15" +es-abstract@^1.23.5, es-abstract@^1.23.9, es-abstract@^1.24.0: + version "1.24.0" + resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.24.0.tgz#c44732d2beb0acc1ed60df840869e3106e7af328" + integrity sha512-WSzPgsdLtTcQwm4CROfS5ju2Wa1QQcVeT37jFjYzdFz1r9ahadC8B8/a4qxJxM+09F18iumCdRmlr96ZYkQvEg== + dependencies: + array-buffer-byte-length "^1.0.2" + arraybuffer.prototype.slice "^1.0.4" + available-typed-arrays "^1.0.7" + call-bind "^1.0.8" + call-bound "^1.0.4" + data-view-buffer "^1.0.2" + data-view-byte-length "^1.0.2" + data-view-byte-offset "^1.0.1" + es-define-property "^1.0.1" + es-errors "^1.3.0" + es-object-atoms "^1.1.1" + es-set-tostringtag "^2.1.0" + es-to-primitive "^1.3.0" + function.prototype.name "^1.1.8" + get-intrinsic "^1.3.0" + get-proto "^1.0.1" + get-symbol-description "^1.1.0" + globalthis "^1.0.4" + gopd "^1.2.0" + has-property-descriptors "^1.0.2" + has-proto "^1.2.0" + has-symbols "^1.1.0" + hasown "^2.0.2" + internal-slot "^1.1.0" + is-array-buffer "^3.0.5" + is-callable "^1.2.7" + is-data-view "^1.0.2" + is-negative-zero "^2.0.3" + is-regex "^1.2.1" + is-set "^2.0.3" + is-shared-array-buffer "^1.0.4" + is-string "^1.1.1" + is-typed-array "^1.1.15" + is-weakref "^1.1.1" + math-intrinsics "^1.1.0" + object-inspect "^1.13.4" + object-keys "^1.1.1" + object.assign "^4.1.7" + own-keys "^1.0.1" + regexp.prototype.flags "^1.5.4" + safe-array-concat "^1.1.3" + safe-push-apply "^1.0.0" + safe-regex-test "^1.1.0" + set-proto "^1.0.0" + stop-iteration-iterator "^1.1.0" + string.prototype.trim "^1.2.10" + string.prototype.trimend "^1.0.9" + string.prototype.trimstart "^1.0.8" + typed-array-buffer "^1.0.3" + typed-array-byte-length "^1.0.3" + typed-array-byte-offset "^1.0.4" + typed-array-length "^1.0.7" + unbox-primitive "^1.1.0" + which-typed-array "^1.1.19" + es-define-property@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/es-define-property/-/es-define-property-1.0.0.tgz#c7faefbdff8b2696cf5f46921edfb77cc4ba3845" @@ -2406,6 +2533,11 @@ es-define-property@^1.0.0: dependencies: get-intrinsic "^1.2.4" +es-define-property@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/es-define-property/-/es-define-property-1.0.1.tgz#983eb2f9a6724e9303f61addf011c72e09e0b0fa" + integrity sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g== + es-errors@^1.2.1, es-errors@^1.3.0: version "1.3.0" resolved "https://registry.yarnpkg.com/es-errors/-/es-errors-1.3.0.tgz#05f75a25dab98e4fb1dcd5e1472c0546d5057c8f" @@ -2423,6 +2555,13 @@ es-object-atoms@^1.0.0: dependencies: es-errors "^1.3.0" +es-object-atoms@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/es-object-atoms/-/es-object-atoms-1.1.1.tgz#1c4f2c4837327597ce69d2ca190a7fdd172338c1" + integrity sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA== + dependencies: + es-errors "^1.3.0" + es-set-tostringtag@^2.0.1: version "2.0.1" resolved "https://registry.yarnpkg.com/es-set-tostringtag/-/es-set-tostringtag-2.0.1.tgz#338d502f6f674301d710b80c8592de8a15f09cd8" @@ -2441,6 +2580,16 @@ es-set-tostringtag@^2.0.3: has-tostringtag "^1.0.2" hasown "^2.0.1" +es-set-tostringtag@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz#f31dbbe0c183b00a6d26eb6325c810c0fd18bd4d" + integrity sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA== + dependencies: + es-errors "^1.3.0" + get-intrinsic "^1.2.6" + has-tostringtag "^1.0.2" + hasown "^2.0.2" + es-shim-unscopables@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/es-shim-unscopables/-/es-shim-unscopables-1.0.0.tgz#702e632193201e3edf8713635d083d378e510241" @@ -2455,6 +2604,13 @@ es-shim-unscopables@^1.0.2: dependencies: hasown "^2.0.0" +es-shim-unscopables@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/es-shim-unscopables/-/es-shim-unscopables-1.1.0.tgz#438df35520dac5d105f3943d927549ea3b00f4b5" + integrity sha512-d9T8ucsEhh8Bi1woXCf+TIKDIROLG5WCkxg8geBCbvk22kzwC5G2OnXVMO6FUsvQlgUUXQ2itephWDLqDzbeCw== + dependencies: + hasown "^2.0.2" + es-to-primitive@^1.2.1: version "1.2.1" resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.2.1.tgz#e55cd4c9cdc188bcefb03b366c736323fc5c898a" @@ -2464,6 +2620,15 @@ es-to-primitive@^1.2.1: is-date-object "^1.0.1" is-symbol "^1.0.2" +es-to-primitive@^1.3.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.3.0.tgz#96c89c82cc49fd8794a24835ba3e1ff87f214e18" + integrity sha512-w+5mJ3GuFL+NjVtJlvydShqE1eN3h3PbI7/5LAsYJP/2qtuMXjfL2LpHSRqo4b4eSF5K/DH1JXKUAHSB2UW50g== + dependencies: + is-callable "^1.2.7" + is-date-object "^1.0.5" + is-symbol "^1.0.4" + es6-error@^4.1.1: version "4.1.1" resolved "https://registry.yarnpkg.com/es6-error/-/es6-error-4.1.1.tgz#9e3af407459deed47e9a91f9b885a84eb05c561d" @@ -2524,6 +2689,13 @@ eslint-import-resolver-node@^0.3.9: is-core-module "^2.13.0" resolve "^1.22.4" +eslint-module-utils@^2.12.1: + version "2.12.1" + resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.12.1.tgz#f76d3220bfb83c057651359295ab5854eaad75ff" + integrity sha512-L8jSWTze7K2mTg0vos/RuLRS5soomksDPoJLXIslC7c8Wmut3bx7CPpJijDcBZtxQ5lrbUdM+s0OlNbz0DCDNw== + dependencies: + debug "^3.2.7" + eslint-module-utils@^2.7.4: version "2.8.0" resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.8.0.tgz#e439fee65fc33f6bba630ff621efc38ec0375c49" @@ -2531,13 +2703,6 @@ eslint-module-utils@^2.7.4: dependencies: debug "^3.2.7" -eslint-module-utils@^2.9.0: - version "2.11.0" - resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.11.0.tgz#b99b211ca4318243f09661fae088f373ad5243c4" - integrity sha512-gbBE5Hitek/oG6MUVj6sFuzEjA/ClzNflVrLovHi/JgLdC7fiN5gLAY1WIPW1a0V5I999MnsrvVrCOGmmVqDBQ== - dependencies: - debug "^3.2.7" - eslint-plugin-es-x@^7.5.0: version "7.8.0" resolved "https://registry.yarnpkg.com/eslint-plugin-es-x/-/eslint-plugin-es-x-7.8.0.tgz#a207aa08da37a7923f2a9599e6d3eb73f3f92b74" @@ -2584,28 +2749,29 @@ eslint-plugin-import@^2.26.0: semver "^6.3.0" tsconfig-paths "^3.14.1" -eslint-plugin-import@^2.30.0: - version "2.30.0" - resolved "https://registry.yarnpkg.com/eslint-plugin-import/-/eslint-plugin-import-2.30.0.tgz#21ceea0fc462657195989dd780e50c92fe95f449" - integrity sha512-/mHNE9jINJfiD2EKkg1BKyPyUk4zdnT54YgbOgfjSakWT5oyX/qQLVNTkehyfpcMxZXMy1zyonZ2v7hZTX43Yw== +eslint-plugin-import@^2.32.0: + version "2.32.0" + resolved "https://registry.yarnpkg.com/eslint-plugin-import/-/eslint-plugin-import-2.32.0.tgz#602b55faa6e4caeaa5e970c198b5c00a37708980" + integrity sha512-whOE1HFo/qJDyX4SnXzP4N6zOWn79WhnCUY/iDR0mPfQZO8wcYE4JClzI2oZrhBnnMUCBCHZhO6VQyoBU95mZA== dependencies: "@rtsao/scc" "^1.1.0" - array-includes "^3.1.8" - array.prototype.findlastindex "^1.2.5" - array.prototype.flat "^1.3.2" - array.prototype.flatmap "^1.3.2" + array-includes "^3.1.9" + array.prototype.findlastindex "^1.2.6" + array.prototype.flat "^1.3.3" + array.prototype.flatmap "^1.3.3" debug "^3.2.7" doctrine "^2.1.0" eslint-import-resolver-node "^0.3.9" - eslint-module-utils "^2.9.0" + eslint-module-utils "^2.12.1" hasown "^2.0.2" - is-core-module "^2.15.1" + is-core-module "^2.16.1" is-glob "^4.0.3" minimatch "^3.1.2" object.fromentries "^2.0.8" object.groupby "^1.0.3" - object.values "^1.2.0" + object.values "^1.2.1" semver "^6.3.1" + string.prototype.trimend "^1.0.9" tsconfig-paths "^3.15.0" eslint-plugin-mocha@^10.5.0: @@ -2696,28 +2862,6 @@ eslint-plugin-standard@^5.0.0: resolved "https://registry.yarnpkg.com/eslint-plugin-standard/-/eslint-plugin-standard-5.0.0.tgz#c43f6925d669f177db46f095ea30be95476b1ee4" integrity sha512-eSIXPc9wBM4BrniMzJRBm2uoVuXz2EPa+NXPk2+itrVt+r5SbKFERx/IgrK/HmfjddyKVz2f+j+7gBRvu19xLg== -eslint-plugin-unicorn@^55.0.0: - version "55.0.0" - resolved "https://registry.yarnpkg.com/eslint-plugin-unicorn/-/eslint-plugin-unicorn-55.0.0.tgz#e2aeb397914799895702480970e7d148df5bcc7b" - integrity sha512-n3AKiVpY2/uDcGrS3+QsYDkjPfaOrNrsfQxU9nt5nitd9KuvVXrfAvgCO9DYPSfap+Gqjw9EOrXIsBp5tlHZjA== - dependencies: - "@babel/helper-validator-identifier" "^7.24.5" - "@eslint-community/eslint-utils" "^4.4.0" - ci-info "^4.0.0" - clean-regexp "^1.0.0" - core-js-compat "^3.37.0" - esquery "^1.5.0" - globals "^15.7.0" - indent-string "^4.0.0" - is-builtin-module "^3.2.1" - jsesc "^3.0.2" - pluralize "^8.0.0" - read-pkg-up "^7.0.1" - regexp-tree "^0.1.27" - regjsparser "^0.10.0" - semver "^7.6.1" - strip-indent "^3.0.0" - eslint-scope@5.1.1: version "5.1.1" resolved "https://registry.yarnpkg.com/eslint-scope/-/eslint-scope-5.1.1.tgz#e786e59a66cb92b3f6c1fb0d508aab174848f48c" @@ -2828,13 +2972,6 @@ esquery@^1.4.2: dependencies: estraverse "^5.1.0" -esquery@^1.5.0: - version "1.6.0" - resolved "https://registry.yarnpkg.com/esquery/-/esquery-1.6.0.tgz#91419234f804d852a82dceec3e16cdc22cf9dae7" - integrity sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg== - dependencies: - estraverse "^5.1.0" - esrecurse@^4.3.0: version "4.3.0" resolved "https://registry.yarnpkg.com/esrecurse/-/esrecurse-4.3.0.tgz#7ad7964d679abb28bee72cec63758b1c5d2c9921" @@ -2999,7 +3136,7 @@ find-up@^3.0.0: dependencies: locate-path "^3.0.0" -find-up@^4.0.0, find-up@^4.1.0: +find-up@^4.0.0: version "4.1.0" resolved "https://registry.yarnpkg.com/find-up/-/find-up-4.1.0.tgz#97afe7d6cdc0bc5928584b7c8d7b16e8a9aa5d19" integrity sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw== @@ -3044,6 +3181,13 @@ for-each@^0.3.3: dependencies: is-callable "^1.1.3" +for-each@^0.3.5: + version "0.3.5" + resolved "https://registry.yarnpkg.com/for-each/-/for-each-0.3.5.tgz#d650688027826920feeb0af747ee7b9421a41d47" + integrity sha512-dKx12eRCVIzqCxFGplyFKJMPvLEWgmNtUrpTiJIR5u97zEhRG8ySrtboPHZXx7daLxQVrl643cTzbab2tkQjxg== + dependencies: + is-callable "^1.2.7" + foreground-child@^3.1.0: version "3.1.1" resolved "https://registry.yarnpkg.com/foreground-child/-/foreground-child-3.1.1.tgz#1d173e776d75d2772fed08efe4a0de1ea1b12d0d" @@ -3117,6 +3261,18 @@ function.prototype.name@^1.1.6: es-abstract "^1.22.1" functions-have-names "^1.2.3" +function.prototype.name@^1.1.8: + version "1.1.8" + resolved "https://registry.yarnpkg.com/function.prototype.name/-/function.prototype.name-1.1.8.tgz#e68e1df7b259a5c949eeef95cdbde53edffabb78" + integrity sha512-e5iwyodOHhbMr/yNrc7fDYG4qlbIvI5gajyzPnb5TCwyhjApznQh1BMFou9b30SevY43gCJKXycoCBjMbsuW0Q== + dependencies: + call-bind "^1.0.8" + call-bound "^1.0.3" + define-properties "^1.2.1" + functions-have-names "^1.2.3" + hasown "^2.0.2" + is-callable "^1.2.7" + functions-have-names@^1.2.2, functions-have-names@^1.2.3: version "1.2.3" resolved "https://registry.yarnpkg.com/functions-have-names/-/functions-have-names-1.2.3.tgz#0404fe4ee2ba2f607f0e0ec3c80bae994133b834" @@ -3153,11 +3309,35 @@ get-intrinsic@^1.2.1, get-intrinsic@^1.2.3, get-intrinsic@^1.2.4: has-symbols "^1.0.3" hasown "^2.0.0" +get-intrinsic@^1.2.5, get-intrinsic@^1.2.6, get-intrinsic@^1.2.7, get-intrinsic@^1.3.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/get-intrinsic/-/get-intrinsic-1.3.0.tgz#743f0e3b6964a93a5491ed1bffaae054d7f98d01" + integrity sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ== + dependencies: + call-bind-apply-helpers "^1.0.2" + es-define-property "^1.0.1" + es-errors "^1.3.0" + es-object-atoms "^1.1.1" + function-bind "^1.1.2" + get-proto "^1.0.1" + gopd "^1.2.0" + has-symbols "^1.1.0" + hasown "^2.0.2" + math-intrinsics "^1.1.0" + get-own-enumerable-property-symbols@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/get-own-enumerable-property-symbols/-/get-own-enumerable-property-symbols-3.0.0.tgz#b877b49a5c16aefac3655f2ed2ea5b684df8d203" integrity sha512-CIJYJC4GGF06TakLg8z4GQKvDsx9EMspVxOYih7LerEL/WosUnFIww45CGfxfeKHqlg3twgUrYRT1O3WQqjGCg== +get-proto@^1.0.0, get-proto@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/get-proto/-/get-proto-1.0.1.tgz#150b3f2743869ef3e851ec0c49d15b1d14d00ee1" + integrity sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g== + dependencies: + dunder-proto "^1.0.1" + es-object-atoms "^1.0.0" + get-stdin@^8.0.0: version "8.0.0" resolved "https://registry.yarnpkg.com/get-stdin/-/get-stdin-8.0.0.tgz#cbad6a73feb75f6eeb22ba9e01f89aa28aa97a53" @@ -3187,6 +3367,15 @@ get-symbol-description@^1.0.2: es-errors "^1.3.0" get-intrinsic "^1.2.4" +get-symbol-description@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/get-symbol-description/-/get-symbol-description-1.1.0.tgz#7bdd54e0befe8ffc9f3b4e203220d9f1e881b6ee" + integrity sha512-w9UMqWwJxHNOvoNzSJ2oPF5wvYcvP7jUvYzhp67yEhTi17ZDBBC1z9pTdGuzjD+EFIqLSYRweZjqfiPzQ06Ebg== + dependencies: + call-bound "^1.0.3" + es-errors "^1.3.0" + get-intrinsic "^1.2.6" + get-tsconfig@^4.7.0: version "4.8.1" resolved "https://registry.yarnpkg.com/get-tsconfig/-/get-tsconfig-4.8.1.tgz#8995eb391ae6e1638d251118c7b56de7eb425471" @@ -3280,11 +3469,6 @@ globals@^13.24.0: dependencies: type-fest "^0.20.2" -globals@^15.7.0: - version "15.9.0" - resolved "https://registry.yarnpkg.com/globals/-/globals-15.9.0.tgz#e9de01771091ffbc37db5714dab484f9f69ff399" - integrity sha512-SmSKyLLKFbSr6rptvP8izbyxJL4ILwqO9Jg23UA0sDlGlu58V59D1//I3vlc0KJphVdUR7vMjHIplYnzBxorQA== - globalthis@^1.0.1, globalthis@^1.0.3: version "1.0.3" resolved "https://registry.yarnpkg.com/globalthis/-/globalthis-1.0.3.tgz#5852882a52b80dc301b0660273e1ed082f0b6ccf" @@ -3292,6 +3476,14 @@ globalthis@^1.0.1, globalthis@^1.0.3: dependencies: define-properties "^1.1.3" +globalthis@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/globalthis/-/globalthis-1.0.4.tgz#7430ed3a975d97bfb59bcce41f5cabbafa651236" + integrity sha512-DpLKbNU4WylpxJykQujfCcwYWiV/Jhm50Goo0wrVILAv5jOr9d+H+UR3PhSCD2rCCEIg0uc+G+muBTwD54JhDQ== + dependencies: + define-properties "^1.2.1" + gopd "^1.0.1" + globby@14.1.0: version "14.1.0" resolved "https://registry.yarnpkg.com/globby/-/globby-14.1.0.tgz#138b78e77cf5a8d794e327b15dce80bf1fb0a73e" @@ -3311,6 +3503,11 @@ gopd@^1.0.1: dependencies: get-intrinsic "^1.1.3" +gopd@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/gopd/-/gopd-1.2.0.tgz#89f56b8217bdbc8802bd299df6d7f1081d7e51a1" + integrity sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg== + got@^11.8.5: version "11.8.5" resolved "https://registry.yarnpkg.com/got/-/got-11.8.5.tgz#ce77d045136de56e8f024bebb82ea349bc730046" @@ -3387,11 +3584,23 @@ has-proto@^1.0.3: resolved "https://registry.yarnpkg.com/has-proto/-/has-proto-1.0.3.tgz#b31ddfe9b0e6e9914536a6ab286426d0214f77fd" integrity sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q== +has-proto@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/has-proto/-/has-proto-1.2.0.tgz#5de5a6eabd95fdffd9818b43055e8065e39fe9d5" + integrity sha512-KIL7eQPfHQRC8+XluaIw7BHUwwqL19bQn4hzNgdr+1wXoU0KKj6rufu47lhY7KbJR2C6T6+PfyN0Ea7wkSS+qQ== + dependencies: + dunder-proto "^1.0.0" + has-symbols@^1.0.2, has-symbols@^1.0.3: version "1.0.3" resolved "https://registry.yarnpkg.com/has-symbols/-/has-symbols-1.0.3.tgz#bb7b2c4349251dce87b125f7bdf874aa7c8b39f8" integrity sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A== +has-symbols@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/has-symbols/-/has-symbols-1.1.0.tgz#fc9c6a783a084951d0b971fe1018de813707a338" + integrity sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ== + has-tostringtag@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/has-tostringtag/-/has-tostringtag-1.0.0.tgz#7e133818a7d394734f941e73c3d3f9291e658b25" @@ -3464,11 +3673,6 @@ hastscript@^8.0.0: property-information "^6.0.0" space-separated-tokens "^2.0.0" -hosted-git-info@^2.1.4: - version "2.8.9" - resolved "https://registry.yarnpkg.com/hosted-git-info/-/hosted-git-info-2.8.9.tgz#dffc0bf9a21c02209090f2aa69429e1414daf3f9" - integrity sha512-mxIDAb9Lsm6DoOJ7xH+5+X4y1LU/4Hi50L9C5sIswK3JzULS4bwk1FvjdBgvYR4bzT4tuUQiC15FE2f5HbLvYw== - hosted-git-info@^7.0.0: version "7.0.2" resolved "https://registry.yarnpkg.com/hosted-git-info/-/hosted-git-info-7.0.2.tgz#9b751acac097757667f30114607ef7b661ff4f17" @@ -3602,6 +3806,15 @@ internal-slot@^1.0.7: hasown "^2.0.0" side-channel "^1.0.4" +internal-slot@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/internal-slot/-/internal-slot-1.1.0.tgz#1eac91762947d2f7056bc838d93e13b2e9604961" + integrity sha512-4gd7VpWNQNB4UKKCFFVcp1AVv+FMOgs9NKzjHKusc8jTMhd5eL1NqQqOpE0KzMds804/yHlglp3uxgluOqAPLw== + dependencies: + es-errors "^1.3.0" + hasown "^2.0.2" + side-channel "^1.1.0" + interpret@^1.0.0: version "1.4.0" resolved "https://registry.yarnpkg.com/interpret/-/interpret-1.4.0.tgz#665ab8bc4da27a774a40584e812e3e0fa45b1a1e" @@ -3642,11 +3855,31 @@ is-array-buffer@^3.0.4: call-bind "^1.0.2" get-intrinsic "^1.2.1" +is-array-buffer@^3.0.5: + version "3.0.5" + resolved "https://registry.yarnpkg.com/is-array-buffer/-/is-array-buffer-3.0.5.tgz#65742e1e687bd2cc666253068fd8707fe4d44280" + integrity sha512-DDfANUiiG2wC1qawP66qlTugJeL5HyzMpfr8lLK+jMQirGzNod0B12cFB/9q838Ru27sBwfw78/rdoU7RERz6A== + dependencies: + call-bind "^1.0.8" + call-bound "^1.0.3" + get-intrinsic "^1.2.6" + is-arrayish@^0.2.1: version "0.2.1" resolved "https://registry.yarnpkg.com/is-arrayish/-/is-arrayish-0.2.1.tgz#77c99840527aa8ecb1a8ba697b80645a7a926a9d" integrity sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0= +is-async-function@^2.0.0: + version "2.1.1" + resolved "https://registry.yarnpkg.com/is-async-function/-/is-async-function-2.1.1.tgz#3e69018c8e04e73b738793d020bfe884b9fd3523" + integrity sha512-9dgM/cZBnNvjzaMYHVoxxfPj2QXt22Ev7SuuPrs+xav0ukGB0S6d4ydZdEiM48kLx5kDV+QBPrpVnFyefL8kkQ== + dependencies: + async-function "^1.0.0" + call-bound "^1.0.3" + get-proto "^1.0.1" + has-tostringtag "^1.0.2" + safe-regex-test "^1.1.0" + is-bigint@^1.0.1: version "1.0.4" resolved "https://registry.yarnpkg.com/is-bigint/-/is-bigint-1.0.4.tgz#08147a1875bc2b32005d41ccd8291dffc6691df3" @@ -3654,6 +3887,13 @@ is-bigint@^1.0.1: dependencies: has-bigints "^1.0.1" +is-bigint@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/is-bigint/-/is-bigint-1.1.0.tgz#dda7a3445df57a42583db4228682eba7c4170672" + integrity sha512-n4ZT37wG78iz03xPRKJrHTdZbe3IicyucEtdRsV5yglwc3GyUfbAfpSeD0FJ41NbUNSt5wbhqfp1fS+BgnvDFQ== + dependencies: + has-bigints "^1.0.2" + is-binary-path@~2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09" @@ -3669,6 +3909,14 @@ is-boolean-object@^1.1.0: call-bind "^1.0.2" has-tostringtag "^1.0.0" +is-boolean-object@^1.2.1: + version "1.2.2" + resolved "https://registry.yarnpkg.com/is-boolean-object/-/is-boolean-object-1.2.2.tgz#7067f47709809a393c71ff5bb3e135d8a9215d9e" + integrity sha512-wa56o2/ElJMYqjCjGkXri7it5FbebW5usLw/nPmCMs5DeZ7eziSYZhSmPRn0txqeW4LnAmQQU7FgqLpsEFKM4A== + dependencies: + call-bound "^1.0.3" + has-tostringtag "^1.0.2" + is-builtin-module@^3.2.1: version "3.2.1" resolved "https://registry.yarnpkg.com/is-builtin-module/-/is-builtin-module-3.2.1.tgz#f03271717d8654cfcaf07ab0463faa3571581169" @@ -3688,13 +3936,20 @@ is-core-module@^2.11.0: dependencies: has "^1.0.3" -is-core-module@^2.12.1, is-core-module@^2.13.0, is-core-module@^2.15.1: +is-core-module@^2.12.1, is-core-module@^2.13.0: version "2.15.1" resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.15.1.tgz#a7363a25bee942fefab0de13bf6aa372c82dcc37" integrity sha512-z0vtXSwucUJtANQWldhbtbt7BnL0vxiFjIdDLAatwhDYty2bad6s+rijD6Ri4YuYJubLzIJLUidCh09e1djEVQ== dependencies: hasown "^2.0.2" +is-core-module@^2.16.1: + version "2.16.1" + resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.16.1.tgz#2a98801a849f43e2add644fbb6bc6229b19a4ef4" + integrity sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w== + dependencies: + hasown "^2.0.2" + is-core-module@^2.8.0: version "2.8.1" resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.8.1.tgz#f59fdfca701d5879d0a6b100a40aa1560ce27211" @@ -3716,6 +3971,15 @@ is-data-view@^1.0.1: dependencies: is-typed-array "^1.1.13" +is-data-view@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/is-data-view/-/is-data-view-1.0.2.tgz#bae0a41b9688986c2188dda6657e56b8f9e63b8e" + integrity sha512-RKtWF8pGmS87i2D6gqQu/l7EYRlVdfzemCJN/P3UOs//x1QE7mfhvzHIApBTRf7axvT6DMGwSwBXYCT0nfB9xw== + dependencies: + call-bound "^1.0.2" + get-intrinsic "^1.2.6" + is-typed-array "^1.1.13" + is-date-object@^1.0.1: version "1.0.5" resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.0.5.tgz#0841d5536e724c25597bf6ea62e1bd38298df31f" @@ -3723,6 +3987,14 @@ is-date-object@^1.0.1: dependencies: has-tostringtag "^1.0.0" +is-date-object@^1.0.5, is-date-object@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.1.0.tgz#ad85541996fc7aa8b2729701d27b7319f95d82f7" + integrity sha512-PwwhEakHVKTdRNVOw+/Gyh0+MzlCl4R6qKvkhuvLtPMggI1WAHt9sOwZxQLSGpUaDnrdyDsomoRgNnCfKNSXXg== + dependencies: + call-bound "^1.0.2" + has-tostringtag "^1.0.2" + is-decimal@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/is-decimal/-/is-decimal-2.0.0.tgz#db1140337809fd043a056ae40a9bd1cdc563034c" @@ -3738,11 +4010,28 @@ is-extglob@^2.1.0, is-extglob@^2.1.1: resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" integrity sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ== +is-finalizationregistry@^1.1.0: + version "1.1.1" + resolved "https://registry.yarnpkg.com/is-finalizationregistry/-/is-finalizationregistry-1.1.1.tgz#eefdcdc6c94ddd0674d9c85887bf93f944a97c90" + integrity sha512-1pC6N8qWJbWoPtEjgcL2xyhQOP491EQjeUo3qTKcmV8YSDDJrOepfG8pcC7h/QgnQHYSv0mJ3Z/ZWxmatVrysg== + dependencies: + call-bound "^1.0.3" + is-fullwidth-code-point@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== +is-generator-function@^1.0.10: + version "1.1.0" + resolved "https://registry.yarnpkg.com/is-generator-function/-/is-generator-function-1.1.0.tgz#bf3eeda931201394f57b5dba2800f91a238309ca" + integrity sha512-nPUB5km40q9e8UfN/Zc24eLlzdSf9OfKByBw9CIdw4H1giPMeA0OIJvbchsCu4npfI2QcMVBsGEBHKZ7wLTWmQ== + dependencies: + call-bound "^1.0.3" + get-proto "^1.0.0" + has-tostringtag "^1.0.2" + safe-regex-test "^1.1.0" + is-glob@^3.1.0: version "3.1.0" resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-3.1.0.tgz#7ba5ae24217804ac70707b96922567486cc3e84a" @@ -3767,6 +4056,11 @@ is-interactive@^2.0.0: resolved "https://registry.yarnpkg.com/is-interactive/-/is-interactive-2.0.0.tgz#40c57614593826da1100ade6059778d597f16e90" integrity sha512-qP1vozQRI+BMOPcjFzrjXuQvdak2pHNUMZoeG2eRbiSqyvbEf/wQtEOTOX1guk6E3t36RkaqiSt8A/6YElNxLQ== +is-map@^2.0.3: + version "2.0.3" + resolved "https://registry.yarnpkg.com/is-map/-/is-map-2.0.3.tgz#ede96b7fe1e270b3c4465e3a465658764926d62e" + integrity sha512-1Qed0/Hr2m+YqxnM09CjA2d/i6YZNfF6R2oRAOj36eUdS6qIV/huPJNSEpKbupewFs+ZsJlxsjjPbc0/afW6Lw== + is-negative-zero@^2.0.2: version "2.0.2" resolved "https://registry.yarnpkg.com/is-negative-zero/-/is-negative-zero-2.0.2.tgz#7bf6f03a28003b8b3965de3ac26f664d765f3150" @@ -3784,6 +4078,14 @@ is-number-object@^1.0.4: dependencies: has-tostringtag "^1.0.0" +is-number-object@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/is-number-object/-/is-number-object-1.1.1.tgz#144b21e95a1bc148205dcc2814a9134ec41b2541" + integrity sha512-lZhclumE1G6VYD8VHe35wFaIif+CTy5SJIi5+3y4psDgWu4wPDoBhF8NxUOinEc7pHgiTsT6MaBb92rKhhD+Xw== + dependencies: + call-bound "^1.0.3" + has-tostringtag "^1.0.2" + is-number@^7.0.0: version "7.0.0" resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" @@ -3824,11 +4126,26 @@ is-regex@^1.1.4: call-bind "^1.0.2" has-tostringtag "^1.0.0" +is-regex@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/is-regex/-/is-regex-1.2.1.tgz#76d70a3ed10ef9be48eb577887d74205bf0cad22" + integrity sha512-MjYsKHO5O7mCsmRGxWcLWheFqN9DJ/2TmngvjKXihe6efViPqc274+Fx/4fYj/r03+ESvBdTXK0V6tA3rgez1g== + dependencies: + call-bound "^1.0.2" + gopd "^1.2.0" + has-tostringtag "^1.0.2" + hasown "^2.0.2" + is-regexp@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/is-regexp/-/is-regexp-1.0.0.tgz#fd2d883545c46bac5a633e7b9a09e87fa2cb5069" integrity sha1-/S2INUXEa6xaYz57mgnof6LLUGk= +is-set@^2.0.3: + version "2.0.3" + resolved "https://registry.yarnpkg.com/is-set/-/is-set-2.0.3.tgz#8ab209ea424608141372ded6e0cb200ef1d9d01d" + integrity sha512-iPAjerrse27/ygGLxw+EBR9agv9Y6uLeYVJMu+QNCoouJ1/1ri0mGrcWpfCqFZuzzx3WjtwxG098X+n4OuRkPg== + is-shared-array-buffer@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/is-shared-array-buffer/-/is-shared-array-buffer-1.0.2.tgz#8f259c573b60b6a32d4058a1a07430c0a7344c79" @@ -3843,6 +4160,13 @@ is-shared-array-buffer@^1.0.3: dependencies: call-bind "^1.0.7" +is-shared-array-buffer@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/is-shared-array-buffer/-/is-shared-array-buffer-1.0.4.tgz#9b67844bd9b7f246ba0708c3a93e34269c774f6f" + integrity sha512-ISWac8drv4ZGfwKl5slpHG9OwPNty4jOWPRIhBpxOoD+hqITiwuipOQ2bNthAzwA3B4fIjO4Nln74N0S9byq8A== + dependencies: + call-bound "^1.0.3" + is-stream@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-2.0.0.tgz#bde9c32680d6fae04129d6ac9d921ce7815f78e3" @@ -3855,6 +4179,14 @@ is-string@^1.0.5, is-string@^1.0.7: dependencies: has-tostringtag "^1.0.0" +is-string@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/is-string/-/is-string-1.1.1.tgz#92ea3f3d5c5b6e039ca8677e5ac8d07ea773cbb9" + integrity sha512-BtEeSsoaQjlSPBemMQIrY1MY0uM6vnS1g5fmufYOtnxLGUZM2178PKbhsk7Ffv58IX+ZtcvoGwccYsh0PglkAA== + dependencies: + call-bound "^1.0.3" + has-tostringtag "^1.0.2" + is-symbol@^1.0.2, is-symbol@^1.0.3: version "1.0.4" resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.0.4.tgz#a6dac93b635b063ca6872236de88910a57af139c" @@ -3862,6 +4194,15 @@ is-symbol@^1.0.2, is-symbol@^1.0.3: dependencies: has-symbols "^1.0.2" +is-symbol@^1.0.4, is-symbol@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.1.1.tgz#f47761279f532e2b05a7024a7506dbbedacd0634" + integrity sha512-9gGx6GTtCQM73BgmHQXfDmLtfjjTUDSyoxTCbp5WtoixAhfgsDirWIcVQ/IHpvI5Vgd5i/J5F7B9cN/WlVbC/w== + dependencies: + call-bound "^1.0.2" + has-symbols "^1.1.0" + safe-regex-test "^1.1.0" + is-typed-array@^1.1.10, is-typed-array@^1.1.9: version "1.1.10" resolved "https://registry.yarnpkg.com/is-typed-array/-/is-typed-array-1.1.10.tgz#36a5b5cb4189b575d1a3e4b08536bfb485801e3f" @@ -3880,6 +4221,13 @@ is-typed-array@^1.1.13: dependencies: which-typed-array "^1.1.14" +is-typed-array@^1.1.14, is-typed-array@^1.1.15: + version "1.1.15" + resolved "https://registry.yarnpkg.com/is-typed-array/-/is-typed-array-1.1.15.tgz#4bfb4a45b61cee83a5a46fba778e4e8d59c0ce0b" + integrity sha512-p3EcsicXjit7SaskXHs1hA91QxgTw46Fv6EFKKGS5DRFLD8yKnohjF3hxoju94b/OcMZoQukzpPpBE9uLVKzgQ== + dependencies: + which-typed-array "^1.1.16" + is-unicode-supported@^1.3.0: version "1.3.0" resolved "https://registry.yarnpkg.com/is-unicode-supported/-/is-unicode-supported-1.3.0.tgz#d824984b616c292a2e198207d4a609983842f714" @@ -3890,6 +4238,11 @@ is-unicode-supported@^2.0.0: resolved "https://registry.yarnpkg.com/is-unicode-supported/-/is-unicode-supported-2.1.0.tgz#09f0ab0de6d3744d48d265ebb98f65d11f2a9b3a" integrity sha512-mE00Gnza5EEB3Ds0HfMyllZzbBrmLOX3vfWoj9A9PEnTfratQ/BcaJOuMhnkhjXvb2+FkY3VuHqtAGpTPmglFQ== +is-weakmap@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/is-weakmap/-/is-weakmap-2.0.2.tgz#bf72615d649dfe5f699079c54b83e47d1ae19cfd" + integrity sha512-K5pXYOm9wqY1RgjpL3YTkF39tni1XajUIkawTLUo9EZEVUFga5gSQJF8nNS7ZwJQ02y+1YCNYcMh+HIf1ZqE+w== + is-weakref@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/is-weakref/-/is-weakref-1.0.2.tgz#9529f383a9338205e89765e0392efc2f100f06f2" @@ -3897,6 +4250,21 @@ is-weakref@^1.0.2: dependencies: call-bind "^1.0.2" +is-weakref@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/is-weakref/-/is-weakref-1.1.1.tgz#eea430182be8d64174bd96bffbc46f21bf3f9293" + integrity sha512-6i9mGWSlqzNMEqpCp93KwRS1uUOodk2OJ6b+sq7ZPDSy2WuI5NFIxp/254TytR8ftefexkWn5xNiHUNpPOfSew== + dependencies: + call-bound "^1.0.3" + +is-weakset@^2.0.3: + version "2.0.4" + resolved "https://registry.yarnpkg.com/is-weakset/-/is-weakset-2.0.4.tgz#c9f5deb0bc1906c6d6f1027f284ddf459249daca" + integrity sha512-mfcwb6IzQyOKTs84CQMrOwW4gQcaTOAWJ0zzJCl2WSPDrWk/OzDaImWFH3djXhb24g4eudZfLRozAvPGw4d9hQ== + dependencies: + call-bound "^1.0.3" + get-intrinsic "^1.2.6" + isarray@^2.0.5: version "2.0.5" resolved "https://registry.yarnpkg.com/isarray/-/isarray-2.0.5.tgz#8af1e4c1221244cc62459faf38940d4e644a5723" @@ -3960,16 +4328,6 @@ js-yaml@^3.2.7: argparse "^1.0.7" esprima "^4.0.0" -jsesc@^3.0.2: - version "3.0.2" - resolved "https://registry.yarnpkg.com/jsesc/-/jsesc-3.0.2.tgz#bb8b09a6597ba426425f2e4a07245c3d00b9343e" - integrity sha512-xKqzzWXDttJuOcawBt4KnKHHIf5oQ/Cxax+0PWFG+DFDgHNAdi+TXECADI+RYiFUMmx8792xsMbbgXj4CwnP4g== - -jsesc@~0.5.0: - version "0.5.0" - resolved "https://registry.yarnpkg.com/jsesc/-/jsesc-0.5.0.tgz#e7dee66e35d6fc16f710fe91d5cf69f70f08911d" - integrity sha512-uZz5UnB7u4T9LvwmFqXii7pZSouaRPorGs5who1Ip7VO0wxanFvBL7GkM6dTHlgX+jhBApRetaWpnDabOeTcnA== - json-buffer@3.0.1, json-buffer@~3.0.1: version "3.0.1" resolved "https://registry.yarnpkg.com/json-buffer/-/json-buffer-3.0.1.tgz#9338802a30d3b6605fbe0613e094008ca8c05a13" @@ -4376,6 +4734,11 @@ matcher@^3.0.0: dependencies: escape-string-regexp "^4.0.0" +math-intrinsics@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/math-intrinsics/-/math-intrinsics-1.1.0.tgz#a0dd74be81e2aa5c2f27e65ce283605ee4e2b7f9" + integrity sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g== + mdast-comment-marker@^1.0.0: version "1.1.1" resolved "https://registry.yarnpkg.com/mdast-comment-marker/-/mdast-comment-marker-1.1.1.tgz#9c9c18e1ed57feafc1965d92b028f37c3c8da70d" @@ -4824,11 +5187,6 @@ mimic-response@^3.1.0: resolved "https://registry.yarnpkg.com/mimic-response/-/mimic-response-3.1.0.tgz#2d1d59af9c1b129815accc2c46a022a5ce1fa3c9" integrity sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ== -min-indent@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/min-indent/-/min-indent-1.0.1.tgz#a63f681673b30571fbe8bc25686ae746eefa9869" - integrity sha512-I9jwMn07Sy/IwOj3zVkVik2JTvgpaykDZEigL6Rx6N9LbMywwUSMtxET+7lVoDLLd3O3IXwJwvuuns8UB/HeAg== - minimatch@^3.0.2, minimatch@^3.0.4, minimatch@^3.0.5, minimatch@^3.1.2: version "3.1.2" resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b" @@ -4964,16 +5322,6 @@ nopt@^7.2.1: dependencies: abbrev "^2.0.0" -normalize-package-data@^2.5.0: - version "2.5.0" - resolved "https://registry.yarnpkg.com/normalize-package-data/-/normalize-package-data-2.5.0.tgz#e66db1838b200c1dfc233225d12cb36520e234a8" - integrity sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA== - dependencies: - hosted-git-info "^2.1.4" - resolve "^1.10.0" - semver "2 || 3 || 4 || 5" - validate-npm-package-license "^3.0.1" - normalize-package-data@^6.0.0: version "6.0.2" resolved "https://registry.yarnpkg.com/normalize-package-data/-/normalize-package-data-6.0.2.tgz#a7bc22167fe24025412bcff0a9651eb768b03506" @@ -5055,6 +5403,11 @@ object-inspect@^1.13.1: resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.13.2.tgz#dea0088467fb991e67af4058147a24824a3043ff" integrity sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g== +object-inspect@^1.13.3, object-inspect@^1.13.4: + version "1.13.4" + resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.13.4.tgz#8375265e21bc20d0fa582c22e1b13485d6e00213" + integrity sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew== + object-keys@^1.1.1: version "1.1.1" resolved "https://registry.yarnpkg.com/object-keys/-/object-keys-1.1.1.tgz#1c47f272df277f3b1daf061677d9c82e2322c60e" @@ -5080,6 +5433,18 @@ object.assign@^4.1.5: has-symbols "^1.0.3" object-keys "^1.1.1" +object.assign@^4.1.7: + version "4.1.7" + resolved "https://registry.yarnpkg.com/object.assign/-/object.assign-4.1.7.tgz#8c14ca1a424c6a561b0bb2a22f66f5049a945d3d" + integrity sha512-nK28WOo+QIjBkDduTINE4JkF/UJJKyf2EJxvJKfblDpyg0Q+pkOHNTL0Qwy6NP6FhE/EnzV73BxxqcJaXY9anw== + dependencies: + call-bind "^1.0.8" + call-bound "^1.0.3" + define-properties "^1.2.1" + es-object-atoms "^1.0.0" + has-symbols "^1.1.0" + object-keys "^1.1.1" + object.entries@^1.1.6: version "1.1.6" resolved "https://registry.yarnpkg.com/object.entries/-/object.entries-1.1.6.tgz#9737d0e5b8291edd340a3e3264bb8a3b00d5fa23" @@ -5134,12 +5499,13 @@ object.values@^1.1.6: define-properties "^1.1.4" es-abstract "^1.20.4" -object.values@^1.2.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/object.values/-/object.values-1.2.0.tgz#65405a9d92cee68ac2d303002e0b8470a4d9ab1b" - integrity sha512-yBYjY9QX2hnRmZHAjG/f13MzmBzxzYgQhFrke06TTyKY5zSTEqkOeukBzIdVA3j3ulu8Qa3MbVFShV7T2RmGtQ== +object.values@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/object.values/-/object.values-1.2.1.tgz#deed520a50809ff7f75a7cfd4bc64c7a038c6216" + integrity sha512-gXah6aZrcUxjWg2zR2MwouP2eHlCBzdV4pygudehaKXSGW4v2AsRQUK+lwwXhii6KFZcunEnmSUoYp5CXibxtA== dependencies: - call-bind "^1.0.7" + call-bind "^1.0.8" + call-bound "^1.0.3" define-properties "^1.2.1" es-object-atoms "^1.0.0" @@ -5191,6 +5557,15 @@ ora@^8.1.0: string-width "^7.2.0" strip-ansi "^7.1.0" +own-keys@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/own-keys/-/own-keys-1.0.1.tgz#e4006910a2bf913585289676eebd6f390cf51358" + integrity sha512-qFOyK5PjiWZd+QQIh+1jhdb9LpxTF0qs7Pm8o5QHYZ0M3vKqSqzsZaEB6oWlxZ+q2sJBMI/Ktgd2N5ZwQoRHfg== + dependencies: + get-intrinsic "^1.2.6" + object-keys "^1.1.1" + safe-push-apply "^1.0.0" + p-cancelable@^2.0.0: version "2.1.1" resolved "https://registry.yarnpkg.com/p-cancelable/-/p-cancelable-2.1.1.tgz#aab7fbd416582fa32a3db49859c122487c5ed2cf" @@ -5579,25 +5954,6 @@ read-package-json-fast@^3.0.0: json-parse-even-better-errors "^3.0.0" npm-normalize-package-bin "^3.0.0" -read-pkg-up@^7.0.1: - version "7.0.1" - resolved "https://registry.yarnpkg.com/read-pkg-up/-/read-pkg-up-7.0.1.tgz#f3a6135758459733ae2b95638056e1854e7ef507" - integrity sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg== - dependencies: - find-up "^4.1.0" - read-pkg "^5.2.0" - type-fest "^0.8.1" - -read-pkg@^5.2.0: - version "5.2.0" - resolved "https://registry.yarnpkg.com/read-pkg/-/read-pkg-5.2.0.tgz#7bf295438ca5a33e56cd30e053b34ee7250c93cc" - integrity sha512-Ug69mNOpfvKDAc2Q8DRpMjjzdtrnv9HcSMX+4VsZxD1aZ6ZzrIE7rlzXBtWTyhULSMKg076AW6WR5iZpD0JiOg== - dependencies: - "@types/normalize-package-data" "^2.4.0" - normalize-package-data "^2.5.0" - parse-json "^5.0.0" - type-fest "^0.6.0" - readable-stream@^2, readable-stream@^2.0.1, readable-stream@~2.3.6: version "2.3.6" resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.6.tgz#b11c27d88b8ff1fbe070643cf94b0c79ae1b0aaf" @@ -5641,10 +5997,19 @@ rechoir@^0.8.0: dependencies: resolve "^1.20.0" -regexp-tree@^0.1.27: - version "0.1.27" - resolved "https://registry.yarnpkg.com/regexp-tree/-/regexp-tree-0.1.27.tgz#2198f0ef54518ffa743fe74d983b56ffd631b6cd" - integrity sha512-iETxpjK6YoRWJG5o6hXLwvjYAoW+FEZn9os0PD/b6AP6xQwsa/Y7lCVgIixBbUPMfhu+i2LtdeAqVTgGlQarfA== +reflect.getprototypeof@^1.0.6, reflect.getprototypeof@^1.0.9: + version "1.0.10" + resolved "https://registry.yarnpkg.com/reflect.getprototypeof/-/reflect.getprototypeof-1.0.10.tgz#c629219e78a3316d8b604c765ef68996964e7bf9" + integrity sha512-00o4I+DVrefhv+nX0ulyi3biSHCPDe+yLv5o/p6d/UVlirijB8E16FtfwSAi4g3tcqrQ4lRAqQSoFEZJehYEcw== + dependencies: + call-bind "^1.0.8" + define-properties "^1.2.1" + es-abstract "^1.23.9" + es-errors "^1.3.0" + es-object-atoms "^1.0.0" + get-intrinsic "^1.2.7" + get-proto "^1.0.1" + which-builtin-type "^1.2.1" regexp.prototype.flags@^1.4.3: version "1.5.0" @@ -5665,18 +6030,23 @@ regexp.prototype.flags@^1.5.2: es-errors "^1.3.0" set-function-name "^2.0.1" +regexp.prototype.flags@^1.5.4: + version "1.5.4" + resolved "https://registry.yarnpkg.com/regexp.prototype.flags/-/regexp.prototype.flags-1.5.4.tgz#1ad6c62d44a259007e55b3970e00f746efbcaa19" + integrity sha512-dYqgNSZbDwkaJ2ceRd9ojCGjBq+mOm9LmtXnAnEGyHhN/5R7iDW2TRw3h+o/jCFxus3P2LfWIIiwowAjANm7IA== + dependencies: + call-bind "^1.0.8" + define-properties "^1.2.1" + es-errors "^1.3.0" + get-proto "^1.0.1" + gopd "^1.2.0" + set-function-name "^2.0.2" + regexpp@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/regexpp/-/regexpp-3.0.0.tgz#dd63982ee3300e67b41c1956f850aa680d9d330e" integrity sha512-Z+hNr7RAVWxznLPuA7DIh8UNX1j9CDrUQxskw9IrBE1Dxue2lyXT+shqEIeLUjrokxIP8CMy1WkjgG3rTsd5/g== -regjsparser@^0.10.0: - version "0.10.0" - resolved "https://registry.yarnpkg.com/regjsparser/-/regjsparser-0.10.0.tgz#b1ed26051736b436f22fdec1c8f72635f9f44892" - integrity sha512-qx+xQGZVsy55CH0a1hiVwHmqjLryfh7wQyF5HO07XJ9f7dQMY/gPQHhlyDkIzJKC+x2fUCpCcUODUUUFrm7SHA== - dependencies: - jsesc "~0.5.0" - remark-cli@^12.0.1: version "12.0.1" resolved "https://registry.yarnpkg.com/remark-cli/-/remark-cli-12.0.1.tgz#991ede01adfdf0471177c381168105da4b93f99a" @@ -6252,15 +6622,6 @@ resolve@^1.1.6: path-parse "^1.0.7" supports-preserve-symlinks-flag "^1.0.0" -resolve@^1.10.0, resolve@^1.22.1: - version "1.22.2" - resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.22.2.tgz#0ed0943d4e301867955766c9f3e1ae6d01c6845f" - integrity sha512-Sb+mjNHOULsBv818T40qSPeRiuWLyaGMa5ewydRLFimneixmVy2zdivRl+AF6jaYPC8ERxGDmFSiqui6SfPd+g== - dependencies: - is-core-module "^2.11.0" - path-parse "^1.0.7" - supports-preserve-symlinks-flag "^1.0.0" - resolve@^1.10.1: version "1.17.0" resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.17.0.tgz#b25941b54968231cc2d1bb76a79cb7f2c0bf8444" @@ -6277,6 +6638,15 @@ resolve@^1.20.0, resolve@^1.22.2, resolve@^1.22.4: path-parse "^1.0.7" supports-preserve-symlinks-flag "^1.0.0" +resolve@^1.22.1: + version "1.22.2" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.22.2.tgz#0ed0943d4e301867955766c9f3e1ae6d01c6845f" + integrity sha512-Sb+mjNHOULsBv818T40qSPeRiuWLyaGMa5ewydRLFimneixmVy2zdivRl+AF6jaYPC8ERxGDmFSiqui6SfPd+g== + dependencies: + is-core-module "^2.11.0" + path-parse "^1.0.7" + supports-preserve-symlinks-flag "^1.0.0" + resolve@^2.0.0-next.4: version "2.0.0-next.4" resolved "https://registry.yarnpkg.com/resolve/-/resolve-2.0.0-next.4.tgz#3d37a113d6429f496ec4752d2a2e58efb1fd4660" @@ -6374,6 +6744,17 @@ safe-array-concat@^1.1.2: has-symbols "^1.0.3" isarray "^2.0.5" +safe-array-concat@^1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/safe-array-concat/-/safe-array-concat-1.1.3.tgz#c9e54ec4f603b0bbb8e7e5007a5ee7aecd1538c3" + integrity sha512-AURm5f0jYEOydBj7VQlVvDrjeFgthDdEF5H1dP+6mNpoXOMo1quQqJ4wvJDyRZ9+pO3kGWoOdmV08cSv2aJV6Q== + dependencies: + call-bind "^1.0.8" + call-bound "^1.0.2" + get-intrinsic "^1.2.6" + has-symbols "^1.1.0" + isarray "^2.0.5" + safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@~5.2.0: version "5.2.1" resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" @@ -6384,6 +6765,14 @@ safe-buffer@~5.1.0, safe-buffer@~5.1.1: resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d" integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g== +safe-push-apply@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/safe-push-apply/-/safe-push-apply-1.0.0.tgz#01850e981c1602d398c85081f360e4e6d03d27f5" + integrity sha512-iKE9w/Z7xCzUMIZqdBsp6pEQvwuEebH4vdpjcDWnyzaI6yl6O9FHvVpmGelvEHNsoY6wGblkxR6Zty/h00WiSA== + dependencies: + es-errors "^1.3.0" + isarray "^2.0.5" + safe-regex-test@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/safe-regex-test/-/safe-regex-test-1.0.0.tgz#793b874d524eb3640d1873aad03596db2d4f2295" @@ -6402,6 +6791,15 @@ safe-regex-test@^1.0.3: es-errors "^1.3.0" is-regex "^1.1.4" +safe-regex-test@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/safe-regex-test/-/safe-regex-test-1.1.0.tgz#7f87dfb67a3150782eaaf18583ff5d1711ac10c1" + integrity sha512-x/+Cz4YrimQxQccJf5mKEbIa1NzeCRNI5Ecl/ekmlYaampdNLPalVyIcCZNNH3MvmqBugV5TMYZXv0ljslUlaw== + dependencies: + call-bound "^1.0.2" + es-errors "^1.3.0" + is-regex "^1.2.1" + schema-utils@^3.0.0, schema-utils@^3.1.1, schema-utils@^3.2.0: version "3.3.0" resolved "https://registry.yarnpkg.com/schema-utils/-/schema-utils-3.3.0.tgz#f50a88877c3c01652a15b622ae9e9795df7a60fe" @@ -6416,11 +6814,6 @@ semver-compare@^1.0.0: resolved "https://registry.yarnpkg.com/semver-compare/-/semver-compare-1.0.0.tgz#0dee216a1c941ab37e9efb1788f6afc5ff5537fc" integrity sha1-De4hahyUGrN+nvsXiPavxf9VN/w= -"semver@2 || 3 || 4 || 5": - version "5.7.2" - resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.2.tgz#48d55db737c3287cd4835e17fa13feace1c41ef8" - integrity sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g== - semver@^6.0.0, semver@^6.1.0, semver@^6.2.0, semver@^6.3.0, semver@^6.3.1: version "6.3.1" resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.1.tgz#556d2ef8689146e46dcea4bfdd095f3434dffcb4" @@ -6433,7 +6826,7 @@ semver@^7.0.0, semver@^7.3.2, semver@^7.3.5, semver@^7.3.8: dependencies: lru-cache "^6.0.0" -semver@^7.1.1, semver@^7.5.3, semver@^7.5.4, semver@^7.6.0, semver@^7.6.1, semver@^7.6.3: +semver@^7.1.1, semver@^7.5.3, semver@^7.5.4, semver@^7.6.0, semver@^7.6.3: version "7.6.3" resolved "https://registry.yarnpkg.com/semver/-/semver-7.6.3.tgz#980f7b5550bc175fb4dc09403085627f9eb33143" integrity sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A== @@ -6452,7 +6845,7 @@ serialize-javascript@^6.0.1: dependencies: randombytes "^2.1.0" -set-function-length@^1.2.1: +set-function-length@^1.2.1, set-function-length@^1.2.2: version "1.2.2" resolved "https://registry.yarnpkg.com/set-function-length/-/set-function-length-1.2.2.tgz#aac72314198eaed975cf77b2c3b6b880695e5449" integrity sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg== @@ -6464,7 +6857,7 @@ set-function-length@^1.2.1: gopd "^1.0.1" has-property-descriptors "^1.0.2" -set-function-name@^2.0.1: +set-function-name@^2.0.1, set-function-name@^2.0.2: version "2.0.2" resolved "https://registry.yarnpkg.com/set-function-name/-/set-function-name-2.0.2.tgz#16a705c5a0dc2f5e638ca96d8a8cd4e1c2b90985" integrity sha512-7PGFlmtwsEADb0WYyvCMa1t+yke6daIG4Wirafur5kcf+MhUnPms1UeR0CKQdTZD81yESwMHbtn+TR+dMviakQ== @@ -6474,6 +6867,15 @@ set-function-name@^2.0.1: functions-have-names "^1.2.3" has-property-descriptors "^1.0.2" +set-proto@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/set-proto/-/set-proto-1.0.0.tgz#0760dbcff30b2d7e801fd6e19983e56da337565e" + integrity sha512-RJRdvCo6IAnPdsvP/7m6bsQqNnn1FCBX5ZNtFL98MmFF/4xAIJTIg1YbHW5DC2W5SKZanrC6i4HsJqlajw/dZw== + dependencies: + dunder-proto "^1.0.1" + es-errors "^1.3.0" + es-object-atoms "^1.0.0" + shallow-clone@^3.0.0: version "3.0.1" resolved "https://registry.yarnpkg.com/shallow-clone/-/shallow-clone-3.0.1.tgz#8f2981ad92531f55035b01fb230769a40e02efa3" @@ -6510,6 +6912,35 @@ shx@^0.3.4: minimist "^1.2.3" shelljs "^0.8.5" +side-channel-list@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/side-channel-list/-/side-channel-list-1.0.0.tgz#10cb5984263115d3b7a0e336591e290a830af8ad" + integrity sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA== + dependencies: + es-errors "^1.3.0" + object-inspect "^1.13.3" + +side-channel-map@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/side-channel-map/-/side-channel-map-1.0.1.tgz#d6bb6b37902c6fef5174e5f533fab4c732a26f42" + integrity sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA== + dependencies: + call-bound "^1.0.2" + es-errors "^1.3.0" + get-intrinsic "^1.2.5" + object-inspect "^1.13.3" + +side-channel-weakmap@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/side-channel-weakmap/-/side-channel-weakmap-1.0.2.tgz#11dda19d5368e40ce9ec2bdc1fb0ecbc0790ecea" + integrity sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A== + dependencies: + call-bound "^1.0.2" + es-errors "^1.3.0" + get-intrinsic "^1.2.5" + object-inspect "^1.13.3" + side-channel-map "^1.0.1" + side-channel@^1.0.4: version "1.0.4" resolved "https://registry.yarnpkg.com/side-channel/-/side-channel-1.0.4.tgz#efce5c8fdc104ee751b25c58d4290011fa5ea2cf" @@ -6529,6 +6960,17 @@ side-channel@^1.0.6: get-intrinsic "^1.2.4" object-inspect "^1.13.1" +side-channel@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/side-channel/-/side-channel-1.1.0.tgz#c3fcff9c4da932784873335ec9765fa94ff66bc9" + integrity sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw== + dependencies: + es-errors "^1.3.0" + object-inspect "^1.13.3" + side-channel-list "^1.0.0" + side-channel-map "^1.0.1" + side-channel-weakmap "^1.0.2" + signal-exit@^3.0.2: version "3.0.3" resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.3.tgz#a1410c2edd8f077b08b4e253c8eacfcaf057461c" @@ -6667,6 +7109,14 @@ stdin-discarder@^0.2.2: resolved "https://registry.yarnpkg.com/stdin-discarder/-/stdin-discarder-0.2.2.tgz#390037f44c4ae1a1ae535c5fe38dc3aba8d997be" integrity sha512-UhDfHmA92YAlNnCfhmq0VeNL5bDbiZGg7sZ2IvPsXubGkiNa9EC+tUTsjBRsYUAz87btI6/1wf4XoVvQ3uRnmQ== +stop-iteration-iterator@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/stop-iteration-iterator/-/stop-iteration-iterator-1.1.0.tgz#f481ff70a548f6124d0312c3aa14cbfa7aa542ad" + integrity sha512-eLoXW/DHyl62zxY4SCaIgnRhuMr6ri4juEYARS8E6sCEqzKpOiE521Ucofdx+KnDZl5xmvGYaaKCk5FEOxJCoQ== + dependencies: + es-errors "^1.3.0" + internal-slot "^1.1.0" + stream-chain@^2.2.5: version "2.2.5" resolved "https://registry.yarnpkg.com/stream-chain/-/stream-chain-2.2.5.tgz#b30967e8f14ee033c5b9a19bbe8a2cba90ba0d09" @@ -6743,6 +7193,19 @@ string.prototype.matchall@^4.0.8: regexp.prototype.flags "^1.4.3" side-channel "^1.0.4" +string.prototype.trim@^1.2.10: + version "1.2.10" + resolved "https://registry.yarnpkg.com/string.prototype.trim/-/string.prototype.trim-1.2.10.tgz#40b2dd5ee94c959b4dcfb1d65ce72e90da480c81" + integrity sha512-Rs66F0P/1kedk5lyYyH9uBzuiI/kNRmwJAR9quK6VOtIpZ2G+hMZd+HQbbv25MgCA6gEffoMZYxlTod4WcdrKA== + dependencies: + call-bind "^1.0.8" + call-bound "^1.0.2" + define-data-property "^1.1.4" + define-properties "^1.2.1" + es-abstract "^1.23.5" + es-object-atoms "^1.0.0" + has-property-descriptors "^1.0.2" + string.prototype.trim@^1.2.7: version "1.2.7" resolved "https://registry.yarnpkg.com/string.prototype.trim/-/string.prototype.trim-1.2.7.tgz#a68352740859f6893f14ce3ef1bb3037f7a90533" @@ -6780,6 +7243,16 @@ string.prototype.trimend@^1.0.8: define-properties "^1.2.1" es-object-atoms "^1.0.0" +string.prototype.trimend@^1.0.9: + version "1.0.9" + resolved "https://registry.yarnpkg.com/string.prototype.trimend/-/string.prototype.trimend-1.0.9.tgz#62e2731272cd285041b36596054e9f66569b6942" + integrity sha512-G7Ok5C6E/j4SGfyLCloXTrngQIQU3PWtXGst3yM7Bea9FRURf1S42ZHlZZtsNque2FN2PoUhfZXYLNWwEr4dLQ== + dependencies: + call-bind "^1.0.8" + call-bound "^1.0.2" + define-properties "^1.2.1" + es-object-atoms "^1.0.0" + string.prototype.trimstart@^1.0.6: version "1.0.6" resolved "https://registry.yarnpkg.com/string.prototype.trimstart/-/string.prototype.trimstart-1.0.6.tgz#e90ab66aa8e4007d92ef591bbf3cd422c56bdcf4" @@ -6852,13 +7325,6 @@ strip-final-newline@^2.0.0: resolved "https://registry.yarnpkg.com/strip-final-newline/-/strip-final-newline-2.0.0.tgz#89b852fb2fcbe936f6f4b3187afb0a12c1ab58ad" integrity sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA== -strip-indent@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/strip-indent/-/strip-indent-3.0.0.tgz#c32e1cee940b6b3432c771bc2c54bcce73cd3001" - integrity sha512-laJTa3Jb+VQpaC6DseHhF7dXVqHTfJPCRDaEbid/drOhgitgYku/letMUqOXFoWV0zIIUbjpdH2t+tYj4bQMRQ== - dependencies: - min-indent "^1.0.0" - strip-json-comments@^3.1.1: version "3.1.1" resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" @@ -7117,16 +7583,6 @@ type-fest@^0.3.0: resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.3.1.tgz#63d00d204e059474fe5e1b7c011112bbd1dc29e1" integrity sha512-cUGJnCdr4STbePCgqNFbpVNCepa+kAVohJs1sLhxzdH+gnEoOd8VhbYa7pD3zZYGiURWM2xzEII3fQcRizDkYQ== -type-fest@^0.6.0: - version "0.6.0" - resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.6.0.tgz#8d2a2370d3df886eb5c90ada1c5bf6188acf838b" - integrity sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg== - -type-fest@^0.8.1: - version "0.8.1" - resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.8.1.tgz#09e249ebde851d3b1e48d27c105444667f17b83d" - integrity sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA== - type-fest@^3.8.0: version "3.13.1" resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-3.13.1.tgz#bb744c1f0678bea7543a2d1ec24e83e68e8c8706" @@ -7141,6 +7597,15 @@ typed-array-buffer@^1.0.2: es-errors "^1.3.0" is-typed-array "^1.1.13" +typed-array-buffer@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/typed-array-buffer/-/typed-array-buffer-1.0.3.tgz#a72395450a4869ec033fd549371b47af3a2ee536" + integrity sha512-nAYYwfY3qnzX30IkA6AQZjVbtK6duGontcQm1WSG1MD94YLqK0515GNApXkoxKOWMusVssAHWLh9SeaoefYFGw== + dependencies: + call-bound "^1.0.3" + es-errors "^1.3.0" + is-typed-array "^1.1.14" + typed-array-byte-length@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/typed-array-byte-length/-/typed-array-byte-length-1.0.1.tgz#d92972d3cff99a3fa2e765a28fcdc0f1d89dec67" @@ -7152,6 +7617,17 @@ typed-array-byte-length@^1.0.1: has-proto "^1.0.3" is-typed-array "^1.1.13" +typed-array-byte-length@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/typed-array-byte-length/-/typed-array-byte-length-1.0.3.tgz#8407a04f7d78684f3d252aa1a143d2b77b4160ce" + integrity sha512-BaXgOuIxz8n8pIq3e7Atg/7s+DpiYrxn4vdot3w9KbnBhcRQq6o3xemQdIfynqSeXeDrF32x+WvfzmOjPiY9lg== + dependencies: + call-bind "^1.0.8" + for-each "^0.3.3" + gopd "^1.2.0" + has-proto "^1.2.0" + is-typed-array "^1.1.14" + typed-array-byte-offset@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/typed-array-byte-offset/-/typed-array-byte-offset-1.0.2.tgz#f9ec1acb9259f395093e4567eb3c28a580d02063" @@ -7164,6 +7640,19 @@ typed-array-byte-offset@^1.0.2: has-proto "^1.0.3" is-typed-array "^1.1.13" +typed-array-byte-offset@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/typed-array-byte-offset/-/typed-array-byte-offset-1.0.4.tgz#ae3698b8ec91a8ab945016108aef00d5bff12355" + integrity sha512-bTlAFB/FBYMcuX81gbL4OcpH5PmlFHqlCCpAl8AlEzMz5k53oNDvN8p1PNOWLEmI2x4orp3raOFB51tv9X+MFQ== + dependencies: + available-typed-arrays "^1.0.7" + call-bind "^1.0.8" + for-each "^0.3.3" + gopd "^1.2.0" + has-proto "^1.2.0" + is-typed-array "^1.1.15" + reflect.getprototypeof "^1.0.9" + typed-array-length@^1.0.4: version "1.0.4" resolved "https://registry.yarnpkg.com/typed-array-length/-/typed-array-length-1.0.4.tgz#89d83785e5c4098bec72e08b319651f0eac9c1bb" @@ -7185,6 +7674,18 @@ typed-array-length@^1.0.6: is-typed-array "^1.1.13" possible-typed-array-names "^1.0.0" +typed-array-length@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/typed-array-length/-/typed-array-length-1.0.7.tgz#ee4deff984b64be1e118b0de8c9c877d5ce73d3d" + integrity sha512-3KS2b+kL7fsuk/eJZ7EQdnEmQoaho/r6KUef7hxvltNA5DR8NAUM+8wJMbJyZ4G9/7i3v5zPBIMN5aybAh2/Jg== + dependencies: + call-bind "^1.0.7" + for-each "^0.3.3" + gopd "^1.0.1" + is-typed-array "^1.1.13" + possible-typed-array-names "^1.0.0" + reflect.getprototypeof "^1.0.6" + typedarray@^0.0.6: version "0.0.6" resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" @@ -7210,6 +7711,16 @@ unbox-primitive@^1.0.2: has-symbols "^1.0.3" which-boxed-primitive "^1.0.2" +unbox-primitive@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/unbox-primitive/-/unbox-primitive-1.1.0.tgz#8d9d2c9edeea8460c7f35033a88867944934d1e2" + integrity sha512-nWJ91DjeOkej/TA8pXQ3myruKpKEYgqvpw9lz4OPHj/NWFNluYrjbz9j01CJ8yKQd2g4jFoOkINCTW2I5LEEyw== + dependencies: + call-bound "^1.0.3" + has-bigints "^1.0.2" + has-symbols "^1.1.0" + which-boxed-primitive "^1.1.1" + undici-types@~6.19.2: version "6.19.8" resolved "https://registry.yarnpkg.com/undici-types/-/undici-types-6.19.8.tgz#35111c9d1437ab83a7cdc0abae2f26d88eda0a02" @@ -7428,7 +7939,7 @@ util-deprecate@^1.0.1, util-deprecate@~1.0.1: resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8= -validate-npm-package-license@^3.0.1, validate-npm-package-license@^3.0.4: +validate-npm-package-license@^3.0.4: version "3.0.4" resolved "https://registry.yarnpkg.com/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz#fc91f6b9c7ba15c857f4cb2c5defeec39d4f410a" integrity sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew== @@ -7662,6 +8173,46 @@ which-boxed-primitive@^1.0.2: is-string "^1.0.5" is-symbol "^1.0.3" +which-boxed-primitive@^1.1.0, which-boxed-primitive@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/which-boxed-primitive/-/which-boxed-primitive-1.1.1.tgz#d76ec27df7fa165f18d5808374a5fe23c29b176e" + integrity sha512-TbX3mj8n0odCBFVlY8AxkqcHASw3L60jIuF8jFP78az3C2YhmGvqbHBpAjTRH2/xqYunrJ9g1jSyjCjpoWzIAA== + dependencies: + is-bigint "^1.1.0" + is-boolean-object "^1.2.1" + is-number-object "^1.1.1" + is-string "^1.1.1" + is-symbol "^1.1.1" + +which-builtin-type@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/which-builtin-type/-/which-builtin-type-1.2.1.tgz#89183da1b4907ab089a6b02029cc5d8d6574270e" + integrity sha512-6iBczoX+kDQ7a3+YJBnh3T+KZRxM/iYNPXicqk66/Qfm1b93iu+yOImkg0zHbj5LNOcNv1TEADiZ0xa34B4q6Q== + dependencies: + call-bound "^1.0.2" + function.prototype.name "^1.1.6" + has-tostringtag "^1.0.2" + is-async-function "^2.0.0" + is-date-object "^1.1.0" + is-finalizationregistry "^1.1.0" + is-generator-function "^1.0.10" + is-regex "^1.2.1" + is-weakref "^1.0.2" + isarray "^2.0.5" + which-boxed-primitive "^1.1.0" + which-collection "^1.0.2" + which-typed-array "^1.1.16" + +which-collection@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/which-collection/-/which-collection-1.0.2.tgz#627ef76243920a107e7ce8e96191debe4b16c2a0" + integrity sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw== + dependencies: + is-map "^2.0.3" + is-set "^2.0.3" + is-weakmap "^2.0.2" + is-weakset "^2.0.3" + which-typed-array@^1.1.14, which-typed-array@^1.1.15: version "1.1.15" resolved "https://registry.yarnpkg.com/which-typed-array/-/which-typed-array-1.1.15.tgz#264859e9b11a649b388bfaaf4f767df1f779b38d" @@ -7673,6 +8224,19 @@ which-typed-array@^1.1.14, which-typed-array@^1.1.15: gopd "^1.0.1" has-tostringtag "^1.0.2" +which-typed-array@^1.1.16, which-typed-array@^1.1.19: + version "1.1.19" + resolved "https://registry.yarnpkg.com/which-typed-array/-/which-typed-array-1.1.19.tgz#df03842e870b6b88e117524a4b364b6fc689f956" + integrity sha512-rEvr90Bck4WZt9HHFC4DJMsjvu7x+r6bImz0/BrbWb7A2djJ8hnZMrWnHo9F8ssv0OMErasDhftrfROTyqSDrw== + dependencies: + available-typed-arrays "^1.0.7" + call-bind "^1.0.8" + call-bound "^1.0.4" + for-each "^0.3.5" + get-proto "^1.0.1" + gopd "^1.2.0" + has-tostringtag "^1.0.2" + which-typed-array@^1.1.9: version "1.1.9" resolved "https://registry.yarnpkg.com/which-typed-array/-/which-typed-array-1.1.9.tgz#307cf898025848cf995e795e8423c7f337efbde6" From 102f740ec2fc8f34601c84b79ea1bf06042e8d00 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 15 Jul 2025 11:31:20 +0200 Subject: [PATCH 144/186] test: add response to bluetooth request possibilities (#47745) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- spec/chromium-spec.ts | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/spec/chromium-spec.ts b/spec/chromium-spec.ts index 90cfe8c8b92eb..da0a183d1e7b1 100644 --- a/spec/chromium-spec.ts +++ b/spec/chromium-spec.ts @@ -3637,8 +3637,14 @@ describe('navigator.bluetooth', () => { it('can request bluetooth devices', async () => { const bluetooth = await w.webContents.executeJavaScript(` - navigator.bluetooth.requestDevice({ acceptAllDevices: true}).then(device => "Found a device!").catch(err => err.message);`, true); - expect(bluetooth).to.be.oneOf(['Found a device!', 'Bluetooth adapter not available.', 'User cancelled the requestDevice() chooser.']); + navigator.bluetooth.requestDevice({ acceptAllDevices: true }).then(device => "Found a device!").catch(err => err.message);`, true); + const requestResponses = [ + 'Found a device!', + 'Bluetooth adapter not available.', + 'User cancelled the requestDevice() chooser.', + 'User denied the browser permission to scan for Bluetooth devices.' + ]; + expect(bluetooth).to.be.oneOf(requestResponses, `Unexpected response: ${bluetooth}`); }); }); @@ -3668,6 +3674,7 @@ describe('navigator.hid', () => { server.close(); closeAllWindows(); }); + afterEach(() => { session.defaultSession.setPermissionCheckHandler(null); session.defaultSession.setDevicePermissionHandler(null); From dac83d743b09fdcd832dc735d533027fa23a029f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 16 Jul 2025 09:52:54 +0200 Subject: [PATCH 145/186] docs: improve `win.setContentProtection()` docs (#47762) * docs: improve win.setContentProtection() docs Co-authored-by: Milan Burda * docs: update Windows display affinity value Co-authored-by: Niklas Wenzel * docs: update Windows behavior description Co-authored-by: Niklas Wenzel * Revert "docs: update Windows behavior description" This reverts commit 6d1942c53a4951b985643432d64cf79df26b2d34. Co-authored-by: Niklas Wenzel * Revert "docs: update Windows display affinity value" This reverts commit c15363e75d271100a437387e4512f084cb8d3cf9. Co-authored-by: Niklas Wenzel --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Milan Burda Co-authored-by: Niklas Wenzel --- docs/api/browser-window.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/api/browser-window.md b/docs/api/browser-window.md index 83bea39c5c1cd..e6e9acb3b8471 100644 --- a/docs/api/browser-window.md +++ b/docs/api/browser-window.md @@ -1527,8 +1527,8 @@ events. Prevents the window contents from being captured by other apps. -On macOS it sets the NSWindow's sharingType to NSWindowSharingNone. -On Windows it calls SetWindowDisplayAffinity with `WDA_EXCLUDEFROMCAPTURE`. +On macOS it sets the NSWindow's [`sharingType`](https://developer.apple.com/documentation/appkit/nswindow/sharingtype-swift.property?language=objc) to [`NSWindowSharingNone`](https://developer.apple.com/documentation/appkit/nswindow/sharingtype-swift.enum/none?language=objc). +On Windows it calls [`SetWindowDisplayAffinity`](https://learn.microsoft.com/en-us/windows/win32/api/winuser/nf-winuser-setwindowdisplayaffinity) with `WDA_EXCLUDEFROMCAPTURE`. For Windows 10 version 2004 and up the window will be removed from capture entirely, older Windows versions behave as if `WDA_MONITOR` is applied capturing a black window. From 591b1e77add5eeb1c987d2e126cb12105d700b30 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 16 Jul 2025 15:04:52 +0200 Subject: [PATCH 146/186] fix: missing SQLite builtin support in Node.js (#47756) https://github.com/nodejs/node/pull/58122 Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- patches/node/build_add_gn_build_files.patch | 48 ++++++++++++++----- ...w_unbundling_of_node_js_dependencies.patch | 8 ++-- ...o_use_custom_inspector_protocol_path.patch | 6 +-- ...ingssl_and_openssl_incompatibilities.patch | 2 +- 4 files changed, 45 insertions(+), 19 deletions(-) diff --git a/patches/node/build_add_gn_build_files.patch b/patches/node/build_add_gn_build_files.patch index 28ee7c05fe8b0..86ea0937ab059 100644 --- a/patches/node/build_add_gn_build_files.patch +++ b/patches/node/build_add_gn_build_files.patch @@ -24,7 +24,7 @@ index 4560bac7b8e3c707ecea5a425f642efb9de9ed36..e9c2a4391f4058a21a259cacaac4fde5 o['variables']['v8_enable_external_code_space'] = 1 if options.enable_pointer_compression else 0 o['variables']['v8_enable_31bit_smis_on_64bit_arch'] = 1 if options.enable_pointer_compression else 0 diff --git a/node.gni b/node.gni -index 35ccd0487f20cece033d58827ecb7ed016908ee4..b4450e3dd17994d1eaf59eb5cff5912545e89793 100644 +index 35ccd0487f20cece033d58827ecb7ed016908ee4..62cd49c6a87074912a1cb6792576c8d4f239b669 100644 --- a/node.gni +++ b/node.gni @@ -5,10 +5,10 @@ @@ -40,7 +40,15 @@ index 35ccd0487f20cece033d58827ecb7ed016908ee4..b4450e3dd17994d1eaf59eb5cff59125 # The location of OpenSSL - use the one from node's deps by default. node_openssl_path = "$node_path/deps/openssl" -@@ -44,7 +44,7 @@ declare_args() { +@@ -39,12 +39,15 @@ declare_args() { + # The variable is called "openssl" for parity with node's GYP build. + node_use_openssl = true + ++ # Build node with SQLite support. ++ node_use_sqlite = true ++ + # Use the specified path to system CA (PEM format) in addition to + # the BoringSSL supplied CA store or compiled-in Mozilla CA copy. node_openssl_system_ca_path = "" # Initialize v8 platform during node.js startup. @@ -49,7 +57,7 @@ index 35ccd0487f20cece033d58827ecb7ed016908ee4..b4450e3dd17994d1eaf59eb5cff59125 # Custom build tag. node_tag = "" -@@ -64,10 +64,16 @@ declare_args() { +@@ -64,10 +67,16 @@ declare_args() { # TODO(zcbenz): There are few broken things for now: # 1. cross-os compilation is not supported. # 2. node_mksnapshot crashes when cross-compiling for x64 from arm64. @@ -271,10 +279,22 @@ index 856878c33681a73d41016729dabe48b0a6a80589..91a11852d206b65485fe90fd037a0bd1 if sys.platform == 'win32': files = [ x.replace('\\', '/') for x in files ] diff --git a/unofficial.gni b/unofficial.gni -index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187f3c04c5c 100644 +index 44641b92678ab2f28e6f5de75a92878f9f3d322d..a6cfd45b109c7b38fcf1529468ff64d3c1c8bd1b 100644 --- a/unofficial.gni +++ b/unofficial.gni -@@ -142,32 +142,42 @@ template("node_gn_build") { +@@ -22,6 +22,11 @@ template("node_gn_build") { + } else { + defines += [ "HAVE_OPENSSL=0" ] + } ++ if (node_use_sqlite) { ++ defines += [ "HAVE_SQLITE=1" ] ++ } else { ++ defines += [ "HAVE_SQLITE=0" ] ++ } + if (node_use_amaro) { + defines += [ "HAVE_AMARO=1" ] + } else { +@@ -142,32 +147,41 @@ template("node_gn_build") { public_configs = [ ":node_external_config", "deps/googletest:googletest_config", @@ -297,7 +317,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187 "deps/nghttp2", - "deps/ngtcp2", "deps/postject", - "deps/sqlite", +- "deps/sqlite", "deps/uvwasi", - "deps/zstd", "//third_party/zlib", @@ -320,7 +340,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187 "$target_gen_dir/node_javascript.cc", ] + gypi_values.node_sources -@@ -190,7 +200,7 @@ template("node_gn_build") { +@@ -190,9 +204,13 @@ template("node_gn_build") { } if (node_use_openssl) { deps += [ "deps/ncrypto" ] @@ -328,8 +348,14 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187 + public_deps += [ "//third_party/boringssl" ] sources += gypi_values.node_crypto_sources } ++ if (node_use_sqlite) { ++ deps += [ "deps/sqlite" ] ++ sources += gypi_values.node_sqlite_sources ++ } if (node_enable_inspector) { -@@ -214,6 +224,10 @@ template("node_gn_build") { + deps += [ + "src/inspector:crdtp", +@@ -214,6 +232,10 @@ template("node_gn_build") { } } @@ -340,7 +366,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187 executable(target_name) { forward_variables_from(invoker, "*") -@@ -288,6 +302,7 @@ template("node_gn_build") { +@@ -288,6 +310,7 @@ template("node_gn_build") { } executable("node_js2c") { @@ -348,7 +374,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187 deps = [ "deps/uv", "$node_simdutf_path", -@@ -298,26 +313,75 @@ template("node_gn_build") { +@@ -298,26 +321,75 @@ template("node_gn_build") { "src/embedded_data.cc", "src/embedded_data.h", ] @@ -434,7 +460,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..e17e4f043af6e4047ab82723ffd83187 outputs = [ "$target_gen_dir/node_javascript.cc" ] # Get the path to node_js2c executable of the host toolchain. -@@ -331,11 +395,11 @@ template("node_gn_build") { +@@ -331,11 +403,11 @@ template("node_gn_build") { get_label_info(":node_js2c($host_toolchain)", "name") + host_executable_suffix diff --git a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch index c36f65af02e60..d93e9bef3bc21 100644 --- a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch +++ b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch @@ -14,10 +14,10 @@ We don't need to do this for zlib, as the existing gn workflow uses the same Upstreamed at https://github.com/nodejs/node/pull/55903 diff --git a/unofficial.gni b/unofficial.gni -index e17e4f043af6e4047ab82723ffd83187f3c04c5c..d591dfc99fdea4f830008502786ee44d863a31fc 100644 +index a6cfd45b109c7b38fcf1529468ff64d3c1c8bd1b..332c9ee7262108ae9616e9bc8bd950a4940a858c 100644 --- a/unofficial.gni +++ b/unofficial.gni -@@ -155,7 +155,6 @@ template("node_gn_build") { +@@ -160,7 +160,6 @@ template("node_gn_build") { ":run_node_js2c", "deps/cares", "deps/histogram", @@ -25,7 +25,7 @@ index e17e4f043af6e4047ab82723ffd83187f3c04c5c..d591dfc99fdea4f830008502786ee44d "deps/nbytes", "deps/nghttp2", "deps/postject", -@@ -194,7 +193,17 @@ template("node_gn_build") { +@@ -198,7 +197,17 @@ template("node_gn_build") { configs -= [ "//build/config/gcc:symbol_visibility_hidden" ] configs += [ "//build/config/gcc:symbol_visibility_default" ] } @@ -44,7 +44,7 @@ index e17e4f043af6e4047ab82723ffd83187f3c04c5c..d591dfc99fdea4f830008502786ee44d if (v8_enable_i18n_support) { deps += [ "//third_party/icu" ] } -@@ -222,6 +231,19 @@ template("node_gn_build") { +@@ -230,6 +239,19 @@ template("node_gn_build") { sources += node_inspector.node_inspector_sources + node_inspector.node_inspector_generated_sources } diff --git a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch b/patches/node/build_option_to_use_custom_inspector_protocol_path.patch index 5b00462181125..339cddb7a744e 100644 --- a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch +++ b/patches/node/build_option_to_use_custom_inspector_protocol_path.patch @@ -12,7 +12,7 @@ protocol deps to contain https://chromium-review.googlesource.com/c/v8/v8/+/5996 Rest of the changes can be upstreamed. diff --git a/node.gni b/node.gni -index 203b4abbc44df9e58083c819f61f9025104abdc6..73bf3839866a2652ca660f1117e8f249d33fa46a 100644 +index 165b26a79a7f2b74d2a2252dc2350b2e10c091e6..c64761b730e61edcdc0e46a48699f2fd5bb1c0a6 100644 --- a/node.gni +++ b/node.gni @@ -16,6 +16,9 @@ declare_args() { @@ -39,10 +39,10 @@ index 3d7aa148678b2646b88fa7c32abec91791b02b82..4810d93eb971b253f7dadff7011a632f gypi_values = exec_script( "../../tools/gypi_to_gn.py", diff --git a/unofficial.gni b/unofficial.gni -index d591dfc99fdea4f830008502786ee44d863a31fc..9e26399482d6a1cdb843efb72c152d5cdd5e08ea 100644 +index 332c9ee7262108ae9616e9bc8bd950a4940a858c..8886f2a79ae77614789d6ae0defd4f18fc756456 100644 --- a/unofficial.gni +++ b/unofficial.gni -@@ -214,13 +214,14 @@ template("node_gn_build") { +@@ -222,13 +222,14 @@ template("node_gn_build") { } if (node_enable_inspector) { deps += [ diff --git a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch index 134bd2a779163..d4dcdd86a2023 100644 --- a/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch +++ b/patches/node/fix_handle_boringssl_and_openssl_incompatibilities.patch @@ -172,7 +172,7 @@ index e5bf2b529bf23914677e25d7468aad58a4684557..9a3c6029ff3319cce58c79782a7bd5d1 }; // Check to see if the given public key is suitable for this DH instance. diff --git a/node.gni b/node.gni -index b4450e3dd17994d1eaf59eb5cff5912545e89793..203b4abbc44df9e58083c819f61f9025104abdc6 100644 +index 62cd49c6a87074912a1cb6792576c8d4f239b669..165b26a79a7f2b74d2a2252dc2350b2e10c091e6 100644 --- a/node.gni +++ b/node.gni @@ -11,7 +11,7 @@ declare_args() { From 52bba3fb5fea5da655f8c1af384b158e9d3ba600 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 16 Jul 2025 15:58:08 +0200 Subject: [PATCH 147/186] docs: fix broken sentence in crashReporter.start() documentation (#47777) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Pratyush <116508117+pratstick@users.noreply.github.com> --- docs/api/crash-reporter.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/api/crash-reporter.md b/docs/api/crash-reporter.md index 2af51c383617c..d00dad544f7b8 100644 --- a/docs/api/crash-reporter.md +++ b/docs/api/crash-reporter.md @@ -63,7 +63,7 @@ The `crashReporter` module has the following methods: * `extra` Record\ (optional) - Extra string key/value annotations that will be sent along with crash reports that are generated in the main process. Only string values are supported. Crashes generated in - child processes will not contain these extra + child processes will not include these extra parameters. To add extra parameters to crash reports generated from child processes, call [`addExtraParameter`](#crashreporteraddextraparameterkey-value) from the child process. From e6f2de587f37725cd1f4e743da1cc5c0c59c4477 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 16 Jul 2025 11:04:23 -0700 Subject: [PATCH 148/186] fix: add macos memory query fallback patch to avoid crash (#47784) * fix: add macos memory query fallback patch to avoid crash Co-authored-by: clavin * chore: remove incorrectly backported patches --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: clavin Co-authored-by: Keeley Hammond --- patches/chromium/.patches | 1 + ...memory_query_fallback_to_avoid_crash.patch | 61 +++++++++++++++++++ 2 files changed, 62 insertions(+) create mode 100644 patches/chromium/fix_add_macos_memory_query_fallback_to_avoid_crash.patch diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 42ea65a667cc0..31f914b813c9f 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -141,3 +141,4 @@ fix_win32_synchronous_spellcheck.patch fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch +fix_add_macos_memory_query_fallback_to_avoid_crash.patch diff --git a/patches/chromium/fix_add_macos_memory_query_fallback_to_avoid_crash.patch b/patches/chromium/fix_add_macos_memory_query_fallback_to_avoid_crash.patch new file mode 100644 index 0000000000000..d9e0b42bd5ea1 --- /dev/null +++ b/patches/chromium/fix_add_macos_memory_query_fallback_to_avoid_crash.patch @@ -0,0 +1,61 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Calvin Watford +Date: Tue, 15 Jul 2025 21:06:52 -0600 +Subject: fix: add macos memory query fallback to avoid crash + +In https://crrev.com/c/6274964 the implementation for querying the physical memory on macOS was changed to use a sysctl call. In that same change the sysctl call was added to the sanbox allowlist. + +This causes a problematic behavior: if an app that's running the old implementation (no sandbox exclusion for that sysctl call) gets swapped with the new implementation (uses new sysctl call) while it's running, then new child processes will trigger a sandbox permission error when calling the new method. + +While this "hot-swapping" behavior isn't supported, many enterprise update scripts may do this anyways, triggering an unfortunate user experience where child processes can never spawn but the browser process continues to live and terminate them (untl the app is restarted). + +This patch should be removed after the new implementation has been present since the beginning of a stable release. The new implementation was released with Electron 37.0.0, but this fallback was not added until after 37.2.2. That means 38.0.0 would be the first safe release to remove this fallback, giving developers a 1-major-version buffer to safely transition implementations. + +diff --git a/base/system/sys_info_apple.mm b/base/system/sys_info_apple.mm +index 02670cbc829a1d8c540c6e0a4bce2f81177eab18..e58f70100b96ff83af4388900946db9962c2a254 100644 +--- a/base/system/sys_info_apple.mm ++++ b/base/system/sys_info_apple.mm +@@ -6,11 +6,31 @@ + + #include + ++#include "base/apple/scoped_mach_port.h" + #include "base/strings/stringprintf.h" + #include "base/system/sys_info_internal.h" + + namespace base { + ++namespace { ++ ++// Implementation of AmountOfPhysicalMemoryImpl before https://crrev.com/c/6274964. ++// See Electron patch adding this fallback for more details. ++uint64_t AmountOfPhysicalMemoryFallback() { ++ struct host_basic_info hostinfo; ++ mach_msg_type_number_t count = HOST_BASIC_INFO_COUNT; ++ base::apple::ScopedMachSendRight host(mach_host_self()); ++ int result = host_info(host.get(), HOST_BASIC_INFO, ++ reinterpret_cast(&hostinfo), &count); ++ if (result != KERN_SUCCESS) { ++ NOTREACHED(); ++ } ++ DCHECK_EQ(HOST_BASIC_INFO_COUNT, count); ++ return hostinfo.max_mem; ++} ++ ++} ++ + namespace internal { + + // Queries sysctlbyname() for the given key and returns the 32 bit integer value +@@ -54,7 +74,10 @@ + uint64_t physical_memory; + size_t size = sizeof(physical_memory); + int rv = sysctlbyname("hw.memsize", &physical_memory, &size, nullptr, 0); +- PCHECK(rv == 0) << "sysctlbyname(\"hw.memsize\")"; ++ // Instead of crashing, fallback to the old implementation. ++ if (rv != 0) { ++ return AmountOfPhysicalMemoryFallback(); ++ } + return physical_memory; + } + From 4c3f14e43643555a5f59a0fbe4679068c56e5159 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 16 Jul 2025 11:36:20 -0700 Subject: [PATCH 149/186] test: deflake clipboard read/write specs (#47788) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- spec/chromium-spec.ts | 34 +++++++++++++++++++++------------- 1 file changed, 21 insertions(+), 13 deletions(-) diff --git a/spec/chromium-spec.ts b/spec/chromium-spec.ts index da0a183d1e7b1..f7db52bf31ba5 100644 --- a/spec/chromium-spec.ts +++ b/spec/chromium-spec.ts @@ -3271,7 +3271,12 @@ describe('navigator.clipboard.read', () => { await w.loadFile(path.join(fixturesPath, 'pages', 'blank.html')); }); - const readClipboard: any = () => { + const readClipboard = async () => { + if (!w.webContents.isFocused()) { + const focus = once(w.webContents, 'focus'); + w.webContents.focus(); + await focus; + } return w.webContents.executeJavaScript(` navigator.clipboard.read().then(clipboard => clipboard.toString()).catch(err => err.message); `, true); @@ -3289,11 +3294,7 @@ describe('navigator.clipboard.read', () => { it('returns an error when permission denied', async () => { session.defaultSession.setPermissionRequestHandler((wc, permission, callback) => { - if (permission === 'clipboard-read') { - callback(false); - } else { - callback(true); - } + callback(permission !== 'clipboard-read'); }); const clipboard = await readClipboard(); expect(clipboard).to.contain('Read permission denied.'); @@ -3301,11 +3302,7 @@ describe('navigator.clipboard.read', () => { it('returns clipboard contents when permission is granted', async () => { session.defaultSession.setPermissionRequestHandler((wc, permission, callback) => { - if (permission === 'clipboard-read') { - callback(true); - } else { - callback(false); - } + callback(permission === 'clipboard-read'); }); const clipboard = await readClipboard(); expect(clipboard).to.not.contain('Read permission denied.'); @@ -3319,7 +3316,12 @@ describe('navigator.clipboard.write', () => { await w.loadFile(path.join(fixturesPath, 'pages', 'blank.html')); }); - const writeClipboard: any = () => { + const writeClipboard = async () => { + if (!w.webContents.isFocused()) { + const focus = once(w.webContents, 'focus'); + w.webContents.focus(); + await focus; + } return w.webContents.executeJavaScript(` navigator.clipboard.writeText('Hello World!').catch(err => err.message); `, true); @@ -3361,7 +3363,13 @@ describe('navigator.clipboard.write', () => { }); describe('paste execCommand', () => { - const readClipboard: any = (w: BrowserWindow) => { + const readClipboard = async (w: BrowserWindow) => { + if (!w.webContents.isFocused()) { + const focus = once(w.webContents, 'focus'); + w.webContents.focus(); + await focus; + } + return w.webContents.executeJavaScript(` new Promise((resolve) => { const timeout = setTimeout(() => { From e845d20789367bdfce1d46549ea83a2716b16922 Mon Sep 17 00:00:00 2001 From: Calvin Date: Wed, 16 Jul 2025 13:03:26 -0600 Subject: [PATCH 150/186] fix: corner smoothing feature gate crash (37-x-y) (#47792) fix: corner smoothing feature gate crash (#47759) --- docs/api/corner-smoothing-css.md | 6 +- docs/api/structures/web-preferences.md | 1 - ...moothing_css_rule_and_blink_painting.patch | 219 ++++++------------ shell/browser/web_contents_preferences.cc | 5 - shell/browser/web_contents_preferences.h | 1 - shell/common/options_switches.h | 3 - shell/renderer/electron_smooth_round_rect.cc | 12 +- spec/api-corner-smoothing-spec.ts | 2 +- 8 files changed, 77 insertions(+), 172 deletions(-) diff --git a/docs/api/corner-smoothing-css.md b/docs/api/corner-smoothing-css.md index 029e74657ff3c..f1cdb75028b2e 100644 --- a/docs/api/corner-smoothing-css.md +++ b/docs/api/corner-smoothing-css.md @@ -51,19 +51,17 @@ Use the `system-ui` keyword to match the smoothness to the OS design language. ### Controlling availibility -This CSS rule can be disabled by setting [the `cornerSmoothingCSS` web preference](./structures/web-preferences.md) to `false`. +This CSS rule can be disabled using the Blink feature flag `ElectronCSSCornerSmoothing`. ```js const myWindow = new BrowserWindow({ // [...] webPreferences: { - enableCornerSmoothingCSS: false // Disables the `-electron-corner-smoothing` CSS rule + disableBlinkFeatures: 'ElectronCSSCornerSmoothing' // Disables the `-electron-corner-smoothing` CSS rule } }) ``` -The CSS rule will still parse, but will have no visual effect. - ### Formal reference * **Initial value**: `0%` diff --git a/docs/api/structures/web-preferences.md b/docs/api/structures/web-preferences.md index 4e6710523615d..26ead57c2329f 100644 --- a/docs/api/structures/web-preferences.md +++ b/docs/api/structures/web-preferences.md @@ -149,7 +149,6 @@ `WebContents` when the preferred size changes. Default is `false`. * `transparent` boolean (optional) - Whether to enable background transparency for the guest page. Default is `true`. **Note:** The guest page's text and background colors are derived from the [color scheme](https://developer.mozilla.org/en-US/docs/Web/CSS/color-scheme) of its root element. When transparency is enabled, the text color will still change accordingly but the background will remain transparent. * `enableDeprecatedPaste` boolean (optional) _Deprecated_ - Whether to enable the `paste` [execCommand](https://developer.mozilla.org/en-US/docs/Web/API/Document/execCommand). Default is `false`. -* `enableCornerSmoothingCSS` boolean (optional) _Experimental_ - Whether the [`-electron-corner-smoothing` CSS rule](../corner-smoothing-css.md) is enabled. Default is `true`. [chrome-content-scripts]: https://developer.chrome.com/extensions/content_scripts#execution-environment [runtime-enabled-features]: https://source.chromium.org/chromium/chromium/src/+/main:third_party/blink/renderer/platform/runtime_enabled_features.json5 diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index 0be7bdc58ffa5..bff7a0db9eee3 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -16,64 +16,9 @@ making three primary changes to Blink: * Modifies graphics to handle smooth `ContouredRect`s, delegating to `//electron/shell/renderer/electron_smooth_round_rect`. -3. Adds a renderer preference / web setting: +3. Adds a renderer feature: * Controls whether the CSS rule is available. - * Mostly simple "plumbing" for the setting through blink. -diff --git a/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc b/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc -index c13dfd7f20e6f281f51ae373ceebeb86104c5cd9..fac89df9f23f3f098096d2a07a07e623b1067270 100644 ---- a/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc -+++ b/third_party/blink/common/renderer_preferences/renderer_preferences_mojom_traits.cc -@@ -128,6 +128,8 @@ bool StructTraitselectron_corner_smoothing_css = data.electron_corner_smoothing_css(); -+ - out->canvas_noise_token = data.canvas_noise_token(); - - out->view_source_line_wrap_enabled = data.view_source_line_wrap_enabled(); -diff --git a/third_party/blink/public/common/renderer_preferences/renderer_preferences.h b/third_party/blink/public/common/renderer_preferences/renderer_preferences.h -index 75acd696a5258e52f5c17b88559dfb3f6373c669..34b5ed725702dca72c383c1def08fdb835f7fa6b 100644 ---- a/third_party/blink/public/common/renderer_preferences/renderer_preferences.h -+++ b/third_party/blink/public/common/renderer_preferences/renderer_preferences.h -@@ -91,6 +91,7 @@ struct BLINK_COMMON_EXPORT RendererPreferences { - bool caret_browsing_enabled{false}; - bool uses_platform_autofill{false}; - std::vector explicitly_allowed_network_ports; -+ bool electron_corner_smoothing_css{true}; - uint64_t canvas_noise_token{0}; - // The default value must be false to avoid performance problems on very large - // source pages. -diff --git a/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h b/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h -index defe40d7091cb4ba4b099a22aeaee71f78ff5e77..e8326fa7a3c45c08c7d9250edd52a6d73fcc3ff9 100644 ---- a/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h -+++ b/third_party/blink/public/common/renderer_preferences/renderer_preferences_mojom_traits.h -@@ -275,6 +275,11 @@ struct BLINK_COMMON_EXPORT - return data.explicitly_allowed_network_ports; - } - -+ static const bool& electron_corner_smoothing_css( -+ const ::blink::RendererPreferences& data) { -+ return data.electron_corner_smoothing_css; -+ } -+ - static const uint64_t& canvas_noise_token( - const ::blink::RendererPreferences& data) { - return data.canvas_noise_token; -diff --git a/third_party/blink/public/mojom/renderer_preferences.mojom b/third_party/blink/public/mojom/renderer_preferences.mojom -index f8361faf6151210d65a597562c533aaa0a5235df..328238c34a9381fbbeb5970af3de721c8412104e 100644 ---- a/third_party/blink/public/mojom/renderer_preferences.mojom -+++ b/third_party/blink/public/mojom/renderer_preferences.mojom -@@ -202,6 +202,8 @@ struct RendererPreferences { - - array explicitly_allowed_network_ports; - -+ bool electron_corner_smoothing_css; -+ - // A randomized 64 bit token that is generated per browser session, - // used for canvas noising. - uint64 canvas_noise_token = 0; diff --git a/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom b/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom index a96527c653d2108de572d1e94c3ce703b45f2830..f8eb2af2c97f888307f2be588c336d4209f6cb3e 100644 --- a/third_party/blink/public/mojom/use_counter/metrics/css_property_id.mojom @@ -86,18 +31,6 @@ index a96527c653d2108de572d1e94c3ce703b45f2830..f8eb2af2c97f888307f2be588c336d42 // This CSSSampleId represents page load for CSS histograms. It is recorded once // per page visit for each CSS histogram being logged on the blink side and the -diff --git a/third_party/blink/public/web/web_settings.h b/third_party/blink/public/web/web_settings.h -index c37f784a1309da14354881d48a5a76a965930926..bffd221d2b3f3701710025103fa564c233e203d1 100644 ---- a/third_party/blink/public/web/web_settings.h -+++ b/third_party/blink/public/web/web_settings.h -@@ -287,6 +287,7 @@ class WebSettings { - virtual void SetRequireTransientActivationAndAuthorizationForSubAppsAPIs( - bool) = 0; - virtual void SetRootScrollbarThemeColor(std::optional) = 0; -+ virtual void SetCornerSmoothingCSS(bool) = 0; - - protected: - ~WebSettings() = default; diff --git a/third_party/blink/renderer/build/scripts/core/css/css_properties.py b/third_party/blink/renderer/build/scripts/core/css/css_properties.py index 6e991652d242795e292cea4c94cff59aaea078fa..b6834c78575520bb6e584dd2ce3333ac17299fef 100755 --- a/third_party/blink/renderer/build/scripts/core/css/css_properties.py @@ -112,16 +45,17 @@ index 6e991652d242795e292cea4c94cff59aaea078fa..b6834c78575520bb6e584dd2ce3333ac 'internal-forced-visited-'): internal_visited_order = 0 diff --git a/third_party/blink/renderer/core/css/css_properties.json5 b/third_party/blink/renderer/core/css/css_properties.json5 -index 5619eae5a36f63627df605eeff049866ea846477..50bad85a916e5bb097d687cbc4d1721ecefa6c39 100644 +index 5619eae5a36f63627df605eeff049866ea846477..2fe353e68972493ac99d0d040902e25f0c6499fb 100644 --- a/third_party/blink/renderer/core/css/css_properties.json5 +++ b/third_party/blink/renderer/core/css/css_properties.json5 -@@ -8866,6 +8866,24 @@ +@@ -8866,6 +8866,26 @@ property_methods: ["ParseShorthand", "CSSValueFromComputedStyleInternal"], }, + { + name: "-electron-corner-smoothing", -+ property_methods: ["ParseSingleValue"], ++ property_methods: ["ParseSingleValue", "CSSValueFromComputedStyleInternal"], ++ interpolable: true, + field_group: "*", + field_template: "external", + // To keep this patch small, Length is used instead of a more descriptive @@ -129,12 +63,13 @@ index 5619eae5a36f63627df605eeff049866ea846477..50bad85a916e5bb097d687cbc4d1721e + // - `system-ui` = `Length::Auto()` + // - percent = `Length::Percent` + type_name: "Length", -+ converter: "ConvertCornerSmoothing", -+ keywords: ["system-ui"], + default_value: "Length::None()", -+ typedom_types: ["Keyword", "Percentage"], -+ is_border_radius: true, -+ invalidate: ["paint", "border-radius", "clip"], ++ keywords: ["system-ui"], ++ converter: "ConvertCornerSmoothing", ++ runtime_flag: "ElectronCSSCornerSmoothing", ++ valid_for_permission_element: true, ++ valid_for_page_context: true, ++ invalidate: ["border-radius", "paint", "corner-shape"], + }, + // Visited properties. @@ -154,10 +89,10 @@ index 9ec4976d64834bd4c09f3740edcd28334dd4ec50..e47da0a85670e800e74da957d6441d70 return a.EmptyCells() == b.EmptyCells(); case CSSPropertyID::kFill: diff --git a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -index e519e13fea11950cc619e384f774b61a6e2385c0..8289ca0a41da1532692673a3e426e8688d93b32e 100644 +index e519e13fea11950cc619e384f774b61a6e2385c0..04746566454401402c21f6381a7a7f0f4652ae4b 100644 --- a/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc +++ b/third_party/blink/renderer/core/css/properties/longhands/longhands_custom.cc -@@ -12175,5 +12175,25 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( +@@ -12175,5 +12175,36 @@ const CSSValue* InternalEmptyLineHeight::ParseSingleValue( CSSValueID::kNone>(stream); } @@ -165,12 +100,6 @@ index e519e13fea11950cc619e384f774b61a6e2385c0..8289ca0a41da1532692673a3e426e868 + CSSParserTokenStream& stream, + const CSSParserContext& context, + const CSSParserLocalContext&) const { -+ // Fail parsing if this rule is disabled by document settings. -+ if (Settings* settings = context.GetDocument()->GetSettings(); -+ settings && !settings->GetElectronCornerSmoothingCSS()) { -+ return nullptr; -+ } -+ + // Try to parse `system-ui` keyword first. + if (auto* ident = + css_parsing_utils::ConsumeIdent(stream)) { @@ -180,18 +109,36 @@ index e519e13fea11950cc619e384f774b61a6e2385c0..8289ca0a41da1532692673a3e426e868 + return css_parsing_utils::ConsumePercent( + stream, context, CSSPrimitiveValue::ValueRange::kNonNegative); +} ++ ++const CSSValue* ElectronCornerSmoothing::CSSValueFromComputedStyleInternal( ++ const ComputedStyle& style, ++ const LayoutObject*, ++ bool allow_visited_style, ++ CSSValuePhase value_phase) const { ++ const Length& length = style.ElectronCornerSmoothing(); ++ switch (length.GetType()) { ++ case Length::kAuto: ++ return CSSIdentifierValue::Create(CSSValueID::kSystemUi); ++ case Length::kPercent: ++ return CSSNumericLiteralValue::Create( ++ length.Percent(), CSSPrimitiveValue::UnitType::kPercentage); ++ default: ++ return CSSIdentifierValue::Create(CSSValueID::kNone); ++ } ++} + } // namespace css_longhand } // namespace blink diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -index 5618121a0b5621290a19f147bfbe9bf316fb3f27..bb1bd90371ce847d48ff9a228b098a26d28f5c6d 100644 +index 5618121a0b5621290a19f147bfbe9bf316fb3f27..eae456c4835b79ab6b3fb9cc839b63c33640e21f 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -@@ -3962,4 +3962,12 @@ FitText StyleBuilderConverter::ConvertFitText(StyleResolverState& state, - return FitText(target, method, size_limit); +@@ -3920,6 +3920,15 @@ PositionArea StyleBuilderConverter::ConvertPositionArea( + return PositionArea(span[0], span[1], span[2], span[3]); } -+Length StyleBuilderConverter::ConvertCornerSmoothing(StyleResolverState& state, const CSSValue& value) { ++Length StyleBuilderConverter::ConvertCornerSmoothing(StyleResolverState& state, ++ const CSSValue& value) { + auto* ident = DynamicTo(value); + if (ident && ident->GetValueID() == CSSValueID::kSystemUi) { + return Length::Auto(); @@ -199,74 +146,21 @@ index 5618121a0b5621290a19f147bfbe9bf316fb3f27..bb1bd90371ce847d48ff9a228b098a26 + return ConvertLength(state, value); +} + - } // namespace blink + FitText StyleBuilderConverter::ConvertFitText(StyleResolverState& state, + const CSSValue& value) { + const auto& list = To(value); diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h -index 7104b5866a9bac0cdd26518eddcf80322280ad92..692b186f302130155fbb1b163bb195c0253276af 100644 +index 7104b5866a9bac0cdd26518eddcf80322280ad92..8c1140d107a3144cd8d067577f355647ae8377d9 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h -@@ -422,6 +422,8 @@ class StyleBuilderConverter { +@@ -421,6 +421,7 @@ class StyleBuilderConverter { + const CSSValue&); static PositionArea ConvertPositionArea(StyleResolverState&, const CSSValue&); - static FitText ConvertFitText(StyleResolverState&, const CSSValue&); -+ + static Length ConvertCornerSmoothing(StyleResolverState&, const CSSValue&); + static FitText ConvertFitText(StyleResolverState&, const CSSValue&); }; - template -diff --git a/third_party/blink/renderer/core/exported/web_settings_impl.cc b/third_party/blink/renderer/core/exported/web_settings_impl.cc -index 90692da7bddd9e26e58cb26d8b29dbddf958fbca..6bcd9d736edab85572e405ab74d57adc0fcce921 100644 ---- a/third_party/blink/renderer/core/exported/web_settings_impl.cc -+++ b/third_party/blink/renderer/core/exported/web_settings_impl.cc -@@ -820,4 +820,8 @@ void WebSettingsImpl::SetRootScrollbarThemeColor( - settings_->SetRootScrollbarThemeColor(theme_color); - } - -+void WebSettingsImpl::SetCornerSmoothingCSS(bool available) { -+ settings_->SetElectronCornerSmoothingCSS(available); -+} -+ - } // namespace blink -diff --git a/third_party/blink/renderer/core/exported/web_settings_impl.h b/third_party/blink/renderer/core/exported/web_settings_impl.h -index aa8b248b94ea7f6c0e04dc66e976dc7923ff3a98..868630ed2adb8f40fb7f002d45b260c0881ef10f 100644 ---- a/third_party/blink/renderer/core/exported/web_settings_impl.h -+++ b/third_party/blink/renderer/core/exported/web_settings_impl.h -@@ -238,6 +238,7 @@ class CORE_EXPORT WebSettingsImpl final : public WebSettings { - void SetRequireTransientActivationAndAuthorizationForSubAppsAPIs( - bool) override; - void SetRootScrollbarThemeColor(std::optional) override; -+ void SetCornerSmoothingCSS(bool) override; - - bool RenderVSyncNotificationEnabled() const { - return render_v_sync_notification_enabled_; -diff --git a/third_party/blink/renderer/core/exported/web_view_impl.cc b/third_party/blink/renderer/core/exported/web_view_impl.cc -index f8fae134e122a223440530bd696db899dce2fe56..cec68a428fbf63932066ceb296c3db3eb9e34166 100644 ---- a/third_party/blink/renderer/core/exported/web_view_impl.cc -+++ b/third_party/blink/renderer/core/exported/web_view_impl.cc -@@ -3579,6 +3579,9 @@ void WebViewImpl::UpdateRendererPreferences( - renderer_preferences_.view_source_line_wrap_enabled); - - MaybePreloadSystemFonts(GetPage()); -+ -+ GetSettings()->SetCornerSmoothingCSS( -+ renderer_preferences_.electron_corner_smoothing_css); - } - - void WebViewImpl::SetHistoryIndexAndLength(int32_t history_index, -diff --git a/third_party/blink/renderer/core/frame/settings.json5 b/third_party/blink/renderer/core/frame/settings.json5 -index c96100f7d26c14b8be1329cdb4d8a007b14d9c00..8b2429d5ac958f9a2c7aae546b44da903def8e69 100644 ---- a/third_party/blink/renderer/core/frame/settings.json5 -+++ b/third_party/blink/renderer/core/frame/settings.json5 -@@ -1265,5 +1265,10 @@ - initial: false, - type: "bool" - }, -+ { -+ name: "electronCornerSmoothingCSS", -+ initial: true, -+ invalidate: ["Style"], -+ }, - ], - } diff --git a/third_party/blink/renderer/core/paint/contoured_border_geometry.cc b/third_party/blink/renderer/core/paint/contoured_border_geometry.cc index 2c2f4f405074e5baa4a26f255283404f86b40e21..ebeb7d6988ee9e6a4e78cb82fc01fdad6721eaef 100644 --- a/third_party/blink/renderer/core/paint/contoured_border_geometry.cc @@ -373,7 +267,7 @@ index 0dbfffdfbea2cb75f7f3ea94ead20cc8bbe08bb3..021b9cdebb023941e7a78afbc1c3c939 // A Corner is a axis-aligned quad, with the points ordered (start, outer, diff --git a/third_party/blink/renderer/platform/geometry/path_builder.cc b/third_party/blink/renderer/platform/geometry/path_builder.cc -index 171cb3dd87609f5ecab79a25fe0978cd6e4b04f4..7e7deae45bfb66c3a3702f30092a23fb5b79bf4b 100644 +index 171cb3dd87609f5ecab79a25fe0978cd6e4b04f4..e454999a4ef64156a86cc8e15c11616e563e2489 100644 --- a/third_party/blink/renderer/platform/geometry/path_builder.cc +++ b/third_party/blink/renderer/platform/geometry/path_builder.cc @@ -4,6 +4,7 @@ @@ -384,7 +278,7 @@ index 171cb3dd87609f5ecab79a25fe0978cd6e4b04f4..7e7deae45bfb66c3a3702f30092a23fb #include "third_party/blink/renderer/platform/geometry/contoured_rect.h" #include "third_party/blink/renderer/platform/geometry/infinite_int_rect.h" #include "third_party/blink/renderer/platform/geometry/path.h" -@@ -247,6 +248,26 @@ PathBuilder& PathBuilder::AddContouredRect( +@@ -247,6 +248,32 @@ PathBuilder& PathBuilder::AddContouredRect( AddRoundedRect(target_rect); return *this; } @@ -400,10 +294,16 @@ index 171cb3dd87609f5ecab79a25fe0978cd6e4b04f4..7e7deae45bfb66c3a3702f30092a23fb + float smoothness = std::clamp( + contoured_rect.GetCornerCurvature().Smoothness(), 0.0f, 1.0f); + ++ // Since the Electron implementation of DrawSmoothRoundRect uses one radius ++ // for both dimensions, we need to use the minimum of the two supplied. ++ auto min_radius = [](const gfx::SizeF& radius) -> float { ++ return std::min(radius.width(), radius.height()); ++ }; ++ + builder_.addPath(electron::DrawSmoothRoundRect( + box.x(), box.y(), box.width(), box.height(), smoothness, -+ radii.TopLeft().width(), radii.TopRight().width(), -+ radii.BottomRight().width(), radii.BottomLeft().width())); ++ min_radius(radii.TopLeft()), min_radius(radii.TopRight()), ++ min_radius(radii.BottomRight()), min_radius(radii.BottomLeft()))); + + return *this; + } @@ -411,3 +311,18 @@ index 171cb3dd87609f5ecab79a25fe0978cd6e4b04f4..7e7deae45bfb66c3a3702f30092a23fb const FloatRoundedRect& origin_rect = contoured_rect.GetOriginRect(); // This would include the outer border of the rect, as well as shadow and +diff --git a/third_party/blink/renderer/platform/runtime_enabled_features.json5 b/third_party/blink/renderer/platform/runtime_enabled_features.json5 +index 93c9798d3de30df26314deb87d1ccd0fac7f2336..a77f28fd08581add36e833252cb2f707043ed669 100644 +--- a/third_party/blink/renderer/platform/runtime_enabled_features.json5 ++++ b/third_party/blink/renderer/platform/runtime_enabled_features.json5 +@@ -214,6 +214,10 @@ + }, + + data: [ ++ { ++ name: "ElectronCSSCornerSmoothing", ++ status: "stable", ++ }, + { + name: "Accelerated2dCanvas", + settable_from_internals: true, diff --git a/shell/browser/web_contents_preferences.cc b/shell/browser/web_contents_preferences.cc index 7096c8bc5f81f..5066bc2e00d20 100644 --- a/shell/browser/web_contents_preferences.cc +++ b/shell/browser/web_contents_preferences.cc @@ -149,7 +149,6 @@ void WebContentsPreferences::Clear() { preload_path_ = std::nullopt; v8_cache_options_ = blink::mojom::V8CacheOptions::kDefault; deprecated_paste_enabled_ = false; - corner_smoothing_css_ = true; #if BUILDFLAG(IS_MAC) scroll_bounce_ = false; @@ -229,8 +228,6 @@ void WebContentsPreferences::SetFromDictionary( if (web_preferences.Get(options::kDisableBlinkFeatures, &disable_blink_features)) disable_blink_features_ = disable_blink_features; - web_preferences.Get(options::kEnableCornerSmoothingCSS, - &corner_smoothing_css_); base::FilePath::StringType preload_path; if (web_preferences.Get(options::kPreloadScript, &preload_path)) { @@ -481,8 +478,6 @@ void WebContentsPreferences::OverrideWebkitPrefs( prefs->v8_cache_options = v8_cache_options_; prefs->dom_paste_enabled = deprecated_paste_enabled_; - - renderer_prefs->electron_corner_smoothing_css = corner_smoothing_css_; } WEB_CONTENTS_USER_DATA_KEY_IMPL(WebContentsPreferences); diff --git a/shell/browser/web_contents_preferences.h b/shell/browser/web_contents_preferences.h index 1e0b47631f47e..4bb6132752cc1 100644 --- a/shell/browser/web_contents_preferences.h +++ b/shell/browser/web_contents_preferences.h @@ -134,7 +134,6 @@ class WebContentsPreferences std::optional preload_path_; blink::mojom::V8CacheOptions v8_cache_options_; bool deprecated_paste_enabled_ = false; - bool corner_smoothing_css_; #if BUILDFLAG(IS_MAC) bool scroll_bounce_; diff --git a/shell/common/options_switches.h b/shell/common/options_switches.h index 1e2aad82727f3..b07313f033ec1 100644 --- a/shell/common/options_switches.h +++ b/shell/common/options_switches.h @@ -219,9 +219,6 @@ inline constexpr std::string_view kSpellcheck = "spellcheck"; inline constexpr std::string_view kEnableDeprecatedPaste = "enableDeprecatedPaste"; -// Whether the -electron-corner-smoothing CSS rule is enabled. -inline constexpr std::string_view kEnableCornerSmoothingCSS = - "enableCornerSmoothingCSS"; } // namespace options // Following are actually command line switches, should be moved to other files. diff --git a/shell/renderer/electron_smooth_round_rect.cc b/shell/renderer/electron_smooth_round_rect.cc index e78f7cf0df43b..58bbc49152cc8 100644 --- a/shell/renderer/electron_smooth_round_rect.cc +++ b/shell/renderer/electron_smooth_round_rect.cc @@ -6,6 +6,7 @@ #include #include "base/check.h" +#include "base/check_op.h" namespace electron { @@ -263,13 +264,14 @@ SkPath DrawSmoothRoundRect(float x, float top_right_radius, float bottom_right_radius, float bottom_left_radius) { - DCHECK(0.0f <= smoothness && smoothness <= 1.0f); + DCHECK_GE(smoothness, 0.0f); + DCHECK_LE(smoothness, 1.0f); // Assume the radii are already constrained within the rectangle size - DCHECK(top_left_radius + top_right_radius <= width); - DCHECK(bottom_left_radius + bottom_right_radius <= width); - DCHECK(top_left_radius + bottom_left_radius <= height); - DCHECK(top_right_radius + bottom_right_radius <= height); + DCHECK_LE(top_left_radius + top_right_radius, width); + DCHECK_LE(bottom_left_radius + bottom_right_radius, width); + DCHECK_LE(top_left_radius + bottom_left_radius, height); + DCHECK_LE(top_right_radius + bottom_right_radius, height); if (width <= 0.0f || height <= 0.0f) { return SkPath(); diff --git a/spec/api-corner-smoothing-spec.ts b/spec/api-corner-smoothing-spec.ts index 2ca9285832a28..804162509281f 100644 --- a/spec/api-corner-smoothing-spec.ts +++ b/spec/api-corner-smoothing-spec.ts @@ -85,7 +85,7 @@ async function pageCaptureTestRecipe ( height: 600, useContentSize: true, webPreferences: { - enableCornerSmoothingCSS: cornerSmoothingAvailable + disableBlinkFeatures: cornerSmoothingAvailable ? undefined : 'ElectronCSSCornerSmoothing' } }); await w.loadFile(pagePath); From 5ba15973409d5b82b50657874dc067a0390b485f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 17 Jul 2025 10:09:13 +0200 Subject: [PATCH 151/186] fix: deprecation warning crash when no Node.js environment available (#47771) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/common/node_util.cc | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) diff --git a/shell/common/node_util.cc b/shell/common/node_util.cc index 57090f8d3c00b..448329c430dc1 100644 --- a/shell/common/node_util.cc +++ b/shell/common/node_util.cc @@ -66,8 +66,13 @@ void EmitWarning(const std::string_view warning_msg, void EmitWarning(v8::Isolate* isolate, const std::string_view warning_msg, const std::string_view warning_type) { - node::ProcessEmitWarningGeneric(node::Environment::GetCurrent(isolate), - warning_msg, warning_type); + node::Environment* env = node::Environment::GetCurrent(isolate); + if (!env) { + // No Node.js environment available, fall back to console logging. + LOG(WARNING) << "[" << warning_type << "] " << warning_msg; + return; + } + node::ProcessEmitWarningGeneric(env, warning_msg, warning_type); } void EmitDeprecationWarning(const std::string_view warning_msg, @@ -79,8 +84,14 @@ void EmitDeprecationWarning(const std::string_view warning_msg, void EmitDeprecationWarning(v8::Isolate* isolate, const std::string_view warning_msg, const std::string_view deprecation_code) { - node::ProcessEmitWarningGeneric(node::Environment::GetCurrent(isolate), - warning_msg, "DeprecationWarning", + node::Environment* env = node::Environment::GetCurrent(isolate); + if (!env) { + // No Node.js environment available, fall back to console logging. + LOG(WARNING) << "[DeprecationWarning] " << warning_msg + << " (code: " << deprecation_code << ")"; + return; + } + node::ProcessEmitWarningGeneric(env, warning_msg, "DeprecationWarning", deprecation_code); } From f4ae0dc342f496ac53fc0638034e3676b3f60eee Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 17 Jul 2025 12:13:19 +0200 Subject: [PATCH 152/186] test: cleanup RenderFrame lifespan tests (#47794) * test: cleanup RenderFrame lifespan tests Co-authored-by: John Kleinschmidt * test: disable navigator.serial tests on arm64 mac debug the hang test: disable navigator.bluetooth on arm64 mac Revert "test: disable navigator.bluetooth on arm64 mac" This reverts commit 4b53a8485a5ff391832c7da93d859f1aa8722e70. Revert "debug the hang" This reverts commit 00338f0d49a7918224822087b4510fa9db0686c3. Revert "test: disable navigator.serial tests on arm64 mac" This reverts commit fb515ce447a9d42185e84b17b460e4fb6d1bf71d. Reapply "test: disable navigator.serial tests on arm64 mac" This reverts commit 0e5608108ffebbe8b8b27af9ea06aadae2ea85dd. Reapply "test: disable navigator.bluetooth on arm64 mac" This reverts commit f4c7d3fc0624a22421cba5d3d75df8c5d4367eea. fixup Co-authored-by: John Kleinschmidt * test: add waitUntil for flaky test Co-authored-by: John Kleinschmidt --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- spec/api-web-frame-main-spec.ts | 5 ++++- spec/chromium-spec.ts | 4 ++-- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/spec/api-web-frame-main-spec.ts b/spec/api-web-frame-main-spec.ts index 236140780a884..9f583786f2157 100644 --- a/spec/api-web-frame-main-spec.ts +++ b/spec/api-web-frame-main-spec.ts @@ -313,6 +313,7 @@ describe('webFrameMain module', () => { beforeEach(async () => { w = new BrowserWindow({ show: false }); }); + afterEach(closeAllWindows); // TODO(jkleinsc) fix this flaky test on linux ifit(process.platform !== 'linux')('throws upon accessing properties when disposed', async () => { @@ -373,7 +374,9 @@ describe('webFrameMain module', () => { await w.webContents.loadURL(server.crossOriginUrl); // senderFrame now points to a disposed RenderFrameHost. It should // be null when attempting to access the lazily evaluated property. - expect(event.senderFrame).to.be.null(); + waitUntil(() => { + return event.senderFrame === null; + }); }); it('is detached when unload handler sends IPC', async () => { diff --git a/spec/chromium-spec.ts b/spec/chromium-spec.ts index f7db52bf31ba5..635ac6889c257 100644 --- a/spec/chromium-spec.ts +++ b/spec/chromium-spec.ts @@ -3089,7 +3089,7 @@ describe('iframe using HTML fullscreen API while window is OS-fullscreened', () }); }); -describe('navigator.serial', () => { +ifdescribe(process.platform !== 'darwin' || process.arch !== 'arm64')('navigator.serial', () => { let w: BrowserWindow; before(async () => { w = new BrowserWindow({ @@ -3629,7 +3629,7 @@ ifdescribe((process.platform !== 'linux' || app.isUnityRunning()))('navigator.se }); }); -describe('navigator.bluetooth', () => { +ifdescribe(process.platform !== 'darwin' || process.arch !== 'arm64')('navigator.bluetooth', () => { let w: BrowserWindow; before(async () => { w = new BrowserWindow({ From 87cdc1e9941302286fac6db23ba14d8cbccb5bff Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 17 Jul 2025 11:34:56 -0400 Subject: [PATCH 153/186] test: fix extensions console flake (#47789) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- spec/extensions-spec.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/extensions-spec.ts b/spec/extensions-spec.ts index fe246b05ad0ca..52e31132c07c8 100644 --- a/spec/extensions-spec.ts +++ b/spec/extensions-spec.ts @@ -18,7 +18,7 @@ const uuid = require('uuid'); const fixtures = path.join(__dirname, 'fixtures'); describe('chrome extensions', () => { - const emptyPage = ''; + const emptyPage = '

EMPTY PAGE

'; // NB. extensions are only allowed on http://, https:// and ftp:// (!) urls by default. let server: http.Server; From 87682eff7f37998b1bff35c0ea8a1f983f86cdd1 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Thu, 17 Jul 2025 11:36:50 -0400 Subject: [PATCH 154/186] chore: bump chromium to 138.0.7204.157 (37-x-y) (#47773) * chore: bump chromium in DEPS to 138.0.7204.157 * chore: update patches * chore: update patches --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt Co-authored-by: Shelley Vohr Co-authored-by: patchup[bot] <73610968+patchup[bot]@users.noreply.github.com> --- DEPS | 2 +- ...not_depend_on_packed_resource_integrity.patch | 2 +- ...r_smoothing_css_rule_and_blink_painting.patch | 6 +++--- patches/chromium/make_gtk_getlibgtk_public.patch | 16 ++++++++-------- 4 files changed, 13 insertions(+), 13 deletions(-) diff --git a/DEPS b/DEPS index 75b990c16b8c1..424c9cb7f1c78 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.100', + '138.0.7204.157', 'node_version': 'v22.17.0', 'nan_version': diff --git a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch index 23c000d2d5947..92e60c3f95f99 100644 --- a/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch +++ b/patches/chromium/build_do_not_depend_on_packed_resource_integrity.patch @@ -46,7 +46,7 @@ index 36fe07a692e9be5b99f9e59157b90963a6485f8b..d8cf68e953213f309537e74d954d8749 # than here in :chrome_dll. deps += [ "//chrome:packed_resources_integrity_header" ] diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn -index 0f493aeb49901e2917009b942f9b1e14e3fcf758..349079dc25f91fd426d523345ba66271c42ea084 100644 +index 6fba5b32b266455d308ac11e2711588b78092c33..5905f62c8b516483026ee95a3dea4cda5f1161b1 100644 --- a/chrome/test/BUILD.gn +++ b/chrome/test/BUILD.gn @@ -7243,9 +7243,12 @@ test("unit_tests") { diff --git a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch index bff7a0db9eee3..dc83246ed4a2d 100644 --- a/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch +++ b/patches/chromium/feat_corner_smoothing_css_rule_and_blink_painting.patch @@ -130,7 +130,7 @@ index e519e13fea11950cc619e384f774b61a6e2385c0..04746566454401402c21f6381a7a7f0f } // namespace css_longhand } // namespace blink diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc -index 5618121a0b5621290a19f147bfbe9bf316fb3f27..eae456c4835b79ab6b3fb9cc839b63c33640e21f 100644 +index 501ef6ba6203fc2661ab36825c4a1b4eee172841..1314bfc4c368be031200fc1555a4db51d27491a7 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.cc @@ -3920,6 +3920,15 @@ PositionArea StyleBuilderConverter::ConvertPositionArea( @@ -150,7 +150,7 @@ index 5618121a0b5621290a19f147bfbe9bf316fb3f27..eae456c4835b79ab6b3fb9cc839b63c3 const CSSValue& value) { const auto& list = To(value); diff --git a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h -index 7104b5866a9bac0cdd26518eddcf80322280ad92..8c1140d107a3144cd8d067577f355647ae8377d9 100644 +index 141de7c9f9d630125cf37be73347a05a6a475aba..b07129478590b6aad6f054be09c22f8f48c60920 100644 --- a/third_party/blink/renderer/core/css/resolver/style_builder_converter.h +++ b/third_party/blink/renderer/core/css/resolver/style_builder_converter.h @@ -421,6 +421,7 @@ class StyleBuilderConverter { @@ -312,7 +312,7 @@ index 171cb3dd87609f5ecab79a25fe0978cd6e4b04f4..e454999a4ef64156a86cc8e15c11616e // This would include the outer border of the rect, as well as shadow and diff --git a/third_party/blink/renderer/platform/runtime_enabled_features.json5 b/third_party/blink/renderer/platform/runtime_enabled_features.json5 -index 93c9798d3de30df26314deb87d1ccd0fac7f2336..a77f28fd08581add36e833252cb2f707043ed669 100644 +index 7b24b556fcfc16ccb67e28e2d8a0753355d07497..ceb5c8e46515a9a8345c0feee801708bfca71310 100644 --- a/third_party/blink/renderer/platform/runtime_enabled_features.json5 +++ b/third_party/blink/renderer/platform/runtime_enabled_features.json5 @@ -214,6 +214,10 @@ diff --git a/patches/chromium/make_gtk_getlibgtk_public.patch b/patches/chromium/make_gtk_getlibgtk_public.patch index fc6108e88b1b5..7d3ef56489a19 100644 --- a/patches/chromium/make_gtk_getlibgtk_public.patch +++ b/patches/chromium/make_gtk_getlibgtk_public.patch @@ -7,10 +7,10 @@ Allows embedders to get a handle to the gdk_pixbuf library already loaded in the process. diff --git a/ui/gtk/gtk_compat.cc b/ui/gtk/gtk_compat.cc -index 37bb48273cf4833c88622f1158aebfee9423d085..2009a095abfae3207d73c47245e061ff3f9cef80 100644 +index bcd86e7a9e870b274d0c6487a691f23ad1888079..4b192c90ce82ddddaedf14970919447e8f43dd7c 100644 --- a/ui/gtk/gtk_compat.cc +++ b/ui/gtk/gtk_compat.cc -@@ -69,11 +69,6 @@ void* GetLibGio() { +@@ -68,11 +68,6 @@ void* GetLibGio() { return libgio; } @@ -22,7 +22,7 @@ index 37bb48273cf4833c88622f1158aebfee9423d085..2009a095abfae3207d73c47245e061ff void* GetLibGdk3() { static void* libgdk3 = DlOpen("libgdk-3.so.0"); return libgdk3; -@@ -169,6 +164,11 @@ gfx::Insets InsetsFromGtkBorder(const GtkBorder& border) { +@@ -165,6 +160,11 @@ gfx::Insets InsetsFromGtkBorder(const GtkBorder& border) { } // namespace @@ -31,14 +31,14 @@ index 37bb48273cf4833c88622f1158aebfee9423d085..2009a095abfae3207d73c47245e061ff + return libgdk_pixbuf; +} + - bool LoadGtk() { - static bool loaded = LoadGtkImpl(); + bool LoadGtk(ui::LinuxUiBackend backend) { + static bool loaded = LoadGtkImpl(backend); return loaded; diff --git a/ui/gtk/gtk_compat.h b/ui/gtk/gtk_compat.h -index 19f73cc179d82a3729c5fe37883460ac05f4d0c3..17aa0b95bd6158ed02c03095c1687185a057fe62 100644 +index 841e2e8fcdbe2da4aac487badd4d352476e461a2..e458df649546fa3bee10e24f0edac147186cc152 100644 --- a/ui/gtk/gtk_compat.h +++ b/ui/gtk/gtk_compat.h -@@ -41,6 +41,9 @@ using SkColor = uint32_t; +@@ -42,6 +42,9 @@ using SkColor = uint32_t; namespace gtk { @@ -46,5 +46,5 @@ index 19f73cc179d82a3729c5fe37883460ac05f4d0c3..17aa0b95bd6158ed02c03095c1687185 +void* GetLibGdkPixbuf(); + // Loads libgtk and related libraries and returns true on success. - bool LoadGtk(); + bool LoadGtk(ui::LinuxUiBackend backend); From fe378a43cdcc22ff2f8c72e0592f45b4ac96004d Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 17 Jul 2025 11:41:40 -0400 Subject: [PATCH 155/186] build: deep update brace-expansion to resolve an audit alert (#47721) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- yarn.lock | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/yarn.lock b/yarn.lock index 4ff9dd5afc01d..9c05dbf4fa63b 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1669,17 +1669,17 @@ boolean@^3.0.1: integrity sha512-d0II/GO9uf9lfUHH2BQsjxzRJZBdsjgsBiW4BvhWk/3qoKwQFjIDVN19PfX8F2D/r9PCMTtLWjYVCFrpeYUzsw== brace-expansion@^1.1.7: - version "1.1.11" - resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" - integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== + version "1.1.12" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.12.tgz#ab9b454466e5a8cc3a187beaad580412a9c5b843" + integrity sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg== dependencies: balanced-match "^1.0.0" concat-map "0.0.1" brace-expansion@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.1.tgz#1edc459e0f0c548486ecf9fc99f2221364b9a0ae" - integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA== + version "2.0.2" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.2.tgz#54fc53237a613d854c7bd37463aad17df87214e7" + integrity sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ== dependencies: balanced-match "^1.0.0" From d5c68c2f6d9b6624456be7ccf061869063be9284 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 18 Jul 2025 10:09:35 +0200 Subject: [PATCH 156/186] fix: handle missing `NativeWindowMac` in `ElectronNSWindow` (#47813) fix: handle missing NativeWindowMac in ElectronNSWindow Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/ui/cocoa/electron_ns_window.mm | 31 ++++++++++++-------- 1 file changed, 18 insertions(+), 13 deletions(-) diff --git a/shell/browser/ui/cocoa/electron_ns_window.mm b/shell/browser/ui/cocoa/electron_ns_window.mm index 3d5daec5df2d2..007997838699d 100644 --- a/shell/browser/ui/cocoa/electron_ns_window.mm +++ b/shell/browser/ui/cocoa/electron_ns_window.mm @@ -173,10 +173,8 @@ - (void)cleanup { } - (id)accessibilityFocusedUIElement { - views::Widget* widget = shell_->widget(); - id superFocus = [super accessibilityFocusedUIElement]; - if (!widget || shell_->IsFocused()) - return superFocus; + if (!shell_ || !shell_->widget() || shell_->IsFocused()) + return [super accessibilityFocusedUIElement]; return nil; } - (NSRect)originalContentRectForFrameRect:(NSRect)frameRect { @@ -184,7 +182,7 @@ - (NSRect)originalContentRectForFrameRect:(NSRect)frameRect { } - (NSTouchBar*)makeTouchBar { - if (shell_->touch_bar()) + if (shell_ && shell_->touch_bar()) return [shell_->touch_bar() makeTouchBar]; else return nil; @@ -214,7 +212,8 @@ - (void)sendEvent:(NSEvent*)event { } - (void)rotateWithEvent:(NSEvent*)event { - shell_->NotifyWindowRotateGesture(event.rotation); + if (shell_) + shell_->NotifyWindowRotateGesture(event.rotation); } - (NSRect)contentRectForFrameRect:(NSRect)frameRect { @@ -238,7 +237,7 @@ - (NSRect)constrainFrameRect:(NSRect)frameRect toScreen:(NSScreen*)screen { // // If there's no frame, put the window wherever the developer // wanted it to go - if (shell_->has_frame()) { + if (shell_ && shell_->has_frame()) { result.size = frameRect.size; } else { result = frameRect; @@ -285,7 +284,7 @@ - (id)accessibilityAttributeValue:(NSString*)attribute { } - (NSString*)accessibilityTitle { - return base::SysUTF8ToNSString(shell_->GetTitle()); + return base::SysUTF8ToNSString(shell_ ? shell_->GetTitle() : ""); } - (BOOL)canBecomeMainWindow { @@ -305,7 +304,7 @@ - (BOOL)validateUserInterfaceItem:(id)item { // support closing a window without title we need to manually do menu item // validation. This code path is used by the "roundedCorners" option. if ([item action] == @selector(performClose:)) - return shell_->IsClosable(); + return shell_ && shell_->IsClosable(); return [super validateUserInterfaceItem:item]; } @@ -325,7 +324,8 @@ - (void)disableHeadlessMode { // shown, but we don't want the headless behavior of allowing the window to // be placed unconstrained. self.isHeadless = false; - shell_->widget()->DisableHeadlessMode(); + if (shell_->widget()) + shell_->widget()->DisableHeadlessMode(); } } @@ -375,6 +375,9 @@ - (void)performClose:(id)sender { } - (BOOL)toggleFullScreenMode:(id)sender { + if (!shell_) + return NO; + bool is_simple_fs = shell_->IsSimpleFullScreen(); bool always_simple_fs = shell_->always_simple_fullscreen(); @@ -408,11 +411,13 @@ - (BOOL)toggleFullScreenMode:(id)sender { } - (void)performMiniaturize:(id)sender { - if (shell_->title_bar_style() == - electron::NativeWindowMac::TitleBarStyle::kCustomButtonsOnHover) + if (shell_ && + shell_->title_bar_style() == + electron::NativeWindowMac::TitleBarStyle::kCustomButtonsOnHover) { [self miniaturize:self]; - else + } else { [super performMiniaturize:sender]; + } } @end From 9e3b0366e54a557b826b22974e4ae821c58d62c8 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 18 Jul 2025 11:04:45 +0200 Subject: [PATCH 157/186] test: re-enable native module tests (#47803) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .../pipeline-segment-electron-test.yml | 1 - spec/api-browser-window-spec.ts | 47 ------------------- 2 files changed, 48 deletions(-) diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index ae2a19b30ae9d..77010f1ea559a 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -194,7 +194,6 @@ jobs: MOCHA_REPORTER: mocha-multi-reporters MOCHA_MULTI_REPORTERS: mocha-junit-reporter, tap ELECTRON_DISABLE_SECURITY_WARNINGS: 1 - ELECTRON_SKIP_NATIVE_MODULE_TESTS: true DISPLAY: ':99.0' NPM_CONFIG_MSVS_VERSION: '2022' run: | diff --git a/spec/api-browser-window-spec.ts b/spec/api-browser-window-spec.ts index 71b62eeb77faa..41a0507891039 100755 --- a/spec/api-browser-window-spec.ts +++ b/spec/api-browser-window-spec.ts @@ -1,4 +1,3 @@ -import { nativeImage } from 'electron'; import { app, BrowserWindow, BrowserView, dialog, ipcMain, OnBeforeSendHeadersListenerDetails, net, protocol, screen, webContents, webFrameMain, session, WebContents, WebFrameMain } from 'electron/main'; import { expect } from 'chai'; @@ -6676,52 +6675,6 @@ describe('BrowserWindow module', () => { }); }); - describe('offscreen rendering image', () => { - afterEach(closeAllWindows); - - const imagePath = path.join(fixtures, 'assets', 'osr.png'); - const targetImage = nativeImage.createFromPath(imagePath); - const nativeModulesEnabled = !process.env.ELECTRON_SKIP_NATIVE_MODULE_TESTS; - ifit(nativeModulesEnabled && ['win32'].includes(process.platform))('use shared texture, hardware acceleration enabled', (done) => { - const { ExtractPixels, InitializeGpu } = require('@electron-ci/osr-gpu'); - - try { - InitializeGpu(); - } catch (e) { - console.log('Failed to initialize GPU, this spec needs a valid GPU device. Skipping...'); - console.error(e); - done(); - return; - } - - const w = new BrowserWindow({ - show: false, - webPreferences: { - offscreen: { - useSharedTexture: true - } - }, - transparent: true, - frame: false, - width: 128, - height: 128 - }); - - w.webContents.once('paint', async (e, dirtyRect) => { - try { - expect(e.texture).to.be.not.null(); - const pixels = ExtractPixels(e.texture!.textureInfo); - const img = nativeImage.createFromBitmap(pixels, { width: dirtyRect.width, height: dirtyRect.height, scaleFactor: 1 }); - expect(img.toBitmap().equals(targetImage.toBitmap())).to.equal(true); - done(); - } catch (e) { - done(e); - } - }); - w.loadFile(imagePath); - }); - }); - describe('"transparent" option', () => { afterEach(closeAllWindows); From 6c9bbdf72a0f42ee7bf7f440d8bdc542480dba4f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 18 Jul 2025 11:04:58 +0200 Subject: [PATCH 158/186] build(dev-deps): drop unused @types/webpack dep (#47808) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- package.json | 1 - yarn.lock | 11 +---------- 2 files changed, 1 insertion(+), 11 deletions(-) diff --git a/package.json b/package.json index 8f6c837ddfa47..a7fbb1b712097 100644 --- a/package.json +++ b/package.json @@ -18,7 +18,6 @@ "@types/semver": "^7.5.8", "@types/stream-json": "^1.7.7", "@types/temp": "^0.9.4", - "@types/webpack": "^5.28.5", "@types/webpack-env": "^1.18.5", "@typescript-eslint/eslint-plugin": "^8.7.0", "@typescript-eslint/parser": "^8.7.0", diff --git a/yarn.lock b/yarn.lock index 9c05dbf4fa63b..05eef81f0ca3b 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1063,15 +1063,6 @@ resolved "https://registry.yarnpkg.com/@types/webpack-env/-/webpack-env-1.18.5.tgz#eccda0b04fe024bed505881e2e532f9c119169bf" integrity sha512-wz7kjjRRj8/Lty4B+Kr0LN6Ypc/3SymeCCGSbaXp2leH0ZVg/PriNiOwNj4bD4uphI7A8NXS4b6Gl373sfO5mA== -"@types/webpack@^5.28.5": - version "5.28.5" - resolved "https://registry.yarnpkg.com/@types/webpack/-/webpack-5.28.5.tgz#0e9d9a15efa09bbda2cef41356ca4ac2031ea9a2" - integrity sha512-wR87cgvxj3p6D0Crt1r5avwqffqPXUkNlnQ1mjU93G7gCuFjufZR4I6j8cz5g1F1tTYpfOOFvly+cmIQwL9wvw== - dependencies: - "@types/node" "*" - tapable "^2.2.0" - webpack "^5" - "@types/yauzl@^2.9.1": version "2.10.0" resolved "https://registry.yarnpkg.com/@types/yauzl/-/yauzl-2.10.0.tgz#b3248295276cf8c6f153ebe6a9aba0c988cb2599" @@ -8125,7 +8116,7 @@ webpack-sources@^3.2.3: resolved "https://registry.yarnpkg.com/webpack-sources/-/webpack-sources-3.2.3.tgz#2d4daab8451fd4b240cc27055ff6a0c2ccea0cde" integrity sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w== -webpack@^5, webpack@^5.95.0: +webpack@^5.95.0: version "5.95.0" resolved "https://registry.yarnpkg.com/webpack/-/webpack-5.95.0.tgz#8fd8c454fa60dad186fbe36c400a55848307b4c0" integrity sha512-2t3XstrKULz41MNMBF+cJ97TyHdyQ8HCt//pqErqDvNjU9YQBnZxIHa11VXsi7F3mb5/aO2tuDxdeTPdU7xu9Q== From 7f00dc74db0859ad0f32f832321e9dab7716af55 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Fri, 18 Jul 2025 14:44:40 +0200 Subject: [PATCH 159/186] ci: remove `kTCCServiceMicrophone` change (#47822) ci: remove kTCCServiceMicrophone change Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .github/workflows/pipeline-segment-electron-test.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index 77010f1ea559a..108c971e72e1a 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -100,7 +100,6 @@ jobs: } userValuesArray=( - "'kTCCServiceMicrophone','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" "'kTCCServiceCamera','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" "'kTCCServiceBluetoothAlways','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" "'kTCCServiceAppleEvents','/usr/local/opt/runner/provisioner/provisioner',1,2,4,1,NULL,NULL,0,'UNUSED',NULL,0,1687786159" From 36aba22fee9de581815ed34b346cac4eb30b6841 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Fri, 18 Jul 2025 14:45:38 +0200 Subject: [PATCH 160/186] chore: bump node to v22.17.1 (37-x-y) (#47774) * chore: bump node in DEPS to v22.17.1 * chore: update patches --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: patchup[bot] <73610968+patchup[bot]@users.noreply.github.com> --- DEPS | 2 +- patches/node/build_compile_with_c_20_support.patch | 2 +- ...ure_native_module_compilation_fails_if_not_using_a_new.patch | 2 +- .../node/build_restore_clang_as_default_compiler_on_macos.patch | 2 +- .../fix_add_default_values_for_variables_in_common_gypi.patch | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/DEPS b/DEPS index 424c9cb7f1c78..46b1b2ad05799 100644 --- a/DEPS +++ b/DEPS @@ -4,7 +4,7 @@ vars = { 'chromium_version': '138.0.7204.157', 'node_version': - 'v22.17.0', + 'v22.17.1', 'nan_version': 'e14bdcd1f72d62bca1d541b66da43130384ec213', 'squirrel.mac_version': diff --git a/patches/node/build_compile_with_c_20_support.patch b/patches/node/build_compile_with_c_20_support.patch index 83862862dcd55..b16baaf70f9e5 100644 --- a/patches/node/build_compile_with_c_20_support.patch +++ b/patches/node/build_compile_with_c_20_support.patch @@ -10,7 +10,7 @@ V8 requires C++20 support as of https://chromium-review.googlesource.com/c/v8/v8 This can be removed when Electron upgrades to a version of Node.js containing the required V8 version. diff --git a/common.gypi b/common.gypi -index 03fefab4b0a9727925411b95310831ffdc33e8d9..f9b5e47f1d67807435529c99d12f419d0fd4269f 100644 +index acfc02510ee1ce34a3f410a7a4ce53adb42abd35..b9264bfb1170928431848bb2b99e4f0dfbe8f95a 100644 --- a/common.gypi +++ b/common.gypi @@ -538,7 +538,7 @@ diff --git a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch index 259c40e0aeb53..8118eaac97d4b 100644 --- a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch +++ b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch @@ -7,7 +7,7 @@ Subject: build: ensure native module compilation fails if not using a new This should not be upstreamed, it is a quality-of-life patch for downstream module builders. diff --git a/common.gypi b/common.gypi -index bfe567e016cf102d2087f7647e64cc051116ab8d..03fefab4b0a9727925411b95310831ffdc33e8d9 100644 +index cf643bcd0bc9080b80bf12afeebc69f2db74bb54..acfc02510ee1ce34a3f410a7a4ce53adb42abd35 100644 --- a/common.gypi +++ b/common.gypi @@ -89,6 +89,8 @@ diff --git a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch index d7262f8fc5c5a..7901c967e9195 100644 --- a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch +++ b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch @@ -11,7 +11,7 @@ node-gyp will use the result of `process.config` that reflects the environment in which the binary got built. diff --git a/common.gypi b/common.gypi -index f9b5e47f1d67807435529c99d12f419d0fd4269f..c99f583d3674347dd6eb9a5eea1ed5588e376d31 100644 +index b9264bfb1170928431848bb2b99e4f0dfbe8f95a..836d96a1bd9c1d5568f0045bbddddca1edb1a0ce 100644 --- a/common.gypi +++ b/common.gypi @@ -128,6 +128,7 @@ diff --git a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch index e2f7f19bc3655..c460fa71649eb 100644 --- a/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch +++ b/patches/node/fix_add_default_values_for_variables_in_common_gypi.patch @@ -7,7 +7,7 @@ common.gypi is a file that's included in the node header bundle, despite the fact that we do not build node with gyp. diff --git a/common.gypi b/common.gypi -index a73d4401f26d8493802d3ecec3e015a77717720a..bfe567e016cf102d2087f7647e64cc051116ab8d 100644 +index b88371ec13da5a287e18f7224bb4970fc94dce66..cf643bcd0bc9080b80bf12afeebc69f2db74bb54 100644 --- a/common.gypi +++ b/common.gypi @@ -91,6 +91,23 @@ From 2e460c0ffb79b7efd10bf9fcf5b8dff9da4b906a Mon Sep 17 00:00:00 2001 From: Shelley Vohr Date: Sat, 19 Jul 2025 10:42:19 +0200 Subject: [PATCH 161/186] refactor: reduce scope of temporaries when getting dictionary values (#47799) refactor: reduce scale of temporaries when getting dictionary values Co-authored-by: Charles Kerr --- shell/browser/native_window.cc | 78 +++++++++++----------------- shell/browser/native_window_mac.mm | 9 ++-- shell/browser/native_window_views.cc | 49 ++++++----------- 3 files changed, 48 insertions(+), 88 deletions(-) diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 36fff501b2047..5a9a189298f68 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -134,19 +134,17 @@ NativeWindow::~NativeWindow() { void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { // Setup window from options. - int x = -1, y = -1; - bool center; - if (options.Get(options::kX, &x) && options.Get(options::kY, &y)) { - SetPosition(gfx::Point(x, y)); + if (int x, y; options.Get(options::kX, &x) && options.Get(options::kY, &y)) { + SetPosition(gfx::Point{x, y}); #if BUILDFLAG(IS_WIN) // FIXME(felixrieseberg): Dirty, dirty workaround for // https://github.com/electron/electron/issues/10862 // Somehow, we need to call `SetBounds` twice to get // usable results. The root cause is still unknown. - SetPosition(gfx::Point(x, y)); + SetPosition(gfx::Point{x, y}); #endif - } else if (options.Get(options::kCenter, ¢er) && center) { + } else if (bool center; options.Get(options::kCenter, ¢er) && center) { Center(); } @@ -185,27 +183,21 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { SetSizeConstraints(size_constraints); } #if BUILDFLAG(IS_WIN) || BUILDFLAG(IS_LINUX) - bool closable; - if (options.Get(options::kClosable, &closable)) { - SetClosable(closable); - } + if (bool val; options.Get(options::kClosable, &val)) + SetClosable(val); #endif - bool movable; - if (options.Get(options::kMovable, &movable)) { - SetMovable(movable); - } - bool has_shadow; - if (options.Get(options::kHasShadow, &has_shadow)) { - SetHasShadow(has_shadow); - } - double opacity; - if (options.Get(options::kOpacity, &opacity)) { - SetOpacity(opacity); - } - bool top; - if (options.Get(options::kAlwaysOnTop, &top) && top) { + + if (bool val; options.Get(options::kMovable, &val)) + SetMovable(val); + + if (bool val; options.Get(options::kHasShadow, &val)) + SetHasShadow(val); + + if (double val; options.Get(options::kOpacity, &val)) + SetOpacity(val); + + if (bool val; options.Get(options::kAlwaysOnTop, &val) && val) SetAlwaysOnTop(ui::ZOrderLevel::kFloatingWindow); - } bool fullscreenable = true; bool fullscreen = false; @@ -222,29 +214,21 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { if (fullscreen) SetFullScreen(true); - bool resizable; - if (options.Get(options::kResizable, &resizable)) { - SetResizable(resizable); - } + if (bool val; options.Get(options::kResizable, &val)) + SetResizable(val); + + if (bool val; options.Get(options::kSkipTaskbar, &val)) + SetSkipTaskbar(val); + + if (bool val; options.Get(options::kKiosk, &val) && val) + SetKiosk(val); - bool skip; - if (options.Get(options::kSkipTaskbar, &skip)) { - SetSkipTaskbar(skip); - } - bool kiosk; - if (options.Get(options::kKiosk, &kiosk) && kiosk) { - SetKiosk(kiosk); - } #if BUILDFLAG(IS_MAC) - std::string type; - if (options.Get(options::kVibrancyType, &type)) { - SetVibrancy(type, 0); - } + if (std::string val; options.Get(options::kVibrancyType, &val)) + SetVibrancy(val, 0); #elif BUILDFLAG(IS_WIN) - std::string material; - if (options.Get(options::kBackgroundMaterial, &material)) { - SetBackgroundMaterial(material); - } + if (std::string val; options.Get(options::kBackgroundMaterial, &val)) + SetBackgroundMaterial(val); #endif SkColor background_color = SK_ColorWHITE; @@ -255,9 +239,7 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { } SetBackgroundColor(background_color); - std::string title(Browser::Get()->GetName()); - options.Get(options::kTitle, &title); - SetTitle(title); + SetTitle(options.ValueOrDefault(options::kTitle, Browser::Get()->GetName())); // Then show it. if (options.ValueOrDefault(options::kShow, true)) diff --git a/shell/browser/native_window_mac.mm b/shell/browser/native_window_mac.mm index 4e3c14b399eb3..2b26687624bb0 100644 --- a/shell/browser/native_window_mac.mm +++ b/shell/browser/native_window_mac.mm @@ -239,8 +239,7 @@ static bool FromV8(v8::Isolate* isolate, [window_ setLevel:NSFloatingWindowLevel]; } - bool focusable; - if (options.Get(options::kFocusable, &focusable) && !focusable) + if (bool val; options.Get(options::kFocusable, &val) && !val) [window_ setDisableKeyOrMainWindow:YES]; if (transparent() || !has_frame()) { @@ -285,12 +284,10 @@ static bool FromV8(v8::Isolate* isolate, // NOTE(@mlaurencin) Spec requirements can be found here: // https://developer.mozilla.org/en-US/docs/Web/API/Window/open#width constexpr int kMinSizeReqdBySpec = 100; - int inner_width = 0; - int inner_height = 0; + const int inner_width = options.ValueOrDefault(options::kinnerWidth, 0); + const int inner_height = options.ValueOrDefault(options::kinnerHeight, 0); bool use_content_size = options.ValueOrDefault(options::kUseContentSize, false); - options.Get(options::kinnerWidth, &inner_width); - options.Get(options::kinnerHeight, &inner_height); if (inner_width || inner_height) { use_content_size = true; if (inner_width) diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index fff2c9dd9a88c..02a9bb3eab438 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -197,9 +197,8 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, : NativeWindow(options, parent) { options.Get(options::kTitle, &title_); - bool menu_bar_autohide; - if (options.Get(options::kAutoHideMenuBar, &menu_bar_autohide)) - root_view_.SetAutoHideMenuBar(menu_bar_autohide); + if (bool val; options.Get(options::kAutoHideMenuBar, &val)) + root_view_.SetAutoHideMenuBar(val); #if BUILDFLAG(IS_WIN) // On Windows we rely on the CanResize() to indicate whether window can be @@ -216,35 +215,20 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, overlay_button_color_ = color_utils::GetSysSkColor(COLOR_BTNFACE); overlay_symbol_color_ = color_utils::GetSysSkColor(COLOR_BTNTEXT); - bool accent_color = true; - std::string accent_color_string; - if (options.Get(options::kAccentColor, &accent_color_string)) { - accent_color_ = ParseCSSColor(accent_color_string); - } else if (options.Get(options::kAccentColor, &accent_color)) { - accent_color_ = accent_color; + if (std::string str; options.Get(options::kAccentColor, &str)) { + accent_color_ = ParseCSSColor(str); + } else if (bool flag; options.Get(options::kAccentColor, &flag)) { + accent_color_ = flag; } #endif - v8::Local titlebar_overlay; - if (options.Get(options::ktitleBarOverlay, &titlebar_overlay) && - titlebar_overlay->IsObject()) { - auto titlebar_overlay_obj = - gin_helper::Dictionary::CreateEmpty(options.isolate()); - options.Get(options::ktitleBarOverlay, &titlebar_overlay_obj); - - std::string overlay_color_string; - if (titlebar_overlay_obj.Get(options::kOverlayButtonColor, - &overlay_color_string)) { - bool success = content::ParseCssColorString(overlay_color_string, - &overlay_button_color_); + if (gin_helper::Dictionary od; options.Get(options::ktitleBarOverlay, &od)) { + if (std::string val; od.Get(options::kOverlayButtonColor, &val)) { + bool success = content::ParseCssColorString(val, &overlay_button_color_); DCHECK(success); } - - std::string overlay_symbol_color_string; - if (titlebar_overlay_obj.Get(options::kOverlaySymbolColor, - &overlay_symbol_color_string)) { - bool success = content::ParseCssColorString(overlay_symbol_color_string, - &overlay_symbol_color_); + if (std::string val; od.Get(options::kOverlaySymbolColor, &val)) { + bool success = content::ParseCssColorString(val, &overlay_symbol_color_); DCHECK(success); } } @@ -290,8 +274,7 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, if (IsTranslucent() && !has_frame()) params.shadow_type = InitParams::ShadowType::kNone; - bool focusable; - if (options.Get(options::kFocusable, &focusable) && !focusable) + if (bool val; options.Get(options::kFocusable, &val) && !val) params.activatable = InitParams::Activatable::kNo; #if BUILDFLAG(IS_WIN) @@ -414,11 +397,9 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, // NOTE(@mlaurencin) Spec requirements can be found here: // https://developer.mozilla.org/en-US/docs/Web/API/Window/open#width - int kMinSizeReqdBySpec = 100; - int inner_width = 0; - int inner_height = 0; - options.Get(options::kinnerWidth, &inner_width); - options.Get(options::kinnerHeight, &inner_height); + constexpr int kMinSizeReqdBySpec = 100; + const int inner_width = options.ValueOrDefault(options::kinnerWidth, 0); + const int inner_height = options.ValueOrDefault(options::kinnerHeight, 0); if (inner_width || inner_height) { use_content_size_ = true; if (inner_width) From d49515db3ec66c470e08c6a18ad8cf70b6016622 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 21 Jul 2025 16:29:52 +0200 Subject: [PATCH 162/186] fix: dialog file filters and macOS app bundles (#47839) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/ui/file_dialog_mac.mm | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/shell/browser/ui/file_dialog_mac.mm b/shell/browser/ui/file_dialog_mac.mm index 98896b6dfac4e..87d0a5a6ff100 100644 --- a/shell/browser/ui/file_dialog_mac.mm +++ b/shell/browser/ui/file_dialog_mac.mm @@ -122,6 +122,18 @@ void SetAllowedFileTypes(NSSavePanel* dialog, const Filters& filters) { if (ext == "*") { [content_types_set addObject:[UTType typeWithFilenameExtension:@"*"]]; break; + } else if (ext == "app") { + // This handles a bug on macOS where the "app" extension by default + // maps to "com.apple.application-file", which is for an Application + // file (older single-file carbon based apps), and not modern + // Application Bundles (multi file packages as you'd see for all modern + // applications). + UTType* superType = + [UTType typeWithIdentifier:@"com.apple.application-bundle"]; + if (UTType* utt = [UTType typeWithFilenameExtension:@"app" + conformingToType:superType]) { + [content_types_set addObject:utt]; + } } else { if (UTType* utt = [UTType typeWithFilenameExtension:@(ext.c_str())]) [content_types_set addObject:utt]; From cb11c333fa208bf1ecaa0cef66a2dd0c37524931 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 21 Jul 2025 15:24:35 -0400 Subject: [PATCH 163/186] build: fix ffmpeg generation on Windows non-x64 (#47846) * build: fix ffmpeg generation on Windows non-x64 Co-authored-by: Shelley Vohr * test: ffmpeg artifact Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .github/actions/build-electron/action.yml | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/.github/actions/build-electron/action.yml b/.github/actions/build-electron/action.yml index 350866638b46d..50b2decbcdcfd 100644 --- a/.github/actions/build-electron/action.yml +++ b/.github/actions/build-electron/action.yml @@ -38,6 +38,12 @@ runs: run: | GN_APPENDED_ARGS="$GN_EXTRA_ARGS target_cpu=\"x64\" v8_snapshot_toolchain=\"//build/toolchain/mac:clang_x64\"" echo "GN_EXTRA_ARGS=$GN_APPENDED_ARGS" >> $GITHUB_ENV + - name: Set GN_EXTRA_ARGS for Windows + shell: bash + if: ${{inputs.target-arch != 'x64' && inputs.target-platform == 'win' }} + run: | + GN_APPENDED_ARGS="$GN_EXTRA_ARGS target_cpu=\"${{ inputs.target-arch }}\"" + echo "GN_EXTRA_ARGS=$GN_APPENDED_ARGS" >> $GITHUB_ENV - name: Add Clang problem matcher shell: bash run: echo "::add-matcher::src/electron/.github/problem-matchers/clang.json" @@ -184,8 +190,8 @@ runs: electron/script/zip-symbols.py -b $BUILD_PATH fi - name: Generate FFMpeg ${{ inputs.step-suffix }} - shell: bash if: ${{ inputs.is-release == 'true' }} + shell: bash run: | cd src gn gen out/ffmpeg --args="import(\"//electron/build/args/ffmpeg.gn\") use_remoteexec=true $GN_EXTRA_ARGS" From 2359cfefbd8f1a0d493ff91e4b99878d2c0f2181 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 22 Jul 2025 09:51:00 +0200 Subject: [PATCH 164/186] build: improve `check-zip-manifest` (#47853) * build: improve check-zip-manifest Co-authored-by: Shelley Vohr * fix: unicode on Windows Co-authored-by: Shelley Vohr --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- script/zip_manifests/check-zip-manifest.py | 91 +++++++++++++++++----- 1 file changed, 73 insertions(+), 18 deletions(-) diff --git a/script/zip_manifests/check-zip-manifest.py b/script/zip_manifests/check-zip-manifest.py index ee744422d847e..6e5773b0567e5 100755 --- a/script/zip_manifests/check-zip-manifest.py +++ b/script/zip_manifests/check-zip-manifest.py @@ -2,24 +2,79 @@ import zipfile import sys +import os -def main(zip_path, manifest_in): - with open(manifest_in, 'r', encoding='utf-8') as manifest, \ - zipfile.ZipFile(zip_path, 'r', allowZip64=True) as z: - files_in_zip = set(z.namelist()) - files_in_manifest = {l.strip() for l in manifest.readlines()} - added_files = files_in_zip - files_in_manifest - removed_files = files_in_manifest - files_in_zip - if added_files: - print("Files added to bundle:") - for f in sorted(list(added_files)): - print('+' + f) - if removed_files: - print("Files removed from bundle:") - for f in sorted(list(removed_files)): - print('-' + f) - - return 1 if added_files or removed_files else 0 +def main(zip_path, manifest_path): + """ + Compare a zip file's contents against a manifest file. + Returns 0 if they match, 1 if there are differences. + """ + + if not os.path.exists(zip_path): + print(f"ERROR: Zip file not found: {zip_path}", file=sys.stderr) + return 1 + + if not os.path.exists(manifest_path): + print(f"ERROR: Manifest file not found: {manifest_path}", file=sys.stderr) + return 1 + + try: + with zipfile.ZipFile(zip_path, 'r', allowZip64=True) as z: + files_in_zip = set(z.namelist()) + except zipfile.BadZipFile: + print(f"ERROR: Invalid zip file: {zip_path}", file=sys.stderr) + return 1 + except Exception as e: + print(f"ERROR: Failed to read zip file {zip_path}: {e}", file=sys.stderr) + return 1 + + try: + with open(manifest_path, 'r', encoding='utf-8') as manifest: + files_in_manifest = {line.strip() for line in manifest.readlines() if line.strip()} + except Exception as e: + print(f"ERROR: Failed to read manifest file {manifest_path}: {e}", file=sys.stderr) + return 1 + + added_files = files_in_zip - files_in_manifest + removed_files = files_in_manifest - files_in_zip + + if not added_files and not removed_files: + print("OK: Zip contents match manifest - no differences found") + return 0 + + print("ERROR: Zip contents do not match manifest!") + print(f"Zip file: {zip_path}") + print(f"Manifest: {manifest_path}") + print() + + if added_files: + print(f"Files in zip but NOT in manifest ({len(added_files)} files):") + for f in sorted(added_files): + print(f" + {f}") + print() + + if removed_files: + print(f"Files in manifest but NOT in zip ({len(removed_files)} files):") + for f in sorted(removed_files): + print(f" - {f}") + print() + + print("ACTION REQUIRED:") + if added_files: + print("- Add the new files to the manifest, or") + print("- Remove them from the zip if they shouldn't be included") + if removed_files: + print("- Remove the missing files from the manifest, or") + print("- Add them to the zip if they should be included") + + return 1 if __name__ == '__main__': - sys.exit(main(sys.argv[1], sys.argv[2])) + if len(sys.argv) != 3: + print("Usage: check-zip-manifest.py ", file=sys.stderr) + print("", file=sys.stderr) + print("Compares the contents of a zip file against a manifest file.", file=sys.stderr) + print("Returns 0 if they match, 1 if there are differences or errors.", file=sys.stderr) + sys.exit(1) + + sys.exit(main(sys.argv[1], sys.argv[2])) From 1bf39c13416a609df55c2697e2fe600fa1a0911f Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Wed, 23 Jul 2025 10:31:51 -0400 Subject: [PATCH 165/186] chore: bump chromium to 138.0.7204.168 (37-x-y) (#47861) chore: bump chromium in DEPS to 138.0.7204.168 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> --- DEPS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DEPS b/DEPS index 46b1b2ad05799..c733b9c05bebd 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.157', + '138.0.7204.168', 'node_version': 'v22.17.1', 'nan_version': From 2d855cd680fc10289f39b39dfeafbb9c33d93b61 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 30 Jul 2025 11:43:51 -0700 Subject: [PATCH 166/186] ci: add ability to debug SSH sessions in CI (#47875) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .github/actions/ssh-debug/action.yml | 20 +++ .github/actions/ssh-debug/bashrc | 4 + .github/actions/ssh-debug/setup-ssh.sh | 140 ++++++++++++++++++ .github/actions/ssh-debug/ssh-session.sh | 21 +++ .../actions/ssh-debug/sshd_config.template | 9 ++ .../pipeline-segment-electron-build.yml | 10 ++ .../pipeline-segment-electron-test.yml | 10 ++ 7 files changed, 214 insertions(+) create mode 100644 .github/actions/ssh-debug/action.yml create mode 100644 .github/actions/ssh-debug/bashrc create mode 100755 .github/actions/ssh-debug/setup-ssh.sh create mode 100755 .github/actions/ssh-debug/ssh-session.sh create mode 100644 .github/actions/ssh-debug/sshd_config.template diff --git a/.github/actions/ssh-debug/action.yml b/.github/actions/ssh-debug/action.yml new file mode 100644 index 0000000000000..96b99671fddd6 --- /dev/null +++ b/.github/actions/ssh-debug/action.yml @@ -0,0 +1,20 @@ +name: Debug via SSH +description: Setup a SSH server with a tunnel to access it to debug via SSH. +inputs: + tunnel: + description: 'Enable SSH tunneling via cloudflared' + required: true + default: 'false' + timeout: + description: 'SSH session timeout in minutes' + required: false + type: number + default: 60 +runs: + using: composite + steps: + - run: $GITHUB_ACTION_PATH/setup-ssh.sh + shell: bash + env: + TUNNEL: ${{ inputs.tunnel }} + TIMEOUT: ${{ inputs.timeout }} diff --git a/.github/actions/ssh-debug/bashrc b/.github/actions/ssh-debug/bashrc new file mode 100644 index 0000000000000..52ecb9592040f --- /dev/null +++ b/.github/actions/ssh-debug/bashrc @@ -0,0 +1,4 @@ +# If we're in an interactive SSH session and we're not already in tmux and there's no explicit SSH command, auto attach tmux +if [ -n "$SSH_TTY" ] && [ -z "$TMUX" ] && [ -z "$SSH_ORIGINAL_COMMAND" ]; then + exec tmux attach || exec tmux +fi diff --git a/.github/actions/ssh-debug/setup-ssh.sh b/.github/actions/ssh-debug/setup-ssh.sh new file mode 100755 index 0000000000000..7407dc20955ea --- /dev/null +++ b/.github/actions/ssh-debug/setup-ssh.sh @@ -0,0 +1,140 @@ +#!/bin/bash -e + +get_authorized_keys() { + if [ -z "$AUTHORIZED_USERS" ] || ! echo "$AUTHORIZED_USERS" | grep -q "\b$GITHUB_ACTOR\b"; then + return 1 + fi + + api_response=$(curl -s "https://api.github.com/users/$GITHUB_ACTOR/keys") + + if echo "$api_response" | jq -e 'type == "object" and has("message")' >/dev/null; then + error_msg=$(echo "$api_response" | jq -r '.message') + echo "Error: $error_msg" + return 1 + else + echo "$api_response" | jq -r '.[].key' + fi +} + +authorized_keys=$(get_authorized_keys "$GITHUB_ACTOR") + +if [ -n "$authorized_keys" ]; then + echo "Configured SSH key(s) for user: $GITHUB_ACTOR" +else + echo "Error: User '$GITHUB_ACTOR' is not authorized to access this debug session." + echo "Authorized users: $AUTHORIZED_USERS" + exit 1 +fi + +if [ "$TUNNEL" != "true" ]; then + echo "SSH tunneling is disabled. Set enable-tunnel: true to enable remote access." + echo "Local SSH server would be available on localhost:2222 if this were a local environment." + exit 0 +fi + +echo "SSH tunneling enabled. Setting up remote access..." + +EXTERNAL_DEPS="curl jq ssh-keygen" + +for dep in $EXTERNAL_DEPS; do + if ! command -v "$dep" > /dev/null 2>&1; then + echo "Command $dep not installed on the system!" >&2 + exit 1 + fi +done + +cd "$GITHUB_ACTION_PATH" + +bashrc_path=$(pwd)/bashrc + +# Source `bashrc` to auto start tmux on SSH login. +if ! grep -q "$bashrc_path" ~/.bash_profile; then + echo >> ~/.bash_profile # On macOS runner there's no newline at the end of the file + echo "source \"$bashrc_path\"" >> ~/.bash_profile +fi + +OS=$(uname -s | tr '[:upper:]' '[:lower:]') +ARCH=$(uname -m) + +if [ "$ARCH" = "x86_64" ]; then + ARCH="amd64" +elif [ "$ARCH" = "aarch64" ]; then + ARCH="arm64" +fi + +# Install tmux on macOS runners if not present. +if [ "$OS" = "darwin" ] && ! command -v tmux > /dev/null 2>&1; then + echo "Installing tmux..." + brew install tmux +fi + +if [ "$OS" = "darwin" ]; then + cloudflared_url="https://github.com/cloudflare/cloudflared/releases/latest/download/cloudflared-${OS}-${ARCH}.tgz" + echo "Downloading \`cloudflared\` from <$cloudflared_url>..." + curl --location --silent --output cloudflared.tgz "$cloudflared_url" + tar xf cloudflared.tgz + rm cloudflared.tgz +else + cloudflared_url="https://github.com/cloudflare/cloudflared/releases/latest/download/cloudflared-${OS}-${ARCH}" + echo "Downloading \`cloudflared\` from <$cloudflared_url>..." + curl --location --silent --output cloudflared "$cloudflared_url" +fi + +chmod +x cloudflared + +echo "Setting up SSH key for authorized user: $GITHUB_ACTOR" +echo "$authorized_keys" > authorized_keys + +echo 'Creating SSH server key...' +ssh-keygen -q -f ssh_host_rsa_key -N '' + +echo 'Creating SSH server config...' +sed "s,\$PWD,$PWD,;s,\$USER,$USER," sshd_config.template > sshd_config + +echo 'Starting SSH server...' +/usr/sbin/sshd -f sshd_config -D & +sshd_pid=$! + +echo 'Starting tmux session...' +(cd "$GITHUB_WORKSPACE" && tmux new-session -d -s debug) + +#if no cloudflare tunnel token is provided, exit +if [ -z "$CLOUDFLARE_TUNNEL_TOKEN" ]; then + echo "Error: required CLOUDFLARE_TUNNEL_TOKEN not found" + exit 1 +fi + +echo 'Starting Cloudflare tunnel...' + +./cloudflared tunnel --no-autoupdate run --token "$CLOUDFLARE_TUNNEL_TOKEN" 2>&1 | tee cloudflared.log | sed -u 's/^/cloudflared: /' & +cloudflared_pid=$! + +url="$TUNNEL_HOSTNAME" + +public_key=$(cut -d' ' -f1,2 < ssh_host_rsa_key.pub) + +( + echo ' ' + echo ' ' + echo 'šŸ”— SSH Debug Session Ready!' + echo '━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━' + echo ' ' + echo 'šŸ“‹ Copy and run this command to connect:' + echo ' ' + if [ -n "$TUNNEL_HOSTNAME" ]; then + echo "ssh-keygen -R action-ssh-debug && echo 'action-ssh-debug $public_key' >> ~/.ssh/known_hosts && ssh -o ProxyCommand='cloudflared access tcp --hostname $url' runner@action-ssh-debug" + else + echo "ssh-keygen -R action-ssh-debug && echo 'action-ssh-debug $public_key' >> ~/.ssh/known_hosts && ssh -o ProxyCommand='cloudflared access tcp --hostname $url' runner@action-ssh-debug" + fi + echo ' ' + echo "ā° Session expires automatically in $TIMEOUT minutes" + echo '━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━' + echo ' ' + echo ' ' +) | cat + +echo 'Starting SSH session in background...' +./ssh-session.sh "$sshd_pid" "$cloudflared_pid" $TIMEOUT & + +echo 'SSH session is running in background. GitHub Action will continue.' +echo 'Session will auto-cleanup after timeout or when processes end.' diff --git a/.github/actions/ssh-debug/ssh-session.sh b/.github/actions/ssh-debug/ssh-session.sh new file mode 100755 index 0000000000000..875acf1c66b70 --- /dev/null +++ b/.github/actions/ssh-debug/ssh-session.sh @@ -0,0 +1,21 @@ +#!/bin/bash + +SSHD_PID=$1 +CLOUDFLARED_PID=$2 +SESSION_TIMEOUT=${3:-3600} + +# Wait for timeout or until processes die. +sleep "$SESSION_TIMEOUT" & +SLEEP_PID=$! + +# Monitor if SSH or cloudflared dies early. +while kill -0 "$SSHD_PID" 2>/dev/null && kill -0 "$CLOUDFLARED_PID" 2>/dev/null && kill -0 "$SLEEP_PID" 2>/dev/null; do + sleep 10 +done + +# Cleanup. +kill "$SLEEP_PID" 2>/dev/null || true +kill "$SSHD_PID" 2>/dev/null || true +kill "$CLOUDFLARED_PID" 2>/dev/null || true + +echo "SSH session ended" diff --git a/.github/actions/ssh-debug/sshd_config.template b/.github/actions/ssh-debug/sshd_config.template new file mode 100644 index 0000000000000..9c7949d8b886a --- /dev/null +++ b/.github/actions/ssh-debug/sshd_config.template @@ -0,0 +1,9 @@ +Port 2222 +HostKey $PWD/ssh_host_rsa_key +PidFile $PWD/sshd.pid + +# Only allow single user +AllowUsers $USER + +# Only allow those keys +AuthorizedKeysFile $PWD/authorized_keys diff --git a/.github/workflows/pipeline-segment-electron-build.yml b/.github/workflows/pipeline-segment-electron-build.yml index ac7d2e78c939f..96768f209222c 100644 --- a/.github/workflows/pipeline-segment-electron-build.yml +++ b/.github/workflows/pipeline-segment-electron-build.yml @@ -73,6 +73,7 @@ env: SUDOWOODO_EXCHANGE_TOKEN: ${{ secrets.SUDOWOODO_EXCHANGE_TOKEN }} GCLIENT_EXTRA_ARGS: ${{ inputs.target-platform == 'macos' && '--custom-var=checkout_mac=True --custom-var=host_os=mac' || inputs.target-platform == 'win' && '--custom-var=checkout_win=True' || '--custom-var=checkout_arm=True --custom-var=checkout_arm64=True' }} ELECTRON_OUT_DIR: Default + ACTIONS_STEP_DEBUG: ${{ secrets.ACTIONS_STEP_DEBUG }} jobs: build: @@ -94,6 +95,15 @@ jobs: path: src/electron fetch-depth: 0 ref: ${{ github.event.pull_request.head.sha }} + - name: Setup SSH Debugging + if: ${{ inputs.target-platform == 'macos' && env.ACTIONS_STEP_DEBUG == 'true' }} + uses: ./src/electron/.github/actions/ssh-debug + with: + tunnel: 'true' + env: + CLOUDFLARE_TUNNEL_TOKEN: ${{ secrets.CLOUDFLARE_TUNNEL_TOKEN }} + TUNNEL_HOSTNAME: ${{ secrets.CLOUDFLARED_SSH_HOSTNAME }} + AUTHORIZED_USERS: ${{ secrets.SSH_DEBUG_AUTHORIZED_USERS }} - name: Free up space (macOS) if: ${{ inputs.target-platform == 'macos' }} uses: ./src/electron/.github/actions/free-space-macos diff --git a/.github/workflows/pipeline-segment-electron-test.yml b/.github/workflows/pipeline-segment-electron-test.yml index 108c971e72e1a..d9adbb0c7ef77 100644 --- a/.github/workflows/pipeline-segment-electron-test.yml +++ b/.github/workflows/pipeline-segment-electron-test.yml @@ -40,6 +40,7 @@ env: CHROMIUM_GIT_COOKIE_WINDOWS_STRING: ${{ secrets.CHROMIUM_GIT_COOKIE_WINDOWS_STRING }} ELECTRON_OUT_DIR: Default ELECTRON_RBE_JWT: ${{ secrets.ELECTRON_RBE_JWT }} + ACTIONS_STEP_DEBUG: ${{ secrets.ACTIONS_STEP_DEBUG }} jobs: test: @@ -124,6 +125,15 @@ jobs: path: src/electron fetch-depth: 0 ref: ${{ github.event.pull_request.head.sha }} + - name: Setup SSH Debugging + if: ${{ inputs.target-platform == 'macos' && env.ACTIONS_STEP_DEBUG == 'true' }} + uses: ./src/electron/.github/actions/ssh-debug + with: + tunnel: 'true' + env: + CLOUDFLARE_TUNNEL_TOKEN: ${{ secrets.CLOUDFLARE_TUNNEL_TOKEN }} + TUNNEL_HOSTNAME: ${{ secrets.CLOUDFLARED_SSH_HOSTNAME }} + AUTHORIZED_USERS: ${{ secrets.SSH_DEBUG_AUTHORIZED_USERS }} - name: Install Dependencies uses: ./src/electron/.github/actions/install-dependencies - name: Set Chromium Git Cookie From 6cc713f0587d6347ffdfd03a473f225778015687 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 30 Jul 2025 16:46:14 -0400 Subject: [PATCH 167/186] ci: use new arc cluster (#47915) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: John Kleinschmidt --- .github/actions/build-electron/action.yml | 5 +++ .github/actions/checkout/action.yml | 2 +- .../actions/restore-cache-azcopy/action.yml | 15 ++++++--- .github/workflows/build-git-cache.yml | 6 ++-- .github/workflows/build.yml | 32 +++++++++---------- .github/workflows/clean-src-cache.yml | 2 +- .github/workflows/linux-publish.yml | 8 ++--- .github/workflows/macos-publish.yml | 2 +- .../workflows/pipeline-electron-docs-only.yml | 2 +- .github/workflows/pipeline-electron-lint.yml | 2 +- .../pipeline-segment-node-nan-test.yml | 4 +-- .github/workflows/windows-publish.yml | 8 ++--- 12 files changed, 49 insertions(+), 39 deletions(-) diff --git a/.github/actions/build-electron/action.yml b/.github/actions/build-electron/action.yml index 50b2decbcdcfd..807895f737552 100644 --- a/.github/actions/build-electron/action.yml +++ b/.github/actions/build-electron/action.yml @@ -47,6 +47,11 @@ runs: - name: Add Clang problem matcher shell: bash run: echo "::add-matcher::src/electron/.github/problem-matchers/clang.json" + - name: Enable long paths for Windows + shell: powershell + if: ${{ inputs.target-platform == 'win' }} + run: | + Set-ItemProperty -Path "HKLM:\SYSTEM\CurrentControlSet\Control\FileSystem" -Name "LongPathsEnabled" -Value 1 -Type DWord - name: Build Electron ${{ inputs.step-suffix }} shell: bash run: | diff --git a/.github/actions/checkout/action.yml b/.github/actions/checkout/action.yml index 98fc18bb566b5..e0d66fa041f21 100644 --- a/.github/actions/checkout/action.yml +++ b/.github/actions/checkout/action.yml @@ -40,7 +40,7 @@ runs: if: ${{ inputs.generate-sas-token == 'true' }} shell: bash run: | - curl --unix-socket /var/run/sas/sas.sock --fail "http://foo/$CACHE_FILE?platform=${{ inputs.target-platform }}" > sas-token + curl --unix-socket /var/run/sas/sas.sock --fail "http://foo/$CACHE_FILE?platform=${{ inputs.target-platform }}&getAccountName=true" > sas-token - name: Save SAS Key if: ${{ inputs.generate-sas-token == 'true' }} uses: actions/cache/save@5a3ec84eff668545956fd18022155c47e93e2684 # v4.2.3 diff --git a/.github/actions/restore-cache-azcopy/action.yml b/.github/actions/restore-cache-azcopy/action.yml index 2272ee6e76876..c731eb59ef6d9 100644 --- a/.github/actions/restore-cache-azcopy/action.yml +++ b/.github/actions/restore-cache-azcopy/action.yml @@ -36,18 +36,23 @@ runs: echo "SAS Token not found; exiting src cache download early..." exit 1 else + echo "const fs = require('fs');" > gettoken.js + echo "const fileContents = fs.readFileSync('sas-token', 'utf8');" >> gettoken.js + echo "const token = JSON.parse(fileContents);" >> gettoken.js + echo "console.log(token[process.argv[2]])" >> gettoken.js + sas_token=$(node ./gettoken.js sasToken) + account_name=$(node ./gettoken.js accountName) if [ "${{ inputs.target-platform }}" = "win" ]; then azcopy copy --log-level=ERROR \ - "https://${{ env.AZURE_AKS_CACHE_STORAGE_ACCOUNT }}.file.core.windows.net/${{ env.AZURE_AKS_WIN_CACHE_SHARE_NAME }}/${{ env.CACHE_PATH }}?$sas_token" $DEPSHASH.tar + "https://$account_name.file.core.windows.net/${{ env.AZURE_AKS_WIN_CACHE_SHARE_NAME }}/${{ env.CACHE_PATH }}?$sas_token" $DEPSHASH.tar else azcopy copy --log-level=ERROR \ - "https://${{ env.AZURE_AKS_CACHE_STORAGE_ACCOUNT }}.file.core.windows.net/${{ env.AZURE_AKS_CACHE_SHARE_NAME }}/${{ env.CACHE_PATH }}?$sas_token" $DEPSHASH.tar + "https://$account_name.file.core.windows.net/${{ env.AZURE_AKS_CACHE_SHARE_NAME }}/${{ env.CACHE_PATH }}?$sas_token" $DEPSHASH.tar fi fi env: - AZURE_AKS_CACHE_STORAGE_ACCOUNT: f723719aa87a34622b5f7f3 - AZURE_AKS_CACHE_SHARE_NAME: pvc-f6a4089f-b082-4bee-a3f9-c3e1c0c02d8f - AZURE_AKS_WIN_CACHE_SHARE_NAME: pvc-71dec4f2-0d44-4fd1-a2c3-add049d70bdf + AZURE_AKS_CACHE_SHARE_NAME: linux-cache + AZURE_AKS_WIN_CACHE_SHARE_NAME: windows-cache - name: Clean SAS Key shell: bash run: rm -f sas-token diff --git a/.github/workflows/build-git-cache.yml b/.github/workflows/build-git-cache.yml index 0fddbd4522a58..43daf56e5aa36 100644 --- a/.github/workflows/build-git-cache.yml +++ b/.github/workflows/build-git-cache.yml @@ -8,7 +8,7 @@ on: jobs: build-git-cache-linux: - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:bc2f48b2415a670de18d13605b1cf0eb5fdbaae1 options: --user root @@ -29,7 +29,7 @@ jobs: target-platform: linux build-git-cache-windows: - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:bc2f48b2415a670de18d13605b1cf0eb5fdbaae1 options: --user root --device /dev/fuse --cap-add SYS_ADMIN @@ -51,7 +51,7 @@ jobs: target-platform: win build-git-cache-macos: - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core # This job updates the same git cache as linux, so it needs to run after the linux one. needs: build-git-cache-linux container: diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 0eaa4c7d87295..4c15823e382a4 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -92,7 +92,7 @@ jobs: checkout-macos: needs: setup if: ${{ needs.setup.outputs.src == 'true' && !inputs.skip-macos}} - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:${{ needs.setup.outputs.build-image-sha }} options: --user root @@ -120,7 +120,7 @@ jobs: checkout-linux: needs: setup if: ${{ needs.setup.outputs.src == 'true' && !inputs.skip-linux}} - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:${{ needs.setup.outputs.build-image-sha }} options: --user root @@ -146,7 +146,7 @@ jobs: checkout-windows: needs: setup if: ${{ needs.setup.outputs.src == 'true' && !inputs.skip-windows }} - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:${{ needs.setup.outputs.build-image-sha }} options: --user root --device /dev/fuse --cap-add SYS_ADMIN @@ -191,7 +191,7 @@ jobs: with: target-platform: linux target-archs: x64 arm arm64 - check-runs-on: electron-arc-linux-amd64-8core + check-runs-on: electron-arc-centralus-linux-amd64-8core check-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' gn-build-type: testing secrets: inherit @@ -202,7 +202,7 @@ jobs: with: target-platform: win target-archs: x64 x86 arm64 - check-runs-on: electron-arc-linux-amd64-8core + check-runs-on: electron-arc-centralus-linux-amd64-8core check-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-windows.outputs.build-image-sha }}","options":"--user root --device /dev/fuse --cap-add SYS_ADMIN","volumes":["/mnt/win-cache:/mnt/win-cache"]}' gn-build-type: testing secrets: inherit @@ -252,8 +252,8 @@ jobs: uses: ./.github/workflows/pipeline-electron-build-and-test-and-nan.yml needs: checkout-linux with: - build-runs-on: electron-arc-linux-amd64-32core - test-runs-on: electron-arc-linux-amd64-4core + build-runs-on: electron-arc-centralus-linux-amd64-32core + test-runs-on: electron-arc-centralus-linux-amd64-4core build-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' test-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root --privileged --init"}' target-platform: linux @@ -272,8 +272,8 @@ jobs: uses: ./.github/workflows/pipeline-electron-build-and-test.yml needs: checkout-linux with: - build-runs-on: electron-arc-linux-amd64-32core - test-runs-on: electron-arc-linux-amd64-4core + build-runs-on: electron-arc-centralus-linux-amd64-32core + test-runs-on: electron-arc-centralus-linux-amd64-4core build-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' test-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root --privileged --init"}' target-platform: linux @@ -293,8 +293,8 @@ jobs: uses: ./.github/workflows/pipeline-electron-build-and-test.yml needs: checkout-linux with: - build-runs-on: electron-arc-linux-amd64-32core - test-runs-on: electron-arc-linux-arm64-4core + build-runs-on: electron-arc-centralus-linux-amd64-32core + test-runs-on: electron-arc-centralus-linux-arm64-4core build-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' test-container: '{"image":"ghcr.io/electron/test:arm32v7-${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root --privileged --init","volumes":["/home/runner/externals:/mnt/runner-externals"]}' target-platform: linux @@ -313,8 +313,8 @@ jobs: uses: ./.github/workflows/pipeline-electron-build-and-test.yml needs: checkout-linux with: - build-runs-on: electron-arc-linux-amd64-32core - test-runs-on: electron-arc-linux-arm64-4core + build-runs-on: electron-arc-centralus-linux-amd64-32core + test-runs-on: electron-arc-centralus-linux-arm64-4core build-container: '{"image":"ghcr.io/electron/build:${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' test-container: '{"image":"ghcr.io/electron/test:arm64v8-${{ needs.checkout-linux.outputs.build-image-sha }}","options":"--user root --privileged --init"}' target-platform: linux @@ -334,7 +334,7 @@ jobs: needs: checkout-windows if: ${{ needs.setup.outputs.src == 'true' && !inputs.skip-windows }} with: - build-runs-on: electron-arc-windows-amd64-16core + build-runs-on: electron-arc-centralus-windows-amd64-16core test-runs-on: windows-latest target-platform: win target-arch: x64 @@ -353,7 +353,7 @@ jobs: needs: checkout-windows if: ${{ needs.setup.outputs.src == 'true' && !inputs.skip-windows }} with: - build-runs-on: electron-arc-windows-amd64-16core + build-runs-on: electron-arc-centralus-windows-amd64-16core test-runs-on: windows-latest target-platform: win target-arch: x86 @@ -372,7 +372,7 @@ jobs: needs: checkout-windows if: ${{ needs.setup.outputs.src == 'true' && !inputs.skip-windows }} with: - build-runs-on: electron-arc-windows-amd64-16core + build-runs-on: electron-arc-centralus-windows-amd64-16core test-runs-on: electron-hosted-windows-arm64-4core target-platform: win target-arch: arm64 diff --git a/.github/workflows/clean-src-cache.yml b/.github/workflows/clean-src-cache.yml index 0c4c5919a0ca3..9a1bfddccc888 100644 --- a/.github/workflows/clean-src-cache.yml +++ b/.github/workflows/clean-src-cache.yml @@ -10,7 +10,7 @@ on: jobs: clean-src-cache: - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:bc2f48b2415a670de18d13605b1cf0eb5fdbaae1 options: --user root diff --git a/.github/workflows/linux-publish.yml b/.github/workflows/linux-publish.yml index 8cadd26d23bcc..7bf533f8eeae3 100644 --- a/.github/workflows/linux-publish.yml +++ b/.github/workflows/linux-publish.yml @@ -19,7 +19,7 @@ on: jobs: checkout-linux: - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:${{ inputs.build-image-sha }} options: --user root @@ -43,7 +43,7 @@ jobs: needs: checkout-linux with: environment: production-release - build-runs-on: electron-arc-linux-amd64-32core + build-runs-on: electron-arc-centralus-linux-amd64-32core build-container: '{"image":"ghcr.io/electron/build:${{ inputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' target-platform: linux target-arch: x64 @@ -59,7 +59,7 @@ jobs: needs: checkout-linux with: environment: production-release - build-runs-on: electron-arc-linux-amd64-32core + build-runs-on: electron-arc-centralus-linux-amd64-32core build-container: '{"image":"ghcr.io/electron/build:${{ inputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' target-platform: linux target-arch: arm @@ -75,7 +75,7 @@ jobs: needs: checkout-linux with: environment: production-release - build-runs-on: electron-arc-linux-amd64-32core + build-runs-on: electron-arc-centralus-linux-amd64-32core build-container: '{"image":"ghcr.io/electron/build:${{ inputs.build-image-sha }}","options":"--user root","volumes":["/mnt/cross-instance-cache:/mnt/cross-instance-cache"]}' target-platform: linux target-arch: arm64 diff --git a/.github/workflows/macos-publish.yml b/.github/workflows/macos-publish.yml index c7241b6a3bb00..3c156fa2a3f61 100644 --- a/.github/workflows/macos-publish.yml +++ b/.github/workflows/macos-publish.yml @@ -20,7 +20,7 @@ on: jobs: checkout-macos: - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:${{ inputs.build-image-sha }} options: --user root diff --git a/.github/workflows/pipeline-electron-docs-only.yml b/.github/workflows/pipeline-electron-docs-only.yml index eb5441d148222..062f3af2f57e7 100644 --- a/.github/workflows/pipeline-electron-docs-only.yml +++ b/.github/workflows/pipeline-electron-docs-only.yml @@ -15,7 +15,7 @@ concurrency: jobs: docs-only: name: Docs Only Compile - runs-on: electron-arc-linux-amd64-4core + runs-on: electron-arc-centralus-linux-amd64-4core timeout-minutes: 20 container: ${{ fromJSON(inputs.container) }} steps: diff --git a/.github/workflows/pipeline-electron-lint.yml b/.github/workflows/pipeline-electron-lint.yml index 6cdbff0259952..7c1b27d0a33b8 100644 --- a/.github/workflows/pipeline-electron-lint.yml +++ b/.github/workflows/pipeline-electron-lint.yml @@ -18,7 +18,7 @@ env: jobs: lint: name: Lint - runs-on: electron-arc-linux-amd64-4core + runs-on: electron-arc-centralus-linux-amd64-4core timeout-minutes: 20 container: ${{ fromJSON(inputs.container) }} steps: diff --git a/.github/workflows/pipeline-segment-node-nan-test.yml b/.github/workflows/pipeline-segment-node-nan-test.yml index 7b5e71c3cd347..087bf6772995d 100644 --- a/.github/workflows/pipeline-segment-node-nan-test.yml +++ b/.github/workflows/pipeline-segment-node-nan-test.yml @@ -38,7 +38,7 @@ env: jobs: node-tests: name: Run Node.js Tests - runs-on: electron-arc-linux-amd64-8core + runs-on: electron-arc-centralus-linux-amd64-8core timeout-minutes: 30 env: TARGET_ARCH: ${{ inputs.target-arch }} @@ -92,7 +92,7 @@ jobs: done nan-tests: name: Run Nan Tests - runs-on: electron-arc-linux-amd64-4core + runs-on: electron-arc-centralus-linux-amd64-4core timeout-minutes: 30 env: TARGET_ARCH: ${{ inputs.target-arch }} diff --git a/.github/workflows/windows-publish.yml b/.github/workflows/windows-publish.yml index e8b7c6172fdd8..407ee819dc753 100644 --- a/.github/workflows/windows-publish.yml +++ b/.github/workflows/windows-publish.yml @@ -20,7 +20,7 @@ on: jobs: checkout-windows: - runs-on: electron-arc-linux-amd64-32core + runs-on: electron-arc-centralus-linux-amd64-32core container: image: ghcr.io/electron/build:${{ inputs.build-image-sha }} options: --user root --device /dev/fuse --cap-add SYS_ADMIN @@ -51,7 +51,7 @@ jobs: needs: checkout-windows with: environment: production-release - build-runs-on: electron-arc-windows-amd64-16core + build-runs-on: electron-arc-centralus-windows-amd64-16core target-platform: win target-arch: x64 is-release: true @@ -65,7 +65,7 @@ jobs: needs: checkout-windows with: environment: production-release - build-runs-on: electron-arc-windows-amd64-16core + build-runs-on: electron-arc-centralus-windows-amd64-16core target-platform: win target-arch: arm64 is-release: true @@ -79,7 +79,7 @@ jobs: needs: checkout-windows with: environment: production-release - build-runs-on: electron-arc-windows-amd64-16core + build-runs-on: electron-arc-centralus-windows-amd64-16core target-platform: win target-arch: x86 is-release: true From 45899d1cd7ba617e7ad2ccdf3f8dd79c85567fcb Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 31 Jul 2025 10:53:28 +0200 Subject: [PATCH 168/186] fix: window content protection on older Windows versions (#47887) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- shell/browser/native_window_views.cc | 17 +++++++++++------ shell/browser/native_window_views.h | 1 + .../electron_desktop_window_tree_host_win.cc | 5 +++++ 3 files changed, 17 insertions(+), 6 deletions(-) diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 02a9bb3eab438..10eef7379c4d8 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -1249,12 +1249,7 @@ void NativeWindowViews::SetOpacity(const double opacity) { #if BUILDFLAG(IS_WIN) const double boundedOpacity = std::clamp(opacity, 0.0, 1.0); HWND hwnd = GetAcceleratedWidget(); - if (!layered_) { - LONG ex_style = ::GetWindowLong(hwnd, GWL_EXSTYLE); - ex_style |= WS_EX_LAYERED; - ::SetWindowLong(hwnd, GWL_EXSTYLE, ex_style); - layered_ = true; - } + SetLayered(); ::SetLayeredWindowAttributes(hwnd, 0, boundedOpacity * 255, LWA_ALPHA); opacity_ = boundedOpacity; #else @@ -1669,6 +1664,16 @@ void NativeWindowViews::UpdateThickFrame() { FlipWindowStyle(GetAcceleratedWidget(), resizable_, WS_THICKFRAME); } } + +void NativeWindowViews::SetLayered() { + HWND hwnd = GetAcceleratedWidget(); + if (!layered_) { + LONG ex_style = ::GetWindowLong(hwnd, GWL_EXSTYLE); + ex_style |= WS_EX_LAYERED; + ::SetWindowLong(hwnd, GWL_EXSTYLE, ex_style); + layered_ = true; + } +} #endif void NativeWindowViews::OnWidgetActivationChanged(views::Widget* changed_widget, diff --git a/shell/browser/native_window_views.h b/shell/browser/native_window_views.h index fb66b981ce474..0788214b433bc 100644 --- a/shell/browser/native_window_views.h +++ b/shell/browser/native_window_views.h @@ -171,6 +171,7 @@ class NativeWindowViews : public NativeWindow, #if BUILDFLAG(IS_WIN) TaskbarHost& taskbar_host() { return taskbar_host_; } void UpdateThickFrame(); + void SetLayered(); #endif SkColor overlay_button_color() const { return overlay_button_color_; } diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc index 38111744620cd..22a1261432d55 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc @@ -167,6 +167,11 @@ void ElectronDesktopWindowTreeHostWin::UpdateAllowScreenshots() { if (allowed == allow_screenshots_) return; + // On some older Windows versions, setting the display affinity + // to WDA_EXCLUDEFROMCAPTURE won't prevent the window from being + // captured - setting WS_EX_LAYERED mitigates this issue. + if (base::win::GetVersion() < base::win::Version::WIN11_22H2) + native_window_view_->SetLayered(); ::SetWindowDisplayAffinity( GetAcceleratedWidget(), allow_screenshots_ ? WDA_NONE : WDA_EXCLUDEFROMCAPTURE); From e17cbc96e2e65966fdeb731afc47d2e11c69d495 Mon Sep 17 00:00:00 2001 From: Shelley Vohr Date: Thu, 31 Jul 2025 11:10:24 +0200 Subject: [PATCH 169/186] fix: default to system accent color on invalid user color (#47800) fix: default to system accent color on invalid user color" --- shell/browser/api/electron_api_base_window.cc | 2 +- .../api/electron_api_browser_window.cc | 4 +- .../browser/api/electron_api_web_contents.cc | 7 +-- shell/browser/native_window.cc | 2 +- shell/browser/native_window_views.cc | 4 +- shell/browser/native_window_views_win.cc | 47 ++++++++----------- shell/browser/ui/cocoa/electron_touch_bar.mm | 2 +- shell/browser/web_contents_preferences.cc | 2 +- shell/common/color_util.cc | 4 +- shell/common/color_util.h | 3 +- shell/common/gin_converters/gfx_converter.cc | 2 +- 11 files changed, 38 insertions(+), 41 deletions(-) diff --git a/shell/browser/api/electron_api_base_window.cc b/shell/browser/api/electron_api_base_window.cc index 81ada7acf9294..a51fab12c25f4 100644 --- a/shell/browser/api/electron_api_base_window.cc +++ b/shell/browser/api/electron_api_base_window.cc @@ -656,7 +656,7 @@ bool BaseWindow::IsTabletMode() const { } void BaseWindow::SetBackgroundColor(const std::string& color_name) { - SkColor color = ParseCSSColor(color_name); + SkColor color = ParseCSSColor(color_name).value_or(SK_ColorWHITE); window_->SetBackgroundColor(color); } diff --git a/shell/browser/api/electron_api_browser_window.cc b/shell/browser/api/electron_api_browser_window.cc index c352ee79a5de7..4af43407d8453 100644 --- a/shell/browser/api/electron_api_browser_window.cc +++ b/shell/browser/api/electron_api_browser_window.cc @@ -234,7 +234,7 @@ void BrowserWindow::Blur() { void BrowserWindow::SetBackgroundColor(const std::string& color_name) { BaseWindow::SetBackgroundColor(color_name); - SkColor color = ParseCSSColor(color_name); + SkColor color = ParseCSSColor(color_name).value_or(SK_ColorWHITE); if (api_web_contents_) { api_web_contents_->SetBackgroundColor(color); // Also update the web preferences object otherwise the view will be reset @@ -242,7 +242,7 @@ void BrowserWindow::SetBackgroundColor(const std::string& color_name) { auto* web_preferences = WebContentsPreferences::From(api_web_contents_->web_contents()); if (web_preferences) { - web_preferences->SetBackgroundColor(ParseCSSColor(color_name)); + web_preferences->SetBackgroundColor(color); } } } diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index e062b7a1aff80..e0ab5961c86a9 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -864,9 +864,10 @@ WebContents::WebContents(v8::Isolate* isolate, // webPreferences does not have a transparent option, so if the window needs // to be transparent, that will be set at electron_api_browser_window.cc#L57 // and we then need to pull it back out and check it here. - std::string background_color; - options.GetHidden(options::kBackgroundColor, &background_color); - bool transparent = ParseCSSColor(background_color) == SK_ColorTRANSPARENT; + std::string background_color_str; + options.GetHidden(options::kBackgroundColor, &background_color_str); + SkColor bc = ParseCSSColor(background_color_str).value_or(SK_ColorWHITE); + bool transparent = bc == SK_ColorTRANSPARENT; content::WebContents::CreateParams params(session->browser_context()); auto* view = new OffScreenWebContentsView( diff --git a/shell/browser/native_window.cc b/shell/browser/native_window.cc index 5a9a189298f68..e0ca93a4ad453 100644 --- a/shell/browser/native_window.cc +++ b/shell/browser/native_window.cc @@ -233,7 +233,7 @@ void NativeWindow::InitFromOptions(const gin_helper::Dictionary& options) { SkColor background_color = SK_ColorWHITE; if (std::string color; options.Get(options::kBackgroundColor, &color)) { - background_color = ParseCSSColor(color); + background_color = ParseCSSColor(color).value_or(SK_ColorWHITE); } else if (IsTranslucent()) { background_color = SK_ColorTRANSPARENT; } diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 10eef7379c4d8..8a05554e10162 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -216,7 +216,9 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, overlay_symbol_color_ = color_utils::GetSysSkColor(COLOR_BTNTEXT); if (std::string str; options.Get(options::kAccentColor, &str)) { - accent_color_ = ParseCSSColor(str); + std::optional parsed_color = ParseCSSColor(str); + if (parsed_color.has_value()) + accent_color_ = parsed_color.value(); } else if (bool flag; options.Get(options::kAccentColor, &flag)) { accent_color_ = flag; } diff --git a/shell/browser/native_window_views_win.cc b/shell/browser/native_window_views_win.cc index c7f3456f2f208..21fbdcfed8468 100644 --- a/shell/browser/native_window_views_win.cc +++ b/shell/browser/native_window_views_win.cc @@ -574,43 +574,36 @@ void NativeWindowViews::UpdateWindowAccentColor() { if (base::win::GetVersion() < base::win::Version::WIN11) return; - COLORREF border_color; + std::optional border_color; bool should_apply_accent = false; - if (std::holds_alternative(accent_color_)) { - bool force_accent = std::get(accent_color_); - if (!force_accent) { - should_apply_accent = false; - } else { - std::optional accent_color = GetAccentColor(); - if (accent_color.has_value()) { - border_color = RGB(GetRValue(accent_color.value()), - GetGValue(accent_color.value()), - GetBValue(accent_color.value())); - should_apply_accent = true; - } - } - } else if (std::holds_alternative(accent_color_)) { + if (std::holds_alternative(accent_color_)) { + // If the user has explicitly set an accent color, use it + // regardless of whether the system accent color is enabled. SkColor color = std::get(accent_color_); border_color = RGB(SkColorGetR(color), SkColorGetG(color), SkColorGetB(color)); should_apply_accent = true; + } else if (std::holds_alternative(accent_color_)) { + // Allow the user to optionally force system color on/off. + should_apply_accent = std::get(accent_color_); } else if (std::holds_alternative(accent_color_)) { - if (IsAccentColorOnTitleBarsEnabled()) { - std::optional accent_color = GetAccentColor(); - if (accent_color.has_value()) { - border_color = RGB(GetRValue(accent_color.value()), - GetGValue(accent_color.value()), - GetBValue(accent_color.value())); - should_apply_accent = true; - } + // If no explicit color was set, default to the system accent color. + should_apply_accent = IsAccentColorOnTitleBarsEnabled(); + } + + // Use system accent color as fallback if no explicit color was set. + if (!border_color.has_value() && should_apply_accent) { + std::optional system_accent_color = GetAccentColor(); + if (system_accent_color.has_value()) { + border_color = RGB(GetRValue(system_accent_color.value()), + GetGValue(system_accent_color.value()), + GetBValue(system_accent_color.value())); } } - // Reset to default system colors when accent color should not be applied. - if (!should_apply_accent) - border_color = DWMWA_COLOR_DEFAULT; - SetWindowBorderAndCaptionColor(GetAcceleratedWidget(), border_color); + COLORREF final_color = border_color.value_or(DWMWA_COLOR_DEFAULT); + SetWindowBorderAndCaptionColor(GetAcceleratedWidget(), final_color); } void NativeWindowViews::ResetWindowControls() { diff --git a/shell/browser/ui/cocoa/electron_touch_bar.mm b/shell/browser/ui/cocoa/electron_touch_bar.mm index ee198098f3baf..8fb63c7c823a8 100644 --- a/shell/browser/ui/cocoa/electron_touch_bar.mm +++ b/shell/browser/ui/cocoa/electron_touch_bar.mm @@ -338,7 +338,7 @@ - (bool)hasItemWithID:(const std::string&)item_id { } - (NSColor*)colorFromHexColorString:(const std::string&)colorString { - SkColor color = electron::ParseCSSColor(colorString); + SkColor color = electron::ParseCSSColor(colorString).value_or(SK_ColorWHITE); return skia::SkColorToDeviceNSColor(color); } diff --git a/shell/browser/web_contents_preferences.cc b/shell/browser/web_contents_preferences.cc index 5066bc2e00d20..ca1172ef0eca3 100644 --- a/shell/browser/web_contents_preferences.cc +++ b/shell/browser/web_contents_preferences.cc @@ -215,7 +215,7 @@ void WebContentsPreferences::SetFromDictionary( } std::string background_color; if (web_preferences.GetHidden(options::kBackgroundColor, &background_color)) - background_color_ = ParseCSSColor(background_color); + background_color_ = ParseCSSColor(background_color).value_or(SK_ColorWHITE); std::string safe_dialogs_message; if (web_preferences.Get("safeDialogsMessage", &safe_dialogs_message)) safe_dialogs_message_ = safe_dialogs_message; diff --git a/shell/common/color_util.cc b/shell/common/color_util.cc index d8b169a4e4d42..66669a38c5bb2 100644 --- a/shell/common/color_util.cc +++ b/shell/common/color_util.cc @@ -28,7 +28,7 @@ bool IsHexFormatWithAlpha(const std::string& str) { namespace electron { -SkColor ParseCSSColor(const std::string& color_string) { +std::optional ParseCSSColor(const std::string& color_string) { // ParseCssColorString expects RGBA and we historically use ARGB // so we need to convert before passing to ParseCssColorString. std::string converted_color_str; @@ -42,7 +42,7 @@ SkColor ParseCSSColor(const std::string& color_string) { SkColor color; if (!content::ParseCssColorString(converted_color_str, &color)) - color = SK_ColorWHITE; + return std::nullopt; return color; } diff --git a/shell/common/color_util.h b/shell/common/color_util.h index 8ea422e75b1b8..c1e880d8fe4af 100644 --- a/shell/common/color_util.h +++ b/shell/common/color_util.h @@ -5,6 +5,7 @@ #ifndef ELECTRON_SHELL_COMMON_COLOR_UTIL_H_ #define ELECTRON_SHELL_COMMON_COLOR_UTIL_H_ +#include #include #include "third_party/skia/include/core/SkColor.h" @@ -22,7 +23,7 @@ namespace electron { // Parses a CSS-style color string from hex, rgb(), rgba(), // hsl(), hsla(), or color name formats. -SkColor ParseCSSColor(const std::string& color_string); +std::optional ParseCSSColor(const std::string& color_string); // Convert color to RGB hex value like "#RRGGBB". std::string ToRGBHex(SkColor color); diff --git a/shell/common/gin_converters/gfx_converter.cc b/shell/common/gin_converters/gfx_converter.cc index c54ec7062eabd..2af4e8a097e85 100644 --- a/shell/common/gin_converters/gfx_converter.cc +++ b/shell/common/gin_converters/gfx_converter.cc @@ -226,7 +226,7 @@ bool Converter::FromV8(v8::Isolate* isolate, std::string str; if (!gin::ConvertFromV8(isolate, val, &str)) return false; - *out = electron::ParseCSSColor(str); + *out = electron::ParseCSSColor(str).value_or(SK_ColorWHITE); return true; } From 46dec46a823615cd4d86982478400c1b3cf615ca Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 31 Jul 2025 14:29:39 +0200 Subject: [PATCH 170/186] fix: dark mode on Linux default themeing (#47920) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .../ui/electron_desktop_window_tree_host_linux.cc | 11 +++++++++++ .../ui/electron_desktop_window_tree_host_linux.h | 3 +++ 2 files changed, 14 insertions(+) diff --git a/shell/browser/ui/electron_desktop_window_tree_host_linux.cc b/shell/browser/ui/electron_desktop_window_tree_host_linux.cc index 7e8f06c2b1ce8..541552bcf7d57 100644 --- a/shell/browser/ui/electron_desktop_window_tree_host_linux.cc +++ b/shell/browser/ui/electron_desktop_window_tree_host_linux.cc @@ -25,6 +25,7 @@ #include "ui/linux/linux_ui.h" #include "ui/ozone/public/ozone_platform.h" #include "ui/platform_window/platform_window.h" +#include "ui/platform_window/platform_window_init_properties.h" #include "ui/views/widget/desktop_aura/desktop_window_tree_host.h" #include "ui/views/widget/desktop_aura/desktop_window_tree_host_linux.h" @@ -307,4 +308,14 @@ void ElectronDesktopWindowTreeHostLinux::DispatchEvent(ui::Event* event) { views::DesktopWindowTreeHostLinux::DispatchEvent(event); } +void ElectronDesktopWindowTreeHostLinux::AddAdditionalInitProperties( + const views::Widget::InitParams& params, + ui::PlatformWindowInitProperties* properties) { + views::DesktopWindowTreeHostLinux::AddAdditionalInitProperties(params, + properties); + const auto* linux_ui_theme = ui::LinuxUiTheme::GetForProfile(nullptr); + properties->prefer_dark_theme = + linux_ui_theme && linux_ui_theme->PreferDarkTheme(); +} + } // namespace electron diff --git a/shell/browser/ui/electron_desktop_window_tree_host_linux.h b/shell/browser/ui/electron_desktop_window_tree_host_linux.h index f1455aa0553de..bc0343c315db2 100644 --- a/shell/browser/ui/electron_desktop_window_tree_host_linux.h +++ b/shell/browser/ui/electron_desktop_window_tree_host_linux.h @@ -61,6 +61,9 @@ class ElectronDesktopWindowTreeHostLinux // views::DesktopWindowTreeHostLinux: void UpdateFrameHints() override; void DispatchEvent(ui::Event* event) override; + void AddAdditionalInitProperties( + const views::Widget::InitParams& params, + ui::PlatformWindowInitProperties* properties) override; private: void UpdateWindowState(ui::PlatformWindowState new_state); From ee8290e7070a6ece5cc1202a64edabc51a832377 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 31 Jul 2025 14:30:15 +0200 Subject: [PATCH 171/186] fix: `webContents.downloadURL()` did not support referer header (#47865) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: xufuhang <576484918@qq.com> --- .../browser/api/electron_api_web_contents.cc | 7 +++ spec/api-session-spec.ts | 47 +++++++++++++++++++ 2 files changed, 54 insertions(+) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index e0ab5961c86a9..da7389567aa4c 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -2411,6 +2411,13 @@ void WebContents::DownloadURL(const GURL& url, gin::Arguments* args) { content::DownloadRequestUtils::CreateDownloadForWebContentsMainFrame( web_contents(), url, MISSING_TRAFFIC_ANNOTATION)); for (const auto& [name, value] : headers) { + if (base::ToLowerASCII(name) == + base::ToLowerASCII(net::HttpRequestHeaders::kReferer)) { + // Setting a Referer header with HTTPS scheme while the download URL's + // scheme is HTTP might lead to download failure. + download_params->set_referrer(GURL(value)); + continue; + } download_params->add_request_header(name, value); } diff --git a/spec/api-session-spec.ts b/spec/api-session-spec.ts index 49b24a78f79e2..37698bbdfa11e 100644 --- a/spec/api-session-spec.ts +++ b/spec/api-session-spec.ts @@ -1289,6 +1289,53 @@ describe('session module', () => { expect(item.getContentDisposition()).to.equal(contentDisposition); }); + it('can perform a download with referer header', async () => { + const server = http.createServer((req, res) => { + const { referer } = req.headers; + if (!referer || !referer.startsWith('http://www.electronjs.org')) { + res.statusCode = 403; + res.end(); + } else { + res.writeHead(200, { + 'Content-Length': mockPDF.length, + 'Content-Type': 'application/pdf', + 'Content-Disposition': req.url === '/?testFilename' ? 'inline' : contentDisposition + }); + res.end(mockPDF); + } + }); + + const { port } = await listen(server); + + const w = new BrowserWindow({ show: false }); + const downloadDone: Promise = new Promise((resolve) => { + w.webContents.session.once('will-download', (e, item) => { + item.savePath = downloadFilePath; + item.on('done', () => { + try { + resolve(item); + } catch { } + }); + }); + }); + + w.webContents.downloadURL(`${url}:${port}`, { + headers: { + // Setting a Referer header with HTTPS scheme while the download URL's + // scheme is HTTP might lead to download failure. + referer: 'http://www.electronjs.org' + } + }); + + const item = await downloadDone; + expect(item.getState()).to.equal('completed'); + expect(item.getFilename()).to.equal('mock.pdf'); + expect(item.getMimeType()).to.equal('application/pdf'); + expect(item.getReceivedBytes()).to.equal(mockPDF.length); + expect(item.getTotalBytes()).to.equal(mockPDF.length); + expect(item.getContentDisposition()).to.equal(contentDisposition); + }); + it('throws when called with invalid headers', () => { const w = new BrowserWindow({ show: false }); expect(() => { From 99b9516a6816ef0dd175461f903794d726dd81ee Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Mon, 4 Aug 2025 14:28:03 +0200 Subject: [PATCH 172/186] fix: crash on `window.close()` with `webContents` on blur (#47954) fix: crash on window.close with WebContentsView on blur Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .../browser/api/electron_api_web_contents.cc | 22 ++++++++++++------- spec/api-web-contents-view-spec.ts | 20 +++++++++++++++++ 2 files changed, 34 insertions(+), 8 deletions(-) diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index da7389567aa4c..be1a45b8e91a5 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -2760,15 +2760,17 @@ void WebContents::CloseDevTools() { if (type_ == Type::kRemote) return; - DCHECK(inspectable_web_contents_); - inspectable_web_contents_->CloseDevTools(); + if (inspectable_web_contents_) + inspectable_web_contents_->CloseDevTools(); } bool WebContents::IsDevToolsOpened() { if (type_ == Type::kRemote) return false; - DCHECK(inspectable_web_contents_); + if (!inspectable_web_contents_) + return false; + return inspectable_web_contents_->IsDevToolsViewShowing(); } @@ -2776,19 +2778,24 @@ std::u16string WebContents::GetDevToolsTitle() { if (type_ == Type::kRemote) return {}; - DCHECK(inspectable_web_contents_); + if (!inspectable_web_contents_) + return {}; + return inspectable_web_contents_->GetDevToolsTitle(); } void WebContents::SetDevToolsTitle(const std::u16string& title) { - inspectable_web_contents_->SetDevToolsTitle(title); + if (inspectable_web_contents_) + inspectable_web_contents_->SetDevToolsTitle(title); } bool WebContents::IsDevToolsFocused() { if (type_ == Type::kRemote) return false; - DCHECK(inspectable_web_contents_); + if (!inspectable_web_contents_) + return false; + return inspectable_web_contents_->GetView()->IsDevToolsViewFocused(); } @@ -2836,10 +2843,9 @@ void WebContents::InspectElement(int x, int y) { if (type_ == Type::kRemote) return; - if (!enable_devtools_) + if (!enable_devtools_ || !inspectable_web_contents_) return; - DCHECK(inspectable_web_contents_); if (!inspectable_web_contents_->GetDevToolsWebContents()) OpenDevTools(nullptr); inspectable_web_contents_->InspectElement(x, y); diff --git a/spec/api-web-contents-view-spec.ts b/spec/api-web-contents-view-spec.ts index 63f45c140edd1..1d55c82531727 100644 --- a/spec/api-web-contents-view-spec.ts +++ b/spec/api-web-contents-view-spec.ts @@ -167,6 +167,26 @@ describe('WebContentsView', () => { }); }); + it('does not crash when closed via window.close()', async () => { + const bw = new BrowserWindow(); + const wcv = new WebContentsView(); + + await bw.loadURL('data:text/html,

Main Window

'); + bw.contentView.addChildView(wcv); + + const dto = new Promise((resolve) => { + wcv.webContents.on('blur', () => { + const devToolsOpen = wcv.webContents.isDevToolsOpened(); + resolve(devToolsOpen); + }); + }); + + wcv.webContents.loadURL('data:text/html,'); + + const open = await dto; + expect(open).to.be.false(); + }); + it('can be fullscreened', async () => { const w = new BaseWindow(); const v = new WebContentsView(); From 6c8dbe45946fe23cd94e5f8697bf94012566e540 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Mon, 4 Aug 2025 16:21:35 +0200 Subject: [PATCH 173/186] chore: bump chromium to 138.0.7204.185 (37-x-y) (#47909) * chore: bump chromium in DEPS to 138.0.7204.183 * chore: bump chromium in DEPS to 138.0.7204.185 --------- Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> --- DEPS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DEPS b/DEPS index c733b9c05bebd..70f0c0cdbb900 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.168', + '138.0.7204.185', 'node_version': 'v22.17.1', 'nan_version': From c7ae20c4f2846851ca058fb4912f86e9d3caa00d Mon Sep 17 00:00:00 2001 From: Shelley Vohr Date: Mon, 4 Aug 2025 17:17:00 +0200 Subject: [PATCH 174/186] fix: abnormal behavior of windows background material (#47956) * fix: abnormal behavior of windows background material * chore: update patches --------- Co-authored-by: patchup[bot] <73610968+patchup[bot]@users.noreply.github.com> --- patches/chromium/.patches | 2 +- ...ivate_background_material_on_windows.patch | 68 ----------- ..._material_update_issue_on_windows_11.patch | 115 ++++++++++++++++++ shell/browser/api/electron_api_base_window.cc | 4 +- shell/browser/api/electron_api_base_window.h | 2 +- .../api/electron_api_browser_window.cc | 13 ++ .../browser/api/electron_api_browser_window.h | 1 + shell/browser/native_window.h | 4 + shell/browser/native_window_views.cc | 84 +++++++------ .../electron_desktop_window_tree_host_win.cc | 9 ++ 10 files changed, 195 insertions(+), 107 deletions(-) delete mode 100644 patches/chromium/fix_activate_background_material_on_windows.patch create mode 100644 patches/chromium/fix_resolve_dynamic_background_material_update_issue_on_windows_11.patch diff --git a/patches/chromium/.patches b/patches/chromium/.patches index 31f914b813c9f..d4bb1f41bc617 100644 --- a/patches/chromium/.patches +++ b/patches/chromium/.patches @@ -109,7 +109,6 @@ fix_use_delegated_generic_capturer_when_available.patch expose_webblob_path_to_allow_embedders_to_get_file_paths.patch fix_move_autopipsettingshelper_behind_branding_buildflag.patch revert_remove_the_allowaggressivethrottlingwithwebsocket_feature.patch -fix_activate_background_material_on_windows.patch feat_allow_passing_of_objecttemplate_to_objecttemplatebuilder.patch chore_remove_check_is_test_on_script_injection_tracker.patch fix_restore_original_resize_performance_on_macos.patch @@ -142,3 +141,4 @@ fix_linter_error.patch chore_grandfather_in_electron_views_and_delegates.patch refactor_patch_electron_permissiontypes_into_blink.patch fix_add_macos_memory_query_fallback_to_avoid_crash.patch +fix_resolve_dynamic_background_material_update_issue_on_windows_11.patch diff --git a/patches/chromium/fix_activate_background_material_on_windows.patch b/patches/chromium/fix_activate_background_material_on_windows.patch deleted file mode 100644 index 3869ca7990f26..0000000000000 --- a/patches/chromium/fix_activate_background_material_on_windows.patch +++ /dev/null @@ -1,68 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: clavin -Date: Mon, 11 Dec 2023 20:43:34 -0300 -Subject: fix: activate background material on windows - -This patch adds a condition to the HWND message handler to allow windows -with translucent background materials to become activated. - -It also ensures the lParam of WM_NCACTIVATE is set to -1 so as to not repaint -the client area, which can lead to a title bar incorrectly being displayed in -frameless windows. - -This patch likely can't be upstreamed as-is, as Chromium doesn't have -this use case in mind currently. - -diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc -index 1a10bd1a6c527633f97d6eee6525b1e45a3fcd3d..2b983ae3ec3e1d17951add818c2610582d586377 100644 ---- a/ui/views/win/hwnd_message_handler.cc -+++ b/ui/views/win/hwnd_message_handler.cc -@@ -937,13 +937,13 @@ void HWNDMessageHandler::FrameTypeChanged() { - - void HWNDMessageHandler::PaintAsActiveChanged() { - if (!delegate_->HasNonClientView() || !delegate_->CanActivate() || -- !delegate_->HasFrame() || -+ (!delegate_->HasFrame() && !is_translucent_) || - (delegate_->GetFrameMode() == FrameMode::CUSTOM_DRAWN)) { - return; - } - - DefWindowProcWithRedrawLock(WM_NCACTIVATE, delegate_->ShouldPaintAsActive(), -- 0); -+ delegate_->HasFrame() ? 0 : -1); - } - - void HWNDMessageHandler::SetWindowIcons(const gfx::ImageSkia& window_icon, -@@ -1732,7 +1732,7 @@ void HWNDMessageHandler::OnActivateApp(BOOL active, DWORD thread_id) { - if (delegate_->HasNonClientView() && !active && - thread_id != GetCurrentThreadId()) { - // Update the native frame if it is rendering the non-client area. -- if (HasSystemFrame()) { -+ if (is_translucent_ || HasSystemFrame()) { - DefWindowProcWithRedrawLock(WM_NCACTIVATE, FALSE, 0); - } - } -@@ -2340,17 +2340,18 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message, - delegate_->SchedulePaint(); - } - -- // Calling DefWindowProc is only necessary if there's a system frame being -- // drawn. Otherwise it can draw an incorrect title bar and cause visual -- // corruption. -- if (!delegate_->HasFrame() || -+ // If the window is translucent, it may have the Mica background. -+ // In that case, it's necessary to call |DefWindowProc|, but we can -+ // pass -1 in the lParam to prevent any non-client area elements from -+ // being displayed. -+ if ((!delegate_->HasFrame() && !is_translucent_) || - delegate_->GetFrameMode() == FrameMode::CUSTOM_DRAWN) { - SetMsgHandled(TRUE); - return TRUE; - } - - return DefWindowProcWithRedrawLock(WM_NCACTIVATE, paint_as_active || active, -- 0); -+ delegate_->HasFrame() ? 0 : -1); - } - - LRESULT HWNDMessageHandler::OnNCCalcSize(BOOL mode, LPARAM l_param) { diff --git a/patches/chromium/fix_resolve_dynamic_background_material_update_issue_on_windows_11.patch b/patches/chromium/fix_resolve_dynamic_background_material_update_issue_on_windows_11.patch new file mode 100644 index 0000000000000..529406fc7aa36 --- /dev/null +++ b/patches/chromium/fix_resolve_dynamic_background_material_update_issue_on_windows_11.patch @@ -0,0 +1,115 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: zoy +Date: Mon, 5 May 2025 23:28:53 +0800 +Subject: fix: resolve dynamic background material update issue on Windows 11 + +This patch addresses issues with background materials on Windows 11, +such as the background turning black when maximizing the window and +dynamic background material settings not taking effect. + +diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +index a415140b94e467adfbc3dbbaa026e897a0f66c06..41470fd55bf2053eb6d523bda3b544f448bfb094 100644 +--- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc ++++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.cc +@@ -176,6 +176,10 @@ void DesktopWindowTreeHostWin::FinishTouchDrag(gfx::Point screen_point) { + } + } + ++void DesktopWindowTreeHostWin::SetIsTranslucent(bool is_translucent) { ++ message_handler_->set_is_translucent(is_translucent); ++} ++ + // DesktopWindowTreeHostWin, DesktopWindowTreeHost implementation: + + void DesktopWindowTreeHostWin::Init(const Widget::InitParams& params) { +diff --git a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h +index b85d1cdec49b10628d2f3d3d2e07513beb830456..232b5121fc2b138c91559d740c5178f0562df66b 100644 +--- a/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h ++++ b/ui/views/widget/desktop_aura/desktop_window_tree_host_win.h +@@ -94,6 +94,8 @@ class VIEWS_EXPORT DesktopWindowTreeHostWin + // false. + void FinishTouchDrag(gfx::Point screen_point); + ++ void SetIsTranslucent(bool is_translucent); ++ + protected: + // Overridden from DesktopWindowTreeHost: + void Init(const Widget::InitParams& params) override; +diff --git a/ui/views/win/hwnd_message_handler.cc b/ui/views/win/hwnd_message_handler.cc +index 1a10bd1a6c527633f97d6eee6525b1e45a3fcd3d..7de4e205fede08d6e0d38ec4aa72c4fa47ac6d9e 100644 +--- a/ui/views/win/hwnd_message_handler.cc ++++ b/ui/views/win/hwnd_message_handler.cc +@@ -937,13 +937,13 @@ void HWNDMessageHandler::FrameTypeChanged() { + + void HWNDMessageHandler::PaintAsActiveChanged() { + if (!delegate_->HasNonClientView() || !delegate_->CanActivate() || +- !delegate_->HasFrame() || ++ (!delegate_->HasFrame() && !is_translucent_) || + (delegate_->GetFrameMode() == FrameMode::CUSTOM_DRAWN)) { + return; + } + + DefWindowProcWithRedrawLock(WM_NCACTIVATE, delegate_->ShouldPaintAsActive(), +- 0); ++ delegate_->HasFrame() ? 0 : -1); + } + + void HWNDMessageHandler::SetWindowIcons(const gfx::ImageSkia& window_icon, +@@ -1027,7 +1027,14 @@ void HWNDMessageHandler::SizeConstraintsChanged() { + // allowing ui::GetResizableFrameThickness() to be used consistently when + // removing the visible system frame. + const bool had_caption_on_init = window_style() & WS_CAPTION; +- const bool can_resize = !is_translucent_ && delegate_->CanResize(); ++ ++ // In Chromium, the !is_translucent_ check was introduced for Glic-specific ++ // behavior. Since Electron does not use Glic, this restriction can be safely ++ // removed. Keeping the is_translucent_ check disables maximization for ++ // translucent framed windows. Original code: !is_translucent_ && ++ // delegate_->CanResize() See: ++ // https://chromium-review.googlesource.com/c/chromium/src/+/6372329 ++ const bool can_resize = delegate_->CanResize(); + const bool can_maximize = can_resize && delegate_->CanMaximize(); + + auto set_style_func = [&style](LONG bit, bool should_set) { +@@ -1622,11 +1629,16 @@ void HWNDMessageHandler::ResetWindowRegion(bool force, bool redraw) { + // through, but that isn't the case when using Direct3D to draw transparent + // windows. So we route translucent windows throught to the delegate to + // allow for a custom hit mask. +- if (!is_translucent_ && !custom_window_region_.is_valid() && ++ // patch: fix_resolve_dynamic_background_material_update_issue_on_windows_11 ++ // Our translucent windows use the native frame by default, and we should not ++ // set a custom region when the window is maximized; otherwise, it will cause ++ // a white title bar to appear under Windows 11. ++ if (!custom_window_region_.is_valid() && + (IsFrameSystemDrawn() || !delegate_->HasNonClientView())) { + if (force) { + SetWindowRgn(hwnd(), nullptr, redraw); + } ++ + return; + } + +@@ -2340,17 +2352,18 @@ LRESULT HWNDMessageHandler::OnNCActivate(UINT message, + delegate_->SchedulePaint(); + } + +- // Calling DefWindowProc is only necessary if there's a system frame being +- // drawn. Otherwise it can draw an incorrect title bar and cause visual +- // corruption. +- if (!delegate_->HasFrame() || ++ // If the window is translucent, it may have the Mica background. ++ // In that case, it's necessary to call |DefWindowProc|, but we can ++ // pass -1 in the lParam to prevent any non-client area elements from ++ // being displayed. ++ if ((!delegate_->HasFrame() && !is_translucent_) || + delegate_->GetFrameMode() == FrameMode::CUSTOM_DRAWN) { + SetMsgHandled(TRUE); + return TRUE; + } + + return DefWindowProcWithRedrawLock(WM_NCACTIVATE, paint_as_active || active, +- 0); ++ delegate_->HasFrame() ? 0 : -1); + } + + LRESULT HWNDMessageHandler::OnNCCalcSize(BOOL mode, LPARAM l_param) { diff --git a/shell/browser/api/electron_api_base_window.cc b/shell/browser/api/electron_api_base_window.cc index a51fab12c25f4..0f121f9822126 100644 --- a/shell/browser/api/electron_api_base_window.cc +++ b/shell/browser/api/electron_api_base_window.cc @@ -850,8 +850,8 @@ void BaseWindow::SetVibrancy(v8::Isolate* isolate, window_->SetVibrancy(type, animation_duration_ms); } -void BaseWindow::SetBackgroundMaterial(const std::string& material_type) { - window_->SetBackgroundMaterial(material_type); +void BaseWindow::SetBackgroundMaterial(const std::string& material) { + window_->SetBackgroundMaterial(material); } #if BUILDFLAG(IS_MAC) diff --git a/shell/browser/api/electron_api_base_window.h b/shell/browser/api/electron_api_base_window.h index e516bf278d9a6..103f33c357cbf 100644 --- a/shell/browser/api/electron_api_base_window.h +++ b/shell/browser/api/electron_api_base_window.h @@ -196,7 +196,7 @@ class BaseWindow : public gin_helper::TrackableObject, virtual void SetVibrancy(v8::Isolate* isolate, v8::Local value, gin_helper::Arguments* args); - void SetBackgroundMaterial(const std::string& vibrancy); + virtual void SetBackgroundMaterial(const std::string& material); #if BUILDFLAG(IS_MAC) std::string GetAlwaysOnTopLevel() const; diff --git a/shell/browser/api/electron_api_browser_window.cc b/shell/browser/api/electron_api_browser_window.cc index 4af43407d8453..f4af58e8b1bec 100644 --- a/shell/browser/api/electron_api_browser_window.cc +++ b/shell/browser/api/electron_api_browser_window.cc @@ -4,6 +4,7 @@ #include "shell/browser/api/electron_api_browser_window.h" +#include "base/containers/fixed_flat_set.h" #include "content/browser/renderer_host/render_widget_host_owner_delegate.h" // nogncheck #include "content/browser/web_contents/web_contents_impl.h" // nogncheck #include "content/public/browser/render_process_host.h" @@ -247,6 +248,18 @@ void BrowserWindow::SetBackgroundColor(const std::string& color_name) { } } +void BrowserWindow::SetBackgroundMaterial(const std::string& material) { + BaseWindow::SetBackgroundMaterial(material); + static constexpr auto materialTypes = + base::MakeFixedFlatSet({"tabbed", "mica", "acrylic"}); + + if (materialTypes.contains(material)) { + SetBackgroundColor(ToRGBAHex(SK_ColorTRANSPARENT)); + } else if (material == "none") { + SetBackgroundColor(ToRGBAHex(SK_ColorWHITE)); + } +} + void BrowserWindow::FocusOnWebView() { web_contents()->GetRenderViewHost()->GetWidget()->Focus(); } diff --git a/shell/browser/api/electron_api_browser_window.h b/shell/browser/api/electron_api_browser_window.h index 4e8822e487cf4..b13ffda8f8a18 100644 --- a/shell/browser/api/electron_api_browser_window.h +++ b/shell/browser/api/electron_api_browser_window.h @@ -64,6 +64,7 @@ class BrowserWindow : public BaseWindow, void Focus() override; void Blur() override; void SetBackgroundColor(const std::string& color_name) override; + void SetBackgroundMaterial(const std::string& material) override; void OnWindowShow() override; void OnWindowHide() override; diff --git a/shell/browser/native_window.h b/shell/browser/native_window.h index be828691dc595..a995997415cb4 100644 --- a/shell/browser/native_window.h +++ b/shell/browser/native_window.h @@ -231,6 +231,10 @@ class NativeWindow : public base::SupportsUserData, // Vibrancy API virtual void SetVibrancy(const std::string& type, int duration); + const std::string& background_material() const { + return background_material_; + } + virtual void SetBackgroundMaterial(const std::string& type); // Traffic Light API diff --git a/shell/browser/native_window_views.cc b/shell/browser/native_window_views.cc index 8a05554e10162..37a184e7bee8e 100644 --- a/shell/browser/native_window_views.cc +++ b/shell/browser/native_window_views.cc @@ -79,6 +79,7 @@ #include "base/win/windows_version.h" #include "shell/browser/ui/views/win_frame_view.h" #include "shell/browser/ui/win/electron_desktop_native_widget_aura.h" +#include "shell/browser/ui/win/electron_desktop_window_tree_host_win.h" #include "shell/common/color_util.h" #include "skia/ext/skia_utils_win.h" #include "ui/display/win/screen_win.h" @@ -354,6 +355,7 @@ NativeWindowViews::NativeWindowViews(const gin_helper::Dictionary& options, if (!has_frame()) { // Set Window style so that we get a minimize and maximize animation when // frameless. + DWORD frame_style = WS_CAPTION | WS_OVERLAPPED; if (resizable_) frame_style |= WS_THICKFRAME; @@ -634,13 +636,7 @@ void NativeWindowViews::SetEnabledInternal(bool enable) { void NativeWindowViews::Maximize() { #if BUILDFLAG(IS_WIN) - if (IsTranslucent()) { - // Semi-transparent windows with backgroundMaterial not set to 'none', and - // not fully transparent, require manual handling of rounded corners when - // maximized. - if (rounded_corner_) - SetRoundedCorners(false); - + if (transparent()) { restore_bounds_ = GetBounds(); auto display = display::Screen::GetScreen()->GetDisplayNearestWindow( GetNativeWindow()); @@ -664,15 +660,10 @@ void NativeWindowViews::Unmaximize() { return; #if BUILDFLAG(IS_WIN) - if (IsTranslucent()) { + if (transparent()) { SetBounds(restore_bounds_, false); NotifyWindowUnmaximize(); - if (transparent()) { - UpdateThickFrame(); - } - if (rounded_corner_) { - SetRoundedCorners(true); - } + UpdateThickFrame(); return; } #endif @@ -689,7 +680,7 @@ bool NativeWindowViews::IsMaximized() const { return true; #if BUILDFLAG(IS_WIN) - if (IsTranslucent() && !IsMinimized()) { + if (transparent() && !IsMinimized()) { // If the window is the same dimensions and placement as the // display, we consider it maximized. auto display = display::Screen::GetScreen()->GetDisplayNearestWindow( @@ -711,15 +702,10 @@ void NativeWindowViews::Minimize() { void NativeWindowViews::Restore() { #if BUILDFLAG(IS_WIN) - if (IsMaximized() && IsTranslucent()) { + if (IsMaximized() && transparent()) { SetBounds(restore_bounds_, false); NotifyWindowRestore(); - if (transparent()) { - UpdateThickFrame(); - } - if (rounded_corner_) { - SetRoundedCorners(true); - } + UpdateThickFrame(); return; } #endif @@ -865,7 +851,7 @@ gfx::Size NativeWindowViews::GetContentSize() const { gfx::Rect NativeWindowViews::GetNormalBounds() const { #if BUILDFLAG(IS_WIN) - if (IsMaximized() && IsTranslucent()) + if (IsMaximized() && transparent()) return restore_bounds_; #endif return widget()->GetRestoredBounds(); @@ -1505,25 +1491,53 @@ void NativeWindowViews::SetBackgroundMaterial(const std::string& material) { return; DWM_SYSTEMBACKDROP_TYPE backdrop_type = GetBackdropFromString(material); - HRESULT result = - DwmSetWindowAttribute(GetAcceleratedWidget(), DWMWA_SYSTEMBACKDROP_TYPE, - &backdrop_type, sizeof(backdrop_type)); + const bool is_translucent = backdrop_type != DWMSBT_NONE && + backdrop_type != DWMSBT_AUTO && !has_frame(); + + HWND hwnd = GetAcceleratedWidget(); + + // We need to update margins ourselves since Chromium won't. + // See: ui/views/widget/widget_hwnd_utils.cc#157 + // See: src/ui/views/win/hwnd_message_handler.cc#1793 + MARGINS m = {0, 0, 0, 0}; + if (is_translucent) + m = {-1, -1, -1, -1}; + + HRESULT result = DwmExtendFrameIntoClientArea(hwnd, &m); + if (FAILED(result)) + LOG(WARNING) << "Failed to extend frame into client area"; + + result = DwmSetWindowAttribute(hwnd, DWMWA_SYSTEMBACKDROP_TYPE, + &backdrop_type, sizeof(backdrop_type)); if (FAILED(result)) LOG(WARNING) << "Failed to set background material to " << material; + auto* desktop_window_tree_host = + static_cast( + GetNativeWindow()->GetHost()); + + // Synchronize the internal state; otherwise, the background material may not + // work properly. + if (desktop_window_tree_host) { + desktop_window_tree_host->SetIsTranslucent(is_translucent); + } + + auto* desktop_native_widget_aura = + static_cast(widget()->native_widget()); + desktop_native_widget_aura->UpdateWindowTransparency(); + // For frameless windows with a background material set, we also need to // remove the caption color so it doesn't render a caption bar (since the // window is frameless) - COLORREF caption_color = DWMWA_COLOR_DEFAULT; - if (backdrop_type != DWMSBT_NONE && backdrop_type != DWMSBT_AUTO && - !has_frame()) { - caption_color = DWMWA_COLOR_NONE; - } - result = DwmSetWindowAttribute(GetAcceleratedWidget(), DWMWA_CAPTION_COLOR, - &caption_color, sizeof(caption_color)); - + COLORREF caption_color = + is_translucent ? DWMWA_COLOR_NONE : DWMWA_COLOR_DEFAULT; + result = DwmSetWindowAttribute(hwnd, DWMWA_CAPTION_COLOR, &caption_color, + sizeof(caption_color)); if (FAILED(result)) LOG(WARNING) << "Failed to set caption color to transparent"; + + // Activate the non-client area of the window + DefWindowProc(hwnd, WM_NCACTIVATE, TRUE, has_frame() ? 0 : -1); #endif } @@ -1846,7 +1860,7 @@ ui::mojom::WindowShowState NativeWindowViews::GetRestoredState() { if (IsMaximized()) { #if BUILDFLAG(IS_WIN) // Restore maximized state for windows that are not translucent. - if (!IsTranslucent()) { + if (!transparent()) { return ui::mojom::WindowShowState::kMaximized; } #else diff --git a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc index 22a1261432d55..2d90f66e1fe83 100644 --- a/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc +++ b/shell/browser/ui/win/electron_desktop_window_tree_host_win.cc @@ -64,7 +64,16 @@ bool ElectronDesktopWindowTreeHostWin::GetDwmFrameInsetsInPixels( gfx::Insets* insets) const { // Set DWMFrameInsets to prevent maximized frameless window from bleeding // into other monitors. + if (IsMaximized() && !native_window_view_->has_frame()) { + // We avoid doing this when the window is translucent (e.g. using + // backgroundMaterial effects), because setting zero insets can interfere + // with DWM rendering of blur or acrylic, potentially causing visual + // glitches. + const std::string& bg_material = native_window_view_->background_material(); + if (!bg_material.empty() && bg_material != "none") { + return false; + } // This would be equivalent to calling: // DwmExtendFrameIntoClientArea({0, 0, 0, 0}); // From e0628b9de10c7b65acb81a541148099510a9b50f Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Tue, 5 Aug 2025 19:06:33 +0200 Subject: [PATCH 175/186] build: roll build-images to 933c7d6 (#47927) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- .devcontainer/docker-compose.yml | 2 +- .github/workflows/build.yml | 4 ++-- .github/workflows/linux-publish.yml | 2 +- .github/workflows/macos-publish.yml | 2 +- .github/workflows/windows-publish.yml | 2 +- 5 files changed, 6 insertions(+), 6 deletions(-) diff --git a/.devcontainer/docker-compose.yml b/.devcontainer/docker-compose.yml index 4eaf46700b472..ddf29ed5de636 100644 --- a/.devcontainer/docker-compose.yml +++ b/.devcontainer/docker-compose.yml @@ -2,7 +2,7 @@ version: '3' services: buildtools: - image: ghcr.io/electron/devcontainer:424eedbf277ad9749ffa9219068aa72ed4a5e373 + image: ghcr.io/electron/devcontainer:933c7d6ff6802706875270bec2e3c891cf8add3f volumes: - ..:/workspaces/gclient/src/electron:cached diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 4c15823e382a4..520e861c7c93e 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -6,7 +6,7 @@ on: build-image-sha: type: string description: 'SHA for electron/build image' - default: '424eedbf277ad9749ffa9219068aa72ed4a5e373' + default: '933c7d6ff6802706875270bec2e3c891cf8add3f' required: true skip-macos: type: boolean @@ -64,7 +64,7 @@ jobs: id: set-output run: | if [ -z "${{ inputs.build-image-sha }}" ]; then - echo "build-image-sha=424eedbf277ad9749ffa9219068aa72ed4a5e373" >> "$GITHUB_OUTPUT" + echo "build-image-sha=933c7d6ff6802706875270bec2e3c891cf8add3f" >> "$GITHUB_OUTPUT" else echo "build-image-sha=${{ inputs.build-image-sha }}" >> "$GITHUB_OUTPUT" fi diff --git a/.github/workflows/linux-publish.yml b/.github/workflows/linux-publish.yml index 7bf533f8eeae3..62b09a4e30ee4 100644 --- a/.github/workflows/linux-publish.yml +++ b/.github/workflows/linux-publish.yml @@ -6,7 +6,7 @@ on: build-image-sha: type: string description: 'SHA for electron/build image' - default: '424eedbf277ad9749ffa9219068aa72ed4a5e373' + default: '933c7d6ff6802706875270bec2e3c891cf8add3f' upload-to-storage: description: 'Uploads to Azure storage' required: false diff --git a/.github/workflows/macos-publish.yml b/.github/workflows/macos-publish.yml index 3c156fa2a3f61..faf1aae291aa1 100644 --- a/.github/workflows/macos-publish.yml +++ b/.github/workflows/macos-publish.yml @@ -6,7 +6,7 @@ on: build-image-sha: type: string description: 'SHA for electron/build image' - default: '424eedbf277ad9749ffa9219068aa72ed4a5e373' + default: '933c7d6ff6802706875270bec2e3c891cf8add3f' required: true upload-to-storage: description: 'Uploads to Azure storage' diff --git a/.github/workflows/windows-publish.yml b/.github/workflows/windows-publish.yml index 407ee819dc753..b72e045d7679d 100644 --- a/.github/workflows/windows-publish.yml +++ b/.github/workflows/windows-publish.yml @@ -6,7 +6,7 @@ on: build-image-sha: type: string description: 'SHA for electron/build image' - default: '424eedbf277ad9749ffa9219068aa72ed4a5e373' + default: '933c7d6ff6802706875270bec2e3c891cf8add3f' required: true upload-to-storage: description: 'Uploads to Azure storage' From 3a493bc01b7600d34e9560cbbd7f72cfca9603a3 Mon Sep 17 00:00:00 2001 From: Keeley Hammond Date: Tue, 5 Aug 2025 18:20:29 -0700 Subject: [PATCH 176/186] fix: video scrubbing on playback (#47971) fix: video scrubbing on playback (#47703) * fix: fix video scrubbing on playback * chore: address review feedback --------- Co-authored-by: Shelley Vohr --- ..._registry_to_multibuffer_data_source.patch | 85 +++++++++++++++---- 1 file changed, 70 insertions(+), 15 deletions(-) diff --git a/patches/chromium/feat_add_streaming-protocol_registry_to_multibuffer_data_source.patch b/patches/chromium/feat_add_streaming-protocol_registry_to_multibuffer_data_source.patch index 0155eecf8873b..ac91885ca2328 100644 --- a/patches/chromium/feat_add_streaming-protocol_registry_to_multibuffer_data_source.patch +++ b/patches/chromium/feat_add_streaming-protocol_registry_to_multibuffer_data_source.patch @@ -12,8 +12,12 @@ This patch adds a list of "streaming protocols" to the MultibufferDataSource in other protocols to register their streaming behavior. MultibufferDataSource::AssumeFullyBuffered() then refers to the list so that it can correctly determine the data source's settings. +This patch also reverts https://chromium-review.googlesource.com/c/chromium/src/+/6431846, +which removed range-requests-supported on non-http protocols. See https://issues.chromium.org/issues/41161335 +for more information. + diff --git a/third_party/blink/renderer/platform/media/multi_buffer_data_source.cc b/third_party/blink/renderer/platform/media/multi_buffer_data_source.cc -index 3e010fbec46d799839a2c50ed14c1d5744e99a30..ed98c853ba013acb8908a1651742d510bc8e4475 100644 +index 3e010fbec46d799839a2c50ed14c1d5744e99a30..e691db48e0a88aef7ada167ca09e7495f5bada5a 100644 --- a/third_party/blink/renderer/platform/media/multi_buffer_data_source.cc +++ b/third_party/blink/renderer/platform/media/multi_buffer_data_source.cc @@ -11,8 +11,10 @@ @@ -27,28 +31,33 @@ index 3e010fbec46d799839a2c50ed14c1d5744e99a30..ed98c853ba013acb8908a1651742d510 #include "media/base/media_log.h" #include "net/base/net_errors.h" #include "third_party/blink/renderer/platform/media/buffered_data_source_host_impl.h" -@@ -67,8 +69,20 @@ const int kUpdateBufferSizeFrequency = 32; - // How long to we delay a seek after a read? - constexpr base::TimeDelta kSeekDelay = base::Milliseconds(20); +@@ -69,6 +71,10 @@ constexpr base::TimeDelta kSeekDelay = base::Milliseconds(20); -+std::vector* GetStreamingSchemes() { -+ static base::NoDestructor> streaming_schemes({ -+ url::kHttpsScheme, -+ url::kHttpScheme -+ }); -+ return streaming_schemes.get(); -+} -+ } // namespace +void AddStreamingScheme(const char* new_scheme) { -+ GetStreamingSchemes()->push_back(new_scheme); ++ MultiBufferDataSource::GetStreamingSchemes()->push_back(new_scheme); +} + class MultiBufferDataSource::ReadOperation { public: ReadOperation() = delete; -@@ -149,7 +163,14 @@ bool MultiBufferDataSource::media_has_played() const { +@@ -143,13 +149,29 @@ MultiBufferDataSource::~MultiBufferDataSource() { + DCHECK(render_task_runner_->BelongsToCurrentThread()); + } + ++// static ++std::vector* MultiBufferDataSource::GetStreamingSchemes() { ++ static base::NoDestructor> streaming_schemes({ ++ url::kHttpsScheme, ++ url::kHttpScheme ++ }); ++ return streaming_schemes.get(); ++} ++ + bool MultiBufferDataSource::media_has_played() const { + return media_has_played_; + } bool MultiBufferDataSource::AssumeFullyBuffered() const { DCHECK(url_data_); @@ -65,7 +74,7 @@ index 3e010fbec46d799839a2c50ed14c1d5744e99a30..ed98c853ba013acb8908a1651742d510 void MultiBufferDataSource::SetReader( diff --git a/third_party/blink/renderer/platform/media/multi_buffer_data_source.h b/third_party/blink/renderer/platform/media/multi_buffer_data_source.h -index e886847425b1ea0b620a60e7b477249efac3c689..92dea7a9f491bb548f68d918ebde60cbf2a7d67f 100644 +index e886847425b1ea0b620a60e7b477249efac3c689..249416683c5381d4263f5f59202ca1687adf4407 100644 --- a/third_party/blink/renderer/platform/media/multi_buffer_data_source.h +++ b/third_party/blink/renderer/platform/media/multi_buffer_data_source.h @@ -17,6 +17,7 @@ @@ -85,3 +94,49 @@ index e886847425b1ea0b620a60e7b477249efac3c689..92dea7a9f491bb548f68d918ebde60cb // A data source capable of loading URLs and buffering the data using an // in-memory sliding window. // +@@ -65,6 +68,8 @@ class PLATFORM_EXPORT MultiBufferDataSource + return url_data_->mime_type(); + } + ++ static std::vector* GetStreamingSchemes(); ++ + // Method called on the render thread. + using InitializeCB = base::OnceCallback; + void Initialize(InitializeCB init_cb) override; +diff --git a/third_party/blink/renderer/platform/media/resource_multi_buffer_data_provider.cc b/third_party/blink/renderer/platform/media/resource_multi_buffer_data_provider.cc +index 34cee8e0f399468ae23a2ab4108bd65a6f12395c..be35c71dc0c7e0ae85c3f42f0b93375c09e43ddb 100644 +--- a/third_party/blink/renderer/platform/media/resource_multi_buffer_data_provider.cc ++++ b/third_party/blink/renderer/platform/media/resource_multi_buffer_data_provider.cc +@@ -8,6 +8,7 @@ + #include + + #include ++#include + + #include "base/containers/contains.h" + #include "base/location.h" +@@ -27,6 +28,7 @@ + #include "third_party/blink/public/platform/web_url_response.h" + #include "third_party/blink/public/web/web_associated_url_loader.h" + #include "third_party/blink/renderer/platform/media/cache_util.h" ++#include "third_party/blink/renderer/platform/media/multi_buffer_data_source.h" + #include "third_party/blink/renderer/platform/media/resource_fetch_context.h" + #include "third_party/blink/renderer/platform/media/url_index.h" + #include "third_party/blink/renderer/platform/weborigin/security_origin.h" +@@ -320,6 +322,16 @@ void ResourceMultiBufferDataProvider::DidReceiveResponse( + do_fail = true; + } + } else { ++ // For non-HTTP protocols, only set range_supported for registered streaming schemes ++ const std::string scheme = destination_url_data->url().Protocol().Ascii(); ++ ++ if (std::ranges::any_of(*MultiBufferDataSource::GetStreamingSchemes(), ++ [&scheme](const std::string& streaming_scheme) { ++ return base::EqualsCaseInsensitiveASCII(scheme, streaming_scheme); ++ })) { ++ destination_url_data->set_range_supported(); ++ } ++ + if (content_length != kPositionNotSpecified) { + destination_url_data->set_length(content_length + byte_pos()); + } From 1919b18b7269c0ceadfcd2cff2d7b095673f27e3 Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Wed, 6 Aug 2025 10:29:25 +0200 Subject: [PATCH 177/186] chore: bump chromium to 138.0.7204.224 (37-x-y) (#47974) chore: bump chromium in DEPS to 138.0.7204.224 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> --- DEPS | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DEPS b/DEPS index 70f0c0cdbb900..3e7299ae958bb 100644 --- a/DEPS +++ b/DEPS @@ -2,7 +2,7 @@ gclient_gn_args_from = 'src' vars = { 'chromium_version': - '138.0.7204.185', + '138.0.7204.224', 'node_version': 'v22.17.1', 'nan_version': From 3474f897f2fbf18029eabcfc792cf059ef6e22d5 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 6 Aug 2025 19:32:27 +0200 Subject: [PATCH 178/186] test: add TS smoke test for electron/utility (#47977) chore: add TS smoke test for electron/utility Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- spec/ts-smoke/electron/utility.ts | 67 +++++++++++++++++++++++++++++++ spec/ts-smoke/tsconfig.json | 1 + 2 files changed, 68 insertions(+) create mode 100644 spec/ts-smoke/electron/utility.ts diff --git a/spec/ts-smoke/electron/utility.ts b/spec/ts-smoke/electron/utility.ts new file mode 100644 index 0000000000000..090e1131e3b3c --- /dev/null +++ b/spec/ts-smoke/electron/utility.ts @@ -0,0 +1,67 @@ +/* eslint-disable */ + +import { net, systemPreferences } from 'electron/utility'; + +process.parentPort.on('message', (e) => { + if (e.data === 'Hello from parent!') { + process.parentPort.postMessage('Hello from child!'); + } +}); + +// net +// https://github.com/electron/electron/blob/main/docs/api/net.md + +const request = net.request('https://github.com'); +request.setHeader('Some-Custom-Header-Name', 'Some-Custom-Header-Value'); +const header = request.getHeader('Some-Custom-Header-Name'); +console.log('header', header); +request.removeHeader('Some-Custom-Header-Name'); +request.on('response', (response) => { + console.log(`Status code: ${response.statusCode}`); + console.log(`Status message: ${response.statusMessage}`); + console.log(`Headers: ${JSON.stringify(response.headers)}`); + console.log(`Http version: ${response.httpVersion}`); + console.log(`Major Http version: ${response.httpVersionMajor}`); + console.log(`Minor Http version: ${response.httpVersionMinor}`); + response.on('data', (chunk) => { + console.log(`BODY: ${chunk}`); + }); + response.on('end', () => { + console.log('No more data in response.'); + }); + response.on('error', () => { + console.log('"error" event emitted'); + }); + response.on('aborted', () => { + console.log('"aborted" event emitted'); + }); +}); +request.on('login', (authInfo, callback) => { + callback('username', 'password'); +}); +request.on('finish', () => { + console.log('"finish" event emitted'); +}); +request.on('abort', () => { + console.log('"abort" event emitted'); +}); +request.on('error', () => { + console.log('"error" event emitted'); +}); +request.write('Hello World!', 'utf-8'); +request.end('Hello World!', 'utf-8'); +request.abort(); + +// systemPreferences +// https://github.com/electron/electron/blob/main/docs/api/system-preferences.md + +if (process.platform === 'win32') { + systemPreferences.on('color-changed', () => { console.log('color changed'); }); +} + +if (process.platform === 'darwin') { + const value = systemPreferences.getUserDefault('Foo', 'string'); + console.log(value); + const value2 = systemPreferences.getUserDefault('Foo', 'boolean'); + console.log(value2); +} diff --git a/spec/ts-smoke/tsconfig.json b/spec/ts-smoke/tsconfig.json index 35f95b765351b..2e19b963c1a9a 100644 --- a/spec/ts-smoke/tsconfig.json +++ b/spec/ts-smoke/tsconfig.json @@ -15,6 +15,7 @@ "files": [ "electron/main.ts", "electron/renderer.ts", + "electron/utility.ts", "../../electron.d.ts" ] } \ No newline at end of file From e83b0f6c2350c2e122fd69ebaf326513ea331f62 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 6 Aug 2025 19:35:15 +0200 Subject: [PATCH 179/186] feat: add `app.getRecentDocuments()` (#47923) feat: add app.getRecentDocuments() Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- docs/api/app.md | 16 ++++++++ docs/tutorial/recent-documents.md | 6 +++ shell/browser/api/electron_api_app.cc | 2 + shell/browser/browser.h | 3 ++ shell/browser/browser_linux.cc | 4 ++ shell/browser/browser_mac.mm | 24 +++++++++--- shell/browser/browser_win.cc | 53 +++++++++++++++++++++++++-- spec/api-app-spec.ts | 45 ++++++++++++++++++++++- 8 files changed, 142 insertions(+), 11 deletions(-) diff --git a/docs/api/app.md b/docs/api/app.md index 119c867abef9b..0ff66e518e1fe 100644 --- a/docs/api/app.md +++ b/docs/api/app.md @@ -775,6 +775,22 @@ bar, and on macOS, you can visit it from dock menu. Clears the recent documents list. +### `app.getRecentDocuments()` _macOS_ _Windows_ + +Returns `string[]` - An array containing documents in the most recent documents list. + +```js +const { app } = require('electron') + +const path = require('node:path') + +const file = path.join(app.getPath('desktop'), 'foo.txt') +app.addRecentDocument(file) + +const recents = app.getRecentDocuments() +console.log(recents) // ['/path/to/desktop/foo.txt'} +``` + ### `app.setAsDefaultProtocolClient(protocol[, path, args])` * `protocol` string - The name of your protocol, without `://`. For example, diff --git a/docs/tutorial/recent-documents.md b/docs/tutorial/recent-documents.md index 8bbe27aad952c..072d8a12e170b 100644 --- a/docs/tutorial/recent-documents.md +++ b/docs/tutorial/recent-documents.md @@ -77,6 +77,11 @@ To clear the list of recent documents, use the In this guide, the list of documents is cleared once all windows have been closed. +#### Accessing the list of recent documents + +To access the list of recent documents, use the +[app.getRecentDocuments][getrecentdocuments] API. + ## Additional information ### Windows Notes @@ -138,5 +143,6 @@ of `app` module will be emitted for it. [dock-menu-image]: https://cloud.githubusercontent.com/assets/639601/5069610/2aa80758-6e97-11e4-8cfb-c1a414a10774.png [addrecentdocument]: ../api/app.md#appaddrecentdocumentpath-macos-windows [clearrecentdocuments]: ../api/app.md#appclearrecentdocuments-macos-windows +[getrecentdocuments]: ../api/app.md#appgetrecentdocuments-macos-windows [app-registration]: https://learn.microsoft.com/en-us/windows/win32/shell/app-registration [menu-item-image]: https://user-images.githubusercontent.com/3168941/33003655-ea601c3a-cd70-11e7-97fa-7c062149cfb1.png diff --git a/shell/browser/api/electron_api_app.cc b/shell/browser/api/electron_api_app.cc index 7ff15cacc5b9a..f2cb65aeeb4ef 100644 --- a/shell/browser/api/electron_api_app.cc +++ b/shell/browser/api/electron_api_app.cc @@ -1719,6 +1719,8 @@ gin::ObjectTemplateBuilder App::GetObjectTemplateBuilder(v8::Isolate* isolate) { base::BindRepeating(&Browser::AddRecentDocument, browser)) .SetMethod("clearRecentDocuments", base::BindRepeating(&Browser::ClearRecentDocuments, browser)) + .SetMethod("getRecentDocuments", + base::BindRepeating(&Browser::GetRecentDocuments, browser)) #if BUILDFLAG(IS_WIN) .SetMethod("setAppUserModelId", base::BindRepeating(&Browser::SetAppUserModelID, browser)) diff --git a/shell/browser/browser.h b/shell/browser/browser.h index aa5c8207c56be..f4edd1d7d77aa 100644 --- a/shell/browser/browser.h +++ b/shell/browser/browser.h @@ -125,6 +125,9 @@ class Browser : private WindowListObserver { // Clear the recent documents list. void ClearRecentDocuments(); + // Return the recent documents list. + std::vector GetRecentDocuments(); + #if BUILDFLAG(IS_WIN) // Set the application user model ID. void SetAppUserModelID(const std::wstring& name); diff --git a/shell/browser/browser_linux.cc b/shell/browser/browser_linux.cc index 55c1762480ce9..03e1a9521c11d 100644 --- a/shell/browser/browser_linux.cc +++ b/shell/browser/browser_linux.cc @@ -95,6 +95,10 @@ bool SetDefaultWebClient(const std::string& protocol) { void Browser::AddRecentDocument(const base::FilePath& path) {} +std::vector Browser::GetRecentDocuments() { + return std::vector(); +} + void Browser::ClearRecentDocuments() {} bool Browser::SetAsDefaultProtocolClient(const std::string& protocol, diff --git a/shell/browser/browser_mac.mm b/shell/browser/browser_mac.mm index 1a78da0a650db..c4b67ed5cc142 100644 --- a/shell/browser/browser_mac.mm +++ b/shell/browser/browser_mac.mm @@ -162,19 +162,31 @@ LoginItemSettings GetLoginItemSettingsDeprecated() { } void Browser::AddRecentDocument(const base::FilePath& path) { - NSString* path_string = base::apple::FilePathToNSString(path); - if (!path_string) + NSURL* url = base::apple::FilePathToNSURL(path); + if (!url) { + LOG(WARNING) << "Failed to convert file path " << path.value() + << " to NSURL"; return; - NSURL* u = [NSURL fileURLWithPath:path_string]; - if (!u) - return; - [[NSDocumentController sharedDocumentController] noteNewRecentDocumentURL:u]; + } + + [[NSDocumentController sharedDocumentController] + noteNewRecentDocumentURL:url]; } void Browser::ClearRecentDocuments() { [[NSDocumentController sharedDocumentController] clearRecentDocuments:nil]; } +std::vector Browser::GetRecentDocuments() { + NSArray* recentURLs = + [[NSDocumentController sharedDocumentController] recentDocumentURLs]; + std::vector documents; + documents.reserve([recentURLs count]); + for (NSURL* url in recentURLs) + documents.push_back(std::string([url.path UTF8String])); + return documents; +} + bool Browser::RemoveAsDefaultProtocolClient(const std::string& protocol, gin::Arguments* args) { NSString* identifier = [base::apple::MainBundle() bundleIdentifier]; diff --git a/shell/browser/browser_win.cc b/shell/browser/browser_win.cc index fb75895404eb2..3b08b32cf6add 100644 --- a/shell/browser/browser_win.cc +++ b/shell/browser/browser_win.cc @@ -17,6 +17,7 @@ #include "base/base_paths.h" #include "base/command_line.h" #include "base/file_version_info.h" +#include "base/files/file_enumerator.h" #include "base/files/file_path.h" #include "base/logging.h" #include "base/path_service.h" @@ -314,14 +315,33 @@ void GetApplicationInfoForProtocolUsingAssocQuery( app_display_name, std::move(promise)); } +std::string ResolveShortcut(const base::FilePath& lnk_path) { + std::string target_path; + + CComPtr shell_link; + if (SUCCEEDED(CoCreateInstance(CLSID_ShellLink, nullptr, CLSCTX_INPROC_SERVER, + IID_PPV_ARGS(&shell_link)))) { + CComPtr persist_file; + if (SUCCEEDED(shell_link->QueryInterface(IID_PPV_ARGS(&persist_file)))) { + if (SUCCEEDED(persist_file->Load(lnk_path.value().c_str(), STGM_READ))) { + WCHAR resolved_path[MAX_PATH]; + if (SUCCEEDED( + shell_link->GetPath(resolved_path, MAX_PATH, nullptr, 0))) { + target_path = base::FilePath(resolved_path).MaybeAsASCII(); + } + } + } + } + + return target_path; +} + void Browser::AddRecentDocument(const base::FilePath& path) { CComPtr item; HRESULT hr = SHCreateItemFromParsingName(path.value().c_str(), nullptr, IID_PPV_ARGS(&item)); if (SUCCEEDED(hr)) { - SHARDAPPIDINFO info; - info.psi = item; - info.pszAppID = GetAppUserModelID(); + SHARDAPPIDINFO info = {item, GetAppUserModelID()}; SHAddToRecentDocs(SHARD_APPIDINFO, &info); } } @@ -330,6 +350,33 @@ void Browser::ClearRecentDocuments() { SHAddToRecentDocs(SHARD_APPIDINFO, nullptr); } +std::vector Browser::GetRecentDocuments() { + ScopedAllowBlockingForElectron allow_blocking; + std::vector docs; + + PWSTR recent_path_ptr = nullptr; + HRESULT hr = + SHGetKnownFolderPath(FOLDERID_Recent, 0, nullptr, &recent_path_ptr); + if (SUCCEEDED(hr) && recent_path_ptr) { + base::FilePath recent_folder(recent_path_ptr); + CoTaskMemFree(recent_path_ptr); + + base::FileEnumerator enumerator(recent_folder, /*recursive=*/false, + base::FileEnumerator::FILES, + FILE_PATH_LITERAL("*.lnk")); + + for (base::FilePath file = enumerator.Next(); !file.empty(); + file = enumerator.Next()) { + std::string resolved_path = ResolveShortcut(file); + if (!resolved_path.empty()) { + docs.push_back(resolved_path); + } + } + } + + return docs; +} + void Browser::SetAppUserModelID(const std::wstring& name) { electron::SetAppUserModelID(name); } diff --git a/spec/api-app-spec.ts b/spec/api-app-spec.ts index 1aa4daae04e07..e6f21f34850ad 100644 --- a/spec/api-app-spec.ts +++ b/spec/api-app-spec.ts @@ -11,6 +11,7 @@ import * as http from 'node:http'; import * as https from 'node:https'; import * as net from 'node:net'; import * as path from 'node:path'; +import { setTimeout } from 'node:timers/promises'; import { promisify } from 'node:util'; import { collectStreamBody, getResponse } from './lib/net-helpers'; @@ -19,6 +20,8 @@ import { closeWindow, closeAllWindows } from './lib/window-helpers'; const fixturesPath = path.resolve(__dirname, 'fixtures'); +const isMacOSx64 = process.platform === 'darwin' && process.arch === 'x64'; + describe('electron module', () => { it('does not expose internal modules to require', () => { expect(() => { @@ -356,6 +359,44 @@ describe('app module', () => { }); }); + // GitHub Actions macOS-13 runners used for x64 seem to have a problem with this test. + ifdescribe(process.platform !== 'linux' && !isMacOSx64)('app.{add|get|clear}RecentDocument(s)', () => { + const tempFiles = [ + path.join(fixturesPath, 'foo.txt'), + path.join(fixturesPath, 'bar.txt'), + path.join(fixturesPath, 'baz.txt') + ]; + + afterEach(() => { + app.clearRecentDocuments(); + for (const file of tempFiles) { + fs.unlinkSync(file); + } + }); + + beforeEach(() => { + for (const file of tempFiles) { + fs.writeFileSync(file, 'Lorem Ipsum'); + } + }); + + it('can add a recent document', async () => { + app.addRecentDocument(tempFiles[0]); + await setTimeout(2000); + expect(app.getRecentDocuments()).to.include.members([tempFiles[0]]); + }); + + it('can clear recent documents', async () => { + app.addRecentDocument(tempFiles[1]); + app.addRecentDocument(tempFiles[2]); + await setTimeout(2000); + expect(app.getRecentDocuments()).to.include.members([tempFiles[1], tempFiles[2]]); + app.clearRecentDocuments(); + await setTimeout(2000); + expect(app.getRecentDocuments()).to.deep.equal([]); + }); + }); + describe('app.relaunch', () => { let server: net.Server | null = null; const socketPath = process.platform === 'win32' ? '\\\\.\\pipe\\electron-app-relaunch' : '/tmp/electron-app-relaunch'; @@ -553,8 +594,8 @@ describe('app module', () => { describe('app.badgeCount', () => { const platformIsNotSupported = - (process.platform === 'win32') || - (process.platform === 'linux' && !app.isUnityRunning()); + (process.platform === 'win32') || + (process.platform === 'linux' && !app.isUnityRunning()); const expectedBadgeCount = 42; From 4f426daecacf4c0360275cda613ce8817b776650 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Wed, 6 Aug 2025 19:40:07 +0200 Subject: [PATCH 180/186] feat: Use DIR_ASSETS path to locate resource bundles (#47951) * feat: Use DIR_ASSETS path to locate resource bundles Co-authored-by: Will Anderson * Use DIR_ASSETS for calculating ASAR relative paths Co-authored-by: Will Anderson * Add test to verify 'assets' matches parent dir of 'exe' Co-authored-by: Will Anderson * Add Mac-specific test for assets path (but it is failing) Co-authored-by: Will Anderson * test: Update app.getPath('assets') to expect an exception on Mac Co-authored-by: Will Anderson * docs: Update docs for 'assets' path to indicate that it's only available on Windows + Linux Co-authored-by: Will Anderson * fix: Don't define 'assets' mapping on macOS Co-authored-by: Will Anderson --------- Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Will Anderson --- docs/api/app.md | 3 ++- shell/app/electron_main_delegate.cc | 2 +- shell/browser/api/electron_api_app.cc | 3 +++ shell/common/asar/archive_win.cc | 8 ++++---- shell/common/node_bindings.cc | 7 +++---- spec/api-app-spec.ts | 14 ++++++++++++++ 6 files changed, 27 insertions(+), 10 deletions(-) diff --git a/docs/api/app.md b/docs/api/app.md index 0ff66e518e1fe..e16d3dc7c33fe 100644 --- a/docs/api/app.md +++ b/docs/api/app.md @@ -601,6 +601,7 @@ Returns `string` - The current application directory. * `%APPDATA%` on Windows * `$XDG_CONFIG_HOME` or `~/.config` on Linux * `~/Library/Application Support` on macOS + * `assets` The directory where app assets such as `resources.pak` are stored. By default this is the same as the folder containing the `exe` path. Available on Windows and Linux only. * `userData` The directory for storing your app's configuration files, which by default is the `appData` directory appended with your app's name. By convention files storing user data should be written to this directory, and @@ -615,7 +616,7 @@ Returns `string` - The current application directory. directory. * `temp` Temporary directory. * `exe` The current executable file. - * `module` The `libchromiumcontent` library. + * `module` The location of the Chromium module. By default this is synonymous with `exe`. * `desktop` The current user's Desktop directory. * `documents` Directory for a user's "My Documents". * `downloads` Directory for a user's downloads. diff --git a/shell/app/electron_main_delegate.cc b/shell/app/electron_main_delegate.cc index fb58a1e8370c2..a15ce416dcd8d 100644 --- a/shell/app/electron_main_delegate.cc +++ b/shell/app/electron_main_delegate.cc @@ -220,7 +220,7 @@ std::string LoadResourceBundle(const std::string& locale) { pak_dir = base::apple::FrameworkBundlePath().Append(FILE_PATH_LITERAL("Resources")); #else - base::PathService::Get(base::DIR_MODULE, &pak_dir); + base::PathService::Get(base::DIR_ASSETS, &pak_dir); #endif std::string loaded_locale = ui::ResourceBundle::InitSharedInstanceWithLocale( diff --git a/shell/browser/api/electron_api_app.cc b/shell/browser/api/electron_api_app.cc index f2cb65aeeb4ef..b914e10fc0d2a 100644 --- a/shell/browser/api/electron_api_app.cc +++ b/shell/browser/api/electron_api_app.cc @@ -382,6 +382,9 @@ int GetPathConstant(std::string_view name) { // clang-format off constexpr auto Lookup = base::MakeFixedFlatMap({ {"appData", DIR_APP_DATA}, +#if !BUILDFLAG(IS_MAC) + {"assets", base::DIR_ASSETS}, +#endif #if BUILDFLAG(IS_POSIX) {"cache", base::DIR_CACHE}, #else diff --git a/shell/common/asar/archive_win.cc b/shell/common/asar/archive_win.cc index 861c2fec086e7..ae3e73797bf4f 100644 --- a/shell/common/asar/archive_win.cc +++ b/shell/common/asar/archive_win.cc @@ -26,13 +26,13 @@ const wchar_t kIntegrityCheckResourceType[] = L"Integrity"; const wchar_t kIntegrityCheckResourceItem[] = L"ElectronAsar"; std::optional Archive::RelativePath() const { - base::FilePath exe_path; - if (!base::PathService::Get(base::FILE_EXE, &exe_path)) { - LOG(FATAL) << "Couldn't get exe file path"; + base::FilePath assets_dir; + if (!base::PathService::Get(base::DIR_ASSETS, &assets_dir)) { + LOG(FATAL) << "Couldn't get assets directory path"; } base::FilePath relative_path; - if (!exe_path.DirName().AppendRelativePath(path_, &relative_path)) { + if (!assets_dir.AppendRelativePath(path_, &relative_path)) { return std::nullopt; } diff --git a/shell/common/node_bindings.cc b/shell/common/node_bindings.cc index c1b1b3e4ef624..031d53d51514b 100644 --- a/shell/common/node_bindings.cc +++ b/shell/common/node_bindings.cc @@ -457,11 +457,10 @@ base::FilePath GetResourcesPath() { #if BUILDFLAG(IS_MAC) return MainApplicationBundlePath().Append("Contents").Append("Resources"); #else - auto* command_line = base::CommandLine::ForCurrentProcess(); - base::FilePath exec_path(command_line->GetProgram()); - base::PathService::Get(base::FILE_EXE, &exec_path); + base::FilePath assets_path; + base::PathService::Get(base::DIR_ASSETS, &assets_path); - return exec_path.DirName().Append(FILE_PATH_LITERAL("resources")); + return assets_path.Append(FILE_PATH_LITERAL("resources")); #endif } } // namespace diff --git a/spec/api-app-spec.ts b/spec/api-app-spec.ts index e6f21f34850ad..34983c484e9e6 100644 --- a/spec/api-app-spec.ts +++ b/spec/api-app-spec.ts @@ -1109,6 +1109,20 @@ describe('app module', () => { expect(paths).to.deep.equal([true, true, true]); }); + if (process.platform === 'darwin') { + it('throws an error when trying to get the assets path on macOS', () => { + expect(() => { + app.getPath('assets' as any); + }).to.throw(/Failed to get 'assets' path/); + }); + } else { + it('returns an assets path that is identical to the module path', () => { + const assetsPath = app.getPath('assets'); + expect(fs.existsSync(assetsPath)).to.be.true(); + expect(assetsPath).to.equal(path.dirname(app.getPath('module'))); + }); + } + it('throws an error when the name is invalid', () => { expect(() => { app.getPath('does-not-exist' as any); From 922f707ef5fada80a6efdc19d284cca8ce6ae69e Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 7 Aug 2025 10:30:56 -0400 Subject: [PATCH 181/186] fix: allow importing from electron/utility at runtime (#47988) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: David Sanders --- lib/common/init.ts | 11 +++++++---- lib/utility/api/net.ts | 3 +-- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/lib/common/init.ts b/lib/common/init.ts index d6ad120eb931d..a8d266d7f3349 100644 --- a/lib/common/init.ts +++ b/lib/common/init.ts @@ -93,20 +93,23 @@ makeElectronModule('electron'); makeElectronModule('electron/common'); if (process.type === 'browser') { makeElectronModule('electron/main'); -} -if (process.type === 'renderer') { +} else if (process.type === 'renderer') { makeElectronModule('electron/renderer'); +} else if (process.type === 'utility') { + makeElectronModule('electron/utility'); } const originalResolveFilename = Module._resolveFilename; -// 'electron/main', 'electron/renderer' and 'electron/common' are module aliases +// 'electron/{common,main,renderer,utility}' are module aliases // of the 'electron' module for TypeScript purposes, i.e., the types for // 'electron/main' consist of only main process modules, etc. It is intentional // that these can be `require()`-ed from both the main process as well as the // renderer process regardless of the names, they're superficial for TypeScript // only. -const electronModuleNames = new Set(['electron', 'electron/main', 'electron/renderer', 'electron/common']); +const electronModuleNames = new Set([ + 'electron', 'electron/main', 'electron/renderer', 'electron/common', 'electron/utility' +]); Module._resolveFilename = function (request, parent, isMain, options) { if (electronModuleNames.has(request)) { return 'electron'; diff --git a/lib/utility/api/net.ts b/lib/utility/api/net.ts index 70228ee0e5f46..8ef93d0e282ff 100644 --- a/lib/utility/api/net.ts +++ b/lib/utility/api/net.ts @@ -1,8 +1,7 @@ import { fetchWithSession } from '@electron/internal/browser/api/net-fetch'; import { ClientRequest } from '@electron/internal/common/api/net-client-request'; -import { IncomingMessage } from 'electron/utility'; -import type { ClientRequestConstructorOptions } from 'electron/utility'; +import type { ClientRequestConstructorOptions, IncomingMessage } from 'electron/utility'; const { isOnline, resolveHost } = process._linkedBinding('electron_common_net'); From f409eb0d7ad32e97ae9f8d44e4402bce0da6b4e7 Mon Sep 17 00:00:00 2001 From: "trop[bot]" <37223003+trop[bot]@users.noreply.github.com> Date: Thu, 7 Aug 2025 17:01:43 -0400 Subject: [PATCH 182/186] fix: compilation error when disabling extensions and pdf_viewer (#47994) Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com> Co-authored-by: Jinli Wu --- shell/browser/plugins/plugin_utils.cc | 3 +-- shell/browser/printing/printing_utils.cc | 4 +++- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/shell/browser/plugins/plugin_utils.cc b/shell/browser/plugins/plugin_utils.cc index 9c220eb888b23..b3f36a8b3d4ac 100644 --- a/shell/browser/plugins/plugin_utils.cc +++ b/shell/browser/plugins/plugin_utils.cc @@ -33,6 +33,7 @@ std::string PluginUtils::GetExtensionIdForMimeType( base::flat_map PluginUtils::GetMimeTypeToExtensionIdMap( content::BrowserContext* browser_context) { + base::flat_map mime_type_to_extension_id_map; #if BUILDFLAG(ENABLE_ELECTRON_EXTENSIONS) const auto& allowed_extension_ids = MimeTypesHandler::GetMIMETypeAllowlist(); if (allowed_extension_ids.empty()) @@ -41,8 +42,6 @@ PluginUtils::GetMimeTypeToExtensionIdMap( const extensions::ExtensionSet& enabled_extensions = extensions::ExtensionRegistry::Get(browser_context)->enabled_extensions(); - base::flat_map mime_type_to_extension_id_map; - // Go through the white-listed extensions and try to use them to intercept // the URL request. for (const std::string& id : allowed_extension_ids) { diff --git a/shell/browser/printing/printing_utils.cc b/shell/browser/printing/printing_utils.cc index 852a0c6dba687..f8e4583630ba8 100644 --- a/shell/browser/printing/printing_utils.cc +++ b/shell/browser/printing/printing_utils.cc @@ -81,6 +81,7 @@ bool IsDeviceNameValid(const std::u16string& device_name) { namespace { +#if BUILDFLAG(ENABLE_PDF_VIEWER) // Duplicated from chrome/browser/printing/print_view_manager_common.cc content::RenderFrameHost* GetFullPagePlugin(content::WebContents* contents) { content::RenderFrameHost* full_page_plugin = nullptr; @@ -99,6 +100,7 @@ content::RenderFrameHost* GetFullPagePlugin(content::WebContents* contents) { #endif // BUILDFLAG(ENABLE_ELECTRON_EXTENSIONS) return full_page_plugin; } +#endif // BUILDFLAG(ENABLE_PDF_VIEWER) } // namespace @@ -119,7 +121,7 @@ content::RenderFrameHost* GetRenderFrameHostToUse( if (pdf_rfh) { return pdf_rfh; } -#endif // BUILDFLAG(ENABLE_PDF) +#endif // BUILDFLAG(ENABLE_PDF_VIEWER) auto* focused_frame = contents->GetFocusedFrame(); return (focused_frame && focused_frame->HasSelection()) ? focused_frame From a954f9f245690f32c7d7ba8b07a17812f15656ea Mon Sep 17 00:00:00 2001 From: "electron-roller[bot]" <84116207+electron-roller[bot]@users.noreply.github.com> Date: Fri, 8 Aug 2025 10:55:00 +0200 Subject: [PATCH 183/186] chore: bump node to v22.18.0 (37-x-y) (#47935) chore: bump node to v22.18.0 Co-authored-by: electron-roller[bot] <84116207+electron-roller[bot]@users.noreply.github.com> Co-authored-by: Shelley Vohr --- DEPS | 2 +- lib/node/asar-fs-wrapper.ts | 18 ++--- patches/node/.patches | 3 - patches/node/build_add_gn_build_files.patch | 24 +++---- ...w_unbundling_of_node_js_dependencies.patch | 4 +- ...etraits_signatures_to_avoid_conflict.patch | 4 +- .../build_compile_with_c_20_support.patch | 6 +- patches/node/build_enable_perfetto.patch | 6 +- ...compilation_fails_if_not_using_a_new.patch | 8 +-- ...f_original-fs_and_custom_embedder_js.patch | 6 +- ...o_use_custom_inspector_protocol_path.patch | 60 ----------------- ...e_clang_as_default_compiler_on_macos.patch | 2 +- ...de_entrypoint_to_be_a_builtin_module.patch | 2 +- ...deprecation_ftbfs_in_simdjson_header.patch | 8 +-- ...e_expose_importmoduledynamically_and.patch | 18 ++--- ...move_protocol_maybe_from_node_string.patch | 33 ---------- ...cli_move_--trace-atomics-wait_to_eol.patch | 50 ++++++++++++-- .../node/cli_remove_deprecated_v8_flag.patch | 8 +-- ...enable_crashpad_linux_node_processes.patch | 13 ++-- ...matched-new-delete_in_debug_utils_cc.patch | 31 --------- ..._values_for_variables_in_common_gypi.patch | 2 +- ...g_fileexists_fn_to_legacymainresolve.patch | 14 ++-- ...ssert_module_in_the_renderer_process.patch | 10 +-- .../fix_crypto_tests_to_run_with_bssl.patch | 10 +-- ..._do_not_resolve_electron_entrypoints.patch | 4 +- ...se_readfilesync_override_for_modules.patch | 4 +- ...n_electron_module_via_the_esm_loader.patch | 34 +++++----- ...ingssl_and_openssl_incompatibilities.patch | 27 ++------ ...in_esm_loaders_to_apply_asar_patches.patch | 24 ++----- .../fix_remove_fastapitypedarray_usage.patch | 66 ++----------------- .../pass_all_globals_through_require.patch | 4 +- ...ch_cppgc_heap_on_v8_isolate_creation.patch | 4 +- ..._on_wrapper-descriptor-based_cppheap.patch | 2 +- ...ted_fields_of_fastapicallbackoptions.patch | 28 ++------ .../node/support_v8_sandboxed_pointers.patch | 2 +- ...st_formally_mark_some_tests_as_flaky.patch | 4 +- script/node-disabled-tests.json | 1 + 37 files changed, 182 insertions(+), 364 deletions(-) delete mode 100644 patches/node/build_option_to_use_custom_inspector_protocol_path.patch delete mode 100644 patches/node/chore_remove_protocol_maybe_from_node_string.patch delete mode 100644 patches/node/fix_-wmismatched-new-delete_in_debug_utils_cc.patch diff --git a/DEPS b/DEPS index 3e7299ae958bb..3dd37c26e3622 100644 --- a/DEPS +++ b/DEPS @@ -4,7 +4,7 @@ vars = { 'chromium_version': '138.0.7204.224', 'node_version': - 'v22.17.1', + 'v22.18.0', 'nan_version': 'e14bdcd1f72d62bca1d541b66da43130384ec213', 'squirrel.mac_version': diff --git a/lib/node/asar-fs-wrapper.ts b/lib/node/asar-fs-wrapper.ts index 90d256342a060..2457fb0f2dd1f 100644 --- a/lib/node/asar-fs-wrapper.ts +++ b/lib/node/asar-fs-wrapper.ts @@ -742,7 +742,7 @@ export const wrapFsWithAsar = (fs: Record) => { } const dirent = getDirent(currentPath, result[0][i], type); - const stat = internalBinding('fs').internalModuleStat(binding, resultPath); + const stat = internalBinding('fs').internalModuleStat(resultPath); context.readdirResults.push(dirent); if (dirent.isDirectory() || stat === 1) { @@ -755,7 +755,7 @@ export const wrapFsWithAsar = (fs: Record) => { for (let i = 0; i < result.length; i++) { const resultPath = path.join(currentPath, result[i]); const relativeResultPath = path.relative(context.basePath, resultPath); - const stat = internalBinding('fs').internalModuleStat(binding, resultPath); + const stat = internalBinding('fs').internalModuleStat(resultPath); context.readdirResults.push(relativeResultPath); if (stat === 1) { @@ -825,7 +825,7 @@ export const wrapFsWithAsar = (fs: Record) => { if (context.withFileTypes) { readdirResult = [ [...readdirResult], readdirResult.map((p: string) => { - return internalBinding('fs').internalModuleStat(binding, path.join(pathArg, p)); + return internalBinding('fs').internalModuleStat(path.join(pathArg, p)); }) ]; } @@ -1010,9 +1010,9 @@ export const wrapFsWithAsar = (fs: Record) => { }); const { internalModuleStat } = binding; - internalBinding('fs').internalModuleStat = (receiver: unknown, pathArgument: string) => { + internalBinding('fs').internalModuleStat = (pathArgument: string) => { const pathInfo = splitPath(pathArgument); - if (!pathInfo.isAsar) return internalModuleStat(receiver, pathArgument); + if (!pathInfo.isAsar) return internalModuleStat(pathArgument); const { asarPath, filePath } = pathInfo; // -ENOENT @@ -1047,7 +1047,7 @@ export const wrapFsWithAsar = (fs: Record) => { if (withFileTypes) { initialItem = [ [...initialItem], initialItem.map((p: string) => { - return internalBinding('fs').internalModuleStat(binding, path.join(originalPath, p)); + return internalBinding('fs').internalModuleStat(path.join(originalPath, p)); }) ]; } @@ -1080,7 +1080,7 @@ export const wrapFsWithAsar = (fs: Record) => { readdirResult = [ [...files], files.map((p: string) => { - return internalBinding('fs').internalModuleStat(binding, path.join(direntPath, p)); + return internalBinding('fs').internalModuleStat(path.join(direntPath, p)); }) ]; } else { @@ -1101,7 +1101,7 @@ export const wrapFsWithAsar = (fs: Record) => { const { 0: pathArg, 1: readDir } = queue.pop(); for (const ent of readDir) { const direntPath = path.join(pathArg, ent); - const stat = internalBinding('fs').internalModuleStat(binding, direntPath); + const stat = internalBinding('fs').internalModuleStat(direntPath); result.push(path.relative(originalPath, direntPath)); if (stat === 1) { @@ -1155,7 +1155,7 @@ export const wrapFsWithAsar = (fs: Record) => { if (context.withFileTypes) { readdirResult = [ [...readdirResult], readdirResult.map((p: string) => { - return internalBinding('fs').internalModuleStat(binding, path.join(pathArg, p)); + return internalBinding('fs').internalModuleStat(path.join(pathArg, p)); }) ]; } diff --git a/patches/node/.patches b/patches/node/.patches index ecbe186e500f9..17e363ed7928b 100644 --- a/patches/node/.patches +++ b/patches/node/.patches @@ -37,7 +37,6 @@ test_use_static_method_names_in_call_stacks.patch fix_remove_fastapitypedarray_usage.patch test_handle_explicit_resource_management_globals.patch build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch -build_option_to_use_custom_inspector_protocol_path.patch fix_adjust_wpt_and_webidl_tests_for_enabled_float16array.patch chore_add_createexternalizabletwobytestring_to_globals.patch refactor_attach_cppgc_heap_on_v8_isolate_creation.patch @@ -46,5 +45,3 @@ cli_move_--trace-atomics-wait_to_eol.patch fix_cppgc_initializing_twice.patch fix_task_starvation_in_inspector_context_test.patch fix_expose_readfilesync_override_for_modules.patch -chore_remove_protocol_maybe_from_node_string.patch -fix_-wmismatched-new-delete_in_debug_utils_cc.patch diff --git a/patches/node/build_add_gn_build_files.patch b/patches/node/build_add_gn_build_files.patch index 86ea0937ab059..5e0111ef8ca4d 100644 --- a/patches/node/build_add_gn_build_files.patch +++ b/patches/node/build_add_gn_build_files.patch @@ -11,7 +11,7 @@ really in 20/21. We have to wait until 22 is released to be able to build with upstream GN files. diff --git a/configure.py b/configure.py -index 4560bac7b8e3c707ecea5a425f642efb9de9ed36..e9c2a4391f4058a21a259cacaac4fde5d199288e 100755 +index 2415940835036226799a7ea14c6687cc0d56c523..0feb07afbccad97a92cee00954443407eb20ac67 100755 --- a/configure.py +++ b/configure.py @@ -1722,7 +1722,7 @@ def configure_v8(o, configs): @@ -24,7 +24,7 @@ index 4560bac7b8e3c707ecea5a425f642efb9de9ed36..e9c2a4391f4058a21a259cacaac4fde5 o['variables']['v8_enable_external_code_space'] = 1 if options.enable_pointer_compression else 0 o['variables']['v8_enable_31bit_smis_on_64bit_arch'] = 1 if options.enable_pointer_compression else 0 diff --git a/node.gni b/node.gni -index 35ccd0487f20cece033d58827ecb7ed016908ee4..62cd49c6a87074912a1cb6792576c8d4f239b669 100644 +index b049f0692980c3e26771c3209c3bdd2e9a4d637b..e2407027ab05e59b2f0f1c213b98ea469db7a91b 100644 --- a/node.gni +++ b/node.gni @@ -5,10 +5,10 @@ @@ -40,7 +40,7 @@ index 35ccd0487f20cece033d58827ecb7ed016908ee4..62cd49c6a87074912a1cb6792576c8d4 # The location of OpenSSL - use the one from node's deps by default. node_openssl_path = "$node_path/deps/openssl" -@@ -39,12 +39,15 @@ declare_args() { +@@ -42,12 +42,15 @@ declare_args() { # The variable is called "openssl" for parity with node's GYP build. node_use_openssl = true @@ -57,7 +57,7 @@ index 35ccd0487f20cece033d58827ecb7ed016908ee4..62cd49c6a87074912a1cb6792576c8d4 # Custom build tag. node_tag = "" -@@ -64,10 +67,16 @@ declare_args() { +@@ -67,10 +70,16 @@ declare_args() { # TODO(zcbenz): There are few broken things for now: # 1. cross-os compilation is not supported. # 2. node_mksnapshot crashes when cross-compiling for x64 from arm64. @@ -76,10 +76,10 @@ index 35ccd0487f20cece033d58827ecb7ed016908ee4..62cd49c6a87074912a1cb6792576c8d4 assert(!node_enable_inspector || node_use_openssl, diff --git a/src/node_builtins.cc b/src/node_builtins.cc -index 092341dbfbabe15b15ed43057d399f754505f6fd..f14b45850e42585f5686b7201e2b8281ed8c24e1 100644 +index abf1583cdac9f139056cf4809f14e28e62f6d24c..8b104e175ccf8de90c138337f83f8f6ce1348ac7 100644 --- a/src/node_builtins.cc +++ b/src/node_builtins.cc -@@ -788,6 +788,7 @@ void BuiltinLoader::RegisterExternalReferences( +@@ -789,6 +789,7 @@ void BuiltinLoader::RegisterExternalReferences( registry->Register(GetNatives); RegisterExternalReferencesForInternalizedBuiltinCode(registry); @@ -279,7 +279,7 @@ index 856878c33681a73d41016729dabe48b0a6a80589..91a11852d206b65485fe90fd037a0bd1 if sys.platform == 'win32': files = [ x.replace('\\', '/') for x in files ] diff --git a/unofficial.gni b/unofficial.gni -index 44641b92678ab2f28e6f5de75a92878f9f3d322d..a6cfd45b109c7b38fcf1529468ff64d3c1c8bd1b 100644 +index da565473f1ae96b4d009935f7733e6ab15ea9de2..26ebc811272ef2990f8d090c54e7f5294aab9d37 100644 --- a/unofficial.gni +++ b/unofficial.gni @@ -22,6 +22,11 @@ template("node_gn_build") { @@ -354,8 +354,8 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..a6cfd45b109c7b38fcf1529468ff64d3 + } if (node_enable_inspector) { deps += [ - "src/inspector:crdtp", -@@ -214,6 +232,10 @@ template("node_gn_build") { + "$node_inspector_protocol_path:crdtp", +@@ -215,6 +233,10 @@ template("node_gn_build") { } } @@ -366,7 +366,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..a6cfd45b109c7b38fcf1529468ff64d3 executable(target_name) { forward_variables_from(invoker, "*") -@@ -288,6 +310,7 @@ template("node_gn_build") { +@@ -289,6 +311,7 @@ template("node_gn_build") { } executable("node_js2c") { @@ -374,7 +374,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..a6cfd45b109c7b38fcf1529468ff64d3 deps = [ "deps/uv", "$node_simdutf_path", -@@ -298,26 +321,75 @@ template("node_gn_build") { +@@ -299,26 +322,75 @@ template("node_gn_build") { "src/embedded_data.cc", "src/embedded_data.h", ] @@ -460,7 +460,7 @@ index 44641b92678ab2f28e6f5de75a92878f9f3d322d..a6cfd45b109c7b38fcf1529468ff64d3 outputs = [ "$target_gen_dir/node_javascript.cc" ] # Get the path to node_js2c executable of the host toolchain. -@@ -331,11 +403,11 @@ template("node_gn_build") { +@@ -332,11 +404,11 @@ template("node_gn_build") { get_label_info(":node_js2c($host_toolchain)", "name") + host_executable_suffix diff --git a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch index d93e9bef3bc21..48d4362fb6792 100644 --- a/patches/node/build_allow_unbundling_of_node_js_dependencies.patch +++ b/patches/node/build_allow_unbundling_of_node_js_dependencies.patch @@ -14,7 +14,7 @@ We don't need to do this for zlib, as the existing gn workflow uses the same Upstreamed at https://github.com/nodejs/node/pull/55903 diff --git a/unofficial.gni b/unofficial.gni -index a6cfd45b109c7b38fcf1529468ff64d3c1c8bd1b..332c9ee7262108ae9616e9bc8bd950a4940a858c 100644 +index 26ebc811272ef2990f8d090c54e7f5294aab9d37..8886f2a79ae77614789d6ae0defd4f18fc756456 100644 --- a/unofficial.gni +++ b/unofficial.gni @@ -160,7 +160,6 @@ template("node_gn_build") { @@ -44,7 +44,7 @@ index a6cfd45b109c7b38fcf1529468ff64d3c1c8bd1b..332c9ee7262108ae9616e9bc8bd950a4 if (v8_enable_i18n_support) { deps += [ "//third_party/icu" ] } -@@ -230,6 +239,19 @@ template("node_gn_build") { +@@ -231,6 +240,19 @@ template("node_gn_build") { sources += node_inspector.node_inspector_sources + node_inspector.node_inspector_generated_sources } diff --git a/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch b/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch index 3054af71962d5..7f669c5b0bd7d 100644 --- a/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch +++ b/patches/node/build_change_crdtp_protocoltypetraits_signatures_to_avoid_conflict.patch @@ -38,10 +38,10 @@ index 8521730bd03cdfce47e9b5d0f5d68a568bc3de8c..28f4598aa7ea0e93350f79566c06d0f0 } diff --git a/src/inspector/node_string.h b/src/inspector/node_string.h -index 94ec9b2301998c4c5aad9ca3dae72ecf323fa0bb..a0d19a592d7bf9b00d6b98ef1ae931626ebb945c 100644 +index bcdedaa2ae4ab1d3267d7a1347f15e0405261277..ddedca4a5b9b35258050f8b4cb446ceeba956896 100644 --- a/src/inspector/node_string.h +++ b/src/inspector/node_string.h -@@ -19,8 +19,8 @@ namespace crdtp { +@@ -18,8 +18,8 @@ namespace crdtp { template <> struct ProtocolTypeTraits { diff --git a/patches/node/build_compile_with_c_20_support.patch b/patches/node/build_compile_with_c_20_support.patch index b16baaf70f9e5..52a25cc54cd5c 100644 --- a/patches/node/build_compile_with_c_20_support.patch +++ b/patches/node/build_compile_with_c_20_support.patch @@ -10,10 +10,10 @@ V8 requires C++20 support as of https://chromium-review.googlesource.com/c/v8/v8 This can be removed when Electron upgrades to a version of Node.js containing the required V8 version. diff --git a/common.gypi b/common.gypi -index acfc02510ee1ce34a3f410a7a4ce53adb42abd35..b9264bfb1170928431848bb2b99e4f0dfbe8f95a 100644 +index 679633dc6b4ce2a1f5f88e93d1a1c1feb4bbadb4..2caa183213d5632be81b763e894e37c09384391f 100644 --- a/common.gypi +++ b/common.gypi -@@ -538,7 +538,7 @@ +@@ -539,7 +539,7 @@ '-fno-rtti', '-fno-exceptions', '-fno-strict-aliasing', @@ -22,7 +22,7 @@ index acfc02510ee1ce34a3f410a7a4ce53adb42abd35..b9264bfb1170928431848bb2b99e4f0d ], 'defines': [ '__STDC_FORMAT_MACROS' ], 'ldflags': [ '-rdynamic' ], -@@ -708,7 +708,7 @@ +@@ -709,7 +709,7 @@ ['clang==1', { 'xcode_settings': { 'GCC_VERSION': 'com.apple.compilers.llvm.clang.1_0', diff --git a/patches/node/build_enable_perfetto.patch b/patches/node/build_enable_perfetto.patch index 1e2e8823fe0cb..1bb292dd46878 100644 --- a/patches/node/build_enable_perfetto.patch +++ b/patches/node/build_enable_perfetto.patch @@ -64,10 +64,10 @@ index 251f51ec454f9cba4023b8b6729241ee753aac13..1de8cac6e3953ce9cab9db03530da327 module.exports = { diff --git a/node.gyp b/node.gyp -index 0434887c363a586cbfa0438765fc8800d4237057..20fbf03cee24e66f9ad0d394dbcfa3ad03348890 100644 +index 442c1e7a6ddafbb7a7ec7a42a97ec04b28ea4d93..3a66c11d39dd2fd129c8f54098a9607e080ecca0 100644 --- a/node.gyp +++ b/node.gyp -@@ -175,7 +175,6 @@ +@@ -176,7 +176,6 @@ 'src/timers.cc', 'src/timer_wrap.cc', 'src/tracing/agent.cc', @@ -75,7 +75,7 @@ index 0434887c363a586cbfa0438765fc8800d4237057..20fbf03cee24e66f9ad0d394dbcfa3ad 'src/tracing/node_trace_writer.cc', 'src/tracing/trace_event.cc', 'src/tracing/traced_value.cc', -@@ -302,7 +301,6 @@ +@@ -304,7 +303,6 @@ 'src/tcp_wrap.h', 'src/timers.h', 'src/tracing/agent.h', diff --git a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch index 8118eaac97d4b..3f5e9b39ae14b 100644 --- a/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch +++ b/patches/node/build_ensure_native_module_compilation_fails_if_not_using_a_new.patch @@ -7,7 +7,7 @@ Subject: build: ensure native module compilation fails if not using a new This should not be upstreamed, it is a quality-of-life patch for downstream module builders. diff --git a/common.gypi b/common.gypi -index cf643bcd0bc9080b80bf12afeebc69f2db74bb54..acfc02510ee1ce34a3f410a7a4ce53adb42abd35 100644 +index 33af43cd768c24b26d523f3db66eb8b9eb26859a..679633dc6b4ce2a1f5f88e93d1a1c1feb4bbadb4 100644 --- a/common.gypi +++ b/common.gypi @@ -89,6 +89,8 @@ @@ -19,7 +19,7 @@ index cf643bcd0bc9080b80bf12afeebc69f2db74bb54..acfc02510ee1ce34a3f410a7a4ce53ad ##### end V8 defaults ##### # When building native modules using 'npm install' with the system npm, -@@ -297,7 +299,8 @@ +@@ -298,7 +300,8 @@ '_GLIBCXX_USE_CXX11_ABI=1', # This help forks when building Node.js on a 32-bit arch as # libuv is always compiled with _FILE_OFFSET_BITS=64 @@ -29,7 +29,7 @@ index cf643bcd0bc9080b80bf12afeebc69f2db74bb54..acfc02510ee1ce34a3f410a7a4ce53ad ], # Forcibly disable -Werror. We support a wide range of compilers, it's -@@ -454,6 +457,11 @@ +@@ -455,6 +458,11 @@ }], ], }], @@ -42,7 +42,7 @@ index cf643bcd0bc9080b80bf12afeebc69f2db74bb54..acfc02510ee1ce34a3f410a7a4ce53ad # list in v8/BUILD.gn. ['v8_enable_v8_checks == 1', { diff --git a/configure.py b/configure.py -index e9c2a4391f4058a21a259cacaac4fde5d199288e..7821a0d3a7179a9e7fa9e48a062c2b0e7705ca6f 100755 +index 0feb07afbccad97a92cee00954443407eb20ac67..5eccced7cf0212f229db68c76cc824a37e4a29bc 100755 --- a/configure.py +++ b/configure.py @@ -1704,6 +1704,7 @@ def configure_library(lib, output, pkgname=None): diff --git a/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch b/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch index 025e06ca2388a..8b7051b7f036c 100644 --- a/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch +++ b/patches/node/build_modify_js2c_py_to_allow_injection_of_original-fs_and_custom_embedder_js.patch @@ -10,10 +10,10 @@ JS errors and ensures embedder JS is loaded via LoadEmbedderJavaScriptSource. That method is generated by our modifications to js2c.cc in the BUILD.gn patch diff --git a/lib/internal/fs/watchers.js b/lib/internal/fs/watchers.js -index 411eab8136d5957ae8a491bc38ffbdc88e59f5da..63c93b5be09692d0d4b6bfbb214b173b50ccca43 100644 +index 0244a214b187e67e0cb89f26cd019855963ec93a..b65a3be6bcb0e28f7f43367d0fa9da533db9d0d1 100644 --- a/lib/internal/fs/watchers.js +++ b/lib/internal/fs/watchers.js -@@ -292,12 +292,13 @@ function emitCloseNT(self) { +@@ -299,12 +299,13 @@ function emitCloseNT(self) { } // Legacy alias on the C++ wrapper object. This is not public API, so we may @@ -34,7 +34,7 @@ index 411eab8136d5957ae8a491bc38ffbdc88e59f5da..63c93b5be09692d0d4b6bfbb214b173b let kResistStopPropagation; diff --git a/src/node_builtins.cc b/src/node_builtins.cc -index f14b45850e42585f5686b7201e2b8281ed8c24e1..915b8cba6d512096e6090272ab3fbc63d5c61ce8 100644 +index 8b104e175ccf8de90c138337f83f8f6ce1348ac7..35cf42a5e533cb799bf129df0c8370bfe8310233 100644 --- a/src/node_builtins.cc +++ b/src/node_builtins.cc @@ -35,6 +35,7 @@ using v8::Value; diff --git a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch b/patches/node/build_option_to_use_custom_inspector_protocol_path.patch deleted file mode 100644 index 339cddb7a744e..0000000000000 --- a/patches/node/build_option_to_use_custom_inspector_protocol_path.patch +++ /dev/null @@ -1,60 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: deepak1556 -Date: Mon, 17 Feb 2025 20:57:05 +0900 -Subject: build: option to use custom inspector_protocol path - -This allows building against //third_party/inspector_protocol -which would align us when building with chromium shared dependencies. - -The span changes will be auto-removed when Node.js bumps their -protocol deps to contain https://chromium-review.googlesource.com/c/v8/v8/+/5996636 - -Rest of the changes can be upstreamed. - -diff --git a/node.gni b/node.gni -index 165b26a79a7f2b74d2a2252dc2350b2e10c091e6..c64761b730e61edcdc0e46a48699f2fd5bb1c0a6 100644 ---- a/node.gni -+++ b/node.gni -@@ -16,6 +16,9 @@ declare_args() { - # The location of simdutf - use the one from node's deps by default. - node_simdutf_path = "//third_party/simdutf" - -+ # The location of inspector_protocol - use the one from node's deps by default. -+ node_inspector_protocol_path = "//third_party/inspector_protocol" -+ - # The NODE_MODULE_VERSION defined in node_version.h. - node_module_version = exec_script("$node_path/tools/getmoduleversion.py", [], "value") - -diff --git a/src/inspector/unofficial.gni b/src/inspector/unofficial.gni -index 3d7aa148678b2646b88fa7c32abec91791b02b82..4810d93eb971b253f7dadff7011a632f6dbe6a2b 100644 ---- a/src/inspector/unofficial.gni -+++ b/src/inspector/unofficial.gni -@@ -13,7 +13,7 @@ template("inspector_gn_build") { - } - - node_gen_dir = get_label_info("../..", "target_gen_dir") -- protocol_tool_path = "../../deps/inspector_protocol" -+ protocol_tool_path = "$node_inspector_protocol_path" - - gypi_values = exec_script( - "../../tools/gypi_to_gn.py", -diff --git a/unofficial.gni b/unofficial.gni -index 332c9ee7262108ae9616e9bc8bd950a4940a858c..8886f2a79ae77614789d6ae0defd4f18fc756456 100644 ---- a/unofficial.gni -+++ b/unofficial.gni -@@ -222,13 +222,14 @@ template("node_gn_build") { - } - if (node_enable_inspector) { - deps += [ -- "src/inspector:crdtp", -+ "$node_inspector_protocol_path:crdtp", - "src/inspector:node_protocol_generated_sources", - "src/inspector:v8_inspector_compress_protocol_json", - ] - include_dirs = [ - "$target_gen_dir/src", - "$target_gen_dir/src/inspector", -+ "$node_inspector_protocol_path", - ] - node_inspector = exec_script( - "./tools/gypi_to_gn.py", diff --git a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch index 7901c967e9195..88f7586d58c69 100644 --- a/patches/node/build_restore_clang_as_default_compiler_on_macos.patch +++ b/patches/node/build_restore_clang_as_default_compiler_on_macos.patch @@ -11,7 +11,7 @@ node-gyp will use the result of `process.config` that reflects the environment in which the binary got built. diff --git a/common.gypi b/common.gypi -index b9264bfb1170928431848bb2b99e4f0dfbe8f95a..836d96a1bd9c1d5568f0045bbddddca1edb1a0ce 100644 +index 2caa183213d5632be81b763e894e37c09384391f..2cce436c4a9e3d942f957f6c94a4ef9e3db391ce 100644 --- a/common.gypi +++ b/common.gypi @@ -128,6 +128,7 @@ diff --git a/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch b/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch index ae864ce06db1d..a2901455347a2 100644 --- a/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch +++ b/patches/node/chore_allow_the_node_entrypoint_to_be_a_builtin_module.patch @@ -8,7 +8,7 @@ they use themselves as the entry point. We should try to upstream some form of this. diff --git a/lib/internal/process/pre_execution.js b/lib/internal/process/pre_execution.js -index 4e7be0594ca1e1ceaf1963debbce46783893ed77..a6df0672bf6ae6e9a74ebbb0e4debff63599cc99 100644 +index 0cda54fd85e1e0bff13d4718a269eb3e7c60312a..6b165062a5eaa40f6e5614bca50bc33ccbdb85cc 100644 --- a/lib/internal/process/pre_execution.js +++ b/lib/internal/process/pre_execution.js @@ -245,12 +245,14 @@ function patchProcessObject(expandArgv1) { diff --git a/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch b/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch index 0bde5d3fc9c81..b91313c8345e4 100644 --- a/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch +++ b/patches/node/chore_disable_deprecation_ftbfs_in_simdjson_header.patch @@ -11,10 +11,10 @@ Without this patch, building with simdjson fails with This patch can be removed once this is fixed upstream in simdjson. diff --git a/deps/simdjson/simdjson.h b/deps/simdjson/simdjson.h -index a0d449975224a3e0db5c05de79b290763d6e390c..e77e47f972b4609e38aa8b68ab0d81ed1575effb 100644 +index 8f52a4331d59996786450eec982659da9244cac1..74729673d87b068dff5f24166bbb77d844f15f42 100644 --- a/deps/simdjson/simdjson.h +++ b/deps/simdjson/simdjson.h -@@ -3868,12 +3868,17 @@ inline std::ostream& operator<<(std::ostream& out, simdjson_result padded_string::load(std::string_view filen +@@ -4304,6 +4309,9 @@ inline simdjson_result padded_string::load(std::string_view filen } // namespace simdjson @@ -42,7 +42,7 @@ index a0d449975224a3e0db5c05de79b290763d6e390c..e77e47f972b4609e38aa8b68ab0d81ed inline simdjson::padded_string operator ""_padded(const char *str, size_t len) { return simdjson::padded_string(str, len); } -@@ -4281,6 +4289,8 @@ inline simdjson::padded_string operator ""_padded(const char8_t *str, size_t len +@@ -4312,6 +4320,8 @@ inline simdjson::padded_string operator ""_padded(const char8_t *str, size_t len return simdjson::padded_string(reinterpret_cast(str), len); } #endif diff --git a/patches/node/chore_expose_importmoduledynamically_and.patch b/patches/node/chore_expose_importmoduledynamically_and.patch index 497ea5842d984..3f44ec26449ef 100644 --- a/patches/node/chore_expose_importmoduledynamically_and.patch +++ b/patches/node/chore_expose_importmoduledynamically_and.patch @@ -11,7 +11,7 @@ its own blended handler between Node and Blink. Not upstreamable. diff --git a/lib/internal/modules/esm/utils.js b/lib/internal/modules/esm/utils.js -index 9d6f850f667c5186efe6855bc3d5f5af332bdaa7..8521759e20adf53024e5893dbf3cb36e1752085e 100644 +index 9b41db8b0714b7408f79cbd5b4c460d9bc08f239..35ecfb9bbaf2c8e7351e1c69da84c82a4a7cb049 100644 --- a/lib/internal/modules/esm/utils.js +++ b/lib/internal/modules/esm/utils.js @@ -30,7 +30,7 @@ const { @@ -23,7 +23,7 @@ index 9d6f850f667c5186efe6855bc3d5f5af332bdaa7..8521759e20adf53024e5893dbf3cb36e const { loadPreloadModules, initializeFrozenIntrinsics, -@@ -280,12 +280,13 @@ let _forceDefaultLoader = false; +@@ -281,12 +281,13 @@ let _forceDefaultLoader = false; * @param {boolean} [forceDefaultLoader=false] - A boolean indicating disabling custom loaders. */ function initializeESM(forceDefaultLoader = false) { @@ -40,10 +40,10 @@ index 9d6f850f667c5186efe6855bc3d5f5af332bdaa7..8521759e20adf53024e5893dbf3cb36e /** diff --git a/src/module_wrap.cc b/src/module_wrap.cc -index cdd0ba00eb0cafbc79b816017423f9021ca2979d..6916497f6feb14e482cf5080b57d639ae7292d20 100644 +index e317a84e55714af0a93719336d02ac26410ad724..e3880111172363feafb53b51deb08c93596cd4f4 100644 --- a/src/module_wrap.cc +++ b/src/module_wrap.cc -@@ -875,7 +875,7 @@ MaybeLocal ModuleWrap::ResolveModuleCallback( +@@ -895,7 +895,7 @@ MaybeLocal ModuleWrap::ResolveModuleCallback( return module->module_.Get(isolate); } @@ -52,7 +52,7 @@ index cdd0ba00eb0cafbc79b816017423f9021ca2979d..6916497f6feb14e482cf5080b57d639a Local context, Local host_defined_options, Local resource_name, -@@ -947,12 +947,13 @@ void ModuleWrap::SetImportModuleDynamicallyCallback( +@@ -967,12 +967,13 @@ void ModuleWrap::SetImportModuleDynamicallyCallback( Realm* realm = Realm::GetCurrent(args); HandleScope handle_scope(isolate); @@ -68,7 +68,7 @@ index cdd0ba00eb0cafbc79b816017423f9021ca2979d..6916497f6feb14e482cf5080b57d639a } void ModuleWrap::HostInitializeImportMetaObjectCallback( -@@ -994,13 +995,14 @@ void ModuleWrap::SetInitializeImportMetaObjectCallback( +@@ -1014,13 +1015,14 @@ void ModuleWrap::SetInitializeImportMetaObjectCallback( Realm* realm = Realm::GetCurrent(args); Isolate* isolate = realm->isolate(); @@ -87,7 +87,7 @@ index cdd0ba00eb0cafbc79b816017423f9021ca2979d..6916497f6feb14e482cf5080b57d639a MaybeLocal ModuleWrap::SyntheticModuleEvaluationStepsCallback( diff --git a/src/module_wrap.h b/src/module_wrap.h -index ef4dfd1d6b091d2b0f71b946904a47415b6435ba..862f946a75f2a2949d7eeb7f97e96289beab8078 100644 +index 9363ce73e51cde3d3a94f9912f072d532d0f8560..c0e972ed293157726efc5fa76dfa62d3da51c22a 100644 --- a/src/module_wrap.h +++ b/src/module_wrap.h @@ -8,6 +8,7 @@ @@ -114,7 +114,7 @@ index ef4dfd1d6b091d2b0f71b946904a47415b6435ba..862f946a75f2a2949d7eeb7f97e96289 public: enum InternalFields { kModuleSlot = BaseObject::kInternalFieldCount, -@@ -91,6 +99,8 @@ class ModuleWrap : public BaseObject { +@@ -92,6 +100,8 @@ class ModuleWrap : public BaseObject { static void CreateRequiredModuleFacade( const v8::FunctionCallbackInfo& args); @@ -123,7 +123,7 @@ index ef4dfd1d6b091d2b0f71b946904a47415b6435ba..862f946a75f2a2949d7eeb7f97e96289 private: ModuleWrap(Realm* realm, v8::Local object, -@@ -130,7 +140,6 @@ class ModuleWrap : public BaseObject { +@@ -131,7 +141,6 @@ class ModuleWrap : public BaseObject { v8::Local specifier, v8::Local import_attributes, v8::Local referrer); diff --git a/patches/node/chore_remove_protocol_maybe_from_node_string.patch b/patches/node/chore_remove_protocol_maybe_from_node_string.patch deleted file mode 100644 index 12352945185c9..0000000000000 --- a/patches/node/chore_remove_protocol_maybe_from_node_string.patch +++ /dev/null @@ -1,33 +0,0 @@ -From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 -From: Shelley Vohr -Date: Thu, 26 Jun 2025 09:20:43 +0000 -Subject: chore: remove protocol::Maybe from node_string - -It was removed upstream in https://chromium-review.googlesource.com/c/chromium/src/+/6049967. - -This should be upstreamed. - -diff --git a/src/inspector/node_string.h b/src/inspector/node_string.h -index a0d19a592d7bf9b00d6b98ef1ae931626ebb945c..ddedca4a5b9b35258050f8b4cb446ceeba956896 100644 ---- a/src/inspector/node_string.h -+++ b/src/inspector/node_string.h -@@ -6,7 +6,6 @@ - #include - #include - #include --#include "crdtp/maybe.h" - #include "crdtp/protocol_core.h" - #include "util.h" - #include "v8-inspector.h" -@@ -31,11 +30,6 @@ struct ProtocolTypeTraits { - std::vector* bytes); - }; - --template <> --struct detail::MaybeTypedef { -- typedef ValueMaybe type; --}; -- - } // namespace crdtp - - namespace node { diff --git a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch index 681ea40add6e0..dae7ed917b98d 100644 --- a/patches/node/cli_move_--trace-atomics-wait_to_eol.patch +++ b/patches/node/cli_move_--trace-atomics-wait_to_eol.patch @@ -15,10 +15,50 @@ Reviewed-By: Benjamin Gruenbaum Reviewed-By: Yagiz Nizipli diff --git a/doc/api/cli.md b/doc/api/cli.md -index d924287df3ca29681cf71e2fbd402314ce8edd97..f2f4d25a838b9758234cd667b0fb537d0d0fcced 100644 +index 404e87e6d1237b5ee79cafd8a959c1b6d9d23fe5..7deda572c940f7b2e8c6813f1826796a13e4db38 100644 --- a/doc/api/cli.md +++ b/doc/api/cli.md -@@ -3386,7 +3386,6 @@ one is included in the list below. +@@ -2709,39 +2709,6 @@ added: v12.0.0 + Set default [`tls.DEFAULT_MIN_VERSION`][] to 'TLSv1.3'. Use to disable support + for TLSv1.2, which is not as secure as TLSv1.3. + +-### `--trace-atomics-wait` +- +- +- +-> Stability: 0 - Deprecated +- +-Print short summaries of calls to [`Atomics.wait()`][] to stderr. +-The output could look like this: +- +-```text +-(node:15701) [Thread 0] Atomics.wait(<address> + 0, 1, inf) started +-(node:15701) [Thread 0] Atomics.wait(<address> + 0, 1, inf) did not wait because the values mismatched +-(node:15701) [Thread 0] Atomics.wait(<address> + 0, 0, 10) started +-(node:15701) [Thread 0] Atomics.wait(<address> + 0, 0, 10) timed out +-(node:15701) [Thread 0] Atomics.wait(<address> + 4, 0, inf) started +-(node:15701) [Thread 1] Atomics.wait(<address> + 4, -1, inf) started +-(node:15701) [Thread 0] Atomics.wait(<address> + 4, 0, inf) was woken up by another thread +-(node:15701) [Thread 1] Atomics.wait(<address> + 4, -1, inf) was woken up by another thread +-``` +- +-The fields here correspond to: +- +-* The thread id as given by [`worker_threads.threadId`][] +-* The base address of the `SharedArrayBuffer` in question, as well as the +- byte offset corresponding to the index passed to `Atomics.wait()` +-* The expected value that was passed to `Atomics.wait()` +-* The timeout passed to `Atomics.wait` +- + ### `--trace-deprecation` + +