LibJS: Add PropertyLookupPhase enum to distinguish Object [[Get]] calls

We can now tell the difference between an own property access and a
subsequent (automatic) prototype chain access.

This will be used to implement caching of prototype chain accesses.
This commit is contained in:
Andreas Kling 2024-05-02 11:13:08 +02:00
commit 493a04d5fe
Notes: sideshowbarker 2024-07-17 23:07:41 +09:00
17 changed files with 34 additions and 28 deletions

View file

@ -113,7 +113,7 @@ JS::ThrowCompletionOr<bool> SheetGlobalObject::internal_has_property(JS::Propert
return Object::internal_has_property(name); return Object::internal_has_property(name);
} }
JS::ThrowCompletionOr<JS::Value> SheetGlobalObject::internal_get(const JS::PropertyKey& property_name, JS::Value receiver, JS::CacheablePropertyMetadata*) const JS::ThrowCompletionOr<JS::Value> SheetGlobalObject::internal_get(const JS::PropertyKey& property_name, JS::Value receiver, JS::CacheablePropertyMetadata*, PropertyLookupPhase) const
{ {
if (property_name.is_string()) { if (property_name.is_string()) {
if (property_name.as_string() == "value") { if (property_name.as_string() == "value") {

View file

@ -29,7 +29,7 @@ public:
virtual ~SheetGlobalObject() override = default; virtual ~SheetGlobalObject() override = default;
virtual JS::ThrowCompletionOr<bool> internal_has_property(JS::PropertyKey const& name) const override; virtual JS::ThrowCompletionOr<bool> internal_has_property(JS::PropertyKey const& name) const override;
virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*) const override; virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*, PropertyLookupPhase) const override;
virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override; virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override;
JS_DECLARE_NATIVE_FUNCTION(get_real_cell_contents); JS_DECLARE_NATIVE_FUNCTION(get_real_cell_contents);

View file

@ -33,7 +33,7 @@ void ArgumentsObject::visit_edges(Cell::Visitor& visitor)
} }
// 10.4.4.3 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-arguments-exotic-objects-get-p-receiver // 10.4.4.3 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-arguments-exotic-objects-get-p-receiver
ThrowCompletionOr<Value> ArgumentsObject::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata) const ThrowCompletionOr<Value> ArgumentsObject::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata, PropertyLookupPhase phase) const
{ {
// 1. Let map be args.[[ParameterMap]]. // 1. Let map be args.[[ParameterMap]].
auto& map = *m_parameter_map; auto& map = *m_parameter_map;
@ -44,7 +44,7 @@ ThrowCompletionOr<Value> ArgumentsObject::internal_get(PropertyKey const& proper
// 3. If isMapped is false, then // 3. If isMapped is false, then
if (!is_mapped) { if (!is_mapped) {
// a. Return ? OrdinaryGet(args, P, Receiver). // a. Return ? OrdinaryGet(args, P, Receiver).
return Object::internal_get(property_key, receiver, cacheable_metadata); return Object::internal_get(property_key, receiver, cacheable_metadata, phase);
} }
// FIXME: a. Assert: map contains a formal parameter mapping for P. // FIXME: a. Assert: map contains a formal parameter mapping for P.

View file

@ -24,7 +24,7 @@ public:
virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const override; virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const override;
virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&) override; virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&) override;
virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata*) const override; virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata*, PropertyLookupPhase) const override;
virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata*) override; virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata*) override;
virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&) override; virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&) override;

View file

