diff options
author | Nathan Ringo <nathan@remexre.com> | 2024-11-29 15:37:04 -0600 |
---|---|---|
committer | Nathan Ringo <nathan@remexre.com> | 2024-11-29 15:37:04 -0600 |
commit | f54faf130e4a1f6fb75eba1634bb07a9adc038a6 (patch) | |
tree | c9360513bc5edbc5df0ad4f23875ccf32030d64e /src | |
parent | b3149099a17d392289db9699b5b5d83444d25173 (diff) |
Diffstat (limited to 'src')
-rw-r--r-- | src/gc/sms.c | 6 | ||||
-rw-r--r-- | src/platform/linux.c | 44 | ||||
-rw-r--r-- | src/value.c | 14 | ||||
-rw-r--r-- | src/value.h | 7 |
4 files changed, 25 insertions, 46 deletions
diff --git a/src/gc/sms.c b/src/gc/sms.c index eb76dab..427edc5 100644 --- a/src/gc/sms.c +++ b/src/gc/sms.c @@ -53,7 +53,11 @@ static const struct object_header *hdrc(const void *ptr) { static size_t collect_amount[5] = {0}; static size_t collect_amount_i = 0; -void gc_init(void) {} +void gc_init(void) { + for (size_t i = 0; i < sizeof(collect_amount) / sizeof(collect_amount[0]); + i++) + collect_amount[i] = (size_t)-1; +} static void gc_mark(const struct value initial_value) { // If the initial value wasn't a pointer to an unmarked object, we can bail diff --git a/src/platform/linux.c b/src/platform/linux.c index 3305869..052c00c 100644 --- a/src/platform/linux.c +++ b/src/platform/linux.c @@ -11,49 +11,13 @@ #include <unistd.h> int main(int argc, char **argv) { - // As a test of the garbage collector, we're doing a bunch of random - // mutations. gc_init(); - srand(0); - gc_debug(); - - const struct value ZERO = {.bits = (0 << 2) | TAG_FIXNUM}; - - struct object *values = gc_alloc(64, 0); - struct object *value_slot_counts = gc_alloc(64, 0); - gc_root_push(&values); - gc_root_push(&value_slot_counts); - - for (size_t i = 0; i < 1000000; i++) { - if ((rand() & 0b11) == 0) { - size_t value_slot_count = 3; - if (!value_slot_count) - value_slot_count = 1; - size_t untraced_slot_count = rand() & 255; - struct value value = - alloc_builtin_object(ZERO, value_slot_count, untraced_slot_count); - size_t i = rand() % 63; - gc_write_value_slot(values, i, value); - gc_write_value_slot(value_slot_counts, i, - integer_of_int(value_slot_count)); - } else { - size_t i = rand() & 63; - struct value value = gc_read_value_slot(values, i); - struct value value_slot_count_value = - gc_read_value_slot(value_slot_counts, i); - if (!value.bits) - continue; - assume(get_tag(value) == TAG_BUILTIN_OBJECT); - assume(get_tag(value_slot_count_value) == TAG_FIXNUM); - struct object *obj = untag_ptr(value); - intptr_t value_slot_count = untag_fixnum(value_slot_count_value); - size_t j = rand() % value_slot_count; - size_t k = rand() % 63; - gc_write_value_slot(obj, j, gc_read_value_slot(values, k)); - } - } + bootstrap(); gc_debug(); + gc_collect(GC_COLLECT_MANUAL); + gc_debug(); + return 0; } diff --git a/src/value.c b/src/value.c index eacc21c..e240646 100644 --- a/src/value.c +++ b/src/value.c @@ -152,14 +152,18 @@ struct object *untag_ptr(struct value value) { } void bootstrap(void) { + // Register every builtin slot as a root. + for (size_t i = 0; i < BUILTINS_COUNT; i++) + gc_root_push(&builtins[i]); + // Since it is its own class, standard-class needs to be constructed // manually. { - struct object *obj = gc_alloc(STANDARD_CLASS_SLOT_COUNT + 1, 0); - builtins[BUILTIN_BUILTIN_CLASS_STANDARD_CLASS] = (struct value){ - .bits = (uintptr_t)obj | TAG_BUILTIN_OBJECT, - }; - gc_write_value_slot(obj, 0, builtins[BUILTIN_BUILTIN_CLASS_STANDARD_CLASS]); + builtins[BUILTIN_BUILTIN_CLASS_STANDARD_CLASS] = + tag_ptr(gc_alloc(STANDARD_CLASS_SLOT_COUNT + 1, 0), TAG_BUILTIN_OBJECT); + builtin_object_write_value_slot( + builtins[BUILTIN_BUILTIN_CLASS_STANDARD_CLASS], 0, + builtins[BUILTIN_BUILTIN_CLASS_STANDARD_CLASS]); // TODO } diff --git a/src/value.h b/src/value.h index 1331d9d..50c50f9 100644 --- a/src/value.h +++ b/src/value.h @@ -89,6 +89,13 @@ intptr_t untag_fixnum(struct value); */ struct object *untag_ptr(struct value); +struct value builtin_object_read_value_slot(const struct value, size_t); +uintptr_t builtin_object_read_untraced_slot(const struct value, size_t); +uint8_t builtin_object_read_untraced_byte(const struct value, size_t); +void builtin_object_write_value_slot(struct value, size_t, struct value); +void builtin_object_write_untraced_slot(struct value, size_t, uintptr_t); +void builtin_object_write_untraced_byte(struct value, size_t, uint8_t); + /** * Bootstraps the class heirarchy. This should only be called once. */ |