diff --git a/patches/chromium/chore_add_electron_objects_to_wrappablepointertag.patch b/patches/chromium/chore_add_electron_objects_to_wrappablepointertag.patch index 4f63db0719..807c2c461f 100644 --- a/patches/chromium/chore_add_electron_objects_to_wrappablepointertag.patch +++ b/patches/chromium/chore_add_electron_objects_to_wrappablepointertag.patch @@ -8,17 +8,18 @@ electron objects that extend gin::Wrappable and gets allocated on the cpp heap diff --git a/gin/public/wrappable_pointer_tags.h b/gin/public/wrappable_pointer_tags.h -index 80ec409efe1635390887d1324be661643818abff..112a23f81680f5fcc2b016d8f5362e3a03507c8a 100644 +index 80ec409efe1635390887d1324be661643818abff..2b82f96d12715b6476c456b73dfd1a7342736f8e 100644 --- a/gin/public/wrappable_pointer_tags.h +++ b/gin/public/wrappable_pointer_tags.h -@@ -66,7 +66,10 @@ enum WrappablePointerTag : uint16_t { +@@ -66,7 +66,11 @@ enum WrappablePointerTag : uint16_t { kTextInputControllerBindings, // content::TextInputControllerBindings kWebAXObjectProxy, // content::WebAXObjectProxy kWrappedExceptionHandler, // extensions::WrappedExceptionHandler - kLastPointerTag = kWrappedExceptionHandler, + kElectronApp, // electron::api::App -+ kElectronSession, // electron::api::Session ++ kElectronDebugger, // electron::api::Debugger + kElectronEvent, // gin_helper::internal::Event ++ kElectronSession, // electron::api::Session + kLastPointerTag = kElectronEvent, }; diff --git a/shell/browser/api/electron_api_debugger.cc b/shell/browser/api/electron_api_debugger.cc index b760639166..29f496c746 100644 --- a/shell/browser/api/electron_api_debugger.cc +++ b/shell/browser/api/electron_api_debugger.cc @@ -19,15 +19,18 @@ #include "shell/common/gin_converters/value_converter.h" #include "shell/common/gin_helper/handle.h" #include "shell/common/gin_helper/promise.h" +#include "v8/include/cppgc/allocation.h" +#include "v8/include/v8-cppgc.h" using content::DevToolsAgentHost; namespace electron::api { -gin::DeprecatedWrapperInfo Debugger::kWrapperInfo = {gin::kEmbedderNativeGin}; +gin::WrapperInfo Debugger::kWrapperInfo = {{gin::kEmbedderNativeGin}, + gin::kElectronDebugger}; -Debugger::Debugger(v8::Isolate* isolate, content::WebContents* web_contents) - : content::WebContentsObserver(web_contents), web_contents_(web_contents) {} +Debugger::Debugger(content::WebContents* web_contents) + : content::WebContentsObserver{web_contents}, web_contents_{web_contents} {} Debugger::~Debugger() = default; @@ -178,10 +181,10 @@ void Debugger::ClearPendingRequests() { } // static -gin_helper::Handle Debugger::Create( - v8::Isolate* isolate, - content::WebContents* web_contents) { - return gin_helper::CreateHandle(isolate, new Debugger(isolate, web_contents)); +Debugger* Debugger::Create(v8::Isolate* isolate, + content::WebContents* web_contents) { + return cppgc::MakeGarbageCollected( + isolate->GetCppHeap()->GetAllocationHandle(), web_contents); } gin::ObjectTemplateBuilder Debugger::GetObjectTemplateBuilder( @@ -194,8 +197,12 @@ gin::ObjectTemplateBuilder Debugger::GetObjectTemplateBuilder( .SetMethod("sendCommand", &Debugger::SendCommand); } -const char* Debugger::GetTypeName() { - return "Debugger"; +const gin::WrapperInfo* Debugger::wrapper_info() const { + return &kWrapperInfo; +} + +const char* Debugger::GetHumanReadableName() const { + return "Electron / Debugger"; } } // namespace electron::api diff --git a/shell/browser/api/electron_api_debugger.h b/shell/browser/api/electron_api_debugger.h index 4a017244d3..1d40c4f16e 100644 --- a/shell/browser/api/electron_api_debugger.h +++ b/shell/browser/api/electron_api_debugger.h @@ -11,8 +11,8 @@ #include "base/values.h" #include "content/public/browser/devtools_agent_host_client.h" #include "content/public/browser/web_contents_observer.h" +#include "gin/wrappable.h" #include "shell/browser/event_emitter_mixin.h" -#include "shell/common/gin_helper/wrappable.h" namespace content { class DevToolsAgentHost; @@ -32,29 +32,32 @@ class Promise; namespace electron::api { -class Debugger final : public gin_helper::DeprecatedWrappable, +class Debugger final : public gin::Wrappable, public gin_helper::EventEmitterMixin, public content::DevToolsAgentHostClient, private content::WebContentsObserver { public: - static gin_helper::Handle Create( - v8::Isolate* isolate, - content::WebContents* web_contents); + static Debugger* Create(v8::Isolate* isolate, + content::WebContents* web_contents); + + // Make public for cppgc::MakeGarbageCollected. + explicit Debugger(content::WebContents* web_contents); + ~Debugger() override; // gin_helper::Wrappable - static gin::DeprecatedWrapperInfo kWrapperInfo; + static gin::WrapperInfo kWrapperInfo; gin::ObjectTemplateBuilder GetObjectTemplateBuilder( v8::Isolate* isolate) override; - const char* GetTypeName() override; + const gin::WrapperInfo* wrapper_info() const override; + const char* GetHumanReadableName() const override; + + const char* GetClassName() const { return "Debugger"; } // disable copy Debugger(const Debugger&) = delete; Debugger& operator=(const Debugger&) = delete; protected: - Debugger(v8::Isolate* isolate, content::WebContents* web_contents); - ~Debugger() override; - // content::DevToolsAgentHostClient: void AgentHostClosed(content::DevToolsAgentHost* agent_host) override; void DispatchProtocolMessage(content::DevToolsAgentHost* agent_host, diff --git a/shell/browser/api/electron_api_web_contents.cc b/shell/browser/api/electron_api_web_contents.cc index 14e4f49833..5e5797a3bc 100644 --- a/shell/browser/api/electron_api_web_contents.cc +++ b/shell/browser/api/electron_api_web_contents.cc @@ -3804,11 +3804,16 @@ v8::Local WebContents::DevToolsWebContents(v8::Isolate* isolate) { } v8::Local WebContents::Debugger(v8::Isolate* isolate) { - if (debugger_.IsEmpty()) { - auto handle = electron::api::Debugger::Create(isolate, web_contents()); - debugger_.Reset(isolate, handle.ToV8()); + if (!debugger_) { + debugger_ = electron::api::Debugger::Create(isolate, web_contents()); } - return v8::Local::New(isolate, debugger_); + + v8::HandleScope handle_scope{isolate}; + v8::Local wrapper; + if (!debugger_->GetWrapper(isolate).ToLocal(&wrapper)) { + return v8::Null(isolate); + } + return v8::Local::New(isolate, wrapper); } content::RenderFrameHost* WebContents::MainFrame() { diff --git a/shell/browser/api/electron_api_web_contents.h b/shell/browser/api/electron_api_web_contents.h index 09c3edf534..9e506880f6 100644 --- a/shell/browser/api/electron_api_web_contents.h +++ b/shell/browser/api/electron_api_web_contents.h @@ -31,6 +31,7 @@ #include "content/public/common/stop_find_action.h" #include "electron/buildflags/buildflags.h" #include "printing/buildflags/buildflags.h" +#include "shell/browser/api/electron_api_debugger.h" #include "shell/browser/api/electron_api_session.h" #include "shell/browser/api/save_page_handler.h" #include "shell/browser/background_throttling_source.h" @@ -772,7 +773,7 @@ class WebContents final : public ExclusiveAccessContext, cppgc::Persistent session_; v8::Global devtools_web_contents_; - v8::Global debugger_; + cppgc::Persistent debugger_; std::unique_ptr guest_delegate_; std::unique_ptr frame_subscriber_; diff --git a/shell/browser/event_emitter_mixin.h b/shell/browser/event_emitter_mixin.h index 7260f93407..33d77a1bb1 100644 --- a/shell/browser/event_emitter_mixin.h +++ b/shell/browser/event_emitter_mixin.h @@ -6,6 +6,7 @@ #define ELECTRON_SHELL_BROWSER_EVENT_EMITTER_MIXIN_H_ #include +#include #include #include "gin/object_template_builder.h" @@ -57,17 +58,37 @@ class EventEmitterMixin { gin::ObjectTemplateBuilder GetObjectTemplateBuilder(v8::Isolate* isolate) { gin::PerIsolateData* data = gin::PerIsolateData::From(isolate); auto* wrapper_info = &(static_cast(this)->kWrapperInfo); - v8::Local constructor = - data->DeprecatedGetFunctionTemplate(wrapper_info); + + // DeprecatedWrapperInfo support will be removed as part of + // https://github.com/electron/electron/issues/47922 + constexpr bool is_deprecated_wrapper = + std::is_same_v; + + v8::Local constructor; + if constexpr (is_deprecated_wrapper) { + constructor = data->DeprecatedGetFunctionTemplate(wrapper_info); + } else { + constructor = data->GetFunctionTemplate(wrapper_info); + } + + const char* class_name = ""; + if constexpr (is_deprecated_wrapper) { + class_name = static_cast(this)->GetTypeName(); + } else { + class_name = static_cast(this)->GetClassName(); + } + if (constructor.IsEmpty()) { constructor = v8::FunctionTemplate::New(isolate); - constructor->SetClassName( - gin::StringToV8(isolate, static_cast(this)->GetTypeName())); + constructor->SetClassName(gin::StringToV8(isolate, class_name)); constructor->Inherit(internal::GetEventEmitterTemplate(isolate)); - data->DeprecatedSetFunctionTemplate(wrapper_info, constructor); + if constexpr (is_deprecated_wrapper) { + data->DeprecatedSetFunctionTemplate(wrapper_info, constructor); + } else { + data->SetFunctionTemplate(wrapper_info, constructor); + } } - return gin::ObjectTemplateBuilder(isolate, - static_cast(this)->GetTypeName(), + return gin::ObjectTemplateBuilder(isolate, class_name, constructor->InstanceTemplate()); } };