Convert name_err_mesg to use rb_gc_mark_and_move

The `p->field = rb_gc_location(p->field)` isn't ideal because it means all
references are rewritten on compaction, regardless of whether the referenced
object has moved. This isn't good for caches nor for Copy-on-Write.

`rb_gc_mark_and_move` avoid needless writes, and most of the time allow to
have a single function for both marking and updating references.
This commit is contained in:
Jean Boussier 2025-08-07 14:42:14 +02:00
parent aee8e65c70
commit bc9781c264

21
error.c
View file

@ -2517,30 +2517,21 @@ typedef struct name_error_message_struct {
} name_error_message_t; } name_error_message_t;
static void static void
name_err_mesg_mark(void *p) name_err_mesg_mark_and_move(void *p)
{ {
name_error_message_t *ptr = (name_error_message_t *)p; name_error_message_t *ptr = (name_error_message_t *)p;
rb_gc_mark_movable(ptr->mesg); rb_gc_mark_and_move(&ptr->mesg);
rb_gc_mark_movable(ptr->recv); rb_gc_mark_and_move(&ptr->recv);
rb_gc_mark_movable(ptr->name); rb_gc_mark_and_move(&ptr->name);
}
static void
name_err_mesg_update(void *p)
{
name_error_message_t *ptr = (name_error_message_t *)p;
ptr->mesg = rb_gc_location(ptr->mesg);
ptr->recv = rb_gc_location(ptr->recv);
ptr->name = rb_gc_location(ptr->name);
} }
static const rb_data_type_t name_err_mesg_data_type = { static const rb_data_type_t name_err_mesg_data_type = {
"name_err_mesg", "name_err_mesg",
{ {
name_err_mesg_mark, name_err_mesg_mark_and_move,
RUBY_TYPED_DEFAULT_FREE, RUBY_TYPED_DEFAULT_FREE,
NULL, // No external memory to report, NULL, // No external memory to report,
name_err_mesg_update, name_err_mesg_mark_and_move,
}, },
0, 0, RUBY_TYPED_FREE_IMMEDIATELY | RUBY_TYPED_WB_PROTECTED | RUBY_TYPED_EMBEDDABLE 0, 0, RUBY_TYPED_FREE_IMMEDIATELY | RUBY_TYPED_WB_PROTECTED | RUBY_TYPED_EMBEDDABLE
}; };