From a1ea55bed1fe116ff57ac952e366a8e8eb431169 Mon Sep 17 00:00:00 2001 From: tmijieux Date: Mon, 3 Jan 2022 17:03:42 +0000 Subject: [PATCH] transform sgen_get_descriptor to parallel safe version in job_major_mod_union_preclean Fixes mono/mono#21369 job_major_mod_union_preclean can race with the tarjan bridge implementation that changes the vtable pointer by settings the three lower bits. this results in invalid loading of the vtable (shifted by 7 bytes) which in turn give a wrong desc to the scan functions This change is released under the MIT license. --- src/mono/mono/sgen/sgen-cardtable.c | 4 ++-- src/mono/mono/sgen/sgen-marksweep.c | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/mono/mono/sgen/sgen-cardtable.c b/src/mono/mono/sgen/sgen-cardtable.c index 120afe0d4ea2c9..31a25f47fd8fdc 100644 --- a/src/mono/mono/sgen/sgen-cardtable.c +++ b/src/mono/mono/sgen/sgen-cardtable.c @@ -594,9 +594,9 @@ sgen_cardtable_scan_object (GCObject *obj, mword block_obj_size, guint8 *cards, HEAVY_STAT (++bloby_objects); if (cards) { if (sgen_card_table_is_range_marked (cards, (mword)obj, block_obj_size)) - ctx.ops->scan_object (obj, sgen_obj_get_descriptor (obj), ctx.queue); + ctx.ops->scan_object (obj, sgen_obj_get_descriptor_safe (obj), ctx.queue); } else if (sgen_card_table_region_begin_scanning ((mword)obj, block_obj_size)) { - ctx.ops->scan_object (obj, sgen_obj_get_descriptor (obj), ctx.queue); + ctx.ops->scan_object (obj, sgen_obj_get_descriptor_safe (obj), ctx.queue); } sgen_binary_protocol_card_scan (obj, sgen_safe_object_get_size (obj)); diff --git a/src/mono/mono/sgen/sgen-marksweep.c b/src/mono/mono/sgen/sgen-marksweep.c index ca01a483e9d545..f767431c1699ee 100644 --- a/src/mono/mono/sgen/sgen-marksweep.c +++ b/src/mono/mono/sgen/sgen-marksweep.c @@ -2661,7 +2661,7 @@ scan_card_table_for_block (MSBlockInfo *block, CardTableScanType scan_type, Scan if (small_objects) { HEAVY_STAT (++scanned_objects); - scan_func (object, sgen_obj_get_descriptor (object), queue); + scan_func (object, sgen_obj_get_descriptor_safe (object), queue); } else { size_t offset = sgen_card_table_get_card_offset (obj, block_start); sgen_cardtable_scan_object (object, block_obj_size, card_base + offset, ctx);