| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2013 Google Inc. All rights reserved. | 2 * Copyright (C) 2013 Google Inc. All rights reserved. |
| 3 * | 3 * |
| 4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
| 5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
| 6 * met: | 6 * met: |
| 7 * | 7 * |
| 8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
| 9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
| 10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
| (...skipping 708 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 719 | 719 |
| 720 #define UNEXPECTED_GCSTATE(s) case ThreadState::s: RELEASE_ASSERT_WITH_MESSAGE(f
alse, "Unexpected transition while in GCState " #s); return | 720 #define UNEXPECTED_GCSTATE(s) case ThreadState::s: RELEASE_ASSERT_WITH_MESSAGE(f
alse, "Unexpected transition while in GCState " #s); return |
| 721 | 721 |
| 722 void unexpectedGCState(ThreadState::GCState gcState) | 722 void unexpectedGCState(ThreadState::GCState gcState) |
| 723 { | 723 { |
| 724 switch (gcState) { | 724 switch (gcState) { |
| 725 UNEXPECTED_GCSTATE(NoGCScheduled); | 725 UNEXPECTED_GCSTATE(NoGCScheduled); |
| 726 UNEXPECTED_GCSTATE(IdleGCScheduled); | 726 UNEXPECTED_GCSTATE(IdleGCScheduled); |
| 727 UNEXPECTED_GCSTATE(PreciseGCScheduled); | 727 UNEXPECTED_GCSTATE(PreciseGCScheduled); |
| 728 UNEXPECTED_GCSTATE(FullGCScheduled); | 728 UNEXPECTED_GCSTATE(FullGCScheduled); |
| 729 UNEXPECTED_GCSTATE(StoppingOtherThreads); | |
| 730 UNEXPECTED_GCSTATE(GCRunning); | 729 UNEXPECTED_GCSTATE(GCRunning); |
| 731 UNEXPECTED_GCSTATE(EagerSweepScheduled); | 730 UNEXPECTED_GCSTATE(EagerSweepScheduled); |
| 732 UNEXPECTED_GCSTATE(LazySweepScheduled); | 731 UNEXPECTED_GCSTATE(LazySweepScheduled); |
| 733 UNEXPECTED_GCSTATE(Sweeping); | 732 UNEXPECTED_GCSTATE(Sweeping); |
| 734 UNEXPECTED_GCSTATE(SweepingAndIdleGCScheduled); | 733 UNEXPECTED_GCSTATE(SweepingAndIdleGCScheduled); |
| 735 UNEXPECTED_GCSTATE(SweepingAndPreciseGCScheduled); | 734 UNEXPECTED_GCSTATE(SweepingAndPreciseGCScheduled); |
| 736 default: | 735 default: |
| 737 ASSERT_NOT_REACHED(); | 736 ASSERT_NOT_REACHED(); |
| 738 return; | 737 return; |
| 739 } | 738 } |
| 740 } | 739 } |
| 741 | 740 |
| 742 #undef UNEXPECTED_GCSTATE | 741 #undef UNEXPECTED_GCSTATE |
| 743 | 742 |
| 744 } // namespace | 743 } // namespace |
| 745 | 744 |
| 746 #define VERIFY_STATE_TRANSITION(condition) if (UNLIKELY(!(condition))) unexpecte
dGCState(m_gcState) | 745 #define VERIFY_STATE_TRANSITION(condition) if (UNLIKELY(!(condition))) unexpecte
dGCState(m_gcState) |
| 747 | 746 |
| 748 void ThreadState::setGCState(GCState gcState) | 747 void ThreadState::setGCState(GCState gcState) |
| 749 { | 748 { |
| 750 switch (gcState) { | 749 switch (gcState) { |
| 751 case NoGCScheduled: | 750 case NoGCScheduled: |
| 752 checkThread(); | 751 checkThread(); |
| 753 VERIFY_STATE_TRANSITION(m_gcState == StoppingOtherThreads || m_gcState =
= Sweeping || m_gcState == SweepingAndIdleGCScheduled); | 752 VERIFY_STATE_TRANSITION(m_gcState == Sweeping || m_gcState == SweepingAn
dIdleGCScheduled); |
| 754 break; | 753 break; |
| 755 case IdleGCScheduled: | 754 case IdleGCScheduled: |
| 756 case PreciseGCScheduled: | 755 case PreciseGCScheduled: |
| 757 case FullGCScheduled: | 756 case FullGCScheduled: |
| 758 checkThread(); | 757 checkThread(); |
| 759 VERIFY_STATE_TRANSITION(m_gcState == NoGCScheduled || m_gcState == IdleG
CScheduled || m_gcState == PreciseGCScheduled || m_gcState == FullGCScheduled ||
m_gcState == StoppingOtherThreads || m_gcState == SweepingAndIdleGCScheduled ||
m_gcState == SweepingAndPreciseGCScheduled); | 758 VERIFY_STATE_TRANSITION(m_gcState == NoGCScheduled || m_gcState == IdleG
CScheduled || m_gcState == PreciseGCScheduled || m_gcState == FullGCScheduled ||
m_gcState == SweepingAndIdleGCScheduled || m_gcState == SweepingAndPreciseGCSch
eduled); |
| 760 completeSweep(); | 759 completeSweep(); |
| 761 break; | 760 break; |
| 762 case StoppingOtherThreads: | |
| 763 checkThread(); | |
| 764 VERIFY_STATE_TRANSITION(m_gcState == NoGCScheduled || m_gcState == IdleG
CScheduled || m_gcState == PreciseGCScheduled || m_gcState == FullGCScheduled ||
m_gcState == Sweeping || m_gcState == SweepingAndIdleGCScheduled || m_gcState =
= SweepingAndPreciseGCScheduled); | |
| 765 break; | |
| 766 case GCRunning: | 761 case GCRunning: |
| 767 ASSERT(!isInGC()); | 762 ASSERT(!isInGC()); |
| 768 VERIFY_STATE_TRANSITION(m_gcState != GCRunning); | 763 VERIFY_STATE_TRANSITION(m_gcState != GCRunning); |
| 769 break; | 764 break; |
| 770 case EagerSweepScheduled: | 765 case EagerSweepScheduled: |
| 771 case LazySweepScheduled: | 766 case LazySweepScheduled: |
| 772 ASSERT(isInGC()); | 767 ASSERT(isInGC()); |
| 773 VERIFY_STATE_TRANSITION(m_gcState == GCRunning); | 768 VERIFY_STATE_TRANSITION(m_gcState == GCRunning); |
| 774 break; | 769 break; |
| 775 case Sweeping: | 770 case Sweeping: |
| 776 checkThread(); | 771 checkThread(); |
| 777 VERIFY_STATE_TRANSITION(m_gcState == StoppingOtherThreads || m_gcState =
= EagerSweepScheduled || m_gcState == LazySweepScheduled); | 772 VERIFY_STATE_TRANSITION(m_gcState == EagerSweepScheduled || m_gcState ==
LazySweepScheduled); |
| 778 break; | 773 break; |
| 779 case SweepingAndIdleGCScheduled: | 774 case SweepingAndIdleGCScheduled: |
| 780 case SweepingAndPreciseGCScheduled: | 775 case SweepingAndPreciseGCScheduled: |
| 781 checkThread(); | 776 checkThread(); |
| 782 VERIFY_STATE_TRANSITION(m_gcState == StoppingOtherThreads || m_gcState =
= Sweeping || m_gcState == SweepingAndIdleGCScheduled || m_gcState == SweepingAn
dPreciseGCScheduled); | 777 VERIFY_STATE_TRANSITION(m_gcState == Sweeping || m_gcState == SweepingAn
dIdleGCScheduled || m_gcState == SweepingAndPreciseGCScheduled); |
| 783 break; | 778 break; |
| 784 default: | 779 default: |
| 785 ASSERT_NOT_REACHED(); | 780 ASSERT_NOT_REACHED(); |
| 786 } | 781 } |
| 787 m_gcState = gcState; | 782 m_gcState = gcState; |
| 788 } | 783 } |
| 789 | 784 |
| 790 #undef VERIFY_STATE_TRANSITION | 785 #undef VERIFY_STATE_TRANSITION |
| 791 | 786 |
| 792 ThreadState::GCState ThreadState::gcState() const | 787 ThreadState::GCState ThreadState::gcState() const |
| (...skipping 11 matching lines...) Expand all Loading... |
| 804 Heap::setEstimatedLiveObjectSize(Heap::estimatedLiveObjectSize() / 2); | 799 Heap::setEstimatedLiveObjectSize(Heap::estimatedLiveObjectSize() / 2); |
| 805 } | 800 } |
| 806 } | 801 } |
| 807 | 802 |
| 808 void ThreadState::runScheduledGC(StackState stackState) | 803 void ThreadState::runScheduledGC(StackState stackState) |
| 809 { | 804 { |
| 810 checkThread(); | 805 checkThread(); |
| 811 if (stackState != NoHeapPointersOnStack) | 806 if (stackState != NoHeapPointersOnStack) |
| 812 return; | 807 return; |
| 813 | 808 |
| 809 // If a safe point is entered while initiating a GC, we clearly do |
| 810 // not want to do another as part that -- the safe point is only |
| 811 // entered after checking if a scheduled GC ought to run first. |
| 812 // Prevent that from happening by marking GCs as forbidden while |
| 813 // one is initiated and later running. |
| 814 if (isGCForbidden()) |
| 815 return; |
| 816 |
| 814 switch (gcState()) { | 817 switch (gcState()) { |
| 815 case FullGCScheduled: | 818 case FullGCScheduled: |
| 816 Heap::collectAllGarbage(); | 819 Heap::collectAllGarbage(); |
| 817 break; | 820 break; |
| 818 case PreciseGCScheduled: | 821 case PreciseGCScheduled: |
| 819 Heap::collectGarbage(NoHeapPointersOnStack, GCWithoutSweep, Heap::Precis
eGC); | 822 Heap::collectGarbage(NoHeapPointersOnStack, GCWithoutSweep, Heap::Precis
eGC); |
| 820 break; | 823 break; |
| 821 case IdleGCScheduled: | 824 case IdleGCScheduled: |
| 822 // Idle time GC will be scheduled by Blink Scheduler. | 825 // Idle time GC will be scheduled by Blink Scheduler. |
| 823 break; | 826 break; |
| (...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1103 #endif | 1106 #endif |
| 1104 | 1107 |
| 1105 void ThreadState::enterSafePoint(StackState stackState, void* scopeMarker) | 1108 void ThreadState::enterSafePoint(StackState stackState, void* scopeMarker) |
| 1106 { | 1109 { |
| 1107 checkThread(); | 1110 checkThread(); |
| 1108 #ifdef ADDRESS_SANITIZER | 1111 #ifdef ADDRESS_SANITIZER |
| 1109 if (stackState == HeapPointersOnStack) | 1112 if (stackState == HeapPointersOnStack) |
| 1110 scopeMarker = adjustScopeMarkerForAdressSanitizer(scopeMarker); | 1113 scopeMarker = adjustScopeMarkerForAdressSanitizer(scopeMarker); |
| 1111 #endif | 1114 #endif |
| 1112 ASSERT(stackState == NoHeapPointersOnStack || scopeMarker); | 1115 ASSERT(stackState == NoHeapPointersOnStack || scopeMarker); |
| 1113 ASSERT(!isGCForbidden()); | |
| 1114 runScheduledGC(stackState); | 1116 runScheduledGC(stackState); |
| 1115 ASSERT(!m_atSafePoint); | 1117 ASSERT(!m_atSafePoint); |
| 1116 m_atSafePoint = true; | 1118 m_atSafePoint = true; |
| 1117 m_stackState = stackState; | 1119 m_stackState = stackState; |
| 1118 m_safePointScopeMarker = scopeMarker; | 1120 m_safePointScopeMarker = scopeMarker; |
| 1119 s_safePointBarrier->enterSafePoint(this); | 1121 s_safePointBarrier->enterSafePoint(this); |
| 1120 } | 1122 } |
| 1121 | 1123 |
| 1122 void ThreadState::leaveSafePoint(SafePointAwareMutexLocker* locker) | 1124 void ThreadState::leaveSafePoint(SafePointAwareMutexLocker* locker) |
| 1123 { | 1125 { |
| (...skipping 228 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1352 json->beginArray(it->key.ascii().data()); | 1354 json->beginArray(it->key.ascii().data()); |
| 1353 for (size_t age = 0; age <= maxHeapObjectAge; ++age) | 1355 for (size_t age = 0; age <= maxHeapObjectAge; ++age) |
| 1354 json->pushInteger(it->value.ages[age]); | 1356 json->pushInteger(it->value.ages[age]); |
| 1355 json->endArray(); | 1357 json->endArray(); |
| 1356 } | 1358 } |
| 1357 TRACE_EVENT_OBJECT_SNAPSHOT_WITH_ID(TRACE_DISABLED_BY_DEFAULT("blink_gc"), s
tatsName, this, json.release()); | 1359 TRACE_EVENT_OBJECT_SNAPSHOT_WITH_ID(TRACE_DISABLED_BY_DEFAULT("blink_gc"), s
tatsName, this, json.release()); |
| 1358 } | 1360 } |
| 1359 #endif | 1361 #endif |
| 1360 | 1362 |
| 1361 } // namespace blink | 1363 } // namespace blink |
| OLD | NEW |