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 3303 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3314 Object* result; | 3314 Object* result; |
3315 { MaybeObject* maybe_result = | 3315 { MaybeObject* maybe_result = |
3316 AllocateRaw(map->instance_size(), space, retry_space); | 3316 AllocateRaw(map->instance_size(), space, retry_space); |
3317 if (!maybe_result->ToObject(&result)) return maybe_result; | 3317 if (!maybe_result->ToObject(&result)) return maybe_result; |
3318 } | 3318 } |
3319 HeapObject::cast(result)->set_map(map); | 3319 HeapObject::cast(result)->set_map(map); |
3320 return result; | 3320 return result; |
3321 } | 3321 } |
3322 | 3322 |
3323 | 3323 |
3324 MaybeObject* Heap::InitializeFunction(JSFunction* function, | 3324 void Heap::InitializeFunction(JSFunction* function, |
3325 SharedFunctionInfo* shared, | 3325 SharedFunctionInfo* shared, |
3326 Object* prototype) { | 3326 Object* prototype) { |
3327 ASSERT(!prototype->IsMap()); | 3327 ASSERT(!prototype->IsMap()); |
3328 function->initialize_properties(); | 3328 function->initialize_properties(); |
3329 function->initialize_elements(); | 3329 function->initialize_elements(); |
3330 function->set_shared(shared); | 3330 function->set_shared(shared); |
3331 function->set_code(shared->code()); | 3331 function->set_code(shared->code()); |
3332 function->set_prototype_or_initial_map(prototype); | 3332 function->set_prototype_or_initial_map(prototype); |
3333 function->set_context(undefined_value()); | 3333 function->set_context(undefined_value()); |
3334 function->set_literals(empty_fixed_array()); | 3334 function->set_literals(empty_fixed_array()); |
3335 function->set_next_function_link(undefined_value()); | 3335 function->set_next_function_link(undefined_value()); |
3336 return function; | |
3337 } | 3336 } |
3338 | 3337 |
3339 | 3338 |
3340 MaybeObject* Heap::AllocateFunctionPrototype(JSFunction* function) { | 3339 MaybeObject* Heap::AllocateFunctionPrototype(JSFunction* function) { |
3341 // Allocate the prototype. Make sure to use the object function | 3340 // Allocate the prototype. Make sure to use the object function |
3342 // from the function's context, since the function can be from a | 3341 // from the function's context, since the function can be from a |
3343 // different context. | 3342 // different context. |
3344 JSFunction* object_function = | 3343 JSFunction* object_function = |
3345 function->context()->global_context()->object_function(); | 3344 function->context()->global_context()->object_function(); |
3346 | 3345 |
(...skipping 25 matching lines...) Expand all Loading... |
3372 MaybeObject* Heap::AllocateFunction(Map* function_map, | 3371 MaybeObject* Heap::AllocateFunction(Map* function_map, |
3373 SharedFunctionInfo* shared, | 3372 SharedFunctionInfo* shared, |
3374 Object* prototype, | 3373 Object* prototype, |
3375 PretenureFlag pretenure) { | 3374 PretenureFlag pretenure) { |
3376 AllocationSpace space = | 3375 AllocationSpace space = |
3377 (pretenure == TENURED) ? OLD_POINTER_SPACE : NEW_SPACE; | 3376 (pretenure == TENURED) ? OLD_POINTER_SPACE : NEW_SPACE; |
3378 Object* result; | 3377 Object* result; |
3379 { MaybeObject* maybe_result = Allocate(function_map, space); | 3378 { MaybeObject* maybe_result = Allocate(function_map, space); |
3380 if (!maybe_result->ToObject(&result)) return maybe_result; | 3379 if (!maybe_result->ToObject(&result)) return maybe_result; |
3381 } | 3380 } |
3382 return InitializeFunction(JSFunction::cast(result), shared, prototype); | 3381 InitializeFunction(JSFunction::cast(result), shared, prototype); |
| 3382 return result; |
3383 } | 3383 } |
3384 | 3384 |
3385 | 3385 |
3386 MaybeObject* Heap::AllocateArgumentsObject(Object* callee, int length) { | 3386 MaybeObject* Heap::AllocateArgumentsObject(Object* callee, int length) { |
3387 // To get fast allocation and map sharing for arguments objects we | 3387 // To get fast allocation and map sharing for arguments objects we |
3388 // allocate them based on an arguments boilerplate. | 3388 // allocate them based on an arguments boilerplate. |
3389 | 3389 |
3390 JSObject* boilerplate; | 3390 JSObject* boilerplate; |
3391 int arguments_object_size; | 3391 int arguments_object_size; |
3392 bool strict_mode_callee = callee->IsJSFunction() && | 3392 bool strict_mode_callee = callee->IsJSFunction() && |
(...skipping 419 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3812 } | 3812 } |
3813 // Return the new clone. | 3813 // Return the new clone. |
3814 return clone; | 3814 return clone; |
3815 } | 3815 } |
3816 | 3816 |
3817 | 3817 |
3818 MaybeObject* Heap::ReinitializeJSReceiver( | 3818 MaybeObject* Heap::ReinitializeJSReceiver( |
3819 JSReceiver* object, InstanceType type, int size) { | 3819 JSReceiver* object, InstanceType type, int size) { |
3820 ASSERT(type >= FIRST_JS_OBJECT_TYPE); | 3820 ASSERT(type >= FIRST_JS_OBJECT_TYPE); |
3821 | 3821 |
3822 // Save identity hash. | |
3823 MaybeObject* maybe_hash = object->GetIdentityHash(OMIT_CREATION); | |
3824 | |
3825 // Allocate fresh map. | 3822 // Allocate fresh map. |
3826 // TODO(rossberg): Once we optimize proxies, cache these maps. | 3823 // TODO(rossberg): Once we optimize proxies, cache these maps. |
3827 Map* map; | 3824 Map* map; |
3828 MaybeObject* maybe = AllocateMap(type, size); | 3825 MaybeObject* maybe = AllocateMap(type, size); |
3829 if (!maybe->To<Map>(&map)) return maybe; | 3826 if (!maybe->To<Map>(&map)) return maybe; |
3830 | 3827 |
3831 // Check that the receiver has at least the size of the fresh object. | 3828 // Check that the receiver has at least the size of the fresh object. |
3832 int size_difference = object->map()->instance_size() - map->instance_size(); | 3829 int size_difference = object->map()->instance_size() - map->instance_size(); |
3833 ASSERT(size_difference >= 0); | 3830 ASSERT(size_difference >= 0); |
3834 | 3831 |
3835 map->set_prototype(object->map()->prototype()); | 3832 map->set_prototype(object->map()->prototype()); |
3836 | 3833 |
3837 // Allocate the backing storage for the properties. | 3834 // Allocate the backing storage for the properties. |
3838 int prop_size = map->unused_property_fields() - map->inobject_properties(); | 3835 int prop_size = map->unused_property_fields() - map->inobject_properties(); |
3839 Object* properties; | 3836 Object* properties; |
3840 { MaybeObject* maybe_properties = AllocateFixedArray(prop_size, TENURED); | 3837 maybe = AllocateFixedArray(prop_size, TENURED); |
3841 if (!maybe_properties->ToObject(&properties)) return maybe_properties; | 3838 if (!maybe->ToObject(&properties)) return maybe; |
| 3839 |
| 3840 // Functions require some allocation, which might fail here. |
| 3841 SharedFunctionInfo* shared = NULL; |
| 3842 if (type == JS_FUNCTION_TYPE) { |
| 3843 String* name; |
| 3844 maybe = LookupAsciiSymbol("<freezing call trap>"); |
| 3845 if (!maybe->To<String>(&name)) return maybe; |
| 3846 maybe = AllocateSharedFunctionInfo(name); |
| 3847 if (!maybe->To<SharedFunctionInfo>(&shared)) return maybe; |
3842 } | 3848 } |
3843 | 3849 |
| 3850 // We must NOT fail after this point! |
| 3851 |
3844 // Reset the map for the object. | 3852 // Reset the map for the object. |
3845 object->set_map(map); | 3853 object->set_map(map); |
3846 JSObject* jsobj = JSObject::cast(object); | 3854 JSObject* jsobj = JSObject::cast(object); |
3847 | 3855 |
3848 // Reinitialize the object from the constructor map. | 3856 // Reinitialize the object from the constructor map. |
3849 InitializeJSObjectFromMap(jsobj, FixedArray::cast(properties), map); | 3857 InitializeJSObjectFromMap(jsobj, FixedArray::cast(properties), map); |
3850 | 3858 |
3851 // Functions require some minimal initialization. | 3859 // Functions require some minimal initialization. |
3852 if (type == JS_FUNCTION_TYPE) { | 3860 if (type == JS_FUNCTION_TYPE) { |
3853 map->set_function_with_prototype(true); | 3861 map->set_function_with_prototype(true); |
3854 String* name; | 3862 InitializeFunction(JSFunction::cast(object), shared, the_hole_value()); |
3855 maybe = LookupAsciiSymbol("<freezing call trap>"); | 3863 JSFunction::cast(object)->set_context( |
3856 if (!maybe->To<String>(&name)) return maybe; | 3864 isolate()->context()->global_context()); |
3857 SharedFunctionInfo* shared; | |
3858 maybe = AllocateSharedFunctionInfo(name); | |
3859 if (!maybe->To<SharedFunctionInfo>(&shared)) return maybe; | |
3860 JSFunction* func; | |
3861 maybe = InitializeFunction( | |
3862 JSFunction::cast(object), shared, the_hole_value()); | |
3863 if (!maybe->To<JSFunction>(&func)) return maybe; | |
3864 func->set_context(isolate()->context()->global_context()); | |
3865 } | 3865 } |
3866 | 3866 |
3867 // Put in filler if the new object is smaller than the old. | 3867 // Put in filler if the new object is smaller than the old. |
3868 if (size_difference > 0) { | 3868 if (size_difference > 0) { |
3869 CreateFillerObjectAt( | 3869 CreateFillerObjectAt( |
3870 object->address() + map->instance_size(), size_difference); | 3870 object->address() + map->instance_size(), size_difference); |
3871 } | 3871 } |
3872 | 3872 |
3873 // Inherit identity, if it was present. | |
3874 Object* hash; | |
3875 if (maybe_hash->To<Object>(&hash) && hash->IsSmi()) { | |
3876 maybe = jsobj->SetIdentityHash(hash, ALLOW_CREATION); | |
3877 if (maybe->IsFailure()) return maybe; | |
3878 } | |
3879 | |
3880 return object; | 3873 return object; |
3881 } | 3874 } |
3882 | 3875 |
3883 | 3876 |
3884 MaybeObject* Heap::ReinitializeJSGlobalProxy(JSFunction* constructor, | 3877 MaybeObject* Heap::ReinitializeJSGlobalProxy(JSFunction* constructor, |
3885 JSGlobalProxy* object) { | 3878 JSGlobalProxy* object) { |
3886 ASSERT(constructor->has_initial_map()); | 3879 ASSERT(constructor->has_initial_map()); |
3887 Map* map = constructor->initial_map(); | 3880 Map* map = constructor->initial_map(); |
3888 | 3881 |
3889 // Check that the already allocated object has the same size and type as | 3882 // Check that the already allocated object has the same size and type as |
(...skipping 2580 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6470 isolate_->heap()->store_buffer()->Compact(); | 6463 isolate_->heap()->store_buffer()->Compact(); |
6471 isolate_->heap()->store_buffer()->Filter(MemoryChunk::ABOUT_TO_BE_FREED); | 6464 isolate_->heap()->store_buffer()->Filter(MemoryChunk::ABOUT_TO_BE_FREED); |
6472 for (chunk = chunks_queued_for_free_; chunk != NULL; chunk = next) { | 6465 for (chunk = chunks_queued_for_free_; chunk != NULL; chunk = next) { |
6473 next = chunk->next_chunk(); | 6466 next = chunk->next_chunk(); |
6474 isolate_->memory_allocator()->Free(chunk); | 6467 isolate_->memory_allocator()->Free(chunk); |
6475 } | 6468 } |
6476 chunks_queued_for_free_ = NULL; | 6469 chunks_queued_for_free_ = NULL; |
6477 } | 6470 } |
6478 | 6471 |
6479 } } // namespace v8::internal | 6472 } } // namespace v8::internal |
OLD | NEW |