Skip to content

Commit

Permalink
Implement heap walking
Browse files Browse the repository at this point in the history
  • Loading branch information
peterzhu2118 committed Aug 8, 2024
1 parent c4c47bf commit 9903af4
Show file tree
Hide file tree
Showing 8 changed files with 78 additions and 9 deletions.
34 changes: 33 additions & 1 deletion gc/mmtk.c
Original file line number Diff line number Diff line change
Expand Up @@ -218,6 +218,7 @@ rb_gc_impl_new_obj(void *objspace_ptr, void *cache_ptr, VALUE klass, VALUE flags
if (alloc_size > 24) alloc_obj[3] = v2;
if (alloc_size > 32) alloc_obj[4] = v3;

mmtk_post_alloc(cache_ptr, (void*)alloc_obj, alloc_size + 8, MMTK_ALLOCATION_SEMANTICS_DEFAULT);

if (rb_gc_shutdown_call_finalizer_p((VALUE)alloc_obj)) {
mmtk_add_obj_free_candidate(alloc_obj);
Expand Down Expand Up @@ -337,7 +338,38 @@ void rb_gc_impl_writebarrier(void *objspace_ptr, VALUE a, VALUE b) { }
void rb_gc_impl_writebarrier_unprotect(void *objspace_ptr, VALUE obj) { }
void rb_gc_impl_writebarrier_remember(void *objspace_ptr, VALUE obj) { }
// Heap walking
void rb_gc_impl_each_objects(void *objspace_ptr, int (*callback)(void *, void *, size_t, void *), void *data) { }
struct each_objects_data {
bool stop;
int (*callback)(void *, void *, size_t, void *);
void *data;
};

static void
each_objects_i(MMTk_ObjectReference obj, void *d)
{
struct each_objects_data *data = d;

if (data->stop) return;

size_t slot_size = rb_gc_impl_obj_slot_size((VALUE)obj);

if (data->callback(obj, (void *)((char *)obj + slot_size), slot_size, data->data) != 0) {
data->stop = true;
}
}

void
rb_gc_impl_each_objects(void *objspace_ptr, int (*callback)(void *, void *, size_t, void *), void *data)
{
struct each_objects_data each_objects_data = {
.stop = false,
.callback = callback,
.data = data,
};

mmtk_enumerate_objects(each_objects_i, &each_objects_data);
}

void rb_gc_impl_each_object(void *objspace_ptr, void (*func)(VALUE obj, void *data), void *data) { }
// Finalizers
void
Expand Down
7 changes: 7 additions & 0 deletions gc/mmtk.h
Original file line number Diff line number Diff line change
Expand Up @@ -125,8 +125,15 @@ MMTk_Address mmtk_alloc(MMTk_Mutator *mutator,
size_t offset,
MMTk_AllocationSemantics semantics);

void mmtk_post_alloc(MMTk_Mutator *mutator,
MMTk_ObjectReference refer,
size_t bytes,
MMTk_AllocationSemantics semantics);

void mmtk_add_obj_free_candidate(MMTk_ObjectReference object);

void mmtk_enumerate_objects(void (*callback)(MMTk_ObjectReference, void*), void *data);

struct MMTk_RawVecOfObjRef mmtk_get_all_obj_free_candidates(void);

void mmtk_free_raw_vec_of_obj_ref(struct MMTk_RawVecOfObjRef raw_vec);
Expand Down
5 changes: 3 additions & 2 deletions gc/mmtk/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions gc/mmtk/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,8 @@ probe = "0.5"
features = ["is_mmtk_object", "object_pinning", "sticky_immix_non_moving_nursery"]

# Uncomment the following lines to use mmtk-core from the official repository.
git = "https://github.com/mmtk/mmtk-core.git"
rev = "a3a72f8e5795678eff06fdc1524f0b429a62ccc0"
git = "https://github.com/wks/mmtk-core.git"
rev = "7d3f79d4e50dacec881252562c8c7946e2513e55"

# Uncomment the following line to use mmtk-core from a local repository.
# path = "../../mmtk-core"
Expand Down
7 changes: 7 additions & 0 deletions gc/mmtk/src/abi.rs
Original file line number Diff line number Diff line change
Expand Up @@ -402,3 +402,10 @@ pub struct RubyUpcalls {
}

unsafe impl Sync for RubyUpcalls {}

#[repr(C)]
#[derive(Clone)]
pub struct HeapBounds {
pub start: *mut libc::c_void,
pub end: *mut libc::c_void,
}
22 changes: 22 additions & 0 deletions gc/mmtk/src/api.rs
Original file line number Diff line number Diff line change
Expand Up @@ -77,12 +77,34 @@ pub extern "C" fn mmtk_alloc(
)
}

#[no_mangle]
pub extern "C" fn mmtk_post_alloc(
mutator: *mut RubyMutator,
refer: ObjectReference,
bytes: usize,
semantics: AllocationSemantics,
) {
memory_manager::post_alloc::<Ruby>(unsafe { &mut *mutator }, refer, bytes, semantics)
}

// TODO: Replace with buffered mmtk_add_obj_free_candidates
#[no_mangle]
pub extern "C" fn mmtk_add_obj_free_candidate(object: ObjectReference) {
binding().weak_proc.add_obj_free_candidate(object)
}

// =============== Heap walking ===============

#[no_mangle]
pub extern "C" fn mmtk_enumerate_objects(
callback: extern "C" fn(ObjectReference, *mut libc::c_void),
data: *mut libc::c_void,
) {
crate::mmtk().enumerate_objects(|object| {
callback(object, data);
})
}

// =============== Finalizers ===============

#[no_mangle]
Expand Down
6 changes: 3 additions & 3 deletions gc/mmtk/src/scanning.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ impl Scanning<Ruby> for VMScanning {
object_tracer: &mut OT,
) {
debug_assert!(
mmtk::memory_manager::is_mmtk_object(object.to_raw_address()),
mmtk::memory_manager::is_mmtk_object(object.to_raw_address()).is_some(),
"Not an MMTk object: {object}",
);
let gc_tls = unsafe { GCThreadTLS::from_vwt_check(tls) };
Expand All @@ -40,7 +40,7 @@ impl Scanning<Ruby> for VMScanning {
if pin { " pin" } else { "" }
);
debug_assert!(
mmtk::memory_manager::is_mmtk_object(target_object.to_raw_address()),
mmtk::memory_manager::is_mmtk_object(target_object.to_raw_address()).is_some(),
"Destination is not an MMTk object. Src: {object} dst: {target_object}"
);
let forwarded_target = object_tracer.trace_object(target_object);
Expand Down Expand Up @@ -173,7 +173,7 @@ impl VMScanning {
}
);
debug_assert!(
mmtk::memory_manager::is_mmtk_object(object.to_raw_address()),
mmtk::memory_manager::is_mmtk_object(object.to_raw_address()).is_some(),
"Root does not point to MMTk object. object: {object}"
);
buffer.push(object);
Expand Down
2 changes: 1 addition & 1 deletion gc/mmtk/src/weak_proc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -230,7 +230,7 @@ trait GlobalTableProcessingWork {
// of `trace_object` due to the way it is used in `UPDATE_IF_MOVED`.
let forward_object = |_worker, object: ObjectReference, _pin| {
debug_assert!(
mmtk::memory_manager::is_mmtk_object(object.to_address::<Ruby>()),
mmtk::memory_manager::is_mmtk_object(object.to_address::<Ruby>()).is_some(),
"{} is not an MMTk object",
object
);
Expand Down

0 comments on commit 9903af4

Please sign in to comment.