| OLD | NEW |
| 1 // Copyright 2006-2009 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2009 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 2103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2114 | 2114 |
| 2115 Object* JSObject::NormalizeProperties(PropertyNormalizationMode mode) { | 2115 Object* JSObject::NormalizeProperties(PropertyNormalizationMode mode) { |
| 2116 if (!HasFastProperties()) return this; | 2116 if (!HasFastProperties()) return this; |
| 2117 | 2117 |
| 2118 // Allocate new content | 2118 // Allocate new content |
| 2119 Object* obj = | 2119 Object* obj = |
| 2120 StringDictionary::Allocate(map()->NumberOfDescribedProperties() * 2 + 4); | 2120 StringDictionary::Allocate(map()->NumberOfDescribedProperties() * 2 + 4); |
| 2121 if (obj->IsFailure()) return obj; | 2121 if (obj->IsFailure()) return obj; |
| 2122 StringDictionary* dictionary = StringDictionary::cast(obj); | 2122 StringDictionary* dictionary = StringDictionary::cast(obj); |
| 2123 | 2123 |
| 2124 for (DescriptorReader r(map()->instance_descriptors()); | 2124 DescriptorArray* descs = map()->instance_descriptors(); |
| 2125 !r.eos(); | 2125 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 2126 r.advance()) { | 2126 PropertyDetails details = descs->GetDetails(i); |
| 2127 PropertyDetails details = r.GetDetails(); | |
| 2128 switch (details.type()) { | 2127 switch (details.type()) { |
| 2129 case CONSTANT_FUNCTION: { | 2128 case CONSTANT_FUNCTION: { |
| 2130 PropertyDetails d = | 2129 PropertyDetails d = |
| 2131 PropertyDetails(details.attributes(), NORMAL, details.index()); | 2130 PropertyDetails(details.attributes(), NORMAL, details.index()); |
| 2132 Object* value = r.GetConstantFunction(); | 2131 Object* value = descs->GetConstantFunction(i); |
| 2133 if (IsGlobalObject()) { | 2132 if (IsGlobalObject()) { |
| 2134 value = Heap::AllocateJSGlobalPropertyCell(value); | 2133 value = Heap::AllocateJSGlobalPropertyCell(value); |
| 2135 if (value->IsFailure()) return value; | 2134 if (value->IsFailure()) return value; |
| 2136 } | 2135 } |
| 2137 Object* result = dictionary->Add(r.GetKey(), value, d); | 2136 Object* result = dictionary->Add(descs->GetKey(i), value, d); |
| 2138 if (result->IsFailure()) return result; | 2137 if (result->IsFailure()) return result; |
| 2139 dictionary = StringDictionary::cast(result); | 2138 dictionary = StringDictionary::cast(result); |
| 2140 break; | 2139 break; |
| 2141 } | 2140 } |
| 2142 case FIELD: { | 2141 case FIELD: { |
| 2143 PropertyDetails d = | 2142 PropertyDetails d = |
| 2144 PropertyDetails(details.attributes(), NORMAL, details.index()); | 2143 PropertyDetails(details.attributes(), NORMAL, details.index()); |
| 2145 Object* value = FastPropertyAt(r.GetFieldIndex()); | 2144 Object* value = FastPropertyAt(descs->GetFieldIndex(i)); |
| 2146 if (IsGlobalObject()) { | 2145 if (IsGlobalObject()) { |
| 2147 value = Heap::AllocateJSGlobalPropertyCell(value); | 2146 value = Heap::AllocateJSGlobalPropertyCell(value); |
| 2148 if (value->IsFailure()) return value; | 2147 if (value->IsFailure()) return value; |
| 2149 } | 2148 } |
| 2150 Object* result = dictionary->Add(r.GetKey(), value, d); | 2149 Object* result = dictionary->Add(descs->GetKey(i), value, d); |
| 2151 if (result->IsFailure()) return result; | 2150 if (result->IsFailure()) return result; |
| 2152 dictionary = StringDictionary::cast(result); | 2151 dictionary = StringDictionary::cast(result); |
| 2153 break; | 2152 break; |
| 2154 } | 2153 } |
| 2155 case CALLBACKS: { | 2154 case CALLBACKS: { |
| 2156 PropertyDetails d = | 2155 PropertyDetails d = |
| 2157 PropertyDetails(details.attributes(), CALLBACKS, details.index()); | 2156 PropertyDetails(details.attributes(), CALLBACKS, details.index()); |
| 2158 Object* value = r.GetCallbacksObject(); | 2157 Object* value = descs->GetCallbacksObject(i); |
| 2159 if (IsGlobalObject()) { | 2158 if (IsGlobalObject()) { |
| 2160 value = Heap::AllocateJSGlobalPropertyCell(value); | 2159 value = Heap::AllocateJSGlobalPropertyCell(value); |
| 2161 if (value->IsFailure()) return value; | 2160 if (value->IsFailure()) return value; |
| 2162 } | 2161 } |
| 2163 Object* result = dictionary->Add(r.GetKey(), value, d); | 2162 Object* result = dictionary->Add(descs->GetKey(i), value, d); |
| 2164 if (result->IsFailure()) return result; | 2163 if (result->IsFailure()) return result; |
| 2165 dictionary = StringDictionary::cast(result); | 2164 dictionary = StringDictionary::cast(result); |
| 2166 break; | 2165 break; |
| 2167 } | 2166 } |
| 2168 case MAP_TRANSITION: | 2167 case MAP_TRANSITION: |
| 2169 case CONSTANT_TRANSITION: | 2168 case CONSTANT_TRANSITION: |
| 2170 case NULL_DESCRIPTOR: | 2169 case NULL_DESCRIPTOR: |
| 2171 case INTERCEPTOR: | 2170 case INTERCEPTOR: |
| 2172 break; | 2171 break; |
| 2173 default: | 2172 default: |
| (...skipping 393 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2567 return false; | 2566 return false; |
| 2568 } | 2567 } |
| 2569 } | 2568 } |
| 2570 } | 2569 } |
| 2571 return true; | 2570 return true; |
| 2572 } | 2571 } |
| 2573 | 2572 |
| 2574 | 2573 |
| 2575 int Map::NumberOfDescribedProperties() { | 2574 int Map::NumberOfDescribedProperties() { |
| 2576 int result = 0; | 2575 int result = 0; |
| 2577 for (DescriptorReader r(instance_descriptors()); !r.eos(); r.advance()) { | 2576 DescriptorArray* descs = instance_descriptors(); |
| 2578 if (r.IsProperty()) result++; | 2577 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 2578 if (descs->IsProperty(i)) result++; |
| 2579 } | 2579 } |
| 2580 return result; | 2580 return result; |
| 2581 } | 2581 } |
| 2582 | 2582 |
| 2583 | 2583 |
| 2584 int Map::PropertyIndexFor(String* name) { | 2584 int Map::PropertyIndexFor(String* name) { |
| 2585 for (DescriptorReader r(instance_descriptors()); !r.eos(); r.advance()) { | 2585 DescriptorArray* descs = instance_descriptors(); |
| 2586 if (r.Equals(name) && !r.IsNullDescriptor()) return r.GetFieldIndex(); | 2586 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 2587 if (name->Equals(descs->GetKey(i)) && !descs->IsNullDescriptor(i)) { |
| 2588 return descs->GetFieldIndex(i); |
| 2589 } |
| 2587 } | 2590 } |
| 2588 return -1; | 2591 return -1; |
| 2589 } | 2592 } |
| 2590 | 2593 |
| 2591 | 2594 |
| 2592 int Map::NextFreePropertyIndex() { | 2595 int Map::NextFreePropertyIndex() { |
| 2593 int index = -1; | 2596 int max_index = -1; |
| 2594 for (DescriptorReader r(instance_descriptors()); !r.eos(); r.advance()) { | 2597 DescriptorArray* descs = instance_descriptors(); |
| 2595 if (r.type() == FIELD) { | 2598 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 2596 if (r.GetFieldIndex() > index) index = r.GetFieldIndex(); | 2599 if (descs->GetType(i) == FIELD) { |
| 2600 int current_index = descs->GetFieldIndex(i); |
| 2601 if (current_index > max_index) max_index = current_index; |
| 2597 } | 2602 } |
| 2598 } | 2603 } |
| 2599 return index+1; | 2604 return max_index + 1; |
| 2600 } | 2605 } |
| 2601 | 2606 |
| 2602 | 2607 |
| 2603 AccessorDescriptor* Map::FindAccessor(String* name) { | 2608 AccessorDescriptor* Map::FindAccessor(String* name) { |
| 2604 for (DescriptorReader r(instance_descriptors()); !r.eos(); r.advance()) { | 2609 DescriptorArray* descs = instance_descriptors(); |
| 2605 if (r.Equals(name) && r.type() == CALLBACKS) return r.GetCallbacks(); | 2610 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 2611 if (name->Equals(descs->GetKey(i)) && descs->GetType(i) == CALLBACKS) { |
| 2612 return descs->GetCallbacks(i); |
| 2613 } |
| 2606 } | 2614 } |
| 2607 return NULL; | 2615 return NULL; |
| 2608 } | 2616 } |
| 2609 | 2617 |
| 2610 | 2618 |
| 2611 void JSObject::LocalLookup(String* name, LookupResult* result) { | 2619 void JSObject::LocalLookup(String* name, LookupResult* result) { |
| 2612 ASSERT(name->IsString()); | 2620 ASSERT(name->IsString()); |
| 2613 | 2621 |
| 2614 if (IsJSGlobalProxy()) { | 2622 if (IsJSGlobalProxy()) { |
| 2615 Object* proto = GetPrototype(); | 2623 Object* proto = GetPrototype(); |
| (...skipping 227 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2843 } | 2851 } |
| 2844 } | 2852 } |
| 2845 } | 2853 } |
| 2846 } | 2854 } |
| 2847 return Heap::undefined_value(); | 2855 return Heap::undefined_value(); |
| 2848 } | 2856 } |
| 2849 | 2857 |
| 2850 | 2858 |
| 2851 Object* JSObject::SlowReverseLookup(Object* value) { | 2859 Object* JSObject::SlowReverseLookup(Object* value) { |
| 2852 if (HasFastProperties()) { | 2860 if (HasFastProperties()) { |
| 2853 for (DescriptorReader r(map()->instance_descriptors()); | 2861 DescriptorArray* descs = map()->instance_descriptors(); |
| 2854 !r.eos(); | 2862 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 2855 r.advance()) { | 2863 if (descs->GetType(i) == FIELD) { |
| 2856 if (r.type() == FIELD) { | 2864 if (FastPropertyAt(descs->GetFieldIndex(i)) == value) { |
| 2857 if (FastPropertyAt(r.GetFieldIndex()) == value) { | 2865 return descs->GetKey(i); |
| 2858 return r.GetKey(); | |
| 2859 } | 2866 } |
| 2860 } else if (r.type() == CONSTANT_FUNCTION) { | 2867 } else if (descs->GetType(i) == CONSTANT_FUNCTION) { |
| 2861 if (r.GetConstantFunction() == value) { | 2868 if (descs->GetConstantFunction(i) == value) { |
| 2862 return r.GetKey(); | 2869 return descs->GetKey(i); |
| 2863 } | 2870 } |
| 2864 } | 2871 } |
| 2865 } | 2872 } |
| 2866 return Heap::undefined_value(); | 2873 return Heap::undefined_value(); |
| 2867 } else { | 2874 } else { |
| 2868 return property_dictionary()->SlowReverseLookup(value); | 2875 return property_dictionary()->SlowReverseLookup(value); |
| 2869 } | 2876 } |
| 2870 } | 2877 } |
| 2871 | 2878 |
| 2872 | 2879 |
| (...skipping 293 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3166 ASSERT(remove_transitions == !descriptor->GetDetails().IsTransition()); | 3173 ASSERT(remove_transitions == !descriptor->GetDetails().IsTransition()); |
| 3167 ASSERT(descriptor->GetDetails().type() != NULL_DESCRIPTOR); | 3174 ASSERT(descriptor->GetDetails().type() != NULL_DESCRIPTOR); |
| 3168 | 3175 |
| 3169 // Ensure the key is a symbol. | 3176 // Ensure the key is a symbol. |
| 3170 Object* result = descriptor->KeyToSymbol(); | 3177 Object* result = descriptor->KeyToSymbol(); |
| 3171 if (result->IsFailure()) return result; | 3178 if (result->IsFailure()) return result; |
| 3172 | 3179 |
| 3173 int transitions = 0; | 3180 int transitions = 0; |
| 3174 int null_descriptors = 0; | 3181 int null_descriptors = 0; |
| 3175 if (remove_transitions) { | 3182 if (remove_transitions) { |
| 3176 for (DescriptorReader r(this); !r.eos(); r.advance()) { | 3183 for (int i = 0; i < number_of_descriptors(); i++) { |
| 3177 if (r.IsTransition()) transitions++; | 3184 if (IsTransition(i)) transitions++; |
| 3178 if (r.IsNullDescriptor()) null_descriptors++; | 3185 if (IsNullDescriptor(i)) null_descriptors++; |
| 3179 } | 3186 } |
| 3180 } else { | 3187 } else { |
| 3181 for (DescriptorReader r(this); !r.eos(); r.advance()) { | 3188 for (int i = 0; i < number_of_descriptors(); i++) { |
| 3182 if (r.IsNullDescriptor()) null_descriptors++; | 3189 if (IsNullDescriptor(i)) null_descriptors++; |
| 3183 } | 3190 } |
| 3184 } | 3191 } |
| 3185 int new_size = number_of_descriptors() - transitions - null_descriptors; | 3192 int new_size = number_of_descriptors() - transitions - null_descriptors; |
| 3186 | 3193 |
| 3187 // If key is in descriptor, we replace it in-place when filtering. | 3194 // If key is in descriptor, we replace it in-place when filtering. |
| 3188 // Count a null descriptor for key as inserted, not replaced. | 3195 // Count a null descriptor for key as inserted, not replaced. |
| 3189 int index = Search(descriptor->GetKey()); | 3196 int index = Search(descriptor->GetKey()); |
| 3190 const bool inserting = (index == kNotFound); | 3197 const bool inserting = (index == kNotFound); |
| 3191 const bool replacing = !inserting; | 3198 const bool replacing = !inserting; |
| 3192 bool keep_enumeration_index = false; | 3199 bool keep_enumeration_index = false; |
| (...skipping 27 matching lines...) Expand all Loading... |
| 3220 PropertyDetails(GetDetails(index)).index()); | 3227 PropertyDetails(GetDetails(index)).index()); |
| 3221 } else { | 3228 } else { |
| 3222 descriptor->SetEnumerationIndex(enumeration_index); | 3229 descriptor->SetEnumerationIndex(enumeration_index); |
| 3223 ++enumeration_index; | 3230 ++enumeration_index; |
| 3224 } | 3231 } |
| 3225 } | 3232 } |
| 3226 new_descriptors->SetNextEnumerationIndex(enumeration_index); | 3233 new_descriptors->SetNextEnumerationIndex(enumeration_index); |
| 3227 | 3234 |
| 3228 // Copy the descriptors, filtering out transitions and null descriptors, | 3235 // Copy the descriptors, filtering out transitions and null descriptors, |
| 3229 // and inserting or replacing a descriptor. | 3236 // and inserting or replacing a descriptor. |
| 3230 DescriptorWriter w(new_descriptors); | |
| 3231 DescriptorReader r(this); | |
| 3232 uint32_t descriptor_hash = descriptor->GetKey()->Hash(); | 3237 uint32_t descriptor_hash = descriptor->GetKey()->Hash(); |
| 3238 int from_index = 0; |
| 3239 int to_index = 0; |
| 3233 | 3240 |
| 3234 for (; !r.eos(); r.advance()) { | 3241 for (; from_index < number_of_descriptors(); from_index++) { |
| 3235 if (r.GetKey()->Hash() > descriptor_hash || | 3242 String* key = GetKey(from_index); |
| 3236 r.GetKey() == descriptor->GetKey()) break; | 3243 if (key->Hash() > descriptor_hash || key == descriptor->GetKey()) { |
| 3237 if (r.IsNullDescriptor()) continue; | 3244 break; |
| 3238 if (remove_transitions && r.IsTransition()) continue; | 3245 } |
| 3239 w.WriteFrom(&r); | 3246 if (IsNullDescriptor(from_index)) continue; |
| 3247 if (remove_transitions && IsTransition(from_index)) continue; |
| 3248 new_descriptors->SetFrom(to_index++, this, from_index); |
| 3240 } | 3249 } |
| 3241 w.Write(descriptor); | 3250 |
| 3242 if (replacing) { | 3251 new_descriptors->Set(to_index++, descriptor); |
| 3243 ASSERT(r.GetKey() == descriptor->GetKey()); | 3252 if (replacing) from_index++; |
| 3244 r.advance(); | 3253 |
| 3245 } else { | 3254 for (; from_index < number_of_descriptors(); from_index++) { |
| 3246 ASSERT(r.eos() || | 3255 if (IsNullDescriptor(from_index)) continue; |
| 3247 r.GetKey()->Hash() > descriptor_hash || | 3256 if (remove_transitions && IsTransition(from_index)) continue; |
| 3248 r.IsNullDescriptor()); | 3257 new_descriptors->SetFrom(to_index++, this, from_index); |
| 3249 } | 3258 } |
| 3250 for (; !r.eos(); r.advance()) { | 3259 |
| 3251 if (r.IsNullDescriptor()) continue; | 3260 ASSERT(to_index == new_descriptors->number_of_descriptors()); |
| 3252 if (remove_transitions && r.IsTransition()) continue; | 3261 SLOW_ASSERT(new_descriptors->IsSortedNoDuplicates()); |
| 3253 w.WriteFrom(&r); | |
| 3254 } | |
| 3255 ASSERT(w.eos()); | |
| 3256 | 3262 |
| 3257 return new_descriptors; | 3263 return new_descriptors; |
| 3258 } | 3264 } |
| 3259 | 3265 |
| 3260 | 3266 |
| 3261 Object* DescriptorArray::RemoveTransitions() { | 3267 Object* DescriptorArray::RemoveTransitions() { |
| 3262 // Remove all transitions and null descriptors. Return a copy of the array | 3268 // Remove all transitions and null descriptors. Return a copy of the array |
| 3263 // with all transitions removed, or a Failure object if the new array could | 3269 // with all transitions removed, or a Failure object if the new array could |
| 3264 // not be allocated. | 3270 // not be allocated. |
| 3265 | 3271 |
| 3266 // Compute the size of the map transition entries to be removed. | 3272 // Compute the size of the map transition entries to be removed. |
| 3267 int num_removed = 0; | 3273 int num_removed = 0; |
| 3268 for (DescriptorReader r(this); !r.eos(); r.advance()) { | 3274 for (int i = 0; i < number_of_descriptors(); i++) { |
| 3269 if (!r.IsProperty()) num_removed++; | 3275 if (!IsProperty(i)) num_removed++; |
| 3270 } | 3276 } |
| 3271 | 3277 |
| 3272 // Allocate the new descriptor array. | 3278 // Allocate the new descriptor array. |
| 3273 Object* result = Allocate(number_of_descriptors() - num_removed); | 3279 Object* result = Allocate(number_of_descriptors() - num_removed); |
| 3274 if (result->IsFailure()) return result; | 3280 if (result->IsFailure()) return result; |
| 3275 DescriptorArray* new_descriptors = DescriptorArray::cast(result); | 3281 DescriptorArray* new_descriptors = DescriptorArray::cast(result); |
| 3276 | 3282 |
| 3277 // Copy the content. | 3283 // Copy the content. |
| 3278 DescriptorWriter w(new_descriptors); | 3284 int next_descriptor = 0; |
| 3279 for (DescriptorReader r(this); !r.eos(); r.advance()) { | 3285 for (int i = 0; i < number_of_descriptors(); i++) { |
| 3280 if (r.IsProperty()) w.WriteFrom(&r); | 3286 if (IsProperty(i)) new_descriptors->SetFrom(next_descriptor++, this, i); |
| 3281 } | 3287 } |
| 3282 ASSERT(w.eos()); | 3288 ASSERT(next_descriptor == new_descriptors->number_of_descriptors()); |
| 3283 | 3289 |
| 3284 return new_descriptors; | 3290 return new_descriptors; |
| 3285 } | 3291 } |
| 3286 | 3292 |
| 3287 | 3293 |
| 3288 void DescriptorArray::Sort() { | 3294 void DescriptorArray::Sort() { |
| 3289 // In-place heap sort. | 3295 // In-place heap sort. |
| 3290 int len = number_of_descriptors(); | 3296 int len = number_of_descriptors(); |
| 3291 | 3297 |
| 3292 // Bottom-up max-heap construction. | 3298 // Bottom-up max-heap construction. |
| (...skipping 1286 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4579 void String::PrintOn(FILE* file) { | 4585 void String::PrintOn(FILE* file) { |
| 4580 int length = this->length(); | 4586 int length = this->length(); |
| 4581 for (int i = 0; i < length; i++) { | 4587 for (int i = 0; i < length; i++) { |
| 4582 fprintf(file, "%c", Get(i)); | 4588 fprintf(file, "%c", Get(i)); |
| 4583 } | 4589 } |
| 4584 } | 4590 } |
| 4585 | 4591 |
| 4586 | 4592 |
| 4587 void Map::CreateBackPointers() { | 4593 void Map::CreateBackPointers() { |
| 4588 DescriptorArray* descriptors = instance_descriptors(); | 4594 DescriptorArray* descriptors = instance_descriptors(); |
| 4589 for (DescriptorReader r(descriptors); !r.eos(); r.advance()) { | 4595 for (int i = 0; i < descriptors->number_of_descriptors(); i++) { |
| 4590 if (r.type() == MAP_TRANSITION) { | 4596 if (descriptors->GetType(i) == MAP_TRANSITION) { |
| 4591 // Get target. | 4597 // Get target. |
| 4592 Map* target = Map::cast(r.GetValue()); | 4598 Map* target = Map::cast(descriptors->GetValue(i)); |
| 4593 #ifdef DEBUG | 4599 #ifdef DEBUG |
| 4594 // Verify target. | 4600 // Verify target. |
| 4595 Object* source_prototype = prototype(); | 4601 Object* source_prototype = prototype(); |
| 4596 Object* target_prototype = target->prototype(); | 4602 Object* target_prototype = target->prototype(); |
| 4597 ASSERT(source_prototype->IsJSObject() || | 4603 ASSERT(source_prototype->IsJSObject() || |
| 4598 source_prototype->IsMap() || | 4604 source_prototype->IsMap() || |
| 4599 source_prototype->IsNull()); | 4605 source_prototype->IsNull()); |
| 4600 ASSERT(target_prototype->IsJSObject() || | 4606 ASSERT(target_prototype->IsJSObject() || |
| 4601 target_prototype->IsNull()); | 4607 target_prototype->IsNull()); |
| 4602 ASSERT(source_prototype->IsMap() || | 4608 ASSERT(source_prototype->IsMap() || |
| 4603 source_prototype == target_prototype); | 4609 source_prototype == target_prototype); |
| 4604 #endif | 4610 #endif |
| 4605 // Point target back to source. set_prototype() will not let us set | 4611 // Point target back to source. set_prototype() will not let us set |
| 4606 // the prototype to a map, as we do here. | 4612 // the prototype to a map, as we do here. |
| 4607 *RawField(target, kPrototypeOffset) = this; | 4613 *RawField(target, kPrototypeOffset) = this; |
| 4608 } | 4614 } |
| 4609 } | 4615 } |
| 4610 } | 4616 } |
| 4611 | 4617 |
| 4612 | 4618 |
| 4613 void Map::ClearNonLiveTransitions(Object* real_prototype) { | 4619 void Map::ClearNonLiveTransitions(Object* real_prototype) { |
| (...skipping 1397 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6011 } | 6017 } |
| 6012 | 6018 |
| 6013 LookupResult result; | 6019 LookupResult result; |
| 6014 LocalLookupRealNamedProperty(key, &result); | 6020 LocalLookupRealNamedProperty(key, &result); |
| 6015 return result.IsValid() && (result.type() == CALLBACKS); | 6021 return result.IsValid() && (result.type() == CALLBACKS); |
| 6016 } | 6022 } |
| 6017 | 6023 |
| 6018 | 6024 |
| 6019 int JSObject::NumberOfLocalProperties(PropertyAttributes filter) { | 6025 int JSObject::NumberOfLocalProperties(PropertyAttributes filter) { |
| 6020 if (HasFastProperties()) { | 6026 if (HasFastProperties()) { |
| 6027 DescriptorArray* descs = map()->instance_descriptors(); |
| 6021 int result = 0; | 6028 int result = 0; |
| 6022 for (DescriptorReader r(map()->instance_descriptors()); | 6029 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 6023 !r.eos(); | 6030 PropertyDetails details = descs->GetDetails(i); |
| 6024 r.advance()) { | 6031 if (details.IsProperty() && (details.attributes() & filter) == 0) { |
| 6025 PropertyDetails details = r.GetDetails(); | |
| 6026 if (details.IsProperty() && | |
| 6027 (details.attributes() & filter) == 0) { | |
| 6028 result++; | 6032 result++; |
| 6029 } | 6033 } |
| 6030 } | 6034 } |
| 6031 return result; | 6035 return result; |
| 6032 } else { | 6036 } else { |
| 6033 return property_dictionary()->NumberOfElementsFilterAttributes(filter); | 6037 return property_dictionary()->NumberOfElementsFilterAttributes(filter); |
| 6034 } | 6038 } |
| 6035 } | 6039 } |
| 6036 | 6040 |
| 6037 | 6041 |
| (...skipping 112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6150 HeapSortPairs(this, numbers, len); | 6154 HeapSortPairs(this, numbers, len); |
| 6151 return; | 6155 return; |
| 6152 } | 6156 } |
| 6153 } | 6157 } |
| 6154 | 6158 |
| 6155 | 6159 |
| 6156 // Fill in the names of local properties into the supplied storage. The main | 6160 // Fill in the names of local properties into the supplied storage. The main |
| 6157 // purpose of this function is to provide reflection information for the object | 6161 // purpose of this function is to provide reflection information for the object |
| 6158 // mirrors. | 6162 // mirrors. |
| 6159 void JSObject::GetLocalPropertyNames(FixedArray* storage, int index) { | 6163 void JSObject::GetLocalPropertyNames(FixedArray* storage, int index) { |
| 6160 ASSERT(storage->length() >= | 6164 ASSERT(storage->length() >= (NumberOfLocalProperties(NONE) - index)); |
| 6161 NumberOfLocalProperties(static_cast<PropertyAttributes>(NONE)) - | |
| 6162 index); | |
| 6163 if (HasFastProperties()) { | 6165 if (HasFastProperties()) { |
| 6164 for (DescriptorReader r(map()->instance_descriptors()); | 6166 DescriptorArray* descs = map()->instance_descriptors(); |
| 6165 !r.eos(); | 6167 for (int i = 0; i < descs->number_of_descriptors(); i++) { |
| 6166 r.advance()) { | 6168 if (descs->IsProperty(i)) storage->set(index++, descs->GetKey(i)); |
| 6167 if (r.IsProperty()) { | |
| 6168 storage->set(index++, r.GetKey()); | |
| 6169 } | |
| 6170 } | 6169 } |
| 6171 ASSERT(storage->length() >= index); | 6170 ASSERT(storage->length() >= index); |
| 6172 } else { | 6171 } else { |
| 6173 property_dictionary()->CopyKeysTo(storage); | 6172 property_dictionary()->CopyKeysTo(storage); |
| 6174 } | 6173 } |
| 6175 } | 6174 } |
| 6176 | 6175 |
| 6177 | 6176 |
| 6178 int JSObject::NumberOfLocalElements(PropertyAttributes filter) { | 6177 int JSObject::NumberOfLocalElements(PropertyAttributes filter) { |
| 6179 return GetLocalElementKeys(NULL, filter); | 6178 return GetLocalElementKeys(NULL, filter); |
| (...skipping 1223 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7403 | 7402 |
| 7404 int inobject_props = obj->map()->inobject_properties(); | 7403 int inobject_props = obj->map()->inobject_properties(); |
| 7405 int number_of_allocated_fields = | 7404 int number_of_allocated_fields = |
| 7406 number_of_fields + unused_property_fields - inobject_props; | 7405 number_of_fields + unused_property_fields - inobject_props; |
| 7407 | 7406 |
| 7408 // Allocate the fixed array for the fields. | 7407 // Allocate the fixed array for the fields. |
| 7409 Object* fields = Heap::AllocateFixedArray(number_of_allocated_fields); | 7408 Object* fields = Heap::AllocateFixedArray(number_of_allocated_fields); |
| 7410 if (fields->IsFailure()) return fields; | 7409 if (fields->IsFailure()) return fields; |
| 7411 | 7410 |
| 7412 // Fill in the instance descriptor and the fields. | 7411 // Fill in the instance descriptor and the fields. |
| 7413 DescriptorWriter w(descriptors); | 7412 int next_descriptor = 0; |
| 7414 int current_offset = 0; | 7413 int current_offset = 0; |
| 7415 for (int i = 0; i < capacity; i++) { | 7414 for (int i = 0; i < capacity; i++) { |
| 7416 Object* k = KeyAt(i); | 7415 Object* k = KeyAt(i); |
| 7417 if (IsKey(k)) { | 7416 if (IsKey(k)) { |
| 7418 Object* value = ValueAt(i); | 7417 Object* value = ValueAt(i); |
| 7419 // Ensure the key is a symbol before writing into the instance descriptor. | 7418 // Ensure the key is a symbol before writing into the instance descriptor. |
| 7420 Object* key = Heap::LookupSymbol(String::cast(k)); | 7419 Object* key = Heap::LookupSymbol(String::cast(k)); |
| 7421 if (key->IsFailure()) return key; | 7420 if (key->IsFailure()) return key; |
| 7422 PropertyDetails details = DetailsAt(i); | 7421 PropertyDetails details = DetailsAt(i); |
| 7423 PropertyType type = details.type(); | 7422 PropertyType type = details.type(); |
| 7424 | 7423 |
| 7425 if (value->IsJSFunction()) { | 7424 if (value->IsJSFunction()) { |
| 7426 ConstantFunctionDescriptor d(String::cast(key), | 7425 ConstantFunctionDescriptor d(String::cast(key), |
| 7427 JSFunction::cast(value), | 7426 JSFunction::cast(value), |
| 7428 details.attributes(), | 7427 details.attributes(), |
| 7429 details.index()); | 7428 details.index()); |
| 7430 w.Write(&d); | 7429 descriptors->Set(next_descriptor++, &d); |
| 7431 } else if (type == NORMAL) { | 7430 } else if (type == NORMAL) { |
| 7432 if (current_offset < inobject_props) { | 7431 if (current_offset < inobject_props) { |
| 7433 obj->InObjectPropertyAtPut(current_offset, | 7432 obj->InObjectPropertyAtPut(current_offset, |
| 7434 value, | 7433 value, |
| 7435 UPDATE_WRITE_BARRIER); | 7434 UPDATE_WRITE_BARRIER); |
| 7436 } else { | 7435 } else { |
| 7437 int offset = current_offset - inobject_props; | 7436 int offset = current_offset - inobject_props; |
| 7438 FixedArray::cast(fields)->set(offset, value); | 7437 FixedArray::cast(fields)->set(offset, value); |
| 7439 } | 7438 } |
| 7440 FieldDescriptor d(String::cast(key), | 7439 FieldDescriptor d(String::cast(key), |
| 7441 current_offset++, | 7440 current_offset++, |
| 7442 details.attributes(), | 7441 details.attributes(), |
| 7443 details.index()); | 7442 details.index()); |
| 7444 w.Write(&d); | 7443 descriptors->Set(next_descriptor++, &d); |
| 7445 } else if (type == CALLBACKS) { | 7444 } else if (type == CALLBACKS) { |
| 7446 CallbacksDescriptor d(String::cast(key), | 7445 CallbacksDescriptor d(String::cast(key), |
| 7447 value, | 7446 value, |
| 7448 details.attributes(), | 7447 details.attributes(), |
| 7449 details.index()); | 7448 details.index()); |
| 7450 w.Write(&d); | 7449 descriptors->Set(next_descriptor++, &d); |
| 7451 } else { | 7450 } else { |
| 7452 UNREACHABLE(); | 7451 UNREACHABLE(); |
| 7453 } | 7452 } |
| 7454 } | 7453 } |
| 7455 } | 7454 } |
| 7456 ASSERT(current_offset == number_of_fields); | 7455 ASSERT(current_offset == number_of_fields); |
| 7457 | 7456 |
| 7458 descriptors->Sort(); | 7457 descriptors->Sort(); |
| 7459 // Allocate new map. | 7458 // Allocate new map. |
| 7460 Object* new_map = obj->map()->CopyDropDescriptors(); | 7459 Object* new_map = obj->map()->CopyDropDescriptors(); |
| (...skipping 256 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7717 if (break_point_objects()->IsUndefined()) return 0; | 7716 if (break_point_objects()->IsUndefined()) return 0; |
| 7718 // Single beak point. | 7717 // Single beak point. |
| 7719 if (!break_point_objects()->IsFixedArray()) return 1; | 7718 if (!break_point_objects()->IsFixedArray()) return 1; |
| 7720 // Multiple break points. | 7719 // Multiple break points. |
| 7721 return FixedArray::cast(break_point_objects())->length(); | 7720 return FixedArray::cast(break_point_objects())->length(); |
| 7722 } | 7721 } |
| 7723 #endif | 7722 #endif |
| 7724 | 7723 |
| 7725 | 7724 |
| 7726 } } // namespace v8::internal | 7725 } } // namespace v8::internal |
| OLD | NEW |