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 4671 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4682 return cache; | 4682 return cache; |
4683 } | 4683 } |
4684 | 4684 |
4685 | 4685 |
4686 MaybeObject* FixedArray::AddKeysFromJSArray(JSArray* array) { | 4686 MaybeObject* FixedArray::AddKeysFromJSArray(JSArray* array) { |
4687 ASSERT(!array->HasExternalArrayElements()); | 4687 ASSERT(!array->HasExternalArrayElements()); |
4688 switch (array->GetElementsKind()) { | 4688 switch (array->GetElementsKind()) { |
4689 case JSObject::FAST_ELEMENTS: | 4689 case JSObject::FAST_ELEMENTS: |
4690 return UnionOfKeys(FixedArray::cast(array->elements())); | 4690 return UnionOfKeys(FixedArray::cast(array->elements())); |
4691 case JSObject::FAST_DOUBLE_ELEMENTS: | 4691 case JSObject::FAST_DOUBLE_ELEMENTS: |
4692 UNIMPLEMENTED(); | 4692 return UnionOfDoubleKeys(FixedDoubleArray::cast(array->elements())); |
4693 break; | 4693 break; |
4694 case JSObject::DICTIONARY_ELEMENTS: { | 4694 case JSObject::DICTIONARY_ELEMENTS: { |
4695 NumberDictionary* dict = array->element_dictionary(); | 4695 NumberDictionary* dict = array->element_dictionary(); |
4696 int size = dict->NumberOfElements(); | 4696 int size = dict->NumberOfElements(); |
4697 | 4697 |
4698 // Allocate a temporary fixed array. | 4698 // Allocate a temporary fixed array. |
4699 Object* object; | 4699 Object* object; |
4700 { MaybeObject* maybe_object = GetHeap()->AllocateFixedArray(size); | 4700 { MaybeObject* maybe_object = GetHeap()->AllocateFixedArray(size); |
4701 if (!maybe_object->ToObject(&object)) return maybe_object; | 4701 if (!maybe_object->ToObject(&object)) return maybe_object; |
4702 } | 4702 } |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4779 ASSERT(e->IsString() || e->IsNumber()); | 4779 ASSERT(e->IsString() || e->IsNumber()); |
4780 result->set(len0 + index, e, mode); | 4780 result->set(len0 + index, e, mode); |
4781 index++; | 4781 index++; |
4782 } | 4782 } |
4783 } | 4783 } |
4784 ASSERT(extra == index); | 4784 ASSERT(extra == index); |
4785 return result; | 4785 return result; |
4786 } | 4786 } |
4787 | 4787 |
4788 | 4788 |
4789 MaybeObject* FixedArray::UnionOfDoubleKeys(FixedDoubleArray* other) { | |
4790 int len0 = length(); | |
4791 #ifdef DEBUG | |
4792 if (FLAG_enable_slow_asserts) { | |
4793 for (int i = 0; i < len0; i++) { | |
4794 ASSERT(get(i)->IsString() || get(i)->IsNumber()); | |
4795 } | |
4796 } | |
4797 #endif | |
4798 int len1 = other->length(); | |
4799 // Optimize if 'other' is empty. | |
4800 // We cannot optimize if 'this' is empty, as other may have holes | |
4801 // or non keys. | |
4802 if (len1 == 0) return this; | |
4803 | |
4804 // Compute how many elements are not in this. | |
4805 int extra = 0; | |
4806 Heap* heap = GetHeap(); | |
4807 Object* obj; | |
4808 for (int y = 0; y < len1; y++) { | |
4809 if (!other->is_the_hole(y)) { | |
4810 MaybeObject* maybe_obj = heap->NumberFromDouble(other->get(y)); | |
Mads Ager (chromium)
2011/07/22 08:29:20
This is nasty. This can lead to out-of-memory cras
danno
2011/07/22 09:10:12
Submitted as 1567.
On 2011/07/22 08:29:20, Mads Ag
| |
4811 if (!maybe_obj->ToObject(&obj)) return maybe_obj; | |
4812 if (!HasKey(this, obj)) extra++; | |
4813 } | |
4814 } | |
4815 | |
4816 if (extra == 0) return this; | |
4817 | |
4818 // Allocate the result | |
4819 { MaybeObject* maybe_obj = GetHeap()->AllocateFixedArray(len0 + extra); | |
4820 if (!maybe_obj->ToObject(&obj)) return maybe_obj; | |
4821 } | |
4822 // Fill in the content | |
4823 AssertNoAllocation no_gc; | |
Mads Ager (chromium)
2011/07/22 08:29:20
Maybe we should change the name to AssertNoGC at s
danno
2011/07/22 09:10:12
Done.
| |
4824 FixedArray* result = FixedArray::cast(obj); | |
4825 WriteBarrierMode mode = result->GetWriteBarrierMode(no_gc); | |
4826 for (int i = 0; i < len0; i++) { | |
4827 Object* e = get(i); | |
4828 ASSERT(e->IsString() || e->IsNumber()); | |
4829 result->set(i, e, mode); | |
4830 } | |
4831 // Fill in the extra keys. | |
4832 int index = 0; | |
4833 for (int y = 0; y < len1; y++) { | |
4834 if (!other->is_the_hole(y)) { | |
4835 MaybeObject* maybe_obj = heap->NumberFromDouble(other->get(y)); | |
Mads Ager (chromium)
2011/07/22 08:29:20
Here again. So we actually allocate two new heap n
danno
2011/07/22 09:10:12
See above.
| |
4836 if (!maybe_obj->ToObject(&obj)) return maybe_obj; | |
4837 if (!HasKey(this, obj)) { | |
4838 result->set(len0 + index, obj); | |
4839 index++; | |
4840 } | |
4841 } | |
4842 } | |
4843 ASSERT(extra == index); | |
4844 return result; | |
4845 } | |
4846 | |
4847 | |
4789 MaybeObject* FixedArray::CopySize(int new_length) { | 4848 MaybeObject* FixedArray::CopySize(int new_length) { |
4790 Heap* heap = GetHeap(); | 4849 Heap* heap = GetHeap(); |
4791 if (new_length == 0) return heap->empty_fixed_array(); | 4850 if (new_length == 0) return heap->empty_fixed_array(); |
4792 Object* obj; | 4851 Object* obj; |
4793 { MaybeObject* maybe_obj = heap->AllocateFixedArray(new_length); | 4852 { MaybeObject* maybe_obj = heap->AllocateFixedArray(new_length); |
4794 if (!maybe_obj->ToObject(&obj)) return maybe_obj; | 4853 if (!maybe_obj->ToObject(&obj)) return maybe_obj; |
4795 } | 4854 } |
4796 FixedArray* result = FixedArray::cast(obj); | 4855 FixedArray* result = FixedArray::cast(obj); |
4797 // Copy the content | 4856 // Copy the content |
4798 AssertNoAllocation no_gc; | 4857 AssertNoAllocation no_gc; |
(...skipping 2735 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
7534 | 7593 |
7535 | 7594 |
7536 MaybeObject* JSObject::SetSlowElements(Object* len) { | 7595 MaybeObject* JSObject::SetSlowElements(Object* len) { |
7537 // We should never end in here with a pixel or external array. | 7596 // We should never end in here with a pixel or external array. |
7538 ASSERT(!HasExternalArrayElements()); | 7597 ASSERT(!HasExternalArrayElements()); |
7539 | 7598 |
7540 uint32_t new_length = static_cast<uint32_t>(len->Number()); | 7599 uint32_t new_length = static_cast<uint32_t>(len->Number()); |
7541 | 7600 |
7542 switch (GetElementsKind()) { | 7601 switch (GetElementsKind()) { |
7543 case FAST_ELEMENTS: { | 7602 case FAST_ELEMENTS: { |
7603 case FAST_DOUBLE_ELEMENTS: | |
7544 // Make sure we never try to shrink dense arrays into sparse arrays. | 7604 // Make sure we never try to shrink dense arrays into sparse arrays. |
7545 ASSERT(static_cast<uint32_t>(FixedArray::cast(elements())->length()) <= | 7605 ASSERT(static_cast<uint32_t>( |
7546 new_length); | 7606 FixedArrayBase::cast(elements())->length()) <= new_length); |
7547 MaybeObject* result = NormalizeElements(); | 7607 MaybeObject* result = NormalizeElements(); |
7548 if (result->IsFailure()) return result; | 7608 if (result->IsFailure()) return result; |
7549 | 7609 |
7550 // Update length for JSArrays. | 7610 // Update length for JSArrays. |
7551 if (IsJSArray()) JSArray::cast(this)->set_length(len); | 7611 if (IsJSArray()) JSArray::cast(this)->set_length(len); |
7552 break; | 7612 break; |
7553 } | 7613 } |
7554 case DICTIONARY_ELEMENTS: { | 7614 case DICTIONARY_ELEMENTS: { |
7555 if (IsJSArray()) { | 7615 if (IsJSArray()) { |
7556 uint32_t old_length = | 7616 uint32_t old_length = |
7557 static_cast<uint32_t>(JSArray::cast(this)->length()->Number()); | 7617 static_cast<uint32_t>(JSArray::cast(this)->length()->Number()); |
7558 element_dictionary()->RemoveNumberEntries(new_length, old_length), | 7618 element_dictionary()->RemoveNumberEntries(new_length, old_length), |
7559 JSArray::cast(this)->set_length(len); | 7619 JSArray::cast(this)->set_length(len); |
7560 } | 7620 } |
7561 break; | 7621 break; |
7562 } | 7622 } |
7563 case NON_STRICT_ARGUMENTS_ELEMENTS: | 7623 case NON_STRICT_ARGUMENTS_ELEMENTS: |
7564 UNIMPLEMENTED(); | 7624 UNIMPLEMENTED(); |
7565 break; | 7625 break; |
7566 case EXTERNAL_BYTE_ELEMENTS: | 7626 case EXTERNAL_BYTE_ELEMENTS: |
7567 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: | 7627 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: |
7568 case EXTERNAL_SHORT_ELEMENTS: | 7628 case EXTERNAL_SHORT_ELEMENTS: |
7569 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: | 7629 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: |
7570 case EXTERNAL_INT_ELEMENTS: | 7630 case EXTERNAL_INT_ELEMENTS: |
7571 case EXTERNAL_UNSIGNED_INT_ELEMENTS: | 7631 case EXTERNAL_UNSIGNED_INT_ELEMENTS: |
7572 case EXTERNAL_FLOAT_ELEMENTS: | 7632 case EXTERNAL_FLOAT_ELEMENTS: |
7573 case EXTERNAL_DOUBLE_ELEMENTS: | 7633 case EXTERNAL_DOUBLE_ELEMENTS: |
7574 case EXTERNAL_PIXEL_ELEMENTS: | 7634 case EXTERNAL_PIXEL_ELEMENTS: |
7575 case FAST_DOUBLE_ELEMENTS: | |
7576 UNREACHABLE(); | 7635 UNREACHABLE(); |
7577 break; | 7636 break; |
7578 } | 7637 } |
7579 return this; | 7638 return this; |
7580 } | 7639 } |
7581 | 7640 |
7582 | 7641 |
7583 MaybeObject* JSArray::Initialize(int capacity) { | 7642 MaybeObject* JSArray::Initialize(int capacity) { |
7584 Heap* heap = GetHeap(); | 7643 Heap* heap = GetHeap(); |
7585 ASSERT(capacity >= 0); | 7644 ASSERT(capacity >= 0); |
(...skipping 321 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
7907 uint32_t length = IsJSArray() ? | 7966 uint32_t length = IsJSArray() ? |
7908 static_cast<uint32_t> | 7967 static_cast<uint32_t> |
7909 (Smi::cast(JSArray::cast(this)->length())->value()) : | 7968 (Smi::cast(JSArray::cast(this)->length())->value()) : |
7910 static_cast<uint32_t>(FixedArray::cast(elements())->length()); | 7969 static_cast<uint32_t>(FixedArray::cast(elements())->length()); |
7911 if ((index < length) && | 7970 if ((index < length) && |
7912 !FixedArray::cast(elements())->get(index)->IsTheHole()) { | 7971 !FixedArray::cast(elements())->get(index)->IsTheHole()) { |
7913 return true; | 7972 return true; |
7914 } | 7973 } |
7915 break; | 7974 break; |
7916 } | 7975 } |
7976 case FAST_DOUBLE_ELEMENTS: { | |
7977 uint32_t length = IsJSArray() ? | |
7978 static_cast<uint32_t> | |
7979 (Smi::cast(JSArray::cast(this)->length())->value()) : | |
7980 static_cast<uint32_t>(FixedDoubleArray::cast(elements())->length()); | |
7981 if ((index < length) && | |
7982 !FixedDoubleArray::cast(elements())->is_the_hole(index)) { | |
7983 return true; | |
7984 } | |
7985 break; | |
7986 } | |
7917 case EXTERNAL_PIXEL_ELEMENTS: { | 7987 case EXTERNAL_PIXEL_ELEMENTS: { |
7918 ExternalPixelArray* pixels = ExternalPixelArray::cast(elements()); | 7988 ExternalPixelArray* pixels = ExternalPixelArray::cast(elements()); |
7919 if (index < static_cast<uint32_t>(pixels->length())) { | 7989 if (index < static_cast<uint32_t>(pixels->length())) { |
7920 return true; | 7990 return true; |
7921 } | 7991 } |
7922 break; | 7992 break; |
7923 } | 7993 } |
7924 case EXTERNAL_BYTE_ELEMENTS: | 7994 case EXTERNAL_BYTE_ELEMENTS: |
7925 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: | 7995 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: |
7926 case EXTERNAL_SHORT_ELEMENTS: | 7996 case EXTERNAL_SHORT_ELEMENTS: |
7927 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: | 7997 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: |
7928 case EXTERNAL_INT_ELEMENTS: | 7998 case EXTERNAL_INT_ELEMENTS: |
7929 case EXTERNAL_UNSIGNED_INT_ELEMENTS: | 7999 case EXTERNAL_UNSIGNED_INT_ELEMENTS: |
7930 case EXTERNAL_FLOAT_ELEMENTS: | 8000 case EXTERNAL_FLOAT_ELEMENTS: |
7931 case EXTERNAL_DOUBLE_ELEMENTS: | 8001 case EXTERNAL_DOUBLE_ELEMENTS: { |
7932 case FAST_DOUBLE_ELEMENTS: { | |
7933 ExternalArray* array = ExternalArray::cast(elements()); | 8002 ExternalArray* array = ExternalArray::cast(elements()); |
7934 if (index < static_cast<uint32_t>(array->length())) { | 8003 if (index < static_cast<uint32_t>(array->length())) { |
7935 return true; | 8004 return true; |
7936 } | 8005 } |
7937 break; | 8006 break; |
7938 } | 8007 } |
7939 case DICTIONARY_ELEMENTS: { | 8008 case DICTIONARY_ELEMENTS: { |
7940 if (element_dictionary()->FindEntry(index) | 8009 if (element_dictionary()->FindEntry(index) |
7941 != NumberDictionary::kNotFound) { | 8010 != NumberDictionary::kNotFound) { |
7942 return true; | 8011 return true; |
(...skipping 1431 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
9374 | 9443 |
9375 switch (GetElementsKind()) { | 9444 switch (GetElementsKind()) { |
9376 case FAST_ELEMENTS: { | 9445 case FAST_ELEMENTS: { |
9377 uint32_t length = IsJSArray() ? | 9446 uint32_t length = IsJSArray() ? |
9378 static_cast<uint32_t>( | 9447 static_cast<uint32_t>( |
9379 Smi::cast(JSArray::cast(this)->length())->value()) : | 9448 Smi::cast(JSArray::cast(this)->length())->value()) : |
9380 static_cast<uint32_t>(FixedArray::cast(elements())->length()); | 9449 static_cast<uint32_t>(FixedArray::cast(elements())->length()); |
9381 return (index < length) && | 9450 return (index < length) && |
9382 !FixedArray::cast(elements())->get(index)->IsTheHole(); | 9451 !FixedArray::cast(elements())->get(index)->IsTheHole(); |
9383 } | 9452 } |
9453 case FAST_DOUBLE_ELEMENTS: { | |
9454 uint32_t length = IsJSArray() ? | |
9455 static_cast<uint32_t>( | |
9456 Smi::cast(JSArray::cast(this)->length())->value()) : | |
9457 static_cast<uint32_t>(FixedDoubleArray::cast(elements())->length()); | |
9458 return (index < length) && | |
9459 !FixedDoubleArray::cast(elements())->is_the_hole(index); | |
9460 break; | |
9461 } | |
9384 case EXTERNAL_PIXEL_ELEMENTS: { | 9462 case EXTERNAL_PIXEL_ELEMENTS: { |
9385 ExternalPixelArray* pixels = ExternalPixelArray::cast(elements()); | 9463 ExternalPixelArray* pixels = ExternalPixelArray::cast(elements()); |
9386 return index < static_cast<uint32_t>(pixels->length()); | 9464 return index < static_cast<uint32_t>(pixels->length()); |
9387 } | 9465 } |
9388 case EXTERNAL_BYTE_ELEMENTS: | 9466 case EXTERNAL_BYTE_ELEMENTS: |
9389 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: | 9467 case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: |
9390 case EXTERNAL_SHORT_ELEMENTS: | 9468 case EXTERNAL_SHORT_ELEMENTS: |
9391 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: | 9469 case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: |
9392 case EXTERNAL_INT_ELEMENTS: | 9470 case EXTERNAL_INT_ELEMENTS: |
9393 case EXTERNAL_UNSIGNED_INT_ELEMENTS: | 9471 case EXTERNAL_UNSIGNED_INT_ELEMENTS: |
9394 case EXTERNAL_FLOAT_ELEMENTS: | 9472 case EXTERNAL_FLOAT_ELEMENTS: |
9395 case EXTERNAL_DOUBLE_ELEMENTS: { | 9473 case EXTERNAL_DOUBLE_ELEMENTS: { |
9396 ExternalArray* array = ExternalArray::cast(elements()); | 9474 ExternalArray* array = ExternalArray::cast(elements()); |
9397 return index < static_cast<uint32_t>(array->length()); | 9475 return index < static_cast<uint32_t>(array->length()); |
9398 } | 9476 } |
9399 case FAST_DOUBLE_ELEMENTS: | |
9400 UNREACHABLE(); | |
9401 break; | |
9402 case DICTIONARY_ELEMENTS: { | 9477 case DICTIONARY_ELEMENTS: { |
9403 return element_dictionary()->FindEntry(index) | 9478 return element_dictionary()->FindEntry(index) |
9404 != NumberDictionary::kNotFound; | 9479 != NumberDictionary::kNotFound; |
9405 } | 9480 } |
9406 case NON_STRICT_ARGUMENTS_ELEMENTS: | 9481 case NON_STRICT_ARGUMENTS_ELEMENTS: |
9407 UNIMPLEMENTED(); | 9482 UNIMPLEMENTED(); |
9408 break; | 9483 break; |
9409 } | 9484 } |
9410 // All possibilities have been handled above already. | 9485 // All possibilities have been handled above already. |
9411 UNREACHABLE(); | 9486 UNREACHABLE(); |
(...skipping 2434 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
11846 if (break_point_objects()->IsUndefined()) return 0; | 11921 if (break_point_objects()->IsUndefined()) return 0; |
11847 // Single beak point. | 11922 // Single beak point. |
11848 if (!break_point_objects()->IsFixedArray()) return 1; | 11923 if (!break_point_objects()->IsFixedArray()) return 1; |
11849 // Multiple break points. | 11924 // Multiple break points. |
11850 return FixedArray::cast(break_point_objects())->length(); | 11925 return FixedArray::cast(break_point_objects())->length(); |
11851 } | 11926 } |
11852 #endif | 11927 #endif |
11853 | 11928 |
11854 | 11929 |
11855 } } // namespace v8::internal | 11930 } } // namespace v8::internal |
OLD | NEW |