@ -137,14 +137,14 @@ ThrowCompletionOr<bool> ModuleNamespaceObject::internal_has_property(PropertyKey
} }
// 10.4.6.8 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-module-namespace-exotic-objects-get-p-receiver // 10.4.6.8 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-module-namespace-exotic-objects-get-p-receiver
ThrowCompletionOr<Value> ModuleNamespaceObject::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata) const ThrowCompletionOr<Value> ModuleNamespaceObject::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata, PropertyLookupPhase phase) const
{ {
auto& vm = this->vm(); auto& vm = this->vm();
// 1. If Type(P) is Symbol, then // 1. If Type(P) is Symbol, then
if (property_key.is_symbol()) { if (property_key.is_symbol()) {
// a. Return ! OrdinaryGet(O, P, Receiver). // a. Return ! OrdinaryGet(O, P, Receiver).
return MUST(Object::internal_get(property_key, receiver, cacheable_metadata)); return MUST(Object::internal_get(property_key, receiver, cacheable_metadata, phase));
} }
// 2. Let exports be O.[[Exports]]. // 2. Let exports be O.[[Exports]].

View file

@ -26,7 +26,7 @@ public:
virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const override; virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const override;
virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&) override; virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&) override;
virtual ThrowCompletionOr<bool> internal_has_property(PropertyKey const&) const override; virtual ThrowCompletionOr<bool> internal_has_property(PropertyKey const&) const override;
virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata* = nullptr) const override; virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata* = nullptr, PropertyLookupPhase = PropertyLookupPhase::OwnProperty) const override;
virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata*) override; virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata*) override;
virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&) override; virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&) override;
virtual ThrowCompletionOr<MarkedVector<Value>> internal_own_property_keys() const override; virtual ThrowCompletionOr<MarkedVector<Value>> internal_own_property_keys() const override;

View file

@ -873,7 +873,7 @@ ThrowCompletionOr<bool> Object::internal_has_property(PropertyKey const& propert
} }
// 10.1.8 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-ordinary-object-internal-methods-and-internal-slots-get-p-receiver // 10.1.8 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-ordinary-object-internal-methods-and-internal-slots-get-p-receiver
ThrowCompletionOr<Value> Object::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata) const ThrowCompletionOr<Value> Object::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata, PropertyLookupPhase phase) const
{ {
VERIFY(!receiver.is_empty()); VERIFY(!receiver.is_empty());
VERIFY(property_key.is_valid()); VERIFY(property_key.is_valid());
@ -893,18 +893,20 @@ ThrowCompletionOr<Value> Object::internal_get(PropertyKey const& property_key, V
return js_undefined(); return js_undefined();
// c. Return ? parent.[[Get]](P, Receiver). // c. Return ? parent.[[Get]](P, Receiver).
return parent->internal_get(property_key, receiver); return parent->internal_get(property_key, receiver, nullptr, PropertyLookupPhase::PrototypeChain);
} }
// 3. If IsDataDescriptor(desc) is true, return desc.[[Value]]. // 3. If IsDataDescriptor(desc) is true, return desc.[[Value]].
if (descriptor->is_data_descriptor()) { if (descriptor->is_data_descriptor()) {
// Non-standard: If the caller has requested cacheable metadata and the property is an own property, fill it in. // Non-standard: If the caller has requested cacheable metadata and the property is an own property, fill it in.
if (cacheable_metadata && descriptor->property_offset.has_value() && shape().is_cacheable()) { if (cacheable_metadata && descriptor->property_offset.has_value() && shape().is_cacheable()) {
if (phase == PropertyLookupPhase::OwnProperty) {
*cacheable_metadata = CacheablePropertyMetadata { *cacheable_metadata = CacheablePropertyMetadata {
.type = CacheablePropertyMetadata::Type::OwnProperty, .type = CacheablePropertyMetadata::Type::OwnProperty,
.property_offset = descriptor->property_offset.value(), .property_offset = descriptor->property_offset.value(),
}; };
} }
}
return *descriptor->value; return *descriptor->value;
} }

View file

@ -138,7 +138,11 @@ public:
virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const; virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const;
virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&); virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&);
virtual ThrowCompletionOr<bool> internal_has_property(PropertyKey const&) const; virtual ThrowCompletionOr<bool> internal_has_property(PropertyKey const&) const;
virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata* = nullptr) const; enum class PropertyLookupPhase {
OwnProperty,
PrototypeChain,
};
virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata* = nullptr, PropertyLookupPhase = PropertyLookupPhase::OwnProperty) const;
virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata* = nullptr); virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata* = nullptr);
virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&); virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&);
virtual ThrowCompletionOr<MarkedVector<Value>> internal_own_property_keys() const; virtual ThrowCompletionOr<MarkedVector<Value>> internal_own_property_keys() const;

