summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorNathan Ringo <nathan@remexre.com>2024-11-29 15:37:04 -0600
committerNathan Ringo <nathan@remexre.com>2024-11-29 15:37:04 -0600
commitf54faf130e4a1f6fb75eba1634bb07a9adc038a6 (patch)
treec9360513bc5edbc5df0ad4f23875ccf32030d64e /src
parentb3149099a17d392289db9699b5b5d83444d25173 (diff)
mop noteHEADtrunk
Diffstat (limited to 'src')
-rw-r--r--src/gc/sms.c6
-rw-r--r--src/platform/linux.c44
-rw-r--r--src/value.c14
-rw-r--r--src/value.h7
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.
*/