1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-25 05:57:44 +00:00

LibJS: Avoid pointless transitions and metadata lookups in storage_set()

- Replace the misleading abuse of the m_transitions_enabled flag for the
  fast path without lookup with a new m_initialized boolean that's set
  either by Heap::allocate() after calling the Object's initialize(), or
  by the GlobalObject in its special initialize_global_object(). This
  makes it work regardless of the shape's uniqueness.
- When we're adding a new property past the initialization phase,
  there's no need to do a second metadata lookup to retrieve the storage
  value offset - it's known to always be the shape's property count
  minus one. Also, instead of doing manual storage resizing and
  assignment via indexing, just use Vector::append().
- When we didn't add a new property but are overwriting an existing one,
  the property count and therefore storage value offset doesn't change,
  so we don't have to retrieve it either.

As a result, Object::set_shape() is now solely responsible for updating
the m_shape pointer and is not resizing storage anymore, so I moved it
into the header.
This commit is contained in:
Linus Groh 2021-08-28 17:12:14 +01:00
parent d6de0613f5
commit 222e518a53
4 changed files with 40 additions and 29 deletions

View file

@ -132,8 +132,13 @@ void GlobalObject::initialize_global_object()
m_new_ordinary_function_prototype_object_shape->set_prototype_without_transition(m_object_prototype);
m_new_ordinary_function_prototype_object_shape->add_property_without_transition(vm.names.constructor, Attribute::Writable | Attribute::Configurable);
// Normally Heap::allocate() takes care of this, but these are allocated via allocate_without_global_object().
static_cast<FunctionPrototype*>(m_function_prototype)->initialize(*this);
m_function_prototype->set_initialized(Badge<GlobalObject> {});
static_cast<ObjectPrototype*>(m_object_prototype)->initialize(*this);
m_object_prototype->set_initialized(Badge<GlobalObject> {});
auto success = Object::internal_set_prototype_of(m_object_prototype);
VERIFY(success);
@ -265,6 +270,8 @@ void GlobalObject::initialize_global_object()
m_array_prototype_values_function = &m_array_prototype->get_without_side_effects(vm.names.values).as_function();
m_eval_function = &get_without_side_effects(vm.names.eval).as_function();
m_temporal_time_zone_prototype_get_offset_nanoseconds_for_function = &m_temporal_time_zone_prototype->get_without_side_effects(vm.names.getOffsetNanosecondsFor).as_function();
set_initialized(Badge<GlobalObject> {});
}
GlobalObject::~GlobalObject()