From 226994ace22f445793e2c1f44ef03009cbfe0bb9 Mon Sep 17 00:00:00 2001 From: Kunshan Wang Date: Thu, 5 May 2022 19:22:35 +0800 Subject: [PATCH] Change to PolicyTraceObject::post_scan_object Now it is provided as a hook **after** scan_object. It no longer customises how to do scan_object. --- macros/trace_object/src/derive_impl.rs | 17 ++++++----------- macros/trace_object/src/lib.rs | 12 ++++++------ src/plan/generational/immix/global.rs | 2 +- src/plan/immix/global.rs | 2 +- src/plan/transitive_closure.rs | 13 +++++-------- src/policy/gc_work.rs | 18 ++++++------------ src/policy/immix/immixspace.rs | 8 +------- 7 files changed, 26 insertions(+), 46 deletions(-) diff --git a/macros/trace_object/src/derive_impl.rs b/macros/trace_object/src/derive_impl.rs index a082a6663c..9114f28029 100644 --- a/macros/trace_object/src/derive_impl.rs +++ b/macros/trace_object/src/derive_impl.rs @@ -63,32 +63,27 @@ pub fn generate_trace_object<'a>( } } -pub fn generate_scan_object<'a>( - scan_object_fields: &[&'a Field], +pub fn generate_post_scan_object<'a>( + post_scan_object_fields: &[&'a Field], ty_generics: &TypeGenerics, ) -> TokenStream2 { - let scan_field_handler = scan_object_fields.iter().map(|f| { + let scan_field_handler = post_scan_object_fields.iter().map(|f| { let f_ident = f.ident.as_ref().unwrap(); let ref f_ty = f.ty; quote! { if self.#f_ident.in_space(__mmtk_objref) { use crate::policy::gc_work::PolicyTraceObject; - <#f_ty as PolicyTraceObject #ty_generics>::scan_object::(&self.#f_ident, __mmtk_worker_tls, __mmtk_objref, __mmtk_ev); + <#f_ty as PolicyTraceObject #ty_generics>::post_scan_object(&self.#f_ident, __mmtk_objref); return; } } }); quote! { - fn scan_object(&self, __mmtk_worker_tls: crate::util::opaque_pointer::VMWorkerThread, __mmtk_objref: crate::util::ObjectReference, __mmtk_ev: &mut EV) { - use crate::vm::Scanning; - - // Plan specific + #[inline(always)] + fn post_scan_object(&self, __mmtk_objref: crate::util::ObjectReference) { #(#scan_field_handler)* - - // Default - VM::VMScanning::scan_object(__mmtk_worker_tls, __mmtk_objref, __mmtk_ev); } } } diff --git a/macros/trace_object/src/lib.rs b/macros/trace_object/src/lib.rs index c526c0c3af..c3db273b5c 100644 --- a/macros/trace_object/src/lib.rs +++ b/macros/trace_object/src/lib.rs @@ -20,10 +20,10 @@ mod derive_impl; /// * add `#[fallback_trace]` to the parent plan if the plan is composed with other plans (or parent plans). /// For example, `GenImmix` is composed with `Gen`, `Gen` is composed with `CommonPlan`, `CommonPlan` is composed /// with `BasePlan`. -/// * add `#[policy_scan]` to any space field that has some policy-specific scan_object(). For objects in those spaces, -/// `scan_object()` in the policy will be called. For other objects, directly call `VM::VMScanning::scan_object()`. +/// * add `#[post_scan_hook]` to any space field that has some policy-specific post_scan_object(). For objects in those spaces, +/// `post_scan_object()` in the policy will be called after `VM::VMScanning::scan_object()`. #[proc_macro_error] -#[proc_macro_derive(PlanTraceObject, attributes(trace, policy_scan, fallback_trace))] +#[proc_macro_derive(PlanTraceObject, attributes(trace, post_scan_hook, fallback_trace))] pub fn derive_plan_trace_object(input: TokenStream) -> TokenStream { let input = parse_macro_input!(input as DeriveInput); let ident = input.ident; @@ -34,11 +34,11 @@ pub fn derive_plan_trace_object(input: TokenStream) -> TokenStream { .. }) = input.data { let spaces = util::get_fields_with_attribute(fields, "trace"); - let scan_spaces = util::get_fields_with_attribute(fields, "policy_scan"); + let post_scan_hook_spaces = util::get_fields_with_attribute(fields, "post_scan_hook"); let fallback = util::get_unique_field_with_attribute(fields, "fallback_trace"); let trace_object_function = derive_impl::generate_trace_object(&spaces, &fallback, &ty_generics); - let scan_object_function = derive_impl::generate_scan_object(&scan_spaces, &ty_generics); + let post_scan_object_function = derive_impl::generate_post_scan_object(&post_scan_hook_spaces, &ty_generics); let may_move_objects_function = derive_impl::generate_may_move_objects(&spaces, &fallback, &ty_generics); quote!{ impl #impl_generics crate::plan::transitive_closure::PlanTraceObject #ty_generics for #ident #ty_generics #where_clause { @@ -46,7 +46,7 @@ pub fn derive_plan_trace_object(input: TokenStream) -> TokenStream { #trace_object_function #[inline(always)] - #scan_object_function + #post_scan_object_function #[inline(always)] #may_move_objects_function diff --git a/src/plan/generational/immix/global.rs b/src/plan/generational/immix/global.rs index 583408334e..6c27b811df 100644 --- a/src/plan/generational/immix/global.rs +++ b/src/plan/generational/immix/global.rs @@ -38,7 +38,7 @@ pub struct GenImmix { #[fallback_trace] pub gen: Gen, /// An immix space as the mature space. - #[policy_scan] + #[post_scan_hook] #[trace(CopySemantics::Mature)] pub immix: ImmixSpace, /// Whether the last GC was a defrag GC for the immix space. diff --git a/src/plan/immix/global.rs b/src/plan/immix/global.rs index 7fb50909ca..482230ba54 100644 --- a/src/plan/immix/global.rs +++ b/src/plan/immix/global.rs @@ -30,7 +30,7 @@ use mmtk_macro_trace_object::PlanTraceObject; #[derive(PlanTraceObject)] pub struct Immix { - #[policy_scan] + #[post_scan_hook] #[trace(CopySemantics::DefaultCopy)] pub immix_space: ImmixSpace, #[fallback_trace] diff --git a/src/plan/transitive_closure.rs b/src/plan/transitive_closure.rs index 42f6f9151b..07b5f280e6 100644 --- a/src/plan/transitive_closure.rs +++ b/src/plan/transitive_closure.rs @@ -74,7 +74,7 @@ impl<'a, E: ProcessEdgesWork> Drop for ObjectsClosure<'a, E> { use crate::policy::gc_work::TraceKind; use crate::scheduler::GCWork; -use crate::util::VMWorkerThread; + use crate::vm::VMBinding; /// A plan that uses `PlanProcessEdges` needs to provide an implementation for this trait. @@ -97,12 +97,7 @@ pub trait PlanTraceObject { /// Scan objects in the plan. It is expected that each object will be scanned by `VM::VMScanning::scan_object()`. /// If the object is in a policy that has some policy specific behaviors for scanning (e.g. mark lines in Immix), /// this method should also invoke those policy specific methods. - fn scan_object( - &self, - tls: VMWorkerThread, - object: ObjectReference, - edge_visitor: &mut EV, - ); + fn post_scan_object(&self, object: ObjectReference); /// Whether objects in this plan may move. If any of the spaces used by the plan may move objects, this should /// return true. @@ -226,7 +221,9 @@ impl + PlanTraceObject let tls = worker.tls; let mut closure = ObjectsClosure::::new(worker); for object in &self.buffer { - self.plan.scan_object(tls, *object, &mut closure); + use crate::vm::Scanning; + ::VMScanning::scan_object(tls, *object, &mut closure); + self.plan.post_scan_object(*object); } } trace!("PlanScanObjects End"); diff --git a/src/policy/gc_work.rs b/src/policy/gc_work.rs index 756e9f2d03..8520c437bd 100644 --- a/src/policy/gc_work.rs +++ b/src/policy/gc_work.rs @@ -7,9 +7,9 @@ pub const DEFAULT_TRACE: u8 = u8::MAX; use crate::plan::TransitiveClosure; use crate::scheduler::GCWorker; use crate::util::copy::CopySemantics; -use crate::util::opaque_pointer::VMWorkerThread; + use crate::util::ObjectReference; -use crate::vm::EdgeVisitor; + use crate::vm::VMBinding; /// This trait defines policy-specific behavior for tracing objects. @@ -28,17 +28,11 @@ pub trait PolicyTraceObject { worker: &mut GCWorker, ) -> ObjectReference; - /// Policy-specific scan object. The implementation needs to guarantee that - /// they will call `VM::VMScanning::scan_object()` (or `Self::vm_scan_object()`) besides any space-specific work for the object. + /// Policy-specific post-scan-object hook. It is called after scanning + /// each object in this space. #[inline(always)] - fn scan_object( - &self, - tls: VMWorkerThread, - object: ObjectReference, - edge_visitor: &mut EV, - ) { - use crate::vm::Scanning; - VM::VMScanning::scan_object(tls, object, edge_visitor) + fn post_scan_object(&self, _object: ObjectReference) { + // Do nothing. } /// Return whether the policy moves objects. diff --git a/src/policy/immix/immixspace.rs b/src/policy/immix/immixspace.rs index 503680df91..d3f1c7ba5b 100644 --- a/src/policy/immix/immixspace.rs +++ b/src/policy/immix/immixspace.rs @@ -135,13 +135,7 @@ impl crate::policy::gc_work::PolicyTraceObject for ImmixSpace } #[inline(always)] - fn scan_object( - &self, - tls: VMWorkerThread, - object: ObjectReference, - edge_visitor: &mut EV, - ) { - VM::VMScanning::scan_object(tls, object, edge_visitor); + fn post_scan_object(&self, object: ObjectReference) { if super::MARK_LINE_AT_SCAN_TIME && !super::BLOCK_ONLY { debug_assert!(self.in_space(object)); self.mark_lines(object);