Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(211)

Side by Side Diff: src/lookup.cc

Issue 1651913005: [runtime] Fix integer indexed property handling (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 4 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/lookup.h ('k') | src/objects.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 the V8 project authors. All rights reserved. 1 // Copyright 2014 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/lookup.h" 5 #include "src/lookup.h"
6 6
7 #include "src/bootstrapper.h" 7 #include "src/bootstrapper.h"
8 #include "src/deoptimizer.h" 8 #include "src/deoptimizer.h"
9 #include "src/elements.h" 9 #include "src/elements.h"
10 #include "src/isolate-inl.h" 10 #include "src/isolate-inl.h"
(...skipping 372 matching lines...) Expand 10 before | Expand all | Expand 10 after
383 JSObject::ReoptimizeIfPrototype(receiver); 383 JSObject::ReoptimizeIfPrototype(receiver);
384 } 384 }
385 385
386 holder_map_ = handle(receiver->map(), isolate_); 386 holder_map_ = handle(receiver->map(), isolate_);
387 ReloadPropertyInformation(); 387 ReloadPropertyInformation();
388 } 388 }
389 389
390 390
391 bool LookupIterator::HolderIsReceiverOrHiddenPrototype() const { 391 bool LookupIterator::HolderIsReceiverOrHiddenPrototype() const {
392 DCHECK(has_property_ || state_ == INTERCEPTOR || state_ == JSPROXY); 392 DCHECK(has_property_ || state_ == INTERCEPTOR || state_ == JSPROXY);
393 return InternalHolderIsReceiverOrHiddenPrototype();
394 }
395
396 bool LookupIterator::InternalHolderIsReceiverOrHiddenPrototype() const {
397 // Optimization that only works if configuration_ is not mutable. 393 // Optimization that only works if configuration_ is not mutable.
398 if (!check_prototype_chain()) return true; 394 if (!check_prototype_chain()) return true;
399 DisallowHeapAllocation no_gc; 395 DisallowHeapAllocation no_gc;
400 if (!receiver_->IsJSReceiver()) return false; 396 if (!receiver_->IsJSReceiver()) return false;
401 JSReceiver* current = JSReceiver::cast(*receiver_); 397 JSReceiver* current = JSReceiver::cast(*receiver_);
402 JSReceiver* holder = *holder_; 398 JSReceiver* object = *holder_;
403 if (current == holder) return true; 399 if (current == object) return true;
404 if (!holder->map()->is_hidden_prototype()) return false; 400 if (!object->map()->is_hidden_prototype()) return false;
405 // JSProxy do not occur as hidden prototypes. 401 // JSProxy do not occur as hidden prototypes.
406 if (current->IsJSProxy()) return false; 402 if (current->IsJSProxy()) return false;
407 PrototypeIterator iter(isolate(), current); 403 PrototypeIterator iter(isolate(), current);
408 while (!iter.IsAtEnd(PrototypeIterator::END_AT_NON_HIDDEN)) { 404 while (!iter.IsAtEnd(PrototypeIterator::END_AT_NON_HIDDEN)) {
409 if (iter.GetCurrent<JSReceiver>() == holder) return true; 405 if (iter.GetCurrent<JSReceiver>() == object) return true;
410 iter.Advance(); 406 iter.Advance();
411 } 407 }
412 return false; 408 return false;
413 } 409 }
414 410
415 411
416 Handle<Object> LookupIterator::FetchValue() const { 412 Handle<Object> LookupIterator::FetchValue() const {
417 Object* result = NULL; 413 Object* result = NULL;
418 if (IsElement()) { 414 if (IsElement()) {
419 Handle<JSObject> holder = GetHolder<JSObject>(); 415 Handle<JSObject> holder = GetHolder<JSObject>();
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after
516 property_dictionary->ValueAtPut(dictionary_entry(), *value); 512 property_dictionary->ValueAtPut(dictionary_entry(), *value);
517 } else if (property_details_.type() == v8::internal::DATA) { 513 } else if (property_details_.type() == v8::internal::DATA) {
518 JSObject::cast(*holder)->WriteToField(descriptor_number(), *value); 514 JSObject::cast(*holder)->WriteToField(descriptor_number(), *value);
519 } else { 515 } else {
520 DCHECK_EQ(v8::internal::DATA_CONSTANT, property_details_.type()); 516 DCHECK_EQ(v8::internal::DATA_CONSTANT, property_details_.type());
521 } 517 }
522 } 518 }
523 519
524 520
525 bool LookupIterator::IsIntegerIndexedExotic(JSReceiver* holder) { 521 bool LookupIterator::IsIntegerIndexedExotic(JSReceiver* holder) {
526 DCHECK(exotic_index_state_ != ExoticIndexState::kNotExotic); 522 DCHECK(!IsElement());
527 if (exotic_index_state_ == ExoticIndexState::kExotic) return true; 523 if (!name_->IsString()) return false;
528 if (!InternalHolderIsReceiverOrHiddenPrototype()) { 524 if (*receiver_ != holder) return false;
529 exotic_index_state_ = ExoticIndexState::kNotExotic; 525
530 return false; 526 Handle<String> name_string = Handle<String>::cast(name_);
531 } 527 if (name_string->length() == 0) return false;
532 DCHECK(exotic_index_state_ == ExoticIndexState::kUninitialized); 528
533 bool result = false; 529 return IsSpecialIndex(isolate_->unicode_cache(), *name_string);
534 // Compute and cache result.
535 if (IsElement()) {
536 result = index_ >= JSTypedArray::cast(holder)->length_value();
537 } else if (name()->IsString()) {
538 Handle<String> name_string = Handle<String>::cast(name());
539 if (name_string->length() != 0) {
540 result = IsSpecialIndex(isolate_->unicode_cache(), *name_string);
541 }
542 }
543 exotic_index_state_ =
544 result ? ExoticIndexState::kExotic : ExoticIndexState::kNotExotic;
545 return result;
546 } 530 }
547 531
548 532
549 void LookupIterator::InternalizeName() { 533 void LookupIterator::InternalizeName() {
550 if (name_->IsUniqueName()) return; 534 if (name_->IsUniqueName()) return;
551 name_ = factory()->InternalizeString(Handle<String>::cast(name_)); 535 name_ = factory()->InternalizeString(Handle<String>::cast(name_));
552 } 536 }
553 537
554 538
555 bool LookupIterator::HasInterceptor(Map* map) const { 539 bool LookupIterator::HasInterceptor(Map* map) const {
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after
622 return INTERCEPTOR; 606 return INTERCEPTOR;
623 } 607 }
624 // Fall through. 608 // Fall through.
625 case INTERCEPTOR: 609 case INTERCEPTOR:
626 if (IsElement()) { 610 if (IsElement()) {
627 JSObject* js_object = JSObject::cast(holder); 611 JSObject* js_object = JSObject::cast(holder);
628 ElementsAccessor* accessor = js_object->GetElementsAccessor(); 612 ElementsAccessor* accessor = js_object->GetElementsAccessor();
629 FixedArrayBase* backing_store = js_object->elements(); 613 FixedArrayBase* backing_store = js_object->elements();
630 number_ = accessor->GetEntryForIndex(js_object, backing_store, index_); 614 number_ = accessor->GetEntryForIndex(js_object, backing_store, index_);
631 if (number_ == kMaxUInt32) { 615 if (number_ == kMaxUInt32) {
632 if (*receiver_ == Object::cast(holder) && holder->IsJSTypedArray()) { 616 if (*receiver_ == holder && holder->IsJSTypedArray()) {
633 return INTEGER_INDEXED_EXOTIC; 617 return INTEGER_INDEXED_EXOTIC;
634 } 618 }
635 return NOT_FOUND; 619 return NOT_FOUND;
636 } 620 }
637 property_details_ = accessor->GetDetails(js_object, number_); 621 property_details_ = accessor->GetDetails(js_object, number_);
638 } else if (exotic_index_state_ != ExoticIndexState::kNotExotic && 622 } else if (holder->IsJSTypedArray() && IsIntegerIndexedExotic(holder)) {
639 holder->IsJSTypedArray() && IsIntegerIndexedExotic(holder)) {
640 return INTEGER_INDEXED_EXOTIC; 623 return INTEGER_INDEXED_EXOTIC;
641 } else if (!map->is_dictionary_map()) { 624 } else if (!map->is_dictionary_map()) {
642 DescriptorArray* descriptors = map->instance_descriptors(); 625 DescriptorArray* descriptors = map->instance_descriptors();
643 int number = descriptors->SearchWithCache(*name_, map); 626 int number = descriptors->SearchWithCache(*name_, map);
644 if (number == DescriptorArray::kNotFound) return NOT_FOUND; 627 if (number == DescriptorArray::kNotFound) return NOT_FOUND;
645 number_ = static_cast<uint32_t>(number); 628 number_ = static_cast<uint32_t>(number);
646 property_details_ = descriptors->GetDetails(number_); 629 property_details_ = descriptors->GetDetails(number_);
647 } else if (map->IsJSGlobalObjectMap()) { 630 } else if (map->IsJSGlobalObjectMap()) {
648 GlobalDictionary* dict = JSObject::cast(holder)->global_dictionary(); 631 GlobalDictionary* dict = JSObject::cast(holder)->global_dictionary();
649 int number = dict->FindEntry(name_); 632 int number = dict->FindEntry(name_);
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
691 // Fall through. 674 // Fall through.
692 default: 675 default:
693 return NOT_FOUND; 676 return NOT_FOUND;
694 } 677 }
695 UNREACHABLE(); 678 UNREACHABLE();
696 return state_; 679 return state_;
697 } 680 }
698 681
699 } // namespace internal 682 } // namespace internal
700 } // namespace v8 683 } // namespace v8
OLDNEW
« no previous file with comments | « src/lookup.h ('k') | src/objects.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698