OLD | NEW |
---|---|
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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 1805 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1816 | 1816 |
1817 | 1817 |
1818 MaybeObject* JSObject::ReplaceSlowProperty(String* name, | 1818 MaybeObject* JSObject::ReplaceSlowProperty(String* name, |
1819 Object* value, | 1819 Object* value, |
1820 PropertyAttributes attributes) { | 1820 PropertyAttributes attributes) { |
1821 StringDictionary* dictionary = property_dictionary(); | 1821 StringDictionary* dictionary = property_dictionary(); |
1822 int old_index = dictionary->FindEntry(name); | 1822 int old_index = dictionary->FindEntry(name); |
1823 int new_enumeration_index = 0; // 0 means "Use the next available index." | 1823 int new_enumeration_index = 0; // 0 means "Use the next available index." |
1824 if (old_index != -1) { | 1824 if (old_index != -1) { |
1825 // All calls to ReplaceSlowProperty have had all transitions removed. | 1825 // All calls to ReplaceSlowProperty have had all transitions removed. |
1826 ASSERT(!dictionary->DetailsAt(old_index).IsTransition()); | 1826 ASSERT(!dictionary->ContainsTransition(old_index)); |
1827 new_enumeration_index = dictionary->DetailsAt(old_index).index(); | 1827 new_enumeration_index = dictionary->DetailsAt(old_index).index(); |
1828 } | 1828 } |
1829 | 1829 |
1830 PropertyDetails new_details(attributes, NORMAL, new_enumeration_index); | 1830 PropertyDetails new_details(attributes, NORMAL, new_enumeration_index); |
1831 return SetNormalizedProperty(name, value, new_details); | 1831 return SetNormalizedProperty(name, value, new_details); |
1832 } | 1832 } |
1833 | 1833 |
1834 | 1834 |
1835 MaybeObject* JSObject::ConvertDescriptorToFieldAndMapTransition( | 1835 MaybeObject* JSObject::ConvertDescriptorToFieldAndMapTransition( |
1836 String* name, | 1836 String* name, |
(...skipping 3885 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5722 | 5722 |
5723 | 5723 |
5724 MaybeObject* DescriptorArray::CopyInsert(Descriptor* descriptor, | 5724 MaybeObject* DescriptorArray::CopyInsert(Descriptor* descriptor, |
5725 TransitionFlag transition_flag) { | 5725 TransitionFlag transition_flag) { |
5726 // Transitions are only kept when inserting another transition. | 5726 // Transitions are only kept when inserting another transition. |
5727 // This precondition is not required by this function's implementation, but | 5727 // This precondition is not required by this function's implementation, but |
5728 // is currently required by the semantics of maps, so we check it. | 5728 // is currently required by the semantics of maps, so we check it. |
5729 // Conversely, we filter after replacing, so replacing a transition and | 5729 // Conversely, we filter after replacing, so replacing a transition and |
5730 // removing all other transitions is not supported. | 5730 // removing all other transitions is not supported. |
5731 bool remove_transitions = transition_flag == REMOVE_TRANSITIONS; | 5731 bool remove_transitions = transition_flag == REMOVE_TRANSITIONS; |
5732 ASSERT(remove_transitions == !descriptor->GetDetails().IsTransition()); | 5732 ASSERT(remove_transitions == !descriptor->ContainsTransition()); |
5733 ASSERT(descriptor->GetDetails().type() != NULL_DESCRIPTOR); | 5733 ASSERT(descriptor->GetDetails().type() != NULL_DESCRIPTOR); |
5734 | 5734 |
5735 // Ensure the key is a symbol. | 5735 // Ensure the key is a symbol. |
5736 Object* result; | 5736 Object* result; |
5737 { MaybeObject* maybe_result = descriptor->KeyToSymbol(); | 5737 { MaybeObject* maybe_result = descriptor->KeyToSymbol(); |
5738 if (!maybe_result->ToObject(&result)) return maybe_result; | 5738 if (!maybe_result->ToObject(&result)) return maybe_result; |
5739 } | 5739 } |
5740 | 5740 |
5741 int transitions = 0; | 5741 int new_size = 0; |
5742 int null_descriptors = 0; | 5742 for (int i = 0; i < number_of_descriptors(); i++) { |
5743 if (remove_transitions) { | 5743 if (IsNullDescriptor(i)) continue; |
5744 for (int i = 0; i < number_of_descriptors(); i++) { | 5744 if (remove_transitions && IsTransitionOnly(i)) continue; |
5745 if (IsTransition(i)) transitions++; | 5745 new_size++; |
5746 if (IsNullDescriptor(i)) null_descriptors++; | |
5747 } | |
5748 } else { | |
5749 for (int i = 0; i < number_of_descriptors(); i++) { | |
5750 if (IsNullDescriptor(i)) null_descriptors++; | |
5751 } | |
5752 } | 5746 } |
5753 int new_size = number_of_descriptors() - transitions - null_descriptors; | |
5754 | 5747 |
5755 // If key is in descriptor, we replace it in-place when filtering. | 5748 // If key is in descriptor, we replace it in-place when filtering. |
5756 // Count a null descriptor for key as inserted, not replaced. | 5749 // Count a null descriptor for key as inserted, not replaced. |
5757 int index = Search(descriptor->GetKey()); | 5750 int index = Search(descriptor->GetKey()); |
5758 const bool inserting = (index == kNotFound); | 5751 const bool replacing = (index != kNotFound); |
5759 const bool replacing = !inserting; | |
5760 bool keep_enumeration_index = false; | 5752 bool keep_enumeration_index = false; |
5761 if (inserting) { | |
5762 ++new_size; | |
5763 } | |
5764 if (replacing) { | 5753 if (replacing) { |
5765 // We are replacing an existing descriptor. We keep the enumeration | 5754 // We are replacing an existing descriptor. We keep the enumeration |
5766 // index of a visible property. | 5755 // index of a visible property. |
5767 PropertyType t = PropertyDetails(GetDetails(index)).type(); | 5756 PropertyType t = PropertyDetails(GetDetails(index)).type(); |
5768 if (t == CONSTANT_FUNCTION || | 5757 if (t == CONSTANT_FUNCTION || |
5769 t == FIELD || | 5758 t == FIELD || |
5770 t == CALLBACKS || | 5759 t == CALLBACKS || |
5771 t == INTERCEPTOR) { | 5760 t == INTERCEPTOR) { |
5772 keep_enumeration_index = true; | 5761 keep_enumeration_index = true; |
5773 } else if (remove_transitions) { | 5762 } else if (remove_transitions) { |
5774 // Replaced descriptor has been counted as removed if it is | 5763 // Replaced descriptor has been counted as removed if it is |
5775 // a transition that will be replaced. Adjust count in this case. | 5764 // a transition that will be replaced. Adjust count in this case. |
5776 ++new_size; | 5765 ++new_size; |
5777 } | 5766 } |
5767 } else { | |
5768 ++new_size; | |
5778 } | 5769 } |
5779 | 5770 |
5780 DescriptorArray* new_descriptors; | 5771 DescriptorArray* new_descriptors; |
5781 { MaybeObject* maybe_result = Allocate(new_size); | 5772 { MaybeObject* maybe_result = Allocate(new_size); |
5782 if (!maybe_result->To<DescriptorArray>(&new_descriptors)) { | 5773 if (!maybe_result->To<DescriptorArray>(&new_descriptors)) { |
5783 return maybe_result; | 5774 return maybe_result; |
5784 } | 5775 } |
5785 } | 5776 } |
5786 | 5777 |
5787 DescriptorArray::WhitenessWitness witness(new_descriptors); | 5778 DescriptorArray::WhitenessWitness witness(new_descriptors); |
5788 | 5779 |
5789 // Set the enumeration index in the descriptors and set the enumeration index | 5780 // Set the enumeration index in the descriptors and set the enumeration index |
5790 // in the result. | 5781 // in the result. |
5791 int enumeration_index = NextEnumerationIndex(); | 5782 int enumeration_index = NextEnumerationIndex(); |
5792 if (!descriptor->GetDetails().IsTransition()) { | 5783 if (!descriptor->ContainsTransition()) { |
5793 if (keep_enumeration_index) { | 5784 if (keep_enumeration_index) { |
5794 descriptor->SetEnumerationIndex( | 5785 descriptor->SetEnumerationIndex( |
5795 PropertyDetails(GetDetails(index)).index()); | 5786 PropertyDetails(GetDetails(index)).index()); |
5796 } else { | 5787 } else { |
5797 descriptor->SetEnumerationIndex(enumeration_index); | 5788 descriptor->SetEnumerationIndex(enumeration_index); |
5798 ++enumeration_index; | 5789 ++enumeration_index; |
5799 } | 5790 } |
5800 } | 5791 } |
5801 new_descriptors->SetNextEnumerationIndex(enumeration_index); | 5792 new_descriptors->SetNextEnumerationIndex(enumeration_index); |
5802 | 5793 |
5803 // Copy the descriptors, filtering out transitions and null descriptors, | 5794 // Copy the descriptors, filtering out transitions and null descriptors, |
5804 // and inserting or replacing a descriptor. | 5795 // and inserting or replacing a descriptor. |
5805 uint32_t descriptor_hash = descriptor->GetKey()->Hash(); | 5796 uint32_t descriptor_hash = descriptor->GetKey()->Hash(); |
5806 int from_index = 0; | 5797 int from_index = 0; |
5807 int to_index = 0; | 5798 int to_index = 0; |
5808 | 5799 |
5809 for (; from_index < number_of_descriptors(); from_index++) { | 5800 for (; from_index < number_of_descriptors(); from_index++) { |
5810 String* key = GetKey(from_index); | 5801 String* key = GetKey(from_index); |
5811 if (key->Hash() > descriptor_hash || key == descriptor->GetKey()) { | 5802 if (key->Hash() > descriptor_hash || key == descriptor->GetKey()) { |
5812 break; | 5803 break; |
5813 } | 5804 } |
5814 if (IsNullDescriptor(from_index)) continue; | 5805 if (IsNullDescriptor(from_index)) continue; |
5815 if (remove_transitions && IsTransition(from_index)) continue; | 5806 if (remove_transitions && IsTransitionOnly(from_index)) continue; |
5816 new_descriptors->CopyFrom(to_index++, this, from_index, witness); | 5807 new_descriptors->CopyFrom(to_index++, this, from_index, witness); |
5817 } | 5808 } |
5818 | 5809 |
5819 new_descriptors->Set(to_index++, descriptor, witness); | 5810 new_descriptors->Set(to_index++, descriptor, witness); |
5820 if (replacing) from_index++; | 5811 if (replacing) from_index++; |
5821 | 5812 |
5822 for (; from_index < number_of_descriptors(); from_index++) { | 5813 for (; from_index < number_of_descriptors(); from_index++) { |
5823 if (IsNullDescriptor(from_index)) continue; | 5814 if (IsNullDescriptor(from_index)) continue; |
5824 if (remove_transitions && IsTransition(from_index)) continue; | 5815 if (remove_transitions && IsTransitionOnly(from_index)) continue; |
5825 new_descriptors->CopyFrom(to_index++, this, from_index, witness); | 5816 new_descriptors->CopyFrom(to_index++, this, from_index, witness); |
5826 } | 5817 } |
5827 | 5818 |
5828 ASSERT(to_index == new_descriptors->number_of_descriptors()); | 5819 ASSERT(to_index == new_descriptors->number_of_descriptors()); |
5829 SLOW_ASSERT(new_descriptors->IsSortedNoDuplicates()); | 5820 SLOW_ASSERT(new_descriptors->IsSortedNoDuplicates()); |
5830 | 5821 |
5831 return new_descriptors; | 5822 return new_descriptors; |
5832 } | 5823 } |
5833 | 5824 |
5834 | 5825 |
(...skipping 5291 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
11126 set(index, key); | 11117 set(index, key); |
11127 return entry; | 11118 return entry; |
11128 } | 11119 } |
11129 ASSERT(element->IsTheHole() || !String::cast(element)->Equals(key)); | 11120 ASSERT(element->IsTheHole() || !String::cast(element)->Equals(key)); |
11130 entry = NextProbe(entry, count++, capacity); | 11121 entry = NextProbe(entry, count++, capacity); |
11131 } | 11122 } |
11132 return kNotFound; | 11123 return kNotFound; |
11133 } | 11124 } |
11134 | 11125 |
11135 | 11126 |
11127 bool StringDictionary::ContainsTransition(int entry) { | |
11128 switch (DetailsAt(entry).type()) { | |
11129 case MAP_TRANSITION: | |
11130 case CONSTANT_TRANSITION: | |
11131 case ELEMENTS_TRANSITION: | |
11132 return true; | |
11133 case CALLBACKS: { | |
11134 Object* value = ValueAt(entry); | |
11135 if (!value->IsAccessorPair()) return false; | |
11136 AccessorPair* accessors = AccessorPair::cast(value); | |
11137 return accessors->getter()->IsMap() || accessors->setter()->IsMap(); | |
11138 } | |
11139 case NORMAL: | |
11140 case FIELD: | |
11141 case CONSTANT_FUNCTION: | |
11142 case HANDLER: | |
11143 case INTERCEPTOR: | |
Jakob Kummerow
2012/02/03 13:17:14
nit: indentation
Sven Panne
2012/02/03 13:33:14
Done.
| |
11144 case NULL_DESCRIPTOR: | |
11145 return false; | |
11146 } | |
11147 UNREACHABLE(); // keep the compiler happy | |
Jakob Kummerow
2012/02/03 13:17:14
Missing capital and period.
Sven Panne
2012/02/03 13:33:14
Done.
| |
11148 return false; | |
11149 } | |
11150 | |
11151 | |
11136 template<typename Shape, typename Key> | 11152 template<typename Shape, typename Key> |
11137 MaybeObject* HashTable<Shape, Key>::Rehash(HashTable* new_table, Key key) { | 11153 MaybeObject* HashTable<Shape, Key>::Rehash(HashTable* new_table, Key key) { |
11138 ASSERT(NumberOfElements() < new_table->Capacity()); | 11154 ASSERT(NumberOfElements() < new_table->Capacity()); |
11139 | 11155 |
11140 AssertNoAllocation no_gc; | 11156 AssertNoAllocation no_gc; |
11141 WriteBarrierMode mode = new_table->GetWriteBarrierMode(no_gc); | 11157 WriteBarrierMode mode = new_table->GetWriteBarrierMode(no_gc); |
11142 | 11158 |
11143 // Copy prefix to new array. | 11159 // Copy prefix to new array. |
11144 for (int i = kPrefixStartIndex; | 11160 for (int i = kPrefixStartIndex; |
11145 i < kPrefixStartIndex + Shape::kPrefixSize; | 11161 i < kPrefixStartIndex + Shape::kPrefixSize; |
(...skipping 1877 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
13023 if (break_point_objects()->IsUndefined()) return 0; | 13039 if (break_point_objects()->IsUndefined()) return 0; |
13024 // Single break point. | 13040 // Single break point. |
13025 if (!break_point_objects()->IsFixedArray()) return 1; | 13041 if (!break_point_objects()->IsFixedArray()) return 1; |
13026 // Multiple break points. | 13042 // Multiple break points. |
13027 return FixedArray::cast(break_point_objects())->length(); | 13043 return FixedArray::cast(break_point_objects())->length(); |
13028 } | 13044 } |
13029 #endif // ENABLE_DEBUGGER_SUPPORT | 13045 #endif // ENABLE_DEBUGGER_SUPPORT |
13030 | 13046 |
13031 | 13047 |
13032 } } // namespace v8::internal | 13048 } } // namespace v8::internal |
OLD | NEW |