diff options
Diffstat (limited to 'deps/v8/src/lookup.cc')
-rw-r--r-- | deps/v8/src/lookup.cc | 57 |
1 files changed, 44 insertions, 13 deletions
diff --git a/deps/v8/src/lookup.cc b/deps/v8/src/lookup.cc index 2d3cc3253e..71902dff84 100644 --- a/deps/v8/src/lookup.cc +++ b/deps/v8/src/lookup.cc @@ -211,7 +211,7 @@ Handle<JSReceiver> LookupIterator::GetRootForNonJSReceiver( auto root = handle(receiver->GetPrototypeChainRootMap(isolate)->prototype(), isolate); if (root->IsNull(isolate)) { - unsigned int magic = 0xbbbbbbbb; + unsigned int magic = 0xBBBBBBBB; isolate->PushStackTraceAndDie(magic, *receiver, nullptr, magic); } return Handle<JSReceiver>::cast(root); @@ -237,22 +237,45 @@ void LookupIterator::ReloadPropertyInformation() { DCHECK(IsFound() || !holder_->HasFastProperties()); } +namespace { +bool IsTypedArrayFunctionInAnyContext(Isolate* isolate, JSReceiver* holder) { + static uint32_t context_slots[] = { +#define TYPED_ARRAY_CONTEXT_SLOTS(Type, type, TYPE, ctype, size) \ + Context::TYPE##_ARRAY_FUN_INDEX, + + TYPED_ARRAYS(TYPED_ARRAY_CONTEXT_SLOTS) +#undef TYPED_ARRAY_CONTEXT_SLOTS + }; + + if (!holder->IsJSFunction()) return false; + + return std::any_of( + std::begin(context_slots), std::end(context_slots), + [=](uint32_t slot) { return isolate->IsInAnyContext(holder, slot); }); +} +} // namespace + void LookupIterator::InternalUpdateProtector() { if (isolate_->bootstrapper()->IsActive()) return; if (*name_ == heap()->constructor_string()) { if (!isolate_->IsArraySpeciesLookupChainIntact()) return; // Setting the constructor property could change an instance's @@species - if (holder_->IsJSArray()) { + if (holder_->IsJSArray() || holder_->IsJSTypedArray()) { isolate_->CountUsage( v8::Isolate::UseCounterFeature::kArrayInstanceConstructorModified); isolate_->InvalidateArraySpeciesProtector(); } else if (holder_->map()->is_prototype_map()) { DisallowHeapAllocation no_gc; - // Setting the constructor of Array.prototype of any realm also needs - // to invalidate the species protector + // Setting the constructor of Array.prototype or %TypedArray%.prototype of + // any realm also needs to invalidate the species protector. + // For typed arrays, we check a prototype of this holder since TypedArrays + // have different prototypes for each type, and their parent prototype is + // pointing the same TYPED_ARRAY_PROTOTYPE. if (isolate_->IsInAnyContext(*holder_, - Context::INITIAL_ARRAY_PROTOTYPE_INDEX)) { + Context::INITIAL_ARRAY_PROTOTYPE_INDEX) || + isolate_->IsInAnyContext(holder_->map()->prototype(), + Context::TYPED_ARRAY_PROTOTYPE_INDEX)) { isolate_->CountUsage(v8::Isolate::UseCounterFeature:: kArrayPrototypeConstructorModified); isolate_->InvalidateArraySpeciesProtector(); @@ -260,9 +283,10 @@ void LookupIterator::InternalUpdateProtector() { } } else if (*name_ == heap()->species_symbol()) { if (!isolate_->IsArraySpeciesLookupChainIntact()) return; - // Setting the Symbol.species property of any Array constructor invalidates - // the species protector - if (isolate_->IsInAnyContext(*holder_, Context::ARRAY_FUNCTION_INDEX)) { + // Setting the Symbol.species property of any Array or TypedArray + // constructor invalidates the species protector + if (isolate_->IsInAnyContext(*holder_, Context::ARRAY_FUNCTION_INDEX) || + IsTypedArrayFunctionInAnyContext(isolate_, *holder_)) { isolate_->CountUsage( v8::Isolate::UseCounterFeature::kArraySpeciesModified); isolate_->InvalidateArraySpeciesProtector(); @@ -479,6 +503,7 @@ void LookupIterator::ApplyTransitionToDataProperty(Handle<JSObject> receiver) { DCHECK(receiver.is_identical_to(GetStoreTarget())); holder_ = receiver; if (receiver->IsJSGlobalObject()) { + JSObject::InvalidatePrototypeChains(receiver->map()); state_ = DATA; return; } @@ -495,6 +520,9 @@ void LookupIterator::ApplyTransitionToDataProperty(Handle<JSObject> receiver) { Handle<NameDictionary> dictionary(receiver->property_dictionary(), isolate_); int entry; + if (receiver->map()->is_prototype_map()) { + JSObject::InvalidatePrototypeChains(receiver->map()); + } dictionary = NameDictionary::Add(dictionary, name(), isolate_->factory()->uninitialized_value(), property_details_, &entry); @@ -521,8 +549,8 @@ void LookupIterator::Delete() { bool is_prototype_map = holder->map()->is_prototype_map(); RuntimeCallTimerScope stats_scope( isolate_, is_prototype_map - ? &RuntimeCallStats::PrototypeObject_DeleteProperty - : &RuntimeCallStats::Object_DeleteProperty); + ? RuntimeCallCounterId::kPrototypeObject_DeleteProperty + : RuntimeCallCounterId::kObject_DeleteProperty); PropertyNormalizationMode mode = is_prototype_map ? KEEP_INOBJECT_PROPERTIES : CLEAR_INOBJECT_PROPERTIES; @@ -638,9 +666,12 @@ void LookupIterator::TransitionToAccessorPair(Handle<Object> pair, ReloadPropertyInformation<true>(); } else { - PropertyNormalizationMode mode = receiver->map()->is_prototype_map() - ? KEEP_INOBJECT_PROPERTIES - : CLEAR_INOBJECT_PROPERTIES; + PropertyNormalizationMode mode = CLEAR_INOBJECT_PROPERTIES; + if (receiver->map()->is_prototype_map()) { + JSObject::InvalidatePrototypeChains(receiver->map()); + mode = KEEP_INOBJECT_PROPERTIES; + } + // Normalize object to make this operation simple. JSObject::NormalizeProperties(receiver, mode, 0, "TransitionToAccessorPair"); |