View file

@ -455,7 +455,7 @@ ThrowCompletionOr<bool> ProxyObject::internal_has_property(PropertyKey const& pr
} }
// 10.5.8 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-proxy-object-internal-methods-and-internal-slots-get-p-receiver // 10.5.8 [[Get]] ( P, Receiver ), https://tc39.es/ecma262/#sec-proxy-object-internal-methods-and-internal-slots-get-p-receiver
ThrowCompletionOr<Value> ProxyObject::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata*) const ThrowCompletionOr<Value> ProxyObject::internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata*, PropertyLookupPhase) const
{ {
// NOTE: We don't return any cacheable metadata for proxy lookups. // NOTE: We don't return any cacheable metadata for proxy lookups.

View file

@ -39,7 +39,7 @@ public:
virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const override; virtual ThrowCompletionOr<Optional<PropertyDescriptor>> internal_get_own_property(PropertyKey const&) const override;
virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&) override; virtual ThrowCompletionOr<bool> internal_define_own_property(PropertyKey const&, PropertyDescriptor const&) override;
virtual ThrowCompletionOr<bool> internal_has_property(PropertyKey const&) const override; virtual ThrowCompletionOr<bool> internal_has_property(PropertyKey const&) const override;
virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata*) const override; virtual ThrowCompletionOr<Value> internal_get(PropertyKey const&, Value receiver, CacheablePropertyMetadata*, PropertyLookupPhase) const override;
virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata*) override; virtual ThrowCompletionOr<bool> internal_set(PropertyKey const&, Value value, Value receiver, CacheablePropertyMetadata*) override;
virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&) override; virtual ThrowCompletionOr<bool> internal_delete(PropertyKey const&) override;
virtual ThrowCompletionOr<MarkedVector<Value>> internal_own_property_keys() const override; virtual ThrowCompletionOr<MarkedVector<Value>> internal_own_property_keys() const override;

View file

@ -317,7 +317,7 @@ public:
} }
// 10.4.5.4 [[Get]] ( P, Receiver ), 10.4.5.4 [[Get]] ( P, Receiver ) // 10.4.5.4 [[Get]] ( P, Receiver ), 10.4.5.4 [[Get]] ( P, Receiver )
virtual ThrowCompletionOr<Value> internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata) const override virtual ThrowCompletionOr<Value> internal_get(PropertyKey const& property_key, Value receiver, CacheablePropertyMetadata* cacheable_metadata, PropertyLookupPhase phase) const override
{ {
VERIFY(!receiver.is_empty()); VERIFY(!receiver.is_empty());
@ -339,7 +339,7 @@ public:
} }
// 2. Return ? OrdinaryGet(O, P, Receiver). // 2. Return ? OrdinaryGet(O, P, Receiver).
return Object::internal_get(property_key, receiver, cacheable_metadata); return Object::internal_get(property_key, receiver, cacheable_metadata, phase);
} }
// 10.4.5.5 [[Set]] ( P, V, Receiver ), https://tc39.es/ecma262/#sec-integer-indexed-exotic-objects-set-p-v-receiver // 10.4.5.5 [[Set]] ( P, V, Receiver ), https://tc39.es/ecma262/#sec-integer-indexed-exotic-objects-set-p-v-receiver

View file

@ -409,15 +409,15 @@ JS::ThrowCompletionOr<bool> CSSStyleDeclaration::internal_has_property(JS::Prope
return property_id_from_name(name.to_string()) != CSS::PropertyID::Invalid; return property_id_from_name(name.to_string()) != CSS::PropertyID::Invalid;
} }
JS::ThrowCompletionOr<JS::Value> CSSStyleDeclaration::internal_get(JS::PropertyKey const& name, JS::Value receiver, JS::CacheablePropertyMetadata* cacheable_metadata) const JS::ThrowCompletionOr<JS::Value> CSSStyleDeclaration::internal_get(JS::PropertyKey const& name, JS::Value receiver, JS::CacheablePropertyMetadata* cacheable_metadata, PropertyLookupPhase phase) const
{ {
if (name.is_number()) if (name.is_number())
return { JS::PrimitiveString::create(vm(), item(name.as_number())) }; return { JS::PrimitiveString::create(vm(), item(name.as_number())) };
if (!name.is_string()) if (!name.is_string())
return Base::internal_get(name, receiver, cacheable_metadata); return Base::internal_get(name, receiver, cacheable_metadata, phase);
auto property_id = property_id_from_name(name.to_string()); auto property_id = property_id_from_name(name.to_string());
if (property_id == CSS::PropertyID::Invalid) if (property_id == CSS::PropertyID::Invalid)
return Base::internal_get(name, receiver, cacheable_metadata); return Base::internal_get(name, receiver, cacheable_metadata, phase);
if (auto maybe_property = property(property_id); maybe_property.has_value()) if (auto maybe_property = property(property_id); maybe_property.has_value())
return { JS::PrimitiveString::create(vm(), maybe_property->value->to_string()) }; return { JS::PrimitiveString::create(vm(), maybe_property->value->to_string()) };
return { JS::PrimitiveString::create(vm(), String {}) }; return { JS::PrimitiveString::create(vm(), String {}) };

View file

@ -42,7 +42,7 @@ public:
virtual String serialized() const = 0; virtual String serialized() const = 0;
virtual JS::ThrowCompletionOr<bool> internal_has_property(JS::PropertyKey const& name) const override; virtual JS::ThrowCompletionOr<bool> internal_has_property(JS::PropertyKey const& name) const override;
virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*) const override; virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*, PropertyLookupPhase) const override;
virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override; virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override;
protected: protected:

View file

@ -483,13 +483,13 @@ JS::ThrowCompletionOr<bool> Location::internal_define_own_property(JS::PropertyK
} }
// 7.10.5.7 [[Get]] ( P, Receiver ), https://html.spec.whatwg.org/multipage/history.html#location-get // 7.10.5.7 [[Get]] ( P, Receiver ), https://html.spec.whatwg.org/multipage/history.html#location-get
JS::ThrowCompletionOr<JS::Value> Location::internal_get(JS::PropertyKey const& property_key, JS::Value receiver, JS::CacheablePropertyMetadata* cacheable_metadata) const JS::ThrowCompletionOr<JS::Value> Location::internal_get(JS::PropertyKey const& property_key, JS::Value receiver, JS::CacheablePropertyMetadata* cacheable_metadata, PropertyLookupPhase phase) const
{ {
auto& vm = this->vm(); auto& vm = this->vm();
// 1. If IsPlatformObjectSameOrigin(this) is true, then return ? OrdinaryGet(this, P, Receiver). // 1. If IsPlatformObjectSameOrigin(this) is true, then return ? OrdinaryGet(this, P, Receiver).
if (HTML::is_platform_object_same_origin(*this)) if (HTML::is_platform_object_same_origin(*this))
return JS::Object::internal_get(property_key, receiver, cacheable_metadata); return JS::Object::internal_get(property_key, receiver, cacheable_metadata, phase);
// 2. Return ? CrossOriginGet(this, P, Receiver). // 2. Return ? CrossOriginGet(this, P, Receiver).
return HTML::cross_origin_get(vm, static_cast<JS::Object const&>(*this), property_key, receiver); return HTML::cross_origin_get(vm, static_cast<JS::Object const&>(*this), property_key, receiver);

View file

@ -60,7 +60,7 @@ public:
virtual JS::ThrowCompletionOr<bool> internal_prevent_extensions() override; virtual JS::ThrowCompletionOr<bool> internal_prevent_extensions() override;
virtual JS::ThrowCompletionOr<Optional<JS::PropertyDescriptor>> internal_get_own_property(JS::PropertyKey const&) const override; virtual JS::ThrowCompletionOr<Optional<JS::PropertyDescriptor>> internal_get_own_property(JS::PropertyKey const&) const override;
virtual JS::ThrowCompletionOr<bool> internal_define_own_property(JS::PropertyKey const&, JS::PropertyDescriptor const&) override; virtual JS::ThrowCompletionOr<bool> internal_define_own_property(JS::PropertyKey const&, JS::PropertyDescriptor const&) override;
virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*) const override; virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*, PropertyLookupPhase) const override;
virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override; virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override;
virtual JS::ThrowCompletionOr<bool> internal_delete(JS::PropertyKey const&) override; virtual JS::ThrowCompletionOr<bool> internal_delete(JS::PropertyKey const&) override;
virtual JS::ThrowCompletionOr<JS::MarkedVector<JS::Value>> internal_own_property_keys() const override; virtual JS::ThrowCompletionOr<JS::MarkedVector<JS::Value>> internal_own_property_keys() const override;

View file

@ -153,7 +153,7 @@ JS::ThrowCompletionOr<bool> WindowProxy::internal_define_own_property(JS::Proper
} }
// 7.4.7 [[Get]] ( P, Receiver ), https://html.spec.whatwg.org/multipage/window-object.html#windowproxy-get // 7.4.7 [[Get]] ( P, Receiver ), https://html.spec.whatwg.org/multipage/window-object.html#windowproxy-get
JS::ThrowCompletionOr<JS::Value> WindowProxy::internal_get(JS::PropertyKey const& property_key, JS::Value receiver, JS::CacheablePropertyMetadata*) const JS::ThrowCompletionOr<JS::Value> WindowProxy::internal_get(JS::PropertyKey const& property_key, JS::Value receiver, JS::CacheablePropertyMetadata*, PropertyLookupPhase) const
{ {
auto& vm = this->vm(); auto& vm = this->vm();

View file

@ -27,7 +27,7 @@ public:
virtual JS::ThrowCompletionOr<bool> internal_prevent_extensions() override; virtual JS::ThrowCompletionOr<bool> internal_prevent_extensions() override;
virtual JS::ThrowCompletionOr<Optional<JS::PropertyDescriptor>> internal_get_own_property(JS::PropertyKey const&) const override; virtual JS::ThrowCompletionOr<Optional<JS::PropertyDescriptor>> internal_get_own_property(JS::PropertyKey const&) const override;
virtual JS::ThrowCompletionOr<bool> internal_define_own_property(JS::PropertyKey const&, JS::PropertyDescriptor const&) override; virtual JS::ThrowCompletionOr<bool> internal_define_own_property(JS::PropertyKey const&, JS::PropertyDescriptor const&) override;
virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*) const override; virtual JS::ThrowCompletionOr<JS::Value> internal_get(JS::PropertyKey const&, JS::Value receiver, JS::CacheablePropertyMetadata*, PropertyLookupPhase) const override;
virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override; virtual JS::ThrowCompletionOr<bool> internal_set(JS::PropertyKey const&, JS::Value value, JS::Value receiver, JS::CacheablePropertyMetadata*) override;
virtual JS::ThrowCompletionOr<bool> internal_delete(JS::PropertyKey const&) override; virtual JS::ThrowCompletionOr<bool> internal_delete(JS::PropertyKey const&) override;
virtual JS::ThrowCompletionOr<JS::MarkedVector<JS::Value>> internal_own_property_keys() const override; virtual JS::ThrowCompletionOr<JS::MarkedVector<JS::Value>> internal_own_property_keys() const override;