| 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 360 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 371 } | 371 } |
| 372 | 372 |
| 373 if (FLAG_gc_verbose) Print(); | 373 if (FLAG_gc_verbose) Print(); |
| 374 #endif // DEBUG | 374 #endif // DEBUG |
| 375 | 375 |
| 376 #if defined(DEBUG) | 376 #if defined(DEBUG) |
| 377 ReportStatisticsBeforeGC(); | 377 ReportStatisticsBeforeGC(); |
| 378 #endif // DEBUG | 378 #endif // DEBUG |
| 379 | 379 |
| 380 LiveObjectList::GCPrologue(); | 380 LiveObjectList::GCPrologue(); |
| 381 store_buffer()->GCPrologue(); |
| 381 } | 382 } |
| 382 | 383 |
| 383 intptr_t Heap::SizeOfObjects() { | 384 intptr_t Heap::SizeOfObjects() { |
| 384 intptr_t total = 0; | 385 intptr_t total = 0; |
| 385 AllSpaces spaces; | 386 AllSpaces spaces; |
| 386 for (Space* space = spaces.next(); space != NULL; space = spaces.next()) { | 387 for (Space* space = spaces.next(); space != NULL; space = spaces.next()) { |
| 387 total += space->SizeOfObjects(); | 388 total += space->SizeOfObjects(); |
| 388 } | 389 } |
| 389 return total; | 390 return total; |
| 390 } | 391 } |
| 391 | 392 |
| 392 void Heap::GarbageCollectionEpilogue() { | 393 void Heap::GarbageCollectionEpilogue() { |
| 394 store_buffer()->GCEpilogue(); |
| 393 LiveObjectList::GCEpilogue(); | 395 LiveObjectList::GCEpilogue(); |
| 394 #ifdef DEBUG | 396 #ifdef DEBUG |
| 395 allow_allocation(true); | 397 allow_allocation(true); |
| 396 ZapFromSpace(); | 398 ZapFromSpace(); |
| 397 | 399 |
| 398 if (FLAG_verify_heap) { | 400 if (FLAG_verify_heap) { |
| 399 Verify(); | 401 Verify(); |
| 400 } | 402 } |
| 401 | 403 |
| 402 if (FLAG_print_global_handles) isolate_->global_handles()->Print(); | 404 if (FLAG_print_global_handles) isolate_->global_handles()->Print(); |
| (...skipping 417 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 820 // At any old GC clear the keyed lookup cache to enable collection of unused | 822 // At any old GC clear the keyed lookup cache to enable collection of unused |
| 821 // maps. | 823 // maps. |
| 822 isolate_->keyed_lookup_cache()->Clear(); | 824 isolate_->keyed_lookup_cache()->Clear(); |
| 823 isolate_->context_slot_cache()->Clear(); | 825 isolate_->context_slot_cache()->Clear(); |
| 824 isolate_->descriptor_lookup_cache()->Clear(); | 826 isolate_->descriptor_lookup_cache()->Clear(); |
| 825 | 827 |
| 826 isolate_->compilation_cache()->MarkCompactPrologue(); | 828 isolate_->compilation_cache()->MarkCompactPrologue(); |
| 827 | 829 |
| 828 CompletelyClearInstanceofCache(); | 830 CompletelyClearInstanceofCache(); |
| 829 | 831 |
| 830 // TODO(gc) select heuristic for flushing NumberString cache with | 832 // TODO(1605) select heuristic for flushing NumberString cache with |
| 831 // FlushNumberStringCache | 833 // FlushNumberStringCache |
| 832 if (FLAG_cleanup_code_caches_at_gc) { | 834 if (FLAG_cleanup_code_caches_at_gc) { |
| 833 polymorphic_code_cache()->set_cache(undefined_value()); | 835 polymorphic_code_cache()->set_cache(undefined_value()); |
| 834 } | 836 } |
| 835 | 837 |
| 836 ClearNormalizedMapCaches(); | 838 ClearNormalizedMapCaches(); |
| 837 } | 839 } |
| 838 | 840 |
| 839 | 841 |
| 840 Object* Heap::FindCodeObject(Address a) { | 842 Object* Heap::FindCodeObject(Address a) { |
| (...skipping 599 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1440 ASSERT((size_restriction != SMALL) || | 1442 ASSERT((size_restriction != SMALL) || |
| 1441 (object_size <= Page::kMaxHeapObjectSize)); | 1443 (object_size <= Page::kMaxHeapObjectSize)); |
| 1442 ASSERT(object->Size() == object_size); | 1444 ASSERT(object->Size() == object_size); |
| 1443 | 1445 |
| 1444 Heap* heap = map->GetHeap(); | 1446 Heap* heap = map->GetHeap(); |
| 1445 if (heap->ShouldBePromoted(object->address(), object_size)) { | 1447 if (heap->ShouldBePromoted(object->address(), object_size)) { |
| 1446 MaybeObject* maybe_result; | 1448 MaybeObject* maybe_result; |
| 1447 | 1449 |
| 1448 if ((size_restriction != SMALL) && | 1450 if ((size_restriction != SMALL) && |
| 1449 (object_size > Page::kMaxHeapObjectSize)) { | 1451 (object_size > Page::kMaxHeapObjectSize)) { |
| 1450 if (object_contents == DATA_OBJECT) { | 1452 maybe_result = heap->lo_space()->AllocateRaw(object_size, |
| 1451 maybe_result = heap->lo_space()->AllocateRawData(object_size); | 1453 NOT_EXECUTABLE); |
| 1452 } else { | |
| 1453 maybe_result = heap->lo_space()->AllocateRawFixedArray(object_size); | |
| 1454 } | |
| 1455 } else { | 1454 } else { |
| 1456 if (object_contents == DATA_OBJECT) { | 1455 if (object_contents == DATA_OBJECT) { |
| 1457 maybe_result = heap->old_data_space()->AllocateRaw(object_size); | 1456 maybe_result = heap->old_data_space()->AllocateRaw(object_size); |
| 1458 } else { | 1457 } else { |
| 1459 maybe_result = heap->old_pointer_space()->AllocateRaw(object_size); | 1458 maybe_result = heap->old_pointer_space()->AllocateRaw(object_size); |
| 1460 } | 1459 } |
| 1461 } | 1460 } |
| 1462 | 1461 |
| 1463 Object* result = NULL; // Initialization to please compiler. | 1462 Object* result = NULL; // Initialization to please compiler. |
| 1464 if (maybe_result->ToObject(&result)) { | 1463 if (maybe_result->ToObject(&result)) { |
| (...skipping 1358 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2823 if (length < 0 || length > ByteArray::kMaxLength) { | 2822 if (length < 0 || length > ByteArray::kMaxLength) { |
| 2824 return Failure::OutOfMemoryException(); | 2823 return Failure::OutOfMemoryException(); |
| 2825 } | 2824 } |
| 2826 if (pretenure == NOT_TENURED) { | 2825 if (pretenure == NOT_TENURED) { |
| 2827 return AllocateByteArray(length); | 2826 return AllocateByteArray(length); |
| 2828 } | 2827 } |
| 2829 int size = ByteArray::SizeFor(length); | 2828 int size = ByteArray::SizeFor(length); |
| 2830 Object* result; | 2829 Object* result; |
| 2831 { MaybeObject* maybe_result = (size <= MaxObjectSizeInPagedSpace()) | 2830 { MaybeObject* maybe_result = (size <= MaxObjectSizeInPagedSpace()) |
| 2832 ? old_data_space_->AllocateRaw(size) | 2831 ? old_data_space_->AllocateRaw(size) |
| 2833 : lo_space_->AllocateRawData(size); | 2832 : lo_space_->AllocateRaw(size, NOT_EXECUTABLE); |
| 2834 if (!maybe_result->ToObject(&result)) return maybe_result; | 2833 if (!maybe_result->ToObject(&result)) return maybe_result; |
| 2835 } | 2834 } |
| 2836 | 2835 |
| 2837 reinterpret_cast<ByteArray*>(result)->set_map(byte_array_map()); | 2836 reinterpret_cast<ByteArray*>(result)->set_map(byte_array_map()); |
| 2838 reinterpret_cast<ByteArray*>(result)->set_length(length); | 2837 reinterpret_cast<ByteArray*>(result)->set_length(length); |
| 2839 return result; | 2838 return result; |
| 2840 } | 2839 } |
| 2841 | 2840 |
| 2842 | 2841 |
| 2843 MaybeObject* Heap::AllocateByteArray(int length) { | 2842 MaybeObject* Heap::AllocateByteArray(int length) { |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2906 } | 2905 } |
| 2907 | 2906 |
| 2908 // Compute size. | 2907 // Compute size. |
| 2909 int body_size = RoundUp(desc.instr_size, kObjectAlignment); | 2908 int body_size = RoundUp(desc.instr_size, kObjectAlignment); |
| 2910 int obj_size = Code::SizeFor(body_size); | 2909 int obj_size = Code::SizeFor(body_size); |
| 2911 ASSERT(IsAligned(static_cast<intptr_t>(obj_size), kCodeAlignment)); | 2910 ASSERT(IsAligned(static_cast<intptr_t>(obj_size), kCodeAlignment)); |
| 2912 MaybeObject* maybe_result; | 2911 MaybeObject* maybe_result; |
| 2913 // Large code objects and code objects which should stay at a fixed address | 2912 // Large code objects and code objects which should stay at a fixed address |
| 2914 // are allocated in large object space. | 2913 // are allocated in large object space. |
| 2915 if (obj_size > MaxObjectSizeInPagedSpace() || immovable) { | 2914 if (obj_size > MaxObjectSizeInPagedSpace() || immovable) { |
| 2916 maybe_result = lo_space_->AllocateRawCode(obj_size); | 2915 maybe_result = lo_space_->AllocateRaw(obj_size, EXECUTABLE); |
| 2917 } else { | 2916 } else { |
| 2918 maybe_result = code_space_->AllocateRaw(obj_size); | 2917 maybe_result = code_space_->AllocateRaw(obj_size); |
| 2919 } | 2918 } |
| 2920 | 2919 |
| 2921 Object* result; | 2920 Object* result; |
| 2922 if (!maybe_result->ToObject(&result)) return maybe_result; | 2921 if (!maybe_result->ToObject(&result)) return maybe_result; |
| 2923 | 2922 |
| 2924 // Initialize the object | 2923 // Initialize the object |
| 2925 HeapObject::cast(result)->set_map(code_map()); | 2924 HeapObject::cast(result)->set_map(code_map()); |
| 2926 Code* code = Code::cast(result); | 2925 Code* code = Code::cast(result); |
| (...skipping 24 matching lines...) Expand all Loading... |
| 2951 #endif | 2950 #endif |
| 2952 return code; | 2951 return code; |
| 2953 } | 2952 } |
| 2954 | 2953 |
| 2955 | 2954 |
| 2956 MaybeObject* Heap::CopyCode(Code* code) { | 2955 MaybeObject* Heap::CopyCode(Code* code) { |
| 2957 // Allocate an object the same size as the code object. | 2956 // Allocate an object the same size as the code object. |
| 2958 int obj_size = code->Size(); | 2957 int obj_size = code->Size(); |
| 2959 MaybeObject* maybe_result; | 2958 MaybeObject* maybe_result; |
| 2960 if (obj_size > MaxObjectSizeInPagedSpace()) { | 2959 if (obj_size > MaxObjectSizeInPagedSpace()) { |
| 2961 maybe_result = lo_space_->AllocateRawCode(obj_size); | 2960 maybe_result = lo_space_->AllocateRaw(obj_size, EXECUTABLE); |
| 2962 } else { | 2961 } else { |
| 2963 maybe_result = code_space_->AllocateRaw(obj_size); | 2962 maybe_result = code_space_->AllocateRaw(obj_size); |
| 2964 } | 2963 } |
| 2965 | 2964 |
| 2966 Object* result; | 2965 Object* result; |
| 2967 if (!maybe_result->ToObject(&result)) return maybe_result; | 2966 if (!maybe_result->ToObject(&result)) return maybe_result; |
| 2968 | 2967 |
| 2969 // Copy code object. | 2968 // Copy code object. |
| 2970 Address old_addr = code->address(); | 2969 Address old_addr = code->address(); |
| 2971 Address new_addr = reinterpret_cast<HeapObject*>(result)->address(); | 2970 Address new_addr = reinterpret_cast<HeapObject*>(result)->address(); |
| (...skipping 22 matching lines...) Expand all Loading... |
| 2994 | 2993 |
| 2995 int new_obj_size = Code::SizeFor(new_body_size); | 2994 int new_obj_size = Code::SizeFor(new_body_size); |
| 2996 | 2995 |
| 2997 Address old_addr = code->address(); | 2996 Address old_addr = code->address(); |
| 2998 | 2997 |
| 2999 size_t relocation_offset = | 2998 size_t relocation_offset = |
| 3000 static_cast<size_t>(code->instruction_end() - old_addr); | 2999 static_cast<size_t>(code->instruction_end() - old_addr); |
| 3001 | 3000 |
| 3002 MaybeObject* maybe_result; | 3001 MaybeObject* maybe_result; |
| 3003 if (new_obj_size > MaxObjectSizeInPagedSpace()) { | 3002 if (new_obj_size > MaxObjectSizeInPagedSpace()) { |
| 3004 maybe_result = lo_space_->AllocateRawCode(new_obj_size); | 3003 maybe_result = lo_space_->AllocateRaw(new_obj_size, EXECUTABLE); |
| 3005 } else { | 3004 } else { |
| 3006 maybe_result = code_space_->AllocateRaw(new_obj_size); | 3005 maybe_result = code_space_->AllocateRaw(new_obj_size); |
| 3007 } | 3006 } |
| 3008 | 3007 |
| 3009 Object* result; | 3008 Object* result; |
| 3010 if (!maybe_result->ToObject(&result)) return maybe_result; | 3009 if (!maybe_result->ToObject(&result)) return maybe_result; |
| 3011 | 3010 |
| 3012 // Copy code object. | 3011 // Copy code object. |
| 3013 Address new_addr = reinterpret_cast<HeapObject*>(result)->address(); | 3012 Address new_addr = reinterpret_cast<HeapObject*>(result)->address(); |
| 3014 | 3013 |
| (...skipping 677 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3692 if (chars > SeqTwoByteString::kMaxLength) { | 3691 if (chars > SeqTwoByteString::kMaxLength) { |
| 3693 return Failure::OutOfMemoryException(); | 3692 return Failure::OutOfMemoryException(); |
| 3694 } | 3693 } |
| 3695 map = symbol_map(); | 3694 map = symbol_map(); |
| 3696 size = SeqTwoByteString::SizeFor(chars); | 3695 size = SeqTwoByteString::SizeFor(chars); |
| 3697 } | 3696 } |
| 3698 | 3697 |
| 3699 // Allocate string. | 3698 // Allocate string. |
| 3700 Object* result; | 3699 Object* result; |
| 3701 { MaybeObject* maybe_result = (size > MaxObjectSizeInPagedSpace()) | 3700 { MaybeObject* maybe_result = (size > MaxObjectSizeInPagedSpace()) |
| 3702 ? lo_space_->AllocateRawData(size) | 3701 ? lo_space_->AllocateRaw(size, NOT_EXECUTABLE) |
| 3703 : old_data_space_->AllocateRaw(size); | 3702 : old_data_space_->AllocateRaw(size); |
| 3704 if (!maybe_result->ToObject(&result)) return maybe_result; | 3703 if (!maybe_result->ToObject(&result)) return maybe_result; |
| 3705 } | 3704 } |
| 3706 | 3705 |
| 3707 reinterpret_cast<HeapObject*>(result)->set_map(map); | 3706 reinterpret_cast<HeapObject*>(result)->set_map(map); |
| 3708 // Set length and hash fields of the allocated string. | 3707 // Set length and hash fields of the allocated string. |
| 3709 String* answer = String::cast(result); | 3708 String* answer = String::cast(result); |
| 3710 answer->set_length(chars); | 3709 answer->set_length(chars); |
| 3711 answer->set_hash_field(hash_field); | 3710 answer->set_hash_field(hash_field); |
| 3712 | 3711 |
| (...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3809 if (length < 0 || length > FixedArray::kMaxLength) { | 3808 if (length < 0 || length > FixedArray::kMaxLength) { |
| 3810 return Failure::OutOfMemoryException(); | 3809 return Failure::OutOfMemoryException(); |
| 3811 } | 3810 } |
| 3812 ASSERT(length > 0); | 3811 ASSERT(length > 0); |
| 3813 // Use the general function if we're forced to always allocate. | 3812 // Use the general function if we're forced to always allocate. |
| 3814 if (always_allocate()) return AllocateFixedArray(length, TENURED); | 3813 if (always_allocate()) return AllocateFixedArray(length, TENURED); |
| 3815 // Allocate the raw data for a fixed array. | 3814 // Allocate the raw data for a fixed array. |
| 3816 int size = FixedArray::SizeFor(length); | 3815 int size = FixedArray::SizeFor(length); |
| 3817 return size <= kMaxObjectSizeInNewSpace | 3816 return size <= kMaxObjectSizeInNewSpace |
| 3818 ? new_space_.AllocateRaw(size) | 3817 ? new_space_.AllocateRaw(size) |
| 3819 : lo_space_->AllocateRawFixedArray(size); | 3818 : lo_space_->AllocateRaw(size, NOT_EXECUTABLE); |
| 3820 } | 3819 } |
| 3821 | 3820 |
| 3822 | 3821 |
| 3823 MaybeObject* Heap::CopyFixedArrayWithMap(FixedArray* src, Map* map) { | 3822 MaybeObject* Heap::CopyFixedArrayWithMap(FixedArray* src, Map* map) { |
| 3824 int len = src->length(); | 3823 int len = src->length(); |
| 3825 Object* obj; | 3824 Object* obj; |
| 3826 { MaybeObject* maybe_obj = AllocateRawFixedArray(len); | 3825 { MaybeObject* maybe_obj = AllocateRawFixedArray(len); |
| 3827 if (!maybe_obj->ToObject(&obj)) return maybe_obj; | 3826 if (!maybe_obj->ToObject(&obj)) return maybe_obj; |
| 3828 } | 3827 } |
| 3829 if (InNewSpace(obj)) { | 3828 if (InNewSpace(obj)) { |
| (...skipping 665 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4495 return mod >= Map::kPointerFieldsBeginOffset && | 4494 return mod >= Map::kPointerFieldsBeginOffset && |
| 4496 mod < Map::kPointerFieldsEndOffset; | 4495 mod < Map::kPointerFieldsEndOffset; |
| 4497 } | 4496 } |
| 4498 | 4497 |
| 4499 | 4498 |
| 4500 bool EverythingsAPointer(Object** addr) { | 4499 bool EverythingsAPointer(Object** addr) { |
| 4501 return true; | 4500 return true; |
| 4502 } | 4501 } |
| 4503 | 4502 |
| 4504 | 4503 |
| 4505 static void CheckStoreBuffer(Object** current, | 4504 static void CheckStoreBuffer(Heap* heap, |
| 4505 Object** current, |
| 4506 Object** limit, | 4506 Object** limit, |
| 4507 Object**** store_buffer_position, | 4507 Object**** store_buffer_position, |
| 4508 Object*** store_buffer_top, | 4508 Object*** store_buffer_top, |
| 4509 CheckStoreBufferFilter filter, | 4509 CheckStoreBufferFilter filter, |
| 4510 Address special_garbage_start, | 4510 Address special_garbage_start, |
| 4511 Address special_garbage_end) { | 4511 Address special_garbage_end) { |
| 4512 Map* free_space_map = heap->free_space_map(); |
| 4512 for ( ; current < limit; current++) { | 4513 for ( ; current < limit; current++) { |
| 4513 Object* o = *current; | 4514 Object* o = *current; |
| 4514 Address current_address = reinterpret_cast<Address>(current); | 4515 Address current_address = reinterpret_cast<Address>(current); |
| 4515 // Skip free space. | 4516 // Skip free space. |
| 4516 // TODO(gc) ISOLATES MERGE | 4517 if (o == free_space_map) { |
| 4517 if (o == HEAP->free_space_map()) { | |
| 4518 Address current_address = reinterpret_cast<Address>(current); | 4518 Address current_address = reinterpret_cast<Address>(current); |
| 4519 FreeSpace* free_space = | 4519 FreeSpace* free_space = |
| 4520 FreeSpace::cast(HeapObject::FromAddress(current_address)); | 4520 FreeSpace::cast(HeapObject::FromAddress(current_address)); |
| 4521 int skip = free_space->Size(); | 4521 int skip = free_space->Size(); |
| 4522 ASSERT(current_address + skip <= reinterpret_cast<Address>(limit)); | 4522 ASSERT(current_address + skip <= reinterpret_cast<Address>(limit)); |
| 4523 ASSERT(skip > 0); | 4523 ASSERT(skip > 0); |
| 4524 current_address += skip - kPointerSize; | 4524 current_address += skip - kPointerSize; |
| 4525 current = reinterpret_cast<Object**>(current_address); | 4525 current = reinterpret_cast<Object**>(current_address); |
| 4526 continue; | 4526 continue; |
| 4527 } | 4527 } |
| 4528 // Skip the current linear allocation space between top and limit which is | 4528 // Skip the current linear allocation space between top and limit which is |
| 4529 // unmarked with the free space map, but can contain junk. | 4529 // unmarked with the free space map, but can contain junk. |
| 4530 if (current_address == special_garbage_start && | 4530 if (current_address == special_garbage_start && |
| 4531 special_garbage_end != special_garbage_start) { | 4531 special_garbage_end != special_garbage_start) { |
| 4532 current_address = special_garbage_end - kPointerSize; | 4532 current_address = special_garbage_end - kPointerSize; |
| 4533 current = reinterpret_cast<Object**>(current_address); | 4533 current = reinterpret_cast<Object**>(current_address); |
| 4534 continue; | 4534 continue; |
| 4535 } | 4535 } |
| 4536 if (!(*filter)(current)) continue; | 4536 if (!(*filter)(current)) continue; |
| 4537 ASSERT(current_address < special_garbage_start || | 4537 ASSERT(current_address < special_garbage_start || |
| 4538 current_address >= special_garbage_end); | 4538 current_address >= special_garbage_end); |
| 4539 ASSERT(reinterpret_cast<uintptr_t>(o) != kFreeListZapValue); | 4539 ASSERT(reinterpret_cast<uintptr_t>(o) != kFreeListZapValue); |
| 4540 // We have to check that the pointer does not point into new space | 4540 // We have to check that the pointer does not point into new space |
| 4541 // without trying to cast it to a heap object since the hash field of | 4541 // without trying to cast it to a heap object since the hash field of |
| 4542 // a string can contain values like 1 and 3 which are tagged null | 4542 // a string can contain values like 1 and 3 which are tagged null |
| 4543 // pointers. | 4543 // pointers. |
| 4544 // TODO(gc) ISOLATES MERGE | 4544 if (!heap->InNewSpace(o)) continue; |
| 4545 if (!HEAP->InNewSpace(o)) continue; | |
| 4546 while (**store_buffer_position < current && | 4545 while (**store_buffer_position < current && |
| 4547 *store_buffer_position < store_buffer_top) { | 4546 *store_buffer_position < store_buffer_top) { |
| 4548 (*store_buffer_position)++; | 4547 (*store_buffer_position)++; |
| 4549 } | 4548 } |
| 4550 if (**store_buffer_position != current || | 4549 if (**store_buffer_position != current || |
| 4551 *store_buffer_position == store_buffer_top) { | 4550 *store_buffer_position == store_buffer_top) { |
| 4552 Object** obj_start = current; | 4551 Object** obj_start = current; |
| 4553 while (!(*obj_start)->IsMap()) obj_start--; | 4552 while (!(*obj_start)->IsMap()) obj_start--; |
| 4554 UNREACHABLE(); | 4553 UNREACHABLE(); |
| 4555 } | 4554 } |
| (...skipping 13 matching lines...) Expand all Loading... |
| 4569 while (pages.has_next()) { | 4568 while (pages.has_next()) { |
| 4570 Page* page = pages.next(); | 4569 Page* page = pages.next(); |
| 4571 Object** current = reinterpret_cast<Object**>(page->ObjectAreaStart()); | 4570 Object** current = reinterpret_cast<Object**>(page->ObjectAreaStart()); |
| 4572 | 4571 |
| 4573 Address end = page->ObjectAreaEnd(); | 4572 Address end = page->ObjectAreaEnd(); |
| 4574 | 4573 |
| 4575 Object*** store_buffer_position = store_buffer()->Start(); | 4574 Object*** store_buffer_position = store_buffer()->Start(); |
| 4576 Object*** store_buffer_top = store_buffer()->Top(); | 4575 Object*** store_buffer_top = store_buffer()->Top(); |
| 4577 | 4576 |
| 4578 Object** limit = reinterpret_cast<Object**>(end); | 4577 Object** limit = reinterpret_cast<Object**>(end); |
| 4579 CheckStoreBuffer(current, | 4578 CheckStoreBuffer(this, |
| 4579 current, |
| 4580 limit, | 4580 limit, |
| 4581 &store_buffer_position, | 4581 &store_buffer_position, |
| 4582 store_buffer_top, | 4582 store_buffer_top, |
| 4583 &EverythingsAPointer, | 4583 &EverythingsAPointer, |
| 4584 space->top(), | 4584 space->top(), |
| 4585 space->limit()); | 4585 space->limit()); |
| 4586 } | 4586 } |
| 4587 } | 4587 } |
| 4588 | 4588 |
| 4589 | 4589 |
| 4590 void Heap::MapSpaceCheckStoreBuffer() { | 4590 void Heap::MapSpaceCheckStoreBuffer() { |
| 4591 MapSpace* space = map_space(); | 4591 MapSpace* space = map_space(); |
| 4592 PageIterator pages(space); | 4592 PageIterator pages(space); |
| 4593 | 4593 |
| 4594 store_buffer()->SortUniq(); | 4594 store_buffer()->SortUniq(); |
| 4595 | 4595 |
| 4596 while (pages.has_next()) { | 4596 while (pages.has_next()) { |
| 4597 Page* page = pages.next(); | 4597 Page* page = pages.next(); |
| 4598 Object** current = reinterpret_cast<Object**>(page->ObjectAreaStart()); | 4598 Object** current = reinterpret_cast<Object**>(page->ObjectAreaStart()); |
| 4599 | 4599 |
| 4600 Address end = page->ObjectAreaEnd(); | 4600 Address end = page->ObjectAreaEnd(); |
| 4601 | 4601 |
| 4602 Object*** store_buffer_position = store_buffer()->Start(); | 4602 Object*** store_buffer_position = store_buffer()->Start(); |
| 4603 Object*** store_buffer_top = store_buffer()->Top(); | 4603 Object*** store_buffer_top = store_buffer()->Top(); |
| 4604 | 4604 |
| 4605 Object** limit = reinterpret_cast<Object**>(end); | 4605 Object** limit = reinterpret_cast<Object**>(end); |
| 4606 CheckStoreBuffer(current, | 4606 CheckStoreBuffer(this, |
| 4607 current, |
| 4607 limit, | 4608 limit, |
| 4608 &store_buffer_position, | 4609 &store_buffer_position, |
| 4609 store_buffer_top, | 4610 store_buffer_top, |
| 4610 &IsAMapPointerAddress, | 4611 &IsAMapPointerAddress, |
| 4611 space->top(), | 4612 space->top(), |
| 4612 space->limit()); | 4613 space->limit()); |
| 4613 } | 4614 } |
| 4614 } | 4615 } |
| 4615 | 4616 |
| 4616 | 4617 |
| 4617 void Heap::LargeObjectSpaceCheckStoreBuffer() { | 4618 void Heap::LargeObjectSpaceCheckStoreBuffer() { |
| 4618 LargeObjectIterator it(lo_space()); | 4619 LargeObjectIterator it(lo_space()); |
| 4619 for (HeapObject* object = it.Next(); object != NULL; object = it.Next()) { | 4620 for (HeapObject* object = it.Next(); object != NULL; object = it.Next()) { |
| 4620 // We only have code, sequential strings, or fixed arrays in large | 4621 // We only have code, sequential strings, or fixed arrays in large |
| 4621 // object space, and only fixed arrays can possibly contain pointers to | 4622 // object space, and only fixed arrays can possibly contain pointers to |
| 4622 // the young generation. | 4623 // the young generation. |
| 4623 if (object->IsFixedArray()) { | 4624 if (object->IsFixedArray()) { |
| 4624 Object*** store_buffer_position = store_buffer()->Start(); | 4625 Object*** store_buffer_position = store_buffer()->Start(); |
| 4625 Object*** store_buffer_top = store_buffer()->Top(); | 4626 Object*** store_buffer_top = store_buffer()->Top(); |
| 4626 Object** current = reinterpret_cast<Object**>(object->address()); | 4627 Object** current = reinterpret_cast<Object**>(object->address()); |
| 4627 Object** limit = | 4628 Object** limit = |
| 4628 reinterpret_cast<Object**>(object->address() + object->Size()); | 4629 reinterpret_cast<Object**>(object->address() + object->Size()); |
| 4629 CheckStoreBuffer(current, | 4630 CheckStoreBuffer(this, |
| 4631 current, |
| 4630 limit, | 4632 limit, |
| 4631 &store_buffer_position, | 4633 &store_buffer_position, |
| 4632 store_buffer_top, | 4634 store_buffer_top, |
| 4633 &EverythingsAPointer, | 4635 &EverythingsAPointer, |
| 4634 NULL, | 4636 NULL, |
| 4635 NULL); | 4637 NULL); |
| 4636 } | 4638 } |
| 4637 } | 4639 } |
| 4638 } | 4640 } |
| 4639 #endif | 4641 #endif |
| (...skipping 1384 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6024 } | 6026 } |
| 6025 isolate_->heap()->store_buffer()->Filter(MemoryChunk::ABOUT_TO_BE_FREED); | 6027 isolate_->heap()->store_buffer()->Filter(MemoryChunk::ABOUT_TO_BE_FREED); |
| 6026 for (chunk = chunks_queued_for_free_; chunk != NULL; chunk = next) { | 6028 for (chunk = chunks_queued_for_free_; chunk != NULL; chunk = next) { |
| 6027 next = chunk->next_chunk(); | 6029 next = chunk->next_chunk(); |
| 6028 isolate_->memory_allocator()->Free(chunk); | 6030 isolate_->memory_allocator()->Free(chunk); |
| 6029 } | 6031 } |
| 6030 chunks_queued_for_free_ = NULL; | 6032 chunks_queued_for_free_ = NULL; |
| 6031 } | 6033 } |
| 6032 | 6034 |
| 6033 } } // namespace v8::internal | 6035 } } // namespace v8::internal |
| OLD | NEW |