| OLD | NEW |
| 1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 585 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 596 case CONSTANT_TRANSITION: | 596 case CONSTANT_TRANSITION: |
| 597 case NULL_DESCRIPTOR: | 597 case NULL_DESCRIPTOR: |
| 598 break; | 598 break; |
| 599 } | 599 } |
| 600 UNREACHABLE(); | 600 UNREACHABLE(); |
| 601 return NULL; | 601 return NULL; |
| 602 } | 602 } |
| 603 | 603 |
| 604 | 604 |
| 605 MaybeObject* Object::GetElementWithReceiver(Object* receiver, uint32_t index) { | 605 MaybeObject* Object::GetElementWithReceiver(Object* receiver, uint32_t index) { |
| 606 Object* holder = NULL; | 606 Heap* heap = IsSmi() |
| 607 if (IsSmi()) { | 607 ? Isolate::Current()->heap() |
| 608 Context* global_context = Isolate::Current()->context()->global_context(); | 608 : HeapObject::cast(this)->GetHeap(); |
| 609 holder = global_context->number_function()->instance_prototype(); | 609 Object* holder = this; |
| 610 } else { | |
| 611 HeapObject* heap_object = HeapObject::cast(this); | |
| 612 | 610 |
| 613 if (heap_object->IsJSObject()) { | 611 // Iterate up the prototype chain until an element is found or the null |
| 614 return JSObject::cast(this)->GetElementWithReceiver(receiver, index); | 612 // prototype is encountered. |
| 613 for (holder = this; |
| 614 holder != heap->null_value(); |
| 615 holder = holder->GetPrototype()) { |
| 616 if (holder->IsSmi()) { |
| 617 Context* global_context = Isolate::Current()->context()->global_context(); |
| 618 holder = global_context->number_function()->instance_prototype(); |
| 619 } else { |
| 620 HeapObject* heap_object = HeapObject::cast(holder); |
| 621 if (!heap_object->IsJSObject()) { |
| 622 Isolate* isolate = heap->isolate(); |
| 623 Context* global_context = isolate->context()->global_context(); |
| 624 if (heap_object->IsString()) { |
| 625 holder = global_context->string_function()->instance_prototype(); |
| 626 } else if (heap_object->IsHeapNumber()) { |
| 627 holder = global_context->number_function()->instance_prototype(); |
| 628 } else if (heap_object->IsBoolean()) { |
| 629 holder = global_context->boolean_function()->instance_prototype(); |
| 630 } else if (heap_object->IsJSProxy()) { |
| 631 return heap->undefined_value(); // For now... |
| 632 } else { |
| 633 // Undefined and null have no indexed properties. |
| 634 ASSERT(heap_object->IsUndefined() || heap_object->IsNull()); |
| 635 return heap->undefined_value(); |
| 636 } |
| 637 } |
| 615 } | 638 } |
| 616 Heap* heap = heap_object->GetHeap(); | |
| 617 Isolate* isolate = heap->isolate(); | |
| 618 | 639 |
| 619 Context* global_context = isolate->context()->global_context(); | 640 // Inline the case for JSObjects. Doing so significantly improves the |
| 620 if (heap_object->IsString()) { | 641 // performance of fetching elements where checking the prototype chain is |
| 621 holder = global_context->string_function()->instance_prototype(); | 642 // necessary. |
| 622 } else if (heap_object->IsHeapNumber()) { | 643 JSObject* js_object = JSObject::cast(holder); |
| 623 holder = global_context->number_function()->instance_prototype(); | 644 |
| 624 } else if (heap_object->IsBoolean()) { | 645 // Check access rights if needed. |
| 625 holder = global_context->boolean_function()->instance_prototype(); | 646 if (js_object->IsAccessCheckNeeded()) { |
| 626 } else if (heap_object->IsJSProxy()) { | 647 Isolate* isolate = heap->isolate(); |
| 627 return heap->undefined_value(); // For now... | 648 if (!isolate->MayIndexedAccess(js_object, index, v8::ACCESS_GET)) { |
| 628 } else { | 649 isolate->ReportFailedAccessCheck(js_object, v8::ACCESS_GET); |
| 629 // Undefined and null have no indexed properties. | 650 return heap->undefined_value(); |
| 630 ASSERT(heap_object->IsUndefined() || heap_object->IsNull()); | 651 } |
| 631 return heap->undefined_value(); | 652 } |
| 653 |
| 654 if (js_object->HasIndexedInterceptor()) { |
| 655 return js_object->GetElementWithInterceptor(receiver, index); |
| 656 } |
| 657 |
| 658 if (js_object->elements() != heap->empty_fixed_array()) { |
| 659 MaybeObject* result = js_object->GetElementsAccessor()->GetWithReceiver( |
| 660 js_object, |
| 661 receiver, |
| 662 index); |
| 663 if (result != heap->the_hole_value()) return result; |
| 632 } | 664 } |
| 633 } | 665 } |
| 634 | 666 |
| 635 return JSObject::cast(holder)->GetElementWithReceiver(receiver, index); | 667 return heap->undefined_value(); |
| 636 } | 668 } |
| 637 | 669 |
| 638 | 670 |
| 639 Object* Object::GetPrototype() { | 671 Object* Object::GetPrototype() { |
| 640 if (IsSmi()) { | 672 if (IsSmi()) { |
| 641 Heap* heap = Isolate::Current()->heap(); | 673 Heap* heap = Isolate::Current()->heap(); |
| 642 Context* context = heap->isolate()->context()->global_context(); | 674 Context* context = heap->isolate()->context()->global_context(); |
| 643 return context->number_function()->instance_prototype(); | 675 return context->number_function()->instance_prototype(); |
| 644 } | 676 } |
| 645 | 677 |
| (...skipping 8336 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 8982 if (raw_result != heap->the_hole_value()) return raw_result; | 9014 if (raw_result != heap->the_hole_value()) return raw_result; |
| 8983 | 9015 |
| 8984 RETURN_IF_SCHEDULED_EXCEPTION(isolate); | 9016 RETURN_IF_SCHEDULED_EXCEPTION(isolate); |
| 8985 | 9017 |
| 8986 Object* pt = holder_handle->GetPrototype(); | 9018 Object* pt = holder_handle->GetPrototype(); |
| 8987 if (pt == heap->null_value()) return heap->undefined_value(); | 9019 if (pt == heap->null_value()) return heap->undefined_value(); |
| 8988 return pt->GetElementWithReceiver(*this_handle, index); | 9020 return pt->GetElementWithReceiver(*this_handle, index); |
| 8989 } | 9021 } |
| 8990 | 9022 |
| 8991 | 9023 |
| 8992 MaybeObject* JSObject::GetElementWithReceiver(Object* receiver, | |
| 8993 uint32_t index) { | |
| 8994 // Check access rights if needed. | |
| 8995 if (IsAccessCheckNeeded()) { | |
| 8996 Heap* heap = GetHeap(); | |
| 8997 if (!heap->isolate()->MayIndexedAccess(this, index, v8::ACCESS_GET)) { | |
| 8998 heap->isolate()->ReportFailedAccessCheck(this, v8::ACCESS_GET); | |
| 8999 return heap->undefined_value(); | |
| 9000 } | |
| 9001 } | |
| 9002 | |
| 9003 if (HasIndexedInterceptor()) { | |
| 9004 return GetElementWithInterceptor(receiver, index); | |
| 9005 } | |
| 9006 | |
| 9007 Heap* heap = GetHeap(); | |
| 9008 if (elements() != heap->empty_fixed_array()) { | |
| 9009 MaybeObject* result = GetElementsAccessor()->GetWithReceiver(this, | |
| 9010 receiver, | |
| 9011 index); | |
| 9012 if (result != heap->the_hole_value()) return result; | |
| 9013 } | |
| 9014 | |
| 9015 Object* pt = GetPrototype(); | |
| 9016 if (pt == heap->null_value()) return heap->undefined_value(); | |
| 9017 return pt->GetElementWithReceiver(receiver, index); | |
| 9018 } | |
| 9019 | |
| 9020 | |
| 9021 bool JSObject::HasDenseElements() { | 9024 bool JSObject::HasDenseElements() { |
| 9022 int capacity = 0; | 9025 int capacity = 0; |
| 9023 int used = 0; | 9026 int used = 0; |
| 9024 GetElementsCapacityAndUsage(&capacity, &used); | 9027 GetElementsCapacityAndUsage(&capacity, &used); |
| 9025 return (capacity == 0) || (used > (capacity / 2)); | 9028 return (capacity == 0) || (used > (capacity / 2)); |
| 9026 } | 9029 } |
| 9027 | 9030 |
| 9028 | 9031 |
| 9029 void JSObject::GetElementsCapacityAndUsage(int* capacity, int* used) { | 9032 void JSObject::GetElementsCapacityAndUsage(int* capacity, int* used) { |
| 9030 *capacity = 0; | 9033 *capacity = 0; |
| (...skipping 2855 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 11886 if (break_point_objects()->IsUndefined()) return 0; | 11889 if (break_point_objects()->IsUndefined()) return 0; |
| 11887 // Single break point. | 11890 // Single break point. |
| 11888 if (!break_point_objects()->IsFixedArray()) return 1; | 11891 if (!break_point_objects()->IsFixedArray()) return 1; |
| 11889 // Multiple break points. | 11892 // Multiple break points. |
| 11890 return FixedArray::cast(break_point_objects())->length(); | 11893 return FixedArray::cast(break_point_objects())->length(); |
| 11891 } | 11894 } |
| 11892 #endif | 11895 #endif |
| 11893 | 11896 |
| 11894 | 11897 |
| 11895 } } // namespace v8::internal | 11898 } } // namespace v8::internal |
| OLD | NEW |