aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--gc.c13
1 files changed, 13 insertions, 0 deletions
diff --git a/gc.c b/gc.c
index 4f92c371be..4b619fd33f 100644
--- a/gc.c
+++ b/gc.c
@@ -5810,6 +5810,19 @@ gc_sweep_finish_size_pool(rb_objspace_t *objspace, rb_size_pool_t *size_pool)
min_free_slots = gc_params.heap_init_slots;
}
+ /* If we don't have enough slots and we have pages on the tomb heap, move
+ * pages from the tomb heap to the eden heap. This may prevent page
+ * creation thrashing (frequently allocating and deallocting pages) and
+ * GC thrashing (running GC more frequently than required). */
+ struct heap_page *resurrected_page;
+ while (swept_slots < min_free_slots &&
+ (resurrected_page = heap_page_resurrect(objspace, size_pool))) {
+ swept_slots += resurrected_page->free_slots;
+
+ heap_add_page(objspace, size_pool, heap, resurrected_page);
+ heap_add_freepage(heap, resurrected_page);
+ }
+
if (swept_slots < min_free_slots) {
bool grow_heap = is_full_marking(objspace);