1
Fork 0
mirror of https://git.savannah.gnu.org/git/guile.git synced 2025-05-19 19:20:23 +02:00

Add offset to field-logging fast path

This commit is contained in:
Andy Wingo 2025-01-10 15:42:25 +01:00
parent 209be38640
commit e4048b5296
6 changed files with 17 additions and 2 deletions

View file

@ -59,6 +59,9 @@ static inline size_t gc_write_barrier_card_size(void) {
static inline size_t gc_write_barrier_field_table_alignment(void) { static inline size_t gc_write_barrier_field_table_alignment(void) {
GC_CRASH(); GC_CRASH();
} }
static inline ptrdiff_t gc_write_barrier_field_table_offset(void) {
GC_CRASH();
}
static inline size_t gc_write_barrier_field_fields_per_byte(void) { static inline size_t gc_write_barrier_field_fields_per_byte(void) {
GC_CRASH(); GC_CRASH();
} }

View file

@ -214,7 +214,7 @@ static inline int gc_object_is_old_generation(struct gc_mutator *mut,
uintptr_t high_addr = gc_small_object_nursery_high_address(heap); uintptr_t high_addr = gc_small_object_nursery_high_address(heap);
uintptr_t size = high_addr - low_addr; uintptr_t size = high_addr - low_addr;
uintptr_t addr = gc_ref_value(obj); uintptr_t addr = gc_ref_value(obj);
return addr - low_addr < size; return addr - low_addr >= size;
} }
case GC_OLD_GENERATION_CHECK_SLOW: case GC_OLD_GENERATION_CHECK_SLOW:
return gc_object_is_old_generation_slow(mut, obj); return gc_object_is_old_generation_slow(mut, obj);
@ -252,13 +252,14 @@ static inline int gc_write_barrier_fast(struct gc_mutator *mut, struct gc_ref ob
size_t field_table_alignment = gc_write_barrier_field_table_alignment(); size_t field_table_alignment = gc_write_barrier_field_table_alignment();
size_t fields_per_byte = gc_write_barrier_field_fields_per_byte(); size_t fields_per_byte = gc_write_barrier_field_fields_per_byte();
uint8_t first_bit_pattern = gc_write_barrier_field_first_bit_pattern(); uint8_t first_bit_pattern = gc_write_barrier_field_first_bit_pattern();
ssize_t table_offset = gc_write_barrier_field_table_offset();
uintptr_t addr = gc_edge_address(edge); uintptr_t addr = gc_edge_address(edge);
uintptr_t base = addr & ~(field_table_alignment - 1); uintptr_t base = addr & ~(field_table_alignment - 1);
uintptr_t field = (addr & (field_table_alignment - 1)) / sizeof(uintptr_t); uintptr_t field = (addr & (field_table_alignment - 1)) / sizeof(uintptr_t);
uintptr_t log_byte = field / fields_per_byte; uintptr_t log_byte = field / fields_per_byte;
uint8_t log_bit = first_bit_pattern << (field % fields_per_byte); uint8_t log_bit = first_bit_pattern << (field % fields_per_byte);
uint8_t *byte_loc = (uint8_t*)(base + log_byte); uint8_t *byte_loc = (uint8_t*)(base + table_offset + log_byte);
uint8_t byte = atomic_load_explicit(byte_loc, memory_order_relaxed); uint8_t byte = atomic_load_explicit(byte_loc, memory_order_relaxed);
return !(byte & log_bit); return !(byte & log_bit);
} }

View file

@ -49,6 +49,7 @@ static inline enum gc_write_barrier_kind gc_write_barrier_kind(size_t obj_size)
static inline size_t gc_write_barrier_card_table_alignment(void) GC_ALWAYS_INLINE; static inline size_t gc_write_barrier_card_table_alignment(void) GC_ALWAYS_INLINE;
static inline size_t gc_write_barrier_card_size(void) GC_ALWAYS_INLINE; static inline size_t gc_write_barrier_card_size(void) GC_ALWAYS_INLINE;
static inline size_t gc_write_barrier_field_table_alignment(void) GC_ALWAYS_INLINE; static inline size_t gc_write_barrier_field_table_alignment(void) GC_ALWAYS_INLINE;
static inline ptrdiff_t gc_write_barrier_field_table_offset(void) GC_ALWAYS_INLINE;
static inline size_t gc_write_barrier_field_fields_per_byte(void) GC_ALWAYS_INLINE; static inline size_t gc_write_barrier_field_fields_per_byte(void) GC_ALWAYS_INLINE;
static inline uint8_t gc_write_barrier_field_first_bit_pattern(void) GC_ALWAYS_INLINE; static inline uint8_t gc_write_barrier_field_first_bit_pattern(void) GC_ALWAYS_INLINE;

View file

@ -73,6 +73,10 @@ static inline size_t gc_write_barrier_field_table_alignment(void) {
GC_ASSERT(GC_GENERATIONAL); GC_ASSERT(GC_GENERATIONAL);
return gc_allocator_alloc_table_alignment(); return gc_allocator_alloc_table_alignment();
} }
static inline ptrdiff_t gc_write_barrier_field_table_offset(void) {
GC_ASSERT(GC_GENERATIONAL);
return 0;
}
static inline size_t gc_write_barrier_field_fields_per_byte(void) { static inline size_t gc_write_barrier_field_fields_per_byte(void) {
GC_ASSERT(GC_GENERATIONAL); GC_ASSERT(GC_GENERATIONAL);
return 2; return 2;

View file

@ -62,6 +62,9 @@ static inline size_t gc_write_barrier_card_size(void) {
static inline size_t gc_write_barrier_field_table_alignment(void) { static inline size_t gc_write_barrier_field_table_alignment(void) {
GC_CRASH(); GC_CRASH();
} }
static inline ptrdiff_t gc_write_barrier_field_table_offset(void) {
GC_CRASH();
}
static inline size_t gc_write_barrier_field_fields_per_byte(void) { static inline size_t gc_write_barrier_field_fields_per_byte(void) {
GC_CRASH(); GC_CRASH();
} }

View file

@ -61,6 +61,9 @@ static inline size_t gc_write_barrier_card_size(void) {
static inline size_t gc_write_barrier_field_table_alignment(void) { static inline size_t gc_write_barrier_field_table_alignment(void) {
GC_CRASH(); GC_CRASH();
} }
static inline ptrdiff_t gc_write_barrier_field_table_offset(void) {
GC_CRASH();
}
static inline size_t gc_write_barrier_field_fields_per_byte(void) { static inline size_t gc_write_barrier_field_fields_per_byte(void) {
GC_CRASH(); GC_CRASH();
} }