summaryrefslogtreecommitdiff
path: root/gc.c
diff options
context:
space:
mode:
authorPeter Zhu <peter.zhu@shopify.com>2021-09-13 09:12:08 -0400
committerPeter Zhu <peter@peterzhu.ca>2021-09-15 09:00:42 -0400
commite624d0d202ef691f5c75841b90bf44a624e3cdcc (patch)
tree82682cce609252fac5e2d129e24178e299cf70b4 /gc.c
parent92ac1721c23e3c865b929f201c04edca53ccb5b5 (diff)
downloadruby-e624d0d202ef691f5c75841b90bf44a624e3cdcc.tar.gz
Update the free_slots count of the original page
When invalidating a page during compaction, the free_slots count should be updated for the page of the object and not the page of the forwarding address (since the object gets moved back to the forwarding address).
Diffstat (limited to 'gc.c')
-rw-r--r--gc.c29
1 files changed, 9 insertions, 20 deletions
diff --git a/gc.c b/gc.c
index b5656c59f3..47762c2bfc 100644
--- a/gc.c
+++ b/gc.c
@@ -5818,7 +5818,7 @@ gc_sweep_continue(rb_objspace_t *objspace, rb_size_pool_t *sweep_size_pool, rb_h
}
static void
-invalidate_moved_plane(rb_objspace_t *objspace, struct heap_page *page, uintptr_t p, bits_t bitset, struct gc_sweep_context *ctx)
+invalidate_moved_plane(rb_objspace_t *objspace, struct heap_page *page, uintptr_t p, bits_t bitset)
{
if (bitset) {
do {
@@ -5834,17 +5834,15 @@ invalidate_moved_plane(rb_objspace_t *objspace, struct heap_page *page, uintptr_
object = rb_gc_location(forwarding_object);
- if (FL_TEST(forwarding_object, FL_FROM_FREELIST)) {
- ctx->empty_slots++; /* already freed */
- }
- else {
- ctx->freed_slots++;
- }
-
gc_move(objspace, object, forwarding_object, page->size_pool->slot_size);
/* forwarding_object is now our actual object, and "object"
* is the free slot for the original page */
- heap_page_add_freeobj(objspace, GET_HEAP_PAGE(object), object);
+ struct heap_page *orig_page = GET_HEAP_PAGE(object);
+ orig_page->free_slots++;
+ if (!FL_TEST_RAW(object, FL_FROM_FREELIST)) {
+ objspace->profile.total_freed_objects++;
+ }
+ heap_page_add_freeobj(objspace, orig_page, object);
GC_ASSERT(MARKED_IN_BITMAP(GET_HEAP_MARK_BITS(forwarding_object), forwarding_object));
GC_ASSERT(BUILTIN_TYPE(forwarding_object) != T_MOVED);
@@ -5870,16 +5868,10 @@ invalidate_moved_page(rb_objspace_t *objspace, struct heap_page *page)
p = page->start;
- struct gc_sweep_context ctx;
- ctx.page = page;
- ctx.final_slots = 0;
- ctx.freed_slots = 0;
- ctx.empty_slots = 0;
-
// Skip out of range slots at the head of the page
bitset = pin_bits[0] & ~mark_bits[0];
bitset >>= NUM_IN_PAGE(p);
- invalidate_moved_plane(objspace, page, (uintptr_t)p, bitset, &ctx);
+ invalidate_moved_plane(objspace, page, (uintptr_t)p, bitset);
p += (BITS_BITLENGTH - NUM_IN_PAGE(p));
for (i=1; i < HEAP_PAGE_BITMAP_LIMIT; i++) {
@@ -5887,12 +5879,9 @@ invalidate_moved_page(rb_objspace_t *objspace, struct heap_page *page)
* to indicate there is a moved object in this slot. */
bitset = pin_bits[i] & ~mark_bits[i];
- invalidate_moved_plane(objspace, page, (uintptr_t)p, bitset, &ctx);
+ invalidate_moved_plane(objspace, page, (uintptr_t)p, bitset);
p += BITS_BITLENGTH;
}
-
- page->free_slots += (ctx.empty_slots + ctx.freed_slots);
- objspace->profile.total_freed_objects += ctx.freed_slots;
}
static void