From e23fe8cf87e7417397fcfbc8929d4d4c4f4a36cf Mon Sep 17 00:00:00 2001 From: Andreas Kling Date: Sun, 16 Oct 2022 17:36:18 +0200 Subject: [PATCH] LibJS: Make define_native_foo() take SafeFunctions We were taking AK::Function and then passing them along to NativeFunction, which takes a SafeFunction. This works, since SafeFunction will transparently wrap AK::Function in a CallableWrapper when assigned, but it was causing us to accumulate thousands of pointless wrappers around direct function pointers. By using SafeFunction at every step of the setup call chain, we no longer create any CallableWrappers for the majority of native functions in LibJS. Also, the number of heap-registered SafeFunctions in a new realm goes down from ~5000 to 5. :^) --- Userland/Libraries/LibJS/Runtime/Object.cpp | 4 ++-- Userland/Libraries/LibJS/Runtime/Object.h | 5 +++-- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/Userland/Libraries/LibJS/Runtime/Object.cpp b/Userland/Libraries/LibJS/Runtime/Object.cpp index 6e650d5e09..8033ab6dfc 100644 --- a/Userland/Libraries/LibJS/Runtime/Object.cpp +++ b/Userland/Libraries/LibJS/Runtime/Object.cpp @@ -1069,7 +1069,7 @@ void Object::set_prototype(Object* new_prototype) m_shape = shape.create_prototype_transition(new_prototype); } -void Object::define_native_accessor(Realm& realm, PropertyKey const& property_key, Function(VM&)> getter, Function(VM&)> setter, PropertyAttributes attribute) +void Object::define_native_accessor(Realm& realm, PropertyKey const& property_key, SafeFunction(VM&)> getter, SafeFunction(VM&)> setter, PropertyAttributes attribute) { FunctionObject* getter_function = nullptr; if (getter) @@ -1118,7 +1118,7 @@ Value Object::get_without_side_effects(PropertyKey const& property_key) const return {}; } -void Object::define_native_function(Realm& realm, PropertyKey const& property_key, Function(VM&)> native_function, i32 length, PropertyAttributes attribute) +void Object::define_native_function(Realm& realm, PropertyKey const& property_key, SafeFunction(VM&)> native_function, i32 length, PropertyAttributes attribute) { auto* function = NativeFunction::create(realm, move(native_function), length, property_key, &realm); define_direct_property(property_key, function, attribute); diff --git a/Userland/Libraries/LibJS/Runtime/Object.h b/Userland/Libraries/LibJS/Runtime/Object.h index 6498ca841a..93a29a0256 100644 --- a/Userland/Libraries/LibJS/Runtime/Object.h +++ b/Userland/Libraries/LibJS/Runtime/Object.h @@ -22,6 +22,7 @@ #include #include #include +#include namespace JS { @@ -150,8 +151,8 @@ public: void define_direct_property(PropertyKey const& property_key, Value value, PropertyAttributes attributes) { storage_set(property_key, { value, attributes }); }; void define_direct_accessor(PropertyKey const&, FunctionObject* getter, FunctionObject* setter, PropertyAttributes attributes); - void define_native_function(Realm&, PropertyKey const&, Function(VM&)>, i32 length, PropertyAttributes attributes); - void define_native_accessor(Realm&, PropertyKey const&, Function(VM&)> getter, Function(VM&)> setter, PropertyAttributes attributes); + void define_native_function(Realm&, PropertyKey const&, SafeFunction(VM&)>, i32 length, PropertyAttributes attributes); + void define_native_accessor(Realm&, PropertyKey const&, SafeFunction(VM&)> getter, SafeFunction(VM&)> setter, PropertyAttributes attributes); virtual bool is_function() const { return false; } virtual bool is_typed_array() const { return false; }