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 130 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
141 last_idle_notification_gc_count_init_(false), | 141 last_idle_notification_gc_count_init_(false), |
142 mark_sweeps_since_idle_round_started_(0), | 142 mark_sweeps_since_idle_round_started_(0), |
143 gc_count_at_last_idle_gc_(0), | 143 gc_count_at_last_idle_gc_(0), |
144 scavenges_since_last_idle_round_(kIdleScavengeThreshold), | 144 scavenges_since_last_idle_round_(kIdleScavengeThreshold), |
145 full_codegen_bytes_generated_(0), | 145 full_codegen_bytes_generated_(0), |
146 crankshaft_codegen_bytes_generated_(0), | 146 crankshaft_codegen_bytes_generated_(0), |
147 gcs_since_last_deopt_(0), | 147 gcs_since_last_deopt_(0), |
148 #ifdef VERIFY_HEAP | 148 #ifdef VERIFY_HEAP |
149 no_weak_object_verification_scope_depth_(0), | 149 no_weak_object_verification_scope_depth_(0), |
150 #endif | 150 #endif |
| 151 allocation_sites_scratchpad_length(0), |
151 promotion_queue_(this), | 152 promotion_queue_(this), |
152 configured_(false), | 153 configured_(false), |
153 chunks_queued_for_free_(NULL), | 154 chunks_queued_for_free_(NULL), |
154 relocation_mutex_(NULL) { | 155 relocation_mutex_(NULL) { |
155 // Allow build-time customization of the max semispace size. Building | 156 // Allow build-time customization of the max semispace size. Building |
156 // V8 with snapshots and a non-default max semispace size is much | 157 // V8 with snapshots and a non-default max semispace size is much |
157 // easier if you can define it as part of the build environment. | 158 // easier if you can define it as part of the build environment. |
158 #if defined(V8_MAX_SEMISPACE_SIZE) | 159 #if defined(V8_MAX_SEMISPACE_SIZE) |
159 max_semispace_size_ = reserved_semispace_size_ = V8_MAX_SEMISPACE_SIZE; | 160 max_semispace_size_ = reserved_semispace_size_ = V8_MAX_SEMISPACE_SIZE; |
160 #endif | 161 #endif |
(...skipping 336 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
497 void Heap::RepairFreeListsAfterBoot() { | 498 void Heap::RepairFreeListsAfterBoot() { |
498 PagedSpaces spaces(this); | 499 PagedSpaces spaces(this); |
499 for (PagedSpace* space = spaces.next(); | 500 for (PagedSpace* space = spaces.next(); |
500 space != NULL; | 501 space != NULL; |
501 space = spaces.next()) { | 502 space = spaces.next()) { |
502 space->RepairFreeListsAfterBoot(); | 503 space->RepairFreeListsAfterBoot(); |
503 } | 504 } |
504 } | 505 } |
505 | 506 |
506 | 507 |
507 void Heap::GarbageCollectionEpilogue() { | 508 void Heap::ProcessPretenuringFeedback() { |
508 if (FLAG_allocation_site_pretenuring) { | 509 if (FLAG_allocation_site_pretenuring) { |
509 int tenure_decisions = 0; | 510 int tenure_decisions = 0; |
510 int dont_tenure_decisions = 0; | 511 int dont_tenure_decisions = 0; |
511 int allocation_mementos_found = 0; | 512 int allocation_mementos_found = 0; |
| 513 int allocation_sites = 0; |
| 514 int active_allocation_sites = 0; |
512 | 515 |
513 Object* cur = allocation_sites_list(); | 516 // If the scratchpad overflowed, we have to iterate over the allocation |
514 while (cur->IsAllocationSite()) { | 517 // stites list. |
515 AllocationSite* casted = AllocationSite::cast(cur); | 518 bool use_scratchpad = |
516 allocation_mementos_found += casted->memento_found_count()->value(); | 519 allocation_sites_scratchpad_length < kAllocationSiteScratchpadSize; |
517 if (casted->DigestPretenuringFeedback()) { | 520 |
518 if (casted->GetPretenureMode() == TENURED) { | 521 int i = 0; |
| 522 Object* list_element = allocation_sites_list(); |
| 523 while (use_scratchpad ? |
| 524 i < allocation_sites_scratchpad_length : |
| 525 list_element->IsAllocationSite()) { |
| 526 AllocationSite* site = use_scratchpad ? |
| 527 allocation_sites_scratchpad[i] : AllocationSite::cast(list_element); |
| 528 allocation_mementos_found += site->memento_found_count()->value(); |
| 529 if (site->memento_found_count()->value() > 0) { |
| 530 active_allocation_sites++; |
| 531 } |
| 532 if (site->DigestPretenuringFeedback()) { |
| 533 if (site->GetPretenureMode() == TENURED) { |
519 tenure_decisions++; | 534 tenure_decisions++; |
520 } else { | 535 } else { |
521 dont_tenure_decisions++; | 536 dont_tenure_decisions++; |
522 } | 537 } |
523 } | 538 } |
524 cur = casted->weak_next(); | 539 allocation_sites++; |
| 540 if (use_scratchpad) { |
| 541 i++; |
| 542 } else { |
| 543 list_element = site->weak_next(); |
| 544 } |
525 } | 545 } |
| 546 allocation_sites_scratchpad_length = 0; |
526 | 547 |
527 // TODO(mvstanton): Pretenure decisions are only made once for an allocation | 548 // TODO(mvstanton): Pretenure decisions are only made once for an allocation |
528 // site. Find a sane way to decide about revisiting the decision later. | 549 // site. Find a sane way to decide about revisiting the decision later. |
529 | 550 |
530 if (FLAG_trace_track_allocation_sites && | 551 if (FLAG_trace_track_allocation_sites && |
531 (allocation_mementos_found > 0 || | 552 (allocation_mementos_found > 0 || |
532 tenure_decisions > 0 || | 553 tenure_decisions > 0 || |
533 dont_tenure_decisions > 0)) { | 554 dont_tenure_decisions > 0)) { |
534 PrintF("GC: (#mementos, #tenure decisions, #donttenure decisions) " | 555 PrintF("GC: (mode, #visited allocation sites, #active allocation sites, " |
535 "(%d, %d, %d)\n", | 556 "#mementos, #tenure decisions, #donttenure decisions) " |
| 557 "(%s, %d, %d, %d, %d, %d)\n", |
| 558 use_scratchpad ? "use scratchpad" : "use list", |
| 559 allocation_sites, |
| 560 active_allocation_sites, |
536 allocation_mementos_found, | 561 allocation_mementos_found, |
537 tenure_decisions, | 562 tenure_decisions, |
538 dont_tenure_decisions); | 563 dont_tenure_decisions); |
539 } | 564 } |
540 } | 565 } |
| 566 } |
541 | 567 |
| 568 |
| 569 void Heap::GarbageCollectionEpilogue() { |
542 store_buffer()->GCEpilogue(); | 570 store_buffer()->GCEpilogue(); |
543 | 571 |
544 // In release mode, we only zap the from space under heap verification. | 572 // In release mode, we only zap the from space under heap verification. |
545 if (Heap::ShouldZapGarbage()) { | 573 if (Heap::ShouldZapGarbage()) { |
546 ZapFromSpace(); | 574 ZapFromSpace(); |
547 } | 575 } |
548 | 576 |
549 #ifdef VERIFY_HEAP | 577 #ifdef VERIFY_HEAP |
550 if (FLAG_verify_heap) { | 578 if (FLAG_verify_heap) { |
551 Verify(); | 579 Verify(); |
(...skipping 1006 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1558 // Set age mark. | 1586 // Set age mark. |
1559 new_space_.set_age_mark(new_space_.top()); | 1587 new_space_.set_age_mark(new_space_.top()); |
1560 | 1588 |
1561 new_space_.LowerInlineAllocationLimit( | 1589 new_space_.LowerInlineAllocationLimit( |
1562 new_space_.inline_allocation_limit_step()); | 1590 new_space_.inline_allocation_limit_step()); |
1563 | 1591 |
1564 // Update how much has survived scavenge. | 1592 // Update how much has survived scavenge. |
1565 IncrementYoungSurvivorsCounter(static_cast<int>( | 1593 IncrementYoungSurvivorsCounter(static_cast<int>( |
1566 (PromotedSpaceSizeOfObjects() - survived_watermark) + new_space_.Size())); | 1594 (PromotedSpaceSizeOfObjects() - survived_watermark) + new_space_.Size())); |
1567 | 1595 |
| 1596 ProcessPretenuringFeedback(); |
| 1597 |
1568 LOG(isolate_, ResourceEvent("scavenge", "end")); | 1598 LOG(isolate_, ResourceEvent("scavenge", "end")); |
1569 | 1599 |
1570 gc_state_ = NOT_IN_GC; | 1600 gc_state_ = NOT_IN_GC; |
1571 | 1601 |
1572 scavenges_since_last_idle_round_++; | 1602 scavenges_since_last_idle_round_++; |
1573 } | 1603 } |
1574 | 1604 |
1575 | 1605 |
1576 String* Heap::UpdateNewSpaceReferenceInExternalStringTableEntry(Heap* heap, | 1606 String* Heap::UpdateNewSpaceReferenceInExternalStringTableEntry(Heap* heap, |
1577 Object** p) { | 1607 Object** p) { |
(...skipping 6381 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7959 static_cast<int>(object_sizes_last_time_[index])); | 7989 static_cast<int>(object_sizes_last_time_[index])); |
7960 CODE_AGE_LIST_COMPLETE(ADJUST_LAST_TIME_OBJECT_COUNT) | 7990 CODE_AGE_LIST_COMPLETE(ADJUST_LAST_TIME_OBJECT_COUNT) |
7961 #undef ADJUST_LAST_TIME_OBJECT_COUNT | 7991 #undef ADJUST_LAST_TIME_OBJECT_COUNT |
7962 | 7992 |
7963 OS::MemCopy(object_counts_last_time_, object_counts_, sizeof(object_counts_)); | 7993 OS::MemCopy(object_counts_last_time_, object_counts_, sizeof(object_counts_)); |
7964 OS::MemCopy(object_sizes_last_time_, object_sizes_, sizeof(object_sizes_)); | 7994 OS::MemCopy(object_sizes_last_time_, object_sizes_, sizeof(object_sizes_)); |
7965 ClearObjectStats(); | 7995 ClearObjectStats(); |
7966 } | 7996 } |
7967 | 7997 |
7968 } } // namespace v8::internal | 7998 } } // namespace v8::internal |
OLD | NEW |