| Index: src/objects.cc
|
| diff --git a/src/objects.cc b/src/objects.cc
|
| index 26736d9e6860083a699cc7fd9f4ecdefabb22d58..e5a5bd5c09fbe365f4d6751d967bc92b2abfdf90 100644
|
| --- a/src/objects.cc
|
| +++ b/src/objects.cc
|
| @@ -603,36 +603,68 @@ MaybeObject* Object::GetProperty(Object* receiver,
|
|
|
|
|
| MaybeObject* Object::GetElementWithReceiver(Object* receiver, uint32_t index) {
|
| - Object* holder = NULL;
|
| - if (IsSmi()) {
|
| - Context* global_context = Isolate::Current()->context()->global_context();
|
| - holder = global_context->number_function()->instance_prototype();
|
| - } else {
|
| - HeapObject* heap_object = HeapObject::cast(this);
|
| + Heap* heap = IsSmi()
|
| + ? Isolate::Current()->heap()
|
| + : HeapObject::cast(this)->GetHeap();
|
| + Object* holder = this;
|
| +
|
| + // Iterate up the prototype chain until an element is found or the null
|
| + // prototype is encountered.
|
| + for (holder = this;
|
| + holder != heap->null_value();
|
| + holder = holder->GetPrototype()) {
|
| + if (holder->IsSmi()) {
|
| + Context* global_context = Isolate::Current()->context()->global_context();
|
| + holder = global_context->number_function()->instance_prototype();
|
| + } else {
|
| + HeapObject* heap_object = HeapObject::cast(holder);
|
| + if (!heap_object->IsJSObject()) {
|
| + Isolate* isolate = heap->isolate();
|
| + Context* global_context = isolate->context()->global_context();
|
| + if (heap_object->IsString()) {
|
| + holder = global_context->string_function()->instance_prototype();
|
| + } else if (heap_object->IsHeapNumber()) {
|
| + holder = global_context->number_function()->instance_prototype();
|
| + } else if (heap_object->IsBoolean()) {
|
| + holder = global_context->boolean_function()->instance_prototype();
|
| + } else if (heap_object->IsJSProxy()) {
|
| + return heap->undefined_value(); // For now...
|
| + } else {
|
| + // Undefined and null have no indexed properties.
|
| + ASSERT(heap_object->IsUndefined() || heap_object->IsNull());
|
| + return heap->undefined_value();
|
| + }
|
| + }
|
| + }
|
|
|
| - if (heap_object->IsJSObject()) {
|
| - return JSObject::cast(this)->GetElementWithReceiver(receiver, index);
|
| + // Inline the case for JSObjects. Doing so significantly improves the
|
| + // performance of fetching elements where checking the prototype chain is
|
| + // necessary.
|
| + JSObject* js_object = JSObject::cast(holder);
|
| +
|
| + // Check access rights if needed.
|
| + if (js_object->IsAccessCheckNeeded()) {
|
| + Isolate* isolate = heap->isolate();
|
| + if (!isolate->MayIndexedAccess(js_object, index, v8::ACCESS_GET)) {
|
| + isolate->ReportFailedAccessCheck(js_object, v8::ACCESS_GET);
|
| + return heap->undefined_value();
|
| + }
|
| }
|
| - Heap* heap = heap_object->GetHeap();
|
| - Isolate* isolate = heap->isolate();
|
|
|
| - Context* global_context = isolate->context()->global_context();
|
| - if (heap_object->IsString()) {
|
| - holder = global_context->string_function()->instance_prototype();
|
| - } else if (heap_object->IsHeapNumber()) {
|
| - holder = global_context->number_function()->instance_prototype();
|
| - } else if (heap_object->IsBoolean()) {
|
| - holder = global_context->boolean_function()->instance_prototype();
|
| - } else if (heap_object->IsJSProxy()) {
|
| - return heap->undefined_value(); // For now...
|
| - } else {
|
| - // Undefined and null have no indexed properties.
|
| - ASSERT(heap_object->IsUndefined() || heap_object->IsNull());
|
| - return heap->undefined_value();
|
| + if (js_object->HasIndexedInterceptor()) {
|
| + return js_object->GetElementWithInterceptor(receiver, index);
|
| + }
|
| +
|
| + if (js_object->elements() != heap->empty_fixed_array()) {
|
| + MaybeObject* result = js_object->GetElementsAccessor()->GetWithReceiver(
|
| + js_object,
|
| + receiver,
|
| + index);
|
| + if (result != heap->the_hole_value()) return result;
|
| }
|
| }
|
|
|
| - return JSObject::cast(holder)->GetElementWithReceiver(receiver, index);
|
| + return heap->undefined_value();
|
| }
|
|
|
|
|
| @@ -8989,35 +9021,6 @@ MaybeObject* JSObject::GetElementWithInterceptor(Object* receiver,
|
| }
|
|
|
|
|
| -MaybeObject* JSObject::GetElementWithReceiver(Object* receiver,
|
| - uint32_t index) {
|
| - // Check access rights if needed.
|
| - if (IsAccessCheckNeeded()) {
|
| - Heap* heap = GetHeap();
|
| - if (!heap->isolate()->MayIndexedAccess(this, index, v8::ACCESS_GET)) {
|
| - heap->isolate()->ReportFailedAccessCheck(this, v8::ACCESS_GET);
|
| - return heap->undefined_value();
|
| - }
|
| - }
|
| -
|
| - if (HasIndexedInterceptor()) {
|
| - return GetElementWithInterceptor(receiver, index);
|
| - }
|
| -
|
| - Heap* heap = GetHeap();
|
| - if (elements() != heap->empty_fixed_array()) {
|
| - MaybeObject* result = GetElementsAccessor()->GetWithReceiver(this,
|
| - receiver,
|
| - index);
|
| - if (result != heap->the_hole_value()) return result;
|
| - }
|
| -
|
| - Object* pt = GetPrototype();
|
| - if (pt == heap->null_value()) return heap->undefined_value();
|
| - return pt->GetElementWithReceiver(receiver, index);
|
| -}
|
| -
|
| -
|
| bool JSObject::HasDenseElements() {
|
| int capacity = 0;
|
| int used = 0;
|
|
|