diff --git a/rts/sm/NonMoving.c b/rts/sm/NonMoving.c index c43213043ef0c20e92db44da2165ad2120814320..d222d9c1f3c0e0d71aa0c53c5eae21b162fec7d0 100644 --- a/rts/sm/NonMoving.c +++ b/rts/sm/NonMoving.c @@ -375,7 +375,6 @@ memcount nonmoving_live_words = 0; #if defined(THREADED_RTS) static void* nonmovingConcurrentMark(void *mark_queue); #endif -static void nonmovingClearBitmap(struct NonmovingSegment *seg); static void nonmovingMark_(MarkQueue *mark_queue, StgWeak **dead_weaks, StgTSO **resurrected_threads); static void nonmovingInitSegment(struct NonmovingSegment *seg, uint8_t log_block_size) @@ -682,7 +681,7 @@ void nonmovingAddCapabilities(uint32_t new_n_caps) nonmovingHeap.n_caps = new_n_caps; } -static inline void nonmovingClearBitmap(struct NonmovingSegment *seg) +void nonmovingClearBitmap(struct NonmovingSegment *seg) { unsigned int n = nonmovingSegmentBlockCount(seg); memset(seg->bitmap, 0, n); @@ -696,9 +695,6 @@ static void nonmovingPrepareMark(void) static_flag = static_flag == STATIC_FLAG_A ? STATIC_FLAG_B : STATIC_FLAG_A; - // Should have been cleared by the last sweep - ASSERT(nonmovingHeap.sweep_list == NULL); - nonmovingBumpEpoch(); for (int alloca_idx = 0; alloca_idx < NONMOVING_ALLOCA_CNT; ++alloca_idx) { struct NonmovingAllocator *alloca = nonmovingHeap.allocators[alloca_idx]; @@ -1087,7 +1083,6 @@ static void nonmovingMark_(MarkQueue *mark_queue, StgWeak **dead_weaks, StgTSO * nonmovingSweepStableNameTable(); nonmovingSweep(); - ASSERT(nonmovingHeap.sweep_list == NULL); debugTrace(DEBUG_nonmoving_gc, "Finished sweeping."); traceConcSweepEnd(); #if defined(DEBUG) diff --git a/rts/sm/NonMoving.h b/rts/sm/NonMoving.h index b3d4e14065cd718327b2fd16fa84b12a81e9a93b..36ecd8b0afc618fcd5c07452ee1fb61c32656d81 100644 --- a/rts/sm/NonMoving.h +++ b/rts/sm/NonMoving.h @@ -130,6 +130,7 @@ void nonmovingCollect(StgWeak **dead_weaks, void *nonmovingAllocate(Capability *cap, StgWord sz); void nonmovingAddCapabilities(uint32_t new_n_caps); void nonmovingPushFreeSegment(struct NonmovingSegment *seg); +void nonmovingClearBitmap(struct NonmovingSegment *seg); INLINE_HEADER struct NonmovingSegmentInfo *nonmovingSegmentInfo(struct NonmovingSegment *seg) { diff --git a/rts/sm/NonMovingSweep.c b/rts/sm/NonMovingSweep.c index ead0e1cee8e804eb49b9514b2f009db9d570207b..2b8db9e4c6853735a47b34be0bb47d4dc04f9f70 100644 --- a/rts/sm/NonMovingSweep.c +++ b/rts/sm/NonMovingSweep.c @@ -127,6 +127,8 @@ clear_segment_free_blocks(struct NonmovingSegment* seg) GNUC_ATTR_HOT void nonmovingSweep(void) { + struct NonmovingSegment *new_sweep_list = NULL; + while (nonmovingHeap.sweep_list) { struct NonmovingSegment *seg = nonmovingHeap.sweep_list; @@ -146,12 +148,19 @@ GNUC_ATTR_HOT void nonmovingSweep(void) nonmovingPushActiveSegment(seg); break; case SEGMENT_FILLED: - nonmovingPushFilledSegment(seg); + // Clear bitmap + nonmovingClearBitmap(seg); + // Set snapshot + nonmovingSegmentInfo(seg)->next_free_snap = seg->next_free; + seg->link = new_sweep_list; + new_sweep_list = seg; break; default: barf("nonmovingSweep: weird sweep return: %d\n", ret); } } + + nonmovingHeap.sweep_list = new_sweep_list; } /* Must a closure remain on the mutable